预分频之二

整数分频

整数分频都可以使用计数器简单实现,但奇数分频不作处理不能达到50%的占空比,下面具体讨论整数的分频。

偶数分频

偶数分频的翻转都在相同的沿(上升沿)发生,且都为50%占空比。

波形分析

847278-20161111193616608-642783190.png

偶数分频代码实例

verilog code

module  evenprescaler(
                     output    reg      prescaler,
                     input              clk,
                     input              rstn
                     );
parameter    N = 6;

reg    [7:0]   cnt;  //定义8位宽,以便能实现更都的分频,实际中够用即可
reg    [7:0]   cnt_next;

//计数器
always@(posedge clk,negedge rstn)
begin
    if(!rstn)
        cnt <= 8'b0;
    else
        cnt <= cnt_next;
end

always@(*)
begin
    if(cnt == (N - 1'b1))  //周期设定( 0 - N-1 ) N分频
        cnt_next = 8'b0;
    else
        cnt_next = cnt + 1'b1;
end

//分频翻转
always@(posedge clk,negedge rstn)
begin
    if(cnt == (N - 1'b1)/2)
        prescaler <= 1'b1;
    else if(cnt == (N - 1'b1)) //翻转
        prescaler <= 1'b0;
end

endmodule

testbench

module evenprescaler_tb;

reg                   clk;
reg                   rstn;
wire                  prescaler;

initial
begin
    clk   = 0;
    rstn  = 0;
    @(posedge clk)   rstn = 1;
 
    repeat(100) @(posedge clk);
    @(posedge clk)   $finish;
end

always #5  clk = ~clk;

initial begin
  $fsdbDumpfile("test.fsdb");   //dump波形
  $fsdbDumpvars();
end

evenprescaler    u_evenprescaler(
                                .prescaler(prescaler),
                                .clk(clk),
                                .rstn(rstn)
                                );
endmodule

仿真结果

847278-20161111193643139-1871423061.png


奇数分频

非50%占空比

与偶数分频方法类似,在适当的时钟上升沿置位或复位即可实现。


50%占空比

7分频波形分析

847278-20161111193743749-1614028474.png

上图可见, 7 = 3 + 4 = 3.5 + 3.5,我们需要在下降沿得到一个边沿,以得到半拍,这样错位的两个信号运算即可得到50%的占空比分频,具体请看代码。

代码实例(以7分频为例)

verilog code

module  oddprescaler(
                     output        prescaler,
                     input         clk,
                     input         rstn
                     );

parameter    N = 7;

reg    [7:0]   cnt;  //定义8位宽,以便能实现更都的分频,实际中够用即可
reg    [7:0]   cnt_next;

reg            preodd0;
reg            preodd1;

//计数器
always@(posedge clk,negedge rstn)
begin
    if(!rstn)
        cnt <= 8'b0;
    else
        cnt <= cnt_next;
end

always@(*)
begin
    if(cnt == (N - 1'b1))  //周期设定( 0 - N-1 ) N分频
        cnt_next = 8'b0;
    else
        cnt_next = cnt + 1'b1;
end

always@(posedge clk,negedge rstn)
begin
    if(!rstn)
        preodd0 <= 1'b0;
    else if(cnt == N - 1'b1)
        preodd0 <= 1'b0;
    else if(cnt == (N - 1'b1)/2)  //翻转
        preodd0 <= 1'b1;
end

always@(negedge clk,negedge rstn) //注意使用时钟的下降沿
begin
    if(!rstn)
        preodd1 <= 1'b0;
    else if(cnt == N - 1'b1)
        preodd1 <= 1'b0;
    else if(cnt == (N - 1'b1)/2) //翻转
        preodd1 <= 1'b1;
end

//错位信号进行运算
assign prescaler = preodd0 | preodd1;
endmodule

testbench

module oddprescaler_tb;

reg                   clk;
reg                   rstn;
wire                  prescaler;

initial
begin
    clk   = 0;
    rstn  = 0;
    @(posedge clk)   rstn = 1;
 
    repeat(100) @(posedge clk);
    @(posedge clk)   $finish;
end

always #5  clk = ~clk;

initial begin
  $fsdbDumpfile("test.fsdb");
  $fsdbDumpvars();
end

oddprescaler    u_oddprescaler(
                                .prescaler(prescaler),
                                .clk(clk),
                                .rstn(rstn)
                                );
endmodule
仿真结果

847278-20161111193806967-471811084.png


最后

说了这么多,试一试,思考5分频怎样写呢?
波形已给出,使用两种方法实现,其他奇数分频50占空比都可以使用这种方法实现。

847278-20161111193827280-1128608807.png


参考资料

[1]. 用Verilog语言实现奇数倍分频电路3分频、5分频、7分频
[2]. 基于Verilog的奇数偶数小数分频器设计

转载于:https://www.cnblogs.com/OneFri/p/6055420.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值