边沿检测电路?上升&下降&双边沿

余你余生 / 2023-07-28 / 原文

请设计一个边沿检测电路,检测上升、下降、双边沿?

module edge_detect(
input        sys_clk             ,
input        sys_rst_n           ,
input        in                  ,
output       pose_edge           ,
output       nege_edge           ,
output       dou_edge           
);
//要实现边沿检测,最直接的想法是用两级寄存器,第二级寄存器锁存住某个时钟上升沿到来时的输入电平,第一级寄存器锁存住下一个时钟沿到来时的输入电平,如果这两个寄存器锁存住的电平信号不同,就说明检测到了边沿,具体是上升沿还是下降沿可以通过组合逻辑来实现。
reg  edge_0;  
reg  edge_1;

always@(posedge sys_clk or negedge sys_rst_n) begin
    if(!sys_rst_n) begin 
        edge_0<=1'b0;
        edge_1<=1'b0;
    end 
    else  begin 
        edge_0<=in;
        edge_1<=edge_0;
    end 
end 

assign pose_edge =edge_0&(~edge_1);  //检测上升沿
assign nege_edge =(~edge_0)&edge_1;  // 检测下降沿
assign dou_edge  =edge_0^edge_1;     //检测双沿  edge_0&(~edge_1)|(~edge_0)&edge_1
endmodule 
`timescale 1ns/1ns
module tb_edge_detect();
reg      sys_clk        ;
reg      sys_rst_n      ;
reg      in             ;
wire     pose_edge      ;
wire     nege_edge      ;
wire     dou_edge       ;

initial begin
    sys_clk<=1'b0;
    sys_rst_n<=1'b0;
    in<=1'b0;
    #20
    sys_rst_n<=1'b1;
    #30              //模拟 输入 产生上升沿和下降沿
    in<=1'b1;
    #40
    in<=1'b0;
    #50
    in<=1'b1;
    #40
    in<=1'b0;
    #60
    in<=1'b1;
    #55
    in<=1'b0;
    #30
    in<=1'b1;
    #30
    in<=1'b0;
    #90
    in<=1'b1;
    #30
    in<=1'b0;
    #200
    in<=1'b1;
    #105
    in<=1'b0;
end 

always  #10 sys_clk<=~sys_clk;

edge_detect    edge_detect_inst(
.sys_clk     (sys_clk  )        ,
.sys_rst_n   (sys_rst_n)        ,
.in          (in       )        ,
.pose_edge   (pose_edge)        ,
.nege_edge   (nege_edge)        ,
.dou_edge    (dou_edge )        
);

endmodule

波形图: