计数器
这里我写了两个计数器,计数器1,是现在常用的计数器设计方式;计数器2,是我在一些老旧的书里面看到的一种设计方式。
module text(
input clk,
input rst,
output reg [3:0] cnt1,cnt2
);
parameter kk = 4'd1;
reg [3:0] cnt_next2;
//计数器1
always@(posedge clk or posedge rst)
if(rst)
cnt1 <= 4'd0;
else
cnt1 <= cnt1 + kk;
//计数器2
always@(posedge clk or posedge rst)
if(rst)
cnt2 <= 4'd0;
else
cnt2 <= cnt_next2;
/*
wire [3:0] cnt_next2;
assign cnt_next2 = cnt2 + kk;
*/
always@(*)
begin
cnt_next2 = cnt2 + kk;
end
从代码中分析来看计数器2应该会有个cnt_next2寄存器存在,但是在quartus16.1版本综合完后生成的RTL电路是完全一样的(assign的那种写法在最后综合的结果与电平触发的always写法完全一样),这说明cnt_next2被优化掉了。
接地端
当把上面代码中的kk改成 kk = 4’d2;时,综合结果如下,计数器1输出口有根接地线,再看它前面的寄存器,可以发现只综合了3位的寄存器,因为每次加2时,最低位始终保持0,所以综合器把cnt1综合成了3位的寄存器,输出时是用的拼接的方式,把最低位直接接地了。
而计数器2却没有综合掉,是按照4位的形式进行综合的,再往前看加法器,加法器是3位的加法器,这个与寄存器1是一致的。
再看综合后的警告,是说寄存器cnt1在一些路径中保持他的原始值不变,这个应该就是指其中的最低位了,而计数器2却没有相关的警告。
Warning (10240): Verilog HDL Always Construct warning at text.v(10): inferring latch(es) for variable "cnt1", which holds its previous value in one or more paths through the always construct
那以后再写计数器的时候可能就要用计数器2的形式比较稳定了一点了。还有就是当综合出的电路如果有接地线的时候,可能就是这种原因了,有些数据一直未变化,所以综合器直接按接地了,这时候修改verilog代码时就可以参考计数器2的设计方案了。