解题思路
题目中说了是两个同步的倍频时钟clk0 clk1,已知clk0是clk1的二倍频,属于相关时钟,避免切换时毛刺出现,只需要在组合逻辑的基础上添加下降沿触发的DFF。原理图如下:
那么为什么要使用下降沿触发的DFF呢?
原因是这样,所谓去除毛刺,就是要避免毛刺的产生,那么得先明白毛刺是如何产生的,其实只要两个时钟相反时切换都换产生毛刺,如果没有DFF,比如,在clk1为低电平时,sel马上切换到clk0,恰巧clk0为高电平,但高电平只剩一点了,所以便产生了一个高电平毛刺,当然同理也有低电平毛刺。
但在此时钟切换电路中,sel信号的传输存在着DFF的延迟,也就是说在时钟切换时,两个DFF的输出存在都是0的情况,此时clk_out输出为低电平,这段时间可能很短,如果在两个时钟都是高电平的时候切换,可能会产生低电平毛刺,所以考虑要在两个都为低电平的时候切换最为稳妥。
那么使用下降沿触发的DFF,尽管sel已经有切换指令了,但需要等到下降沿后才通过DFF传到后面,因为是下降沿,所以高电平已经结束了,切换过去可确保无毛刺。
代码实现
`timescale 1ns/1ns
module huawei6(
input wire clk0 ,
input wire clk1 ,
input wire rst ,
input wire sel ,
output wire clk_out
);
reg q0, q1;
always@(negedge clk0 or negedge rst)
if(!rst)
q0 <= 0;
else
q0 <= ~sel & ~q1;
always@(negedge clk1 or negedge rst)
if(!rst)
q1 <= 0;
else
q1 <= sel & ~q0;
assign clk_out = (q0 & clk0) | (q1 & clk1);
endmodule
截止目前2022年4月10日,此题目正确答案未能用过牛客网的测试示例,因为牛客网标准答案中2个DFF的驱动时钟搞反了。