1.上升沿检测
用一个寄存器来储存上个周期的输入,时钟周期到来时将寄存器输出位q。01时就为上升沿。
module top_module (
input clk,
input [7:0] in,
output [7:0] pedge
);
reg [7:0] q;
always@(posedge clk)
begin
q<=in;
pedge<=~q∈
end
endmodule
2.双边沿检测
双边沿和上一题单边沿一样思路。判断换成异或就可以,01/10。
module top_module (
input clk,
input [7:0] in,
output [7:0] anyedge
);
reg [7:0] q; //定义一个寄存器用来存储前一个周期的in,然后比较下个周期的in
always@(posedge clk)
begin
q<=in;
anyedge<=q^in;
end
endmodule
3.Edge capture register
这一题的要求是检测下降沿,检测到下降沿后,输出保持为1,直到reset到来。
关于保持,我用的答案1的方法,out<=(q&~in)|out; 即两种可能out为1,一种是检测到下降沿。
答案2是知乎上的答案,定义一个临时变量判断,效果一样,复杂一些。
答案1:
module top_module (
input clk,
input reset,
input [31:0] in,
output [31:0] out
);
reg [31:0]q;
always@(posedge clk)
begin
q<=in;
if(reset)
out<=32'b0;
else out<=(q&~in)|out;//用out<=out来完成保持
end
endmodule
答案2:
module top_module (
input clk,
input reset,
input [31:0] in,
output [31:0] out
);
reg [31:0] temp;
wire [31:0] capture;
//同理,我们先检测输入信号的上升沿。
always @ (posedge clk)
begin
temp <= in;
end
//这里如果采用reg的话会出现时序错误。
assign capture = ~in & temp;
//检测到上升沿之后,来确定我们的输出
always @ (posedge clk)
begin
if(reset)
out <= 32'b0;
else
begin
for (int i=0; i<32; i=i+1)
begin
if(capture[i] == 1'b1)
out[i] <= 1'b1;
end
end
end
endmodule