logo资料库

分频器原理及实现.docx

第1页 / 共5页
第2页 / 共5页
第3页 / 共5页
第4页 / 共5页
第5页 / 共5页
资料共5页,全文预览结束
分配器原理及实现 分频器是指使输出信号频率为输入信号频率整数分之一的电子电路。在许多 电子设备中如电子钟、频率合成器等,需要各种不同频率的信号协同工作,常用 的方法是以稳定度高的晶振为主振源,通过变换得到所需要的各种频率成分,分 频器是一种主要变换手段。以下以 verilog HDL 语言为基础介绍占空比为 50%的 分频器。 一、偶分频 假设为 N 分频,只需计数到(N/2 – 1),然后时钟翻转同时计数清零,如此就 可以得到 N 分频。 二、奇分频 实现等占空比的奇数分频,需要使用两个时钟沿采样,上升沿和下降沿均需 计数到(N-1)/2 时,翻转时钟,并且计数到(N-1)时再次翻转时钟,然后将上升 沿和下降沿得到的两个波形进行或操作,便可以得到奇数 N 分频。三分频举例 如下图: 如果生成这样一个占空比为 2/3,周期为时钟 3 倍的信号,同时产生一个超 前或落后于它半个 clock 周期时间的信号,对两个信号进行相与,得到的结果恰 好就是三分频的时钟。 如果生成另外一个占空比为 1/3,周期为时钟 3 倍的信号,同时产生一个超 前或落后于它半个 clock 周期时间的信号,对两个信号相或,得到的结果恰好就 是三分频的时钟。 奇数分频的难点在于,三分频要求 1.5 倍的时钟时间翻转一次,这样整体的 周期时间是原来的 3 倍,即三分频,而 verilog 不允许在两个 always 模块里对同 一 reg 赋值。而且这里需要注意的是:在 FPGA 中的有关资料中,曾提到不要同 时使用时钟的上升沿和下降沿。对于奇数分频,需要同时使用到时钟的上升沿和
下降沿,解决方法有以下几种: 1)使用 PLL 得到 180 度反向时钟:先通过 PLL 锁相环产生两个频率相同、 相位差为 180 度的 clk1 和 clk2,然后在每个 clk 的上升沿进行采样。 2)使用 PLL 得到倍频信号:该信号上升沿可同时表示源时钟的上升沿和下 降沿,通过计数器的奇偶进行区分。 3)可以通过将 clk 简单取反得到一个新的 clk_180(clock_n),或者用全局 时钟资源中的 INV 来产生,之后通过 bufg 直接上全局时钟,时钟质量较好。 代码如下: module divider #(parameter DIV_CNT = 32'd1000) ( input wire clk input wire rst output wire clk_div //输出分频后的时钟 ); ,//输入时钟 ,//输入复位信号 wire [31:0] div_cnt_even;//偶数分频系数 wire [31:0] div_cnt_odd;//奇数分频系数 wire odd;//奇数分频使能信号 assign odd = (DIV_CNT[0] == 1) ? 1'b1 : 1'b0; assign div_cnt_even = (odd == 1'b1) ? (31'b0) :((DIV_CNT >> 1) - 1); assign div_cnt_odd = (odd == 1'b1) ? ((DIV_CNT - 1) >> 1) :(31'b0); reg [31:0] cnt_even ; reg [31:0] cnt_odd_pos; reg [31:0] cnt_odd_neg; reg clk_div_even; reg clk_div_odd_pos; reg clk_div_odd_neg; wire clk_div_odd; assign clk_div_odd = clk_div_pos | clk_div_neg; assign clk_div = (odd == 1'b1) ? clk_div_odd : clk_div_even; wire clk_180; assign clk_180 = ~clk; //偶数分频电路 always @ (posedge clk or posedge rst) if(rst)
clk_div_even <= 1'b0; else if(div_cnt_even == 32'b0) clk_div_even <= 1'b0; else if(cnt_even == div_cnt_even) clk_div_even <= ~clk_div_even; always @ (posedge clk or posedge rst) if(rst) cnt_even <= 32'b0; else if(div_cnt_even == 32'b0) cnt_even <= 32'b0; else if(cnt_even == div_cnt_even) cnt_even <= 32'b0; else cnt_even <= cnt_even + 32'd1; //奇数分频电路 always @ (posedge clk or posedge rst) if(rst) clk_div_odd_pos <= 1'b0; else if(div_cnt_odd == 32'b0) clk_div_odd_pos <= 1'b0; else if(cnt_odd_pos == div_cnt_odd) clk_div_odd_pos <= ~clk_div_odd_pos; else if(cnt_odd_pos == DIV_CNT - 1) clk_div_odd_pos <= ~clk_div_odd_pos; always @ (posedge clk or posedge rst) if(rst) cnt_odd_pos <= 32'b0; else if(div_cnt_odd == 32'b0) cnt_odd_pos <= 32'b0; else if(cnt_odd_pos == DIV_CNT - 1) cnt_odd_pos <= 32'b0; clk_div_odd_neg <= 1'b0; else if(div_cnt_odd == 32'b0) clk_div_odd_neg <= 1'b0; else if(cnt_odd_neg == div_cnt_odd) cnt_odd_pos <= cnt_odd_pos + 32'd1; always @ (posedge clk_180 or posedge rst) else if(rst)
clk_div_odd_neg <= ~clk_div_odd_neg; else if(cnt_odd_neg == DIV_CNT - 1) clk_div_odd_neg <= ~clk_div_odd_neg; always @ (posedge clk_180 or posedge rst) if(rst) cnt_odd_neg <= 32'b0; else if(div_cnt_odd == 32'b0) cnt_odd_neg <= 32'b0; else if(cnt_odd_neg == DIV_CNT - 1) cnt_odd_neg <= 32'b0; else cnt_odd_neg <= cnt_odd_neg + 32'd1; //奇数分频电路 另外一种方法 例如三分频 endcase state1 <= 2'b01; if(rst) else begin case(state1) begin 2'b01:state1 <= 2'b10; 2'b10:state1 <= 2'b11; 2'b11:state1 <= 2'b01; default:state2 <= 2'b01; // assign clkout=state1[1]&state2[1]; // always@(posedge clk or posedge rst) // // // // // // // // // // // // // always@(posedge clk_180 or posedge rst) // // // // // // // // // // // end endmodule 2'b01:state2 <= 2'b10; 2'b10:state2 <= 2'b11; 2'b11:state2 <= 2'b01; default:state2 <= 2'b01; end if(rst) else begin state2 <= 2'b01; case(state2) endcase
PLL(Phase Locked Loop):锁相环,锁相环是一种反馈控制电路,利用外部 输入的参考信号控制环路内部振荡信号的频率和相位。
分享到:
收藏