Simulation ends although it should wait 1000 Cycles
See original GitHub issueI’m currently having a weird issue with cocotb 1.4 and verilator 4.100
I’m verifying an asynchronous FIFO design and have a basic 'manual, section which works perfectly, where I test reads and writes and the empty/full flags etc. then, I tried to do this to generate some more stress:
# randomize
cocotb.log.info(f"Test random read/write.")
cocotb.fork(write_fifo(dut, vals))
cocotb.fork(read_fifo(dut, vals))
await ClockCycles(dut.clk_r_i, 1000)
So I am launching 2 coroutines, one of which is writing, the other one is reading and checking, both with random delays.
The coroutines look like this:
async def write_fifo(dut, vals):
w_cnt = 0
while True:
cocotb.log.info(f"In write proc.")
for _ in range(random.randrange(1, 32)):
await FallingEdge(dut.clk_w_i)
if dut.full_o == 0:
cocotb.log.info(f"Random write number {w_cnt}.")
dut.wen_i <= 1
dut.wdata_i <= vals[w_cnt]
await RisingEdge(dut.clk_w_i)
dut.wen_i <= 0
w_cnt = w_cnt + 1
async def read_fifo(dut, vals):
r_cnt = 0
while True:
cocotb.log.info(f"In read proc.")
for _ in range(random.randrange(0, 12)):
await FallingEdge(dut.clk_r_i)
if dut.empty_o == 0:
cocotb.log.info(f"Random read number {r_cnt}.")
dut.ren_i <= 1
await RisingEdge(dut.clk_r_i)
dut.ren_i <= 0
await FallingEdge(dut.clk_r_i)
assert dut.rdata_o == vals[r_cnt], f"Read Data mismatch at value {r_cnt}, got {hex(int(dut.rdata_o))} but expected {hex(int(vals[r_cnt]))}"
r_cnt = r_cnt + 1
The weird thing is, the simulation does not wait for the 1000 cycles of the read clock, it just ends:
0.00ns INFO Running test 1/2: test_afifo
0.00ns INFO Starting test: "test_afifo"
Description: Test that data is being passed across clock domains.
0.00ns INFO Reset AFIFO on both sides.
5.00ns INFO Check empty and not full.
5.00ns INFO Fill FIFO with random values.
285.00ns INFO Test write error flag.
305.00ns INFO Read back previously written data.
1535.50ns INFO Test read error flag.
1609.50ns INFO Test random read/write.
1609.50ns INFO In write proc.
1609.50ns INFO In read proc.
1625.00ns INFO Random write number 0.
1628.00ns INFO Test Passed: test_afifo
You can see from the log that both coroutines do start and that the first write is apparently attempted. I can also confirm that from the waveform, the wen_i signal goes high, but everything ends before the RisingEdge of the write clock clk_w_i does occur.
Either I am overlooking something very stupid or something is wrong here. In my understanding, even if the coroutines were garbage, shouldn’t at least the waiting for the 1000 clocks work?
Issue Analytics
- State:
- Created 3 years ago
- Comments:58 (58 by maintainers)
Top GitHub Comments
@ktbarrett I don’t think that will work, because
last
may haveerase
called on it, invalidating the iterator. I had something similar to that, updatinglast = std::prev(last)
if it was going to be erased, but I couldn’t solve the segfault I was getting.My in-progress verilator loop update is also MUCH faster. The example test runs in ~0.6s vs 10.5s
Opened verilator/verilator#2588.