一看就会的奇偶分频电路


目录

前言

题目

二分频电路

第一步:画波形图

第二步:写状态机

三分频电路——1/3占空比

第一步:画波形图

第二步:写状态机

三分频电路——1/2占空比

第一步:画波形图

第二步:写状态机

4/5/6/7...分频电路

第一步:画波形图

总结


前言


最近又到了招聘季,招聘就离不开笔试面试,而在笔试面试过程中经常出现的一道题就是写出分频电路的verilog代码(以及电路图?),因此在这篇文章里,我们使用一个公式将所有分频电路套进去,以便于在考场上和仿真工具中轻松实现分频电路。

题目

实现2/3/4/5分频电路,给出一个模板:

module clk_div(reset,clk_in,clk_out)
input reset ;
input clk_in ;
output clk_out ;

  //#功能实现模块

endmodule

二分频电路

第一步:画波形图

分频电路是将原始信号频率分成频率更小的衍生信号,信号频率变为二分之一,也就意味着周期变为2倍,因此直接将原本的2个周期所占用的时间现在变为一个周期,即可以生成一个二分频的信号。之所以采用波形图是因为波形图的直观性便于理解和思考,相对于抽象的代码和难以理解的电路图来说。


第二步:写状态机

按照三段式状态机的标准写法(以往文章有过介绍),写一个序列发生器,产生我们想要的信号。在二分频电路里,我们实际上是想实现重复的01信号的产生,这就是最简单的序列发生器。

//#功能实现模块
//三段式状态机

//状态声明
parameter s0 = 0 ;
parameter s1 = 1 ;

reg cs,ns
always@(posedge clk_in) begin
  if (reset)
    cs <= s0;
  else
    cs <= ns;
end

//状态改变
always@(*) begin
  case(cs)
    s0: ns = s1 ;
    s1: ns = s0 ;
end

//输出
always@(*) begin
  case(cs)
    s0: clk_out = 0 ;
    s1: clk_out = 1 ;
end

在二分频电路中产生的是循环的01信号,所以状态机只需要2个状态。二分频电路就这样产生了,接下来看三分频。

三分频电路——1/3占空比

第一步:画波形图

如上图所示,三分频电路即就是将原始clk信号三个周期的时间,变为新信号clk_out_3的一个周期。我们常见的周期信号都是占空比1/2的信号,但是在上图中我们可以看到三分频电路可以分为两种,一种就是1/2占空比(1.5,1.5?),而另一种就是1/3占空比的三分频信号(001,010,100)。按照本文的公式,后者这种规则的循环序列信号很容易产生。由易向难,我们先看1/3占空比的三分频电路。

第二步:写状态机

//#功能实现模块
//三段式状态机

//状态声明
parameter s0 = 0 ;
parameter s1 = 1 ;
parameter s2 = 2 ;

reg [1:0]cs,ns

always@(posedge clk_in) begin
  if (reset)
    cs <= s0;
  else
    cs <= ns;
end

//状态改变
always@(*) begin
  case(cs)
    s0: ns = s1 ;
    s1: ns = s2 ;
    s2: ns = s0 ;
end

//输出
always@(*) begin
  case(cs)
    s0: clk_out = 0 ;
    s1: clk_out = 0 ;
    s2: clk_out = 1 ;
end

要实现三分频电路,那么要产生的序列就是001或者010或100,此时状态机有三个状态,所以需要2位寄存器。简单的1/3占空比三分频电路实现后,现在来看1/2占空比的三分频电路。

三分频电路——1/2占空比

第一步:画波形图

如上图所示,clk_out_3_2即为上面的1/3占空比电路,而现在我们要生成1/2占空比的三分频电路clk_out_3,那么我们就需要在下降沿控制原始信号。但是我们无法使用下降沿和上升沿同时去控制一根信号,所以我们可以使用clk_in的下降沿产生一个010序列信号clk_out_3_1。接下来将clk_out_3_1和clk_out_3_2信号进行或[ | ]操作,即可得到1/2占空比的3分频信号clk_out_3。

第二步:写状态机

//#功能实现模块
//三段式状态机
//上升沿触发
//状态声明
parameter s0 = 0 ;
parameter s1 = 1 ;
parameter s2 = 2 ;

reg [1:0]cs,ns

always@(posedge clk_in) begin
  if (reset)
    cs <= s0;
  else
    cs <= ns;
end

//状态改变
always@(*) begin
  case(cs)
    s0: ns = s1 ;
    s1: ns = s2 ;
    s2: ns = s0 ;
end

//输出
always@(*) begin
  case(cs)
    s0: clk_out_1 = 0 ;
    s1: clk_out_1 = 0 ;
    s2: clk_out_1 = 1 ;
end

//三段式状态机
//下降沿触发
//状态声明
reg [1:0]cts,nts

always@(negedge clk_in) begin
  if (reset)
    cts <= s0;
  else
    cts <= nts;
end

//状态改变
always@(*) begin
  case(cts)
    s0: nts = s1 ;
    s1: nts = s2 ;
    s2: nts = s0 ;
end

//输出
always@(*) begin
  case(cts)
    s0: clk_out_2 = 0 ;
    s1: clk_out_2 = 1 ;
    s2: clk_out_2 = 0 ;
end

//final out
clk_out = clk_out_1 | clk_out_2 ;

4/5/6/7...分频电路

根据上面的模式,我们想实现一个任意分频任意占空比的分频电路已经不是难事了,只要画出波形图,仔细分析想要实现的功能,然后剩下的就只是套用公式了。

第一步:画波形图

四分频电路波形图如下,用2分频电路再2分频即可得到,只需要再次例化二分频电路模块,不用修改模块内部代码即可实现。亦可直接用原始信号写一个具有4种状态的状态机,实现0011序列发生器。当然如果需要实现什么1/4占空比,3/8占空比,那也是被这套公式所支持的。

如下图所示,5分频电路其实就是3分频电路的扩展。使用上升沿实现00011的序列发生器,再使用下降沿实现00110的序列发生器,最后将产生的两个2/5占空比的5分频电路或起来,即可得到1/2占空比的5分频信号clk_out_5。奇分频电路的实现最重要的一点就是使用下降沿触发来实现那0.5,将多出来的这个1分成2个0.5给高电平和低电平。

总结

总的来说,实现奇偶分频电路,只需要套用上述公式,即可轻松得到任意分频任意占空比的分频信号。

最后再次总结一下公式:

1.画波形图 :偶数分频只需要数好周期数,即可找到中间点。而奇数分频可以先实现简单的接近中点的分频,例如1/3(1.5/3)占空比分频,2/5(2.5/5)占空比分频等等,然后将这个接近1/2占空比的信号利用下降沿平移半个原始信号的周期,即可出现那缺少的0.5,最后再通过或[ | ]得到最终的1/2占空比的信号。

2.写状态机:使用状态机实现序列发生器,通过观察波形图得到想要的是什么序列,然后依据本文中的代码示例状态机的格式和写法进行扩展,主要是状态机的状态个数。

希望这篇文章能够让你对奇偶分频增加更多的了解,欢迎指出错误和互相交流。

  • 11
    点赞
  • 89
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值