为行为模型添加延迟的方法
结论:
- 在
always块内部的语句中添加任何延迟都不能准确仿真真实硬件的行为。- 唯一的例外是非阻塞赋值 LHS delay, 这能准确仿真传输延迟(Transport delay model),但通常会牺牲模拟器性能。
- 在连续赋值中添加延迟,或通过无延迟
always块的输出驱动带延迟的连续赋值,都能准确仿真惯性延迟(Inertial delay model)。
1 延迟模型
惯性延迟模型 Inertial delay model
- 仅在输入保持稳定的时间大于模型延迟时,将信号传播到输出。
- 若两次输入变化之间的时间短于过程赋值延迟、连续赋值延迟或门延迟,则先前的输出事件会被覆盖。
传输延迟模型 Transport delay model
- 在任何输入信号发生变化后,都将按顺序传传播到输出端。
剔除和误差模型 Reject & Error delay model
传播大于误差设置的信号,传播介于剔除和误差设置之间信号的未知值,不传播低于剔除设置的信号。
剔除和误差的设置:
?
2 阻塞赋值的延迟模型
- LHS delay:输入第一次变化后,经过
#delay延迟后输出,且输出时采用#delay期间最后更新的输入值。 - RHS delay:输入第一次变化后,经过
#delay延迟后输出,期间无视输入的变化。
阻塞赋值 LHS delay
- 缺陷1:若在
#delay期间输入再次发生改变,输出的值由后续改变的输入决定,但输出仍会根据初次改变的时间延迟输出。
- 缺陷2:输入第一次变化,结果赋值到临时值
tmp,在#delay期间输入再次发生改变,输出仍会根据旧的临时值tmp输出错误的结果。
Guideline
- RTL:不要将延迟放在阻塞赋值的 LHS 侧来建模组合逻辑。
- Testbench:可以将延迟放在阻塞赋值的 LHS 侧。
阻塞赋值 RHS delay
- 缺陷:输入第一次变化后,经过
#delay后输出,期间无视输入的变化。
Guideline
- RTL:不要将延迟放在阻塞赋值的 RHS 侧来建模组合逻辑。
- Testbench:不要将延迟放在阻塞赋值的 RHS 侧。
3 非阻塞赋值的延迟模型
非阻塞赋值 LHS delay
- 缺陷:(与阻塞赋值 LHS delay 相同)若在
#delay期间输入再次发生改变,输出的值由后续改变的输入决定,但输出仍会根据初次改变的时间延迟输出。
Guideline
- RTL:不要将延迟放在非阻塞赋值的 LHS 侧来建模组合逻辑。
- Testbench:非阻塞赋值仿真效率更低,因此一般不建议将延迟放在非阻塞赋值的 LHS 侧。
非阻塞赋值 RHS delay(传输延迟)
- 能准确仿真具有传输延迟(Transport delay model)的组合逻辑。
Guideline
- RTL:
- 建议在非阻塞赋值的 RHS 添加延迟以模拟行为线延迟逻辑。(?)
- 只有在模拟传输延迟行为时,才这么做,它会导致仿真速度变慢。
- Testbench:当必须在未来时钟边沿或设定延迟后调度激励时,通常会用这种编码方式,同时不会阻碍同一程序块中后续激励事件的分配。(?)
多个非阻塞赋值 RHS delay
- 缺陷:所有 RHS 都必须在灵敏度列表中,包括中间值。
- 在
#delay更新tmp后,由于tmp也在灵敏度列表中,将再次触发always块,用正确的值更新{co, sum}。
- 在
Guideline
- RTL:
- 一般情况下,不要在非阻塞赋值的 RHS 添加延迟来模拟组合逻辑。
- 在非阻塞赋值的 RHS 添加延迟来模拟时序逻辑的时钟到输出行为,是常见的做法。
- Testbench:一般不建议
4 连续赋值的延迟模型
连续赋值 LHS delay(惯性延迟)
- 可以准确仿真具有惯性延迟(Inertial delay model)的组合逻辑。
混合使用
Guideline
- RTL:
- 连续赋值 LHS delay可以仿真具有惯性延迟的组合逻辑。
- 使用无延迟
always块建模复杂的组合逻辑,而将其输出驱动到带延迟连续赋值,可以仿真具有惯性延迟的组合逻辑。
- Testbench:连续赋值可用于任何位置。