多比特跨时钟域DMUX(含tb文件)

verilog设计-cdc:多比特信号跨时钟域(DMUX)-优快云博客

跨时钟域同步2---单bit信号同步实战(快到慢+慢到快) - 知乎 (zhihu.com)

IC学习笔记9——多比特信号的跨时钟域处理方法之“MUX/DMUX同步器”_dmux跨时钟域-优快云博客

原理部分可以参考这些文章。1.快到慢。2.慢到快 3.快到慢的testbench 4. 波形

module mult_bit_fast_to_slow_dmux 
    #(parameter DATAWIDTH = 8)
    (
        input                       rst_n,        
        
        input                       clk_fast,
        input  [DATAWIDTH-1:0]      data_fast,
        input                       data_valid_fast,
 
        input                        clk_slow,
        output  reg [DATAWIDTH-1:0]  data_slow,
        output  reg                  data_valid_slow
 
 
     );
 
 
        //signal valid fast to slow cdc
        reg data_valid_fast_reg;
        wire data_valid_slow_ready;
        always@(posedge clk_fast or negedge rst_n)begin
            if(!rst_n)
               data_valid_fast_reg <= 1'b0;
            else if(data_valid_fast  == 1'b1)
               data_valid_fast_reg <= ~data_valid_fast_reg ;  
        end
 
        reg data_valid_fast2slow_reg0,data_valid_fast2slow_reg1;
        always@(posedge clk_slow or negedge rst_n)begin
            if(!rst_n)
               begin
                  data_valid_fast2slow_reg0 <= 1'b0;
                  data_valid_fast2slow_reg1 <= 1'b0;
               end
            else
               begin
                  data_valid_fast2slow_reg0<= data_valid_fast_reg ;  
                  data_valid_fast2slow_reg1<= data_valid_fast2slow_reg0;
               end
        end
 
       reg data_valid_fast2slow_reg2;
        always@(posedge clk_slow or negedge rst_n)begin
            if(!rst_n)
                  data_valid_fast2slow_reg2 <= 1'b0;
            else
                  data_valid_fast2slow_reg2 <= data_valid_fast2slow_reg1;
        end
         
   assign data_valid_slow_ready = data_valid_fast2slow_reg1 ^ data_valid_fast2slow_reg2 ;
        
        always@(posedge clk_slow or negedge rst_n)begin
            if(!rst_n)
                  data_valid_slow<=  0;
            else 
                  data_valid_slow<= data_valid_slow_ready ;
        end
 
        //data fast to slow cdc
        reg  [DATAWIDTH-1:0]  data_fast_reg;
        always@(posedge clk_fast or negedge rst_n)begin
            if(!rst_n)
                  data_fast_reg<=  0;
            else
                  data_fast_reg<= data_fast;
        end
        always@(posedge clk_slow or negedge rst_n)begin
            if(!rst_n)
                  data_slow <=  0;
            else if(data_valid_slow_ready == 1'b1)
                  data_slow <= data_fast_reg ;
        end
 
 
 
 
endmodule
`timescale 1ns/1ps   
         module mult_bit_tb();
          reg aclk;
          reg arst_n;
          reg [7:0] data;
          reg data_valid;
          wire adata_valid;
          wire [7:0] adata;
         
          reg bclk;

          always #5 bclk=~bclk;
          always #3.365 aclk=~aclk;

          initial begin
	        aclk=1;
	        bclk=1;
	        arst_n=0;
	        data_valid=0;
	        data=0;
	        #200;
	        arst_n=1;
	        //第一次数据
	        @(posedge bclk)
	        data_valid=1;
	        data=1;
	        #53.84;
	       @(posedge bclk)
	        data_valid=0;
    
	        #400;
	         //第二次数据
	        @(posedge bclk)
	        data_valid=1;
	        data=2;
	        #53.84;
	       @(posedge bclk)
	        data_valid=0; 
			#53.84;
            $finish;
	        end
 mult_bit_fast_to_slow_dmux  u1(
                           .clk_fast(aclk),
                           .rst_n(arst_n),
                           .clk_slow(bclk),                        
                           .data_fast(data),
                           .data_valid_fast(data_valid),
                           .data_slow(adata),
                           .data_valid_slow(adata_valid)
                                                   );
             endmodule       
module mult_bit_slow_to_fast_dmux 
    #(parameter DATAWIDTH = 8)
    (
        input                       rst_n,        
 
        input                       clk_slow,
        input  [DATAWIDTH-1:0]      data_slow,
        input                       data_valid_slow,
 
        input                       clk_fast,
        output reg [DATAWIDTH-1:0]  data_fast,
        output reg                  data_valid_fast
     );
 
 
        //signal valid slow to fast cdc
        reg data_valid_slow_reg;
        always@(posedge clk_slow or negedge rst_n)begin
            if(!rst_n)
               data_valid_slow_reg <= 1'b0;
            else
               data_valid_slow_reg <= data_valid_slow;  
        end
 
        reg data_valid_slow2fast_reg0,data_valid_slow2fast_reg1;
        always@(posedge clk_fast or negedge rst_n)begin
            if(!rst_n)
               begin
                  data_valid_slow2fast_reg0 <= 1'b0;
                  data_valid_slow2fast_reg1 <= 1'b0;
               end
            else
               begin
                  data_valid_slow2fast_reg0 <= data_valid_slow_reg ;  
                  data_valid_slow2fast_reg1 <= data_valid_slow2fast_reg0 ;
               end
        end
        always@(posedge clk_fast or negedge rst_n)begin
            if(!rst_n)
                  data_valid_fast <= 1'b0;
            else
                  data_valid_fast <= data_valid_slow2fast_reg1 ;
        end
 
        //data slow to fast cdc
        reg  [DATAWIDTH-1:0]      data_slow_reg;
        always@(posedge clk_slow or negedge rst_n)begin
            if(!rst_n)
                  data_slow_reg <=  0;
            else
                  data_slow_reg <= data_slow ;
        end
 
        always@(posedge clk_fast or negedge rst_n)begin
            if(!rst_n)
                  data_fast<=  0;
            else if(data_valid_slow2fast_reg1 == 1'b1)
                  data_fast <= data_slow_reg ;
        end
endmodule

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值