📅  最后修改于: 2021-01-11 15:12:55             🧑  作者: Mango
计数器是顺序逻辑设备,它们遵循由外部时钟(CLK)信号触发的预定计数状态序列。特定计数器在返回其原始第一状态之前通过其前进的状态或计数序列的数量称为模数(MOD)。换句话说,模数(或模)是计数器计数的状态数,并且是计数器的除数。
模数计数器或MOD计数器是根据计数器在返回其原始值之前将要排序的状态数定义的。
例如,一个2位计数器的二进制数从00 2到11 2 ,十进制从0到3,其模数值为4(00→1→10→11,然后返回00);因此,称为4模或4模计数器。还要注意,从00到11花费了四个时钟脉冲。
在此示例中,只有两个位(n = 2),那么计数器的最大可能输出状态数(最大模数)为2 n = 2 2或4。但是,计数器可以设计为计数到任意2 n通过将多个计数级级联在一起以产生单个模数或MOD-N计数器,可以按顺序排列状态。
因此,“ Mod-N”计数器将需要连接“ N”个触发器来计数单个数据位,同时提供2 n种不同的输出状态(n是位数)。注意,N始终是整数。
然后我们可以看到MOD计数器的模数是2的整数次幂,即2、4、8、16等,以产生n位计数器,具体取决于所用触发器的数量,并且如何连接它们,确定计数器的类型和模数。
module modN_ctr
# (parameter N = 10,
parameter WIDTH = 4)
( input clk,
input rstn,
output reg[WIDTH-1:0] out);
always @ (posedge clk) begin
if (!rstn) begin
out <= 0;
end else begin
if (out == N-1)
out <= 0;
else
out <= out + 1;
end
end
endmodule
试验台
以下是上述相同示例的测试平台,例如:
module tb;
parameter N = 10;
parameter WIDTH = 4;
reg clk;
reg rstn;
wire [WIDTH-1:0] out;
modN_ctr u0 ( .clk(clk),
.rstn(rstn),
.out(out));
always #10 clk = ~clk;
initial begin
{clk, rstn} <= 0;
$monitor ("T=%0t rstn=%0b out=0x%0h", $time, rstn, out);
repeat(2) @ (posedge clk);
rstn <= 1;
repeat(20) @ (posedge clk);
$finish;
end
endmodule
输出如下:
ncsim> run
T=0 rstn=0 out=0xx
T=10 rstn=0 out=0x0
T=30 rstn=1 out=0x0
T=50 rstn=1 out=0x1
T=70 rstn=1 out=0x2
T=90 rstn=1 out=0x3
T=110 rstn=1 out=0x4
T=130 rstn=1 out=0x5
T=150 rstn=1 out=0x6
T=170 rstn=1 out=0x7
T=190 rstn=1 out=0x8
T=210 rstn=1 out=0x9
T=230 rstn=1 out=0xa
T=250 rstn=1 out=0x0
T=270 rstn=1 out=0x1
T=290 rstn=1 out=0x2
T=310 rstn=1 out=0x3
T=330 rstn=1 out=0x4
T=350 rstn=1 out=0x5
T=370 rstn=1 out=0x6
T=390 rstn=1 out=0x7
T=410 rstn=1 out=0x8
Simulation complete via $finish(1) at time 430 NS + 0
这是一个重置为所选编号的计数器。例如,留给它自己的设备使用的两位十进制计数器将从00到99进行计数。除非您有100秒的分钟数,否则这对于时钟来说用处不大。
要解决此问题,计数器必须从00到59。这是通过检测左侧数字6并将其重置为零来实现的。这将是Modulo 6计数器,如果我们包含两个数字,则为60。
假设我们要设计一个MOD-5计数器。首先,我们知道“ m = 5”,所以2 n必须大于5。
由于2 1 = 2、2 2 = 4、2 3 = 8,并且8大于5,因此我们需要一个带有三个触发器的计数器(N = 3),从而使我们可以自然计数二进制数000至111( 0到7小数)。