正沿触发3分频电路
下面是源代码和仿真波形:
library ieee;
use ieee.std_logic_1164.all;
entity div3 is port(
clk : in std_logic;
rst : in std_logic;
clk3 : out std_logic);
end div3;
architecture struct of div3 is
signal A : std_logic;
signal B : std_logic;
signal Ain : std_logic;
signal Bin : std_logic;
begin
Ain <= (not A) and (not B);
Bin <= A;
process(clk, rst)
begin
if (rst = '1') then
A <= '0';
B <= '0';
else
if (clk'event and clk = '1') then
A <= Ain;
B <= Bin;
end if;
end if;
end process;
process(clk, A, B)
begin
-- clk3 <= (clk and B and (not A)) or (A and (not B)); -- clk3 has glitch
clk3 <= (clk and Bin and B and (not A)) or Bin or A; -- clk3 no glitch
end process;
end struct;
library ieee;
use ieee.std_logic_1164.all;
entity tb_div3 is
end tb_div3;
architecture behav of tb_div3 is
component div3 port(
clk : in std_logic;
rst : in std_logic;
clk3 : out std_logic);
end component;
constant TCLK : time := 20 ns;
signal clk : std_logic := '0';
signal rst : std_logic := '1';
signal clk3 : std_logic;
begin
process begin
wait for TCLK/2;
clk <= not clk;
end process;
rst <= '0' after TCLK*2;
u1: div3 port map(
clk => clk,
rst => rst,
clk3 => clk3);
end behav;
div3仿真波形

从波形上看,输出clk3的下降沿是和输入clk的下降沿对齐的,
搞不懂你说的只用了上升延。
从实际应用上看,无论是否采用下降沿,这样的3分频电路都会有很多问题,
因为输入clock很可能并不是占空比1:1的,
那么即使用了下降沿也无法实现1:1的三分频电路。
可以实现的
一般先在时钟正沿生产序列“100”,用负沿延迟半个时钟周期,将两个结果“and”生产输出。
谢谢!
所说只用正沿,是指只使用时钟的正沿触发实现3分频电路,主要是区别于既使用时钟正沿触发、又使用时钟负沿触发实现3分频电路的方法。探讨实现奇数及小数分频的各种方法。
请教:我也没明白这个波形,只在模块内部有信号变化,没有输出波形,怎么回事?这个办法好像不是很好呀,还有小数怎么分频的呀,倍频不就好了
fiats:
clk3 有输出波形呀,我不知道你说哪个信号没有输出波形。
主要想法如下:
1、利用LFSR替代通常的counter,为了节省资源;
2、利用clock信号的半周期补偿奇数分频的不均衡,达到1:1占空比,为了不使用时钟的下降沿。
小数分频主要指:1.5,2.5,3.5...的分频。可能最好只能做到4:6或6:4的占空比。
时钟f很低时才可能.
谢谢!
能否详细说一下高f时会出现什么问题?
使用上升沿和下降沿实现奇数分频,可能遇到的问题是:保证上升沿和下降沿同时“很陡”是否容易?
只使用上升沿可以避免上述问题,其它信号由时钟驱动,稍微“落后”于时钟,这样其它信号正半周和时钟的
正半周运算时会有一小部分“重合”,不会形成“负”glitch。
很晕!
三楼的说法我觉得是对的
看了你的程序我知道 什么叫做厉害了
好像可以比较简单来实现的
现在很多公司还是用VHDL的吗?
不知各位高手还在不,谁能告诉我在小编的程序中免毛刺是怎么回事?
谢谢。
VHDL的!
module div3 (
input clk,
output o_clk
);
reg [7:0] cnt_p;
reg [7:0] cnt_n;
reg clk_p;
reg clk_n;
assign o_clk = clk_p | clk_n;
always@(posedge clk)
begin
if (cnt_p == 2) // 0 ~ 2
cnt_p <= 0;
else
cnt_p <= cnt_p + 1;
if (cnt_p < 1) // 0
clk_p = 1;
else // 1 2
clk_p = 0;
end
always@(negedge clk)
begin
if (cnt_n == 2) // 0 ~ 2
cnt_n <= 0;
else
cnt_n <= cnt_n + 1;
if (cnt_n < 1) // 0
clk_n = 1;
else // 1 2
clk_n = 0;
end
endmodule
我说一下我的感觉,组合逻辑产生时钟,可能有亚稳问题,也是时间过边沿可能会有多次跳变,这样的时钟在高性能芯片中,用低速时钟时就会有问题,比如计数器多计数.
用双边沿时,组合逻辑简单一点,这问题会少一点,但这个问题,难以完全避免.
不过作都的思路受教了,先三分,再用组合逻辑组合出50%的占空比.学了.
记得论坛里面有介绍实现小数分频的方法。
17楼的没有reset,仿真动不了哦:)
小数分频我贴多一个code,就在这坛子里~
不错!
