异步时钟无毛刺切换的波形演示

切换原理

一,同步另一个域的控制信号。
二、负沿 gating clock,通过保证时序,避免毛刺。

RTL代码

此代码仅为方便理解,实际中请使用std cell例化。

module async_clk_mux(
    input clk0,clk1,rstn0,rstn1, //clk0 and clk1 has no assured phase relationship
    input sel,  //0 select clk0, 1 select clk1
    output reg clkout
);
    logic sel0, sel1;
    logic ck0_dff_0, ck0_dff_1;  //sync dff
    logic ck1_dff_0, ck1_dff_1;
    logic ck0_dff_1_qn, ck1_dff_1_qn;
    logic clk0_out_pre, clk1_out_pre;

    assign sel0 = ~sel;
    assign sel1 =  sel;

    always_ff @(posedge clk0 or negedge rstn0)
       if(!rstn0)
            ck0_dff_0 <= 1'b0;
       else 
            ck0_dff_0 <= sel0 & ck1_dff_1_qn;

    always_ff @(negedge clk0 or negedge rstn0)
       if(!rstn0)
            ck0_dff_1 <= 1'b0;
       else 
            ck0_dff_1 <= ck0_dff_0;

    assign ck0_dff_1_qn = ~ck0_dff_1;

    always_ff @(posedge clk1 or negedge rstn0)
       if(!rstn0)
            ck1_dff_0 <= 1'b0;
       else 
            ck1_dff_0 <= sel1 & ck0_dff_1_qn;

    always_ff @(negedge clk1 or negedge rstn0)
       if(!rstn0)
            ck1_dff_1 <= 1'b0;
       else 
            ck1_dff_1 <= ck1_dff_0;

    assign ck1_dff_1_qn = ~ck1_dff_1;

    assign clk0_out_pre = clk0 & ck0_dff_1;
    assign clk1_out_pre = clk1 & ck1_dff_1;
    assign clkout = clk0_out_pre | clk1_out_pre;
    
endmodule

仿真环境供参考

module tb_top;
    bit clk0, clk1, sel;
    bit rstn0, rstn1;
    integer dly0, dly1;

    initial begin
        clk0 = 1'b0;
        dly0 = {$random}%100;
        $display("dly0 is %0d", dly0);
        forever
           #(dly0) clk0 = ~clk0; 
    end

    initial begin
        clk1 = 1'b0;
        dly1 = {$random}%77;
        $display("dly1 is %0d", dly1);
        forever
           #(dly1) clk1 = ~clk1; 
    end

    initial begin
        sel = 1'b0;
        rstn0 = 1'b0;
        rstn1 = 1'b0;
        #100;
        rstn0 = 1'b1;
        rstn1 = 1'b1;
        repeat(4) begin
            #10us;
            sel = ~sel;
        end
        $finish;
    end

    initial begin
      $fsdbDumpvars;
      $fsdbDumpon;
    end

    async_clk_mux u_mux(
        .clk0(clk0),
        .rstn0(rstn0),
        .clk1(clk1),
        .rstn1(rstn1),
        .sel(sel),
        .clkout(clkout)
    );
endmodule

电路结构

glitch free async clk mux

波形

在这里插入图片描述clk0 --> clk1
clk0立即关闭
因为clk0_dff_1_qn的延迟,clk1会延迟打开。

在这里插入图片描述clk1 --> clk0
clk1也会立即关闭
因为clk1_dff_1_qn的延迟,clk0会延迟打开。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值