上学的时候读书,书上写得关于非阻塞赋值的描述是:
在赋值操作开始的时刻计算非阻塞赋值符RHS表达式,赋值操作结束的时刻才更新LHS。在计算非阻塞赋值的RHS表达式和更新LHS期间,其他的Verilog语句,包括其他的Verilog非阻塞赋值语句都能同时计算RHS表达式和更新LHS。非阻塞赋值允许其他的Verilog语句同时进行操作。
但是并没有详细藐视关于非阻塞赋值的时序问题。以mem读时序为例,给mem的控制信号代码如下:
而得到r_data的时序如下:
书上并没有说阻塞赋值的时序必然是,上一个时钟周期rd拉高,下一个时钟周期才能拿到数据,那为什么时序会是这样呢。
其实是因为mem_rd信号与mem_adr信号在①上升沿处同时变化,在①处采样不满足mem_adr的A信号的建立时间,而在②上升沿处才满足了mem_adr的A信号的建立时间,所以实际上是在E②处完成的采样,(mem里面读数据是组合逻辑的情况下)mem_rdata在②上升沿完成后开始变化。
若我们把A信号提前变化一段时间,使其在①上升沿处满足采样的建立时间,则mem_rdata的变化也会在①上升沿处产生。时序如下所示:
这类问题经常会在写TB的时候遇到。