Test File: test_pe_col.py
Back to Test: Systolic Gauss-Jordan.
Source file: test/systolic_gauss_jordan/test_pe_col.py
RTL counterpart
What this test checks
This is the direct cocotb truth-table test for the column processing element. It exercises the local stored bit, the incoming opcode token, and the emitted data/output behavior for every relevant small input combination.
The test:
resets the DUT
optionally preloads the local stored bit
enumerates
data_iand all opcode valuescompares observed outputs and next state against the Python golden model
How to run it
make -C test/systolic_gauss_jordan TEST=pe_col
What to inspect while reading it
reset_dut()for the suite-wide reset patternstep()for the one-cycle drive-and-sample helperpe_col_truth_table_exhaustive()for the contract being asserted
Python source
1import cocotb
2from cocotb.clock import Clock
3from cocotb.triggers import FallingEdge, ReadOnly, RisingEdge
4
5from trapeziod_test_utils import (
6 OP_ADD,
7 OP_LOCK,
8 OP_PASS,
9 OP_SWAP,
10 OPCODE_NAMES,
11 pe_col_golden,
12)
13
14
15async def reset_dut(dut):
16 await FallingEdge(dut.clk)
17 dut.rst.value = 1
18 dut.en_i.value = 1
19 dut.data_i.value = 0
20 dut.op_i.value = OP_PASS
21
22 for _ in range(2):
23 await RisingEdge(dut.clk)
24
25 dut.rst.value = 0
26
27
28async def step(dut, data_i, op_i):
29 await FallingEdge(dut.clk)
30 dut.data_i.value = data_i
31 dut.op_i.value = op_i
32 await RisingEdge(dut.clk)
33 await ReadOnly()
34
35 return {
36 "r": int(dut.r.value),
37 "data_o": int(dut.data_o.value),
38 "op_o": int(dut.op_o.value),
39 }
40
41
42@cocotb.test()
43async def pe_col_truth_table_exhaustive(dut):
44 cocotb.start_soon(Clock(dut.clk, 10, unit="ns").start())
45 dut.en_i.value = 1
46
47 opcodes = [OP_PASS, OP_SWAP, OP_ADD, OP_LOCK]
48
49 for r_prev in (0, 1):
50 for data_i in (0, 1):
51 for op_i in opcodes:
52 await reset_dut(dut)
53
54 if r_prev == 1:
55 preload = await step(dut, 1, OP_LOCK)
56 assert preload["r"] == 1, "Failed to preload pe_col.r to 1"
57
58 observed = await step(dut, data_i, op_i)
59 expected = pe_col_golden(r_prev=r_prev, data_i=data_i, op_i=op_i)
60
61 mismatch_row = (
62 f"(r_prev={r_prev}, data_i={data_i}, op_i={OPCODE_NAMES[op_i]})"
63 )
64
65 assert observed["r"] == expected["r_next"], (
66 f"{mismatch_row}: expected r_next={expected['r_next']}, "
67 f"got {observed['r']}"
68 )
69 assert observed["data_o"] == expected["data_o"], (
70 f"{mismatch_row}: expected data_o={expected['data_o']}, "
71 f"got {observed['data_o']}"
72 )
73 assert observed["op_o"] == expected["op_o"], (
74 f"{mismatch_row}: expected op_o={OPCODE_NAMES[expected['op_o']]}, "
75 f"got {OPCODE_NAMES.get(observed['op_o'], observed['op_o'])}"
76 )