理解 Verilog 调度语义:时序、事件与执行顺序
Verilog 设计和测试平台通常包含许多 always 或 initial 块、连续赋值及其他过程语句,它们在仿真过程中不同时间变为活动。
Verilog 模型中信号值的每次变化视为一个更新事件。对这些更新事件敏感的进程(如 always 和 assign 块)以任意顺序求值,称为求值事件。因这些事件发生在不同时间,需通过按仿真时间排列的事件队列管理并确保正确执行顺序。
module tb; reg a, b, c; wire d; // 'always' 进程在 'a' 或 'b' 更新时求值 // 'a' 或 'b' 值变化称为'更新事件' // 'always' 块因 'a' 或 'b' 变化触发称为'求值事件' always @ (a or b) begin c = a & b; end // 'assign' 进程在 'a'、'b' 或 'c' 更新时求值 assign d = a | b ^ c; endmodule
事件队列
一个仿真步骤可分为四个区域。活动事件队列是当前时刻需执行的进程集合,执行可能导致更多进程被调度进活动或其他队列。事件可加入任一区域,但总从活动区域移除。
- 活动事件发生在当前仿真时间,可任意顺序处理。
- 非活动事件发生在当前仿真时间,但在所有活动事件处理完后处理。
- 非阻塞赋值事件在先前某时刻求值,但在当前仿真时间、活动和非活动事件完成后赋值。
- 监视事件在所有活动、非活动、非阻塞赋值事件完成后处理。
当当前时间步的活动队列所有事件执行完,仿真器推进时间到下一时间步并执行其活动队列。
module tb; reg x, y, z initial begin #1 x = 1; y = 1; #1 z = 0; end endmodule
仿真从时间 0 开始,第一条语句调度在仿真时间达到 1 时间单位时执行,赋 x 和 y 为 1。这是当前时间(1 时间单位)的活动队列。仿真器再调度下一条语句在 1 个时间单位后执行,赋 z 为 0。
是什么导致仿真非确定性?
仿真中可能出现竞争条件,导致相同设计和测试平台产生不同输出。非确定性行为的原因之一是活动事件可从队列中移除并以任意顺序处理。
Verilog
- 现代化员工排班:提升留任与生产力的有力依据
- Verilog 入门:数字电路设计完整教程
- 掌握 Verilog 拼接操作:实用指南
- 深入理解 Verilog 赋值语句:类型、语法与最佳实践
- Verilog阻塞与非阻塞赋值:关键区别详解
- 掌握Verilog函数:高效RTL设计的复用利器
- 理解Verilog任务:函数vs任务、语法与用法全解析
- Verilog 时钟发生器设计与实现指南
- 掌握 Verilog 数学函数:高效硬件设计的利器
- 掌握 Verilog $timeformat:精度控制与显示格式化
- 理解与打印 Verilog 任意作用域下的 Timescale
- 掌握 Verilog 文件 I/O:打开、读取、写入和关闭