32 / 37 · 实验
综合实验:连接周期脉冲与使能累加器
明确用旧值实现模块间传递,比较停顿、连续脉冲和同时复位。
课时内容可免费阅读,选课后可保存学习进度。
先定义连接契约
enable=1 的每个上升沿接受无符号四位 sample,每第 N 个接受样本产生注册 pulse。累加器在下一上升沿消费 pulse 和对应保存的 sample,即使此时 enable=0。八位 total 按模 256 回绕。同步 reset 清两级并丢弃待处理样本。
这一拍延迟是契约的一部分。累加器读取旧 pulse 和旧 saved_sample,不能在同一边沿看到另一过程的新非阻塞值。保存参数课的 modulo_tick.sv 和以下 periodic_accumulator.sv。N 必须为正。
module periodic_accumulator #(parameter integer N = 3) (
input logic clk, rst, enable,
input logic [3:0] sample,
output logic pulse,
output logic [7:0] total
);
localparam integer CW = (N <= 1) ? 1 : $clog2(N);
wire [CW-1:0] count;
logic [3:0] saved_sample;
modulo_tick #(.N(N)) tick_u (
.clk(clk), .rst(rst), .enable(enable),
.count(count), .pulse(pulse)
);
always_ff @(posedge clk) begin
if (rst) saved_sample <= 4'b0;
else if (enable) saved_sample <= sample;
end
always_ff @(posedge clk) begin
if (rst) total <= 8'b0;
else if (pulse) total <= total + {4'b0, saved_sample};
end
endmodule一起追踪数据与事件
N=3,输入在边沿前,输出在更新后。
| 边沿 | rst | enable | sample | 更新后 pulse | 更新后 total |
|---|---|---|---|---|---|
| E0 | 1 | 1 | 9 | 0 | 0 |
| E1 | 0 | 1 | 2 | 0 | 0 |
| E2 | 0 | 1 | 4 | 0 | 0 |
| E3 | 0 | 1 | 7 | 1 | 0 |
| E4 | 0 | 0 | 9 | 0 | 7 |
| E5 | 0 | 1 | 1 | 0 | 7 |
| E6 | 0 | 1 | 3 | 0 | 7 |
| E7 | 0 | 1 | 5 | 1 | 7 |
| E8 | 1 | 1 | 15 | 0 | 0 |
E4 加 7 而非外部新 sample 9。enable 只控制新接受,不取消待处理事件。E8 reset 丢弃待处理的 5 并清 total。用 enable && pulse 控制消费会丢掉 E4 事件。
在系统边界写参考模型
保留接受计数、可选待处理值和整数 total。非复位边沿先按模 256 消费旧待处理值,再用当前 enable/sample 决定是否产生新的第 N 个待处理值。reset 清全部。不依赖 tick_u.count 或 saved_sample。用下降沿激励、更新后比较,每拍检查 pulse/total、无待处理值时保持、消费后移除事件。
覆盖集成错误
- N=1 连续 pulse,每个接受样本在下一拍恰好消费一次。
- N=3 在终止样本前后插入禁用间隔,按接受边沿而非所有时钟计数。
- 禁用的消费边沿改变外部 sample,仍须使用保存值。
- 待处理时 reset,清 total 并丢弃事件。
- 累加越过 255,检查模 256 回绕。
把 saved_sample 改成 sample,E4 必须失败;再用 enable 限制消费也必须失败。恢复正确设计后记录通过。本实验验证单时钟有限位宽功能,不证明跨时钟、物理时序收敛或免费 DDS 产品运行,后者需独立证据。
✓ 已学习