我试图验证两个模块之间非常简单的握手。一个模块处于慢速时钟并且引发“#34; req"”,更快的模块应该提升" ack"在下一个快速时钟上按住它直到下一个慢速时钟摆动。最终结果如下:
这就是我写的期望:
expect expect_ack_when_req_go is
(@req_rise_e) => @ack_rise_e
else dut_error("ERROR: ack expected to be asserted when req rises!");
* @req_rise_e和@ack_rise_e都在慢时钟上采样。
运行模拟器会产生错误,因为第一个表达式似乎成功但第二个表达式没有。尽管事实上当跟踪事件到wave时,我可以看到两个事件一起发生(如wave中所见:event_req,event_ack)。
答案 0 :(得分:3)
你试图做重叠的暗示,即你的事件都发生在同一个循环中。 =>
运算符所做的是检查结果是否发生在下一个采样事件上,在这种情况下是下一个慢速时钟边沿。这在 SystemVerilog 断言用语中称为非重叠含义。
您可以通过编写以下内容来获得所需的行为:
expect expect_ack_when_req_go is
(@req_rise_e) => detach({@ack_rise_e; ~[1]})
else dut_error("ERROR: ack expected to be asserted when req rises!");
完整解释here。
在方法论上,我建议不要以不同的方式编写时态表达式。我假设您正在验证正在驱动ack
的模块,并且此模块适用于两个时钟。我还假设该模块使用快速时钟对req
进行采样。将您的支票制定为:
expect expect_ack_when_req_go is
(@req_rise_at_fast_clock_e) => @ack_rise_at_slow_clock_e
else dut_error("ERROR: ack expected to be asserted when req rises!");
通过这种方式,您不必使用detach(...)
并且expect
更贴近您所需行为的自然语言描述。