手撕Verilog面试题专题——(12)脉冲信号的跨时钟域传输
程序员文章站
2022-04-20 08:32:00
...
12 脉冲信号的跨时钟域传输
慢时钟域到快时钟域 打两拍
Verilog代码:
module BitTrans(
input clkb,
input rst,
input din,
output dout
);
reg [1:0] tmp;
[email protected](posedge clkb or negedge rst) begin
if(!rst)
tmp <= 2'b00;
else
tmp <= {tmp[0], din};
end
assign dout = tmp[1];
endmodule
testbench代码:
module BitTrans_tb();
reg clka;
reg clkb;
reg rst;
wire din;
wire dout;
reg [4:0] count;
initial begin
clka = 0;
clkb = 0;
rst = 0;
#25 rst = 1;
end
initial begin
forever #10 clka = ~clka;
end
initial begin
forever #3 clkb = ~clkb;
end
[email protected](posedge clka or negedge rst) begin
if(!rst)
count <= 0;
else
count <= count + 1;
end
assign din = (count == 1) ? 1 : 0;
BitTrans test(
.clkb(clkb),
.rst(rst),
.din(din),
.dout(dout)
);
endmodule
仿真波形:
当调换两个时钟信号即由快时钟域到慢时钟域中传输,若还采用上述方法,仿真波形如下。即可能慢时钟尚未采到,快时钟域的信号已经发生变化。所以要另想办法
快时钟域到慢时钟域
Verilog代码:
module BitTrans(
input clka, //快
input clkb, //慢
input rst,
input din,
output dout
);
reg signal_a;
reg signal_b;
reg [1:0] signal_ar;
reg [1:0] signal_br;
// 在将快时钟域中的脉冲展开
[email protected](posedge clka or negedge rst) begin
if(!rst)
signal_a <= 0;
else if (din)
signal_a <= 1;
else if (signal_ar[1])
signal_a <= 0;
else
signal_a <= signal_a;
end
// 在慢时钟域中的对快时钟域中展开的脉冲进行采样
[email protected](posedge clkb or negedge rst) begin
if(!rst)
signal_b <= 0;
else
signal_b <= signal_a;
end
// 在慢时钟域中打两拍
[email protected](posedge clkb or negedge rst) begin
if(!rst)
signal_br <= 0;
else
signal_br <= {signal_br[0], signal_b};
end
assign dout = ~signal_br[1] & signal_br[0];
// 慢时钟域中采到信号时给快时钟域反馈一个信号
[email protected](posedge clka or negedge rst) begin
if(!rst)
signal_ar <= 0;
else
signal_ar <= {signal_ar[0], signal_br[1]};
end
endmodule
testbench仿真文件:
module BitTrans_tb();
reg clka;
reg clkb;
reg rst;
wire din;
wire dout;
reg [4:0] count;
initial begin
clka = 0;
clkb = 0;
rst = 0;
#25 rst = 1;
end
initial begin
forever #10 clka = ~clka;
end
initial begin
forever #3 clkb = ~clkb;
end
[email protected](posedge clkb or negedge rst) begin
if(!rst)
count <= 0;
else
count <= count + 1;
end
assign din = (count == 1) ? 1 : 0;
BitTrans test(
.clka(clkb),
.clkb(clka),
.rst(rst),
.din(din),
.dout(dout)
);
endmodule
仿真波形:
下一篇: 前端面试题:关于跨域的问题你了解多少!