时序电路的VHDL设计 时序电路的结构与特点 p.552 图7-37 时序电路的信号变化特点: 同步时序电路以时钟信号为驱动;电路内部信号的变化 (或输出信号的变化)只发生在特定的时钟边沿;其他时刻 输入信号的变化对电路不产生影响; 要点:执行条件的控制; 时钟边沿的检测; 执行条件的控制 采用进程描述可以有效控制执行条件,若进程以时钟信 号(clk)为唯一敏感信号,则只有当时钟信号变化时,进程 才执行;在其他时刻,任何输入信号的变化对电路(进程) 不起作用; 时钟边沿的检测 为了确保电路状态只在时钟的特定边沿(上升/下降)发 生变化,需要对时钟边沿进行检测; VHDL通常采用属性语句检测时钟边沿; 与时钟有关的属性语句: clk'event boolean clk有变化时为true; clk'last_value clk在变化之前的值; 例:上升沿的检测: clk'event and clk='1' ; clk'event and clk'last_value='0' ; 在由上升沿导致的进程执行时,上述两个表达式的值都 为true;利用这种表达式构成条件语句中的关系判断,就可以 保障电路状态在特定边沿变化; 注意:上述属性语句只能在子结构中应用(作为局部量); 例 p.643 表7-38 D触发器的设计 方式1 library ieee; use ieee.std_logic_1164.all; entity kdff1 is port ( d,clk: in std_logic; q: out std_logic); end kdff1; architecture beh of kdff1 is begin process --进程采用wait语句,只在上升沿执行; begin wait until clk'event and clk='1' ; q<=d; end process; end beh; 方式2 architecture beh of kdff2 is begin process(clk) --进程采用敏感表,在上升/下降沿都执行; begin if clk'event and clk='1' then q<=d; --赋值只在上升沿进行; else null; end if; end process; end beh; 例2 p.643 表7-37 带复位端的D触发器的设计 library ieee; use ieee.std_logic_1164.all; entity kdff2 is port ( d,clk,clr: in std_logic; q,qn: out std_logic); end kdff2; architecture beh of kdff2 is begin process (clk,clr) --进程采用敏感表,执行的结果通过 begin --条件语句控制; if clr='1' then q<='0' ;qn<='1'; --复位信号优先于时钟; elsif clk'event and clk='1' then q<=d; qn<= not d; end if; end process; end beh; 时序电路的基本单元设计 根据触发控制的不同,时序电路的基本单元主要有锁存 器(Latch)和触发器(flip-flop)两类; Latch 锁存器:输出受时钟电平控制,在一段时间内可 受输入变化影响发生而变化;(电平控制) flip-flop触发器:输出只在时钟边沿时刻发生变化,输入 信号变化不能直接导致输出变化;(边沿控制) 目前数字集成电路中采用最多的时序单元器件为D latch 和D flip-flop; 例 p.678 表 8-4 D latch的设计:在满足使能条件时将输入D传递给输出Q; library ieee; use ieee.std_logic_1164.all; entity kdlatch is port ( d,clk: in std_logic; q: out std_logic); end kdlatch; architecture beh of kdlatch is begin process(clk,d) begin if clk='1' then q<=d; end if; end process; end beh; 该电路中,d和clk的任何变化都会导致进程执行;在clk 为1的时间段内,d的变化就会导致q的立即变化; 与D flip-flop的比较:p.679 表8-6 process ( clk ) begin if clk'event and clk='1' then q<=d; end if ; end process ; 如果clk没有变化或不等于1,则d的变化不会导致q的变化; 在p.678—680,还列出了D latch的结构设计、带有异步置 位和复位功能的D flip-flop的设计; Register 寄存器 寄存器通常由多位触发器连接而成,通常可分为锁存寄存 器和移位寄存器两类; 例 p.680 表8-8 16位锁存寄存器设计: 带有时钟使能控制和输出三态控制; library ieee; use ieee.std_logic_1164.all; entity kreg16 is port ( clk,clken,oe,clr: in std_logic; d:in std_logic_vector(1 to 16); q: out std_logic_vector(1 to 16)); end kreg16; architecture beh of kreg16 is signal iq: std_logic_vector(1 to 16); begin process ( clk,clr,oe,iq) begin if clr='1' then iq<=(others=>'0'); elsif clk'event and clk='1' then if clken = '1' then iq<=d; end if; end if ; if oe='1' then q <= iq; else q<=(others=>'Z'); end if; end process ; end beh; 多种功能的寄存器设计比较 library ieee; use ieee.std_logic_1164.all; entity reginf is port(d,clk,clr,pre,load,data: in bit; q1,q2,q3,q4,q5,q6,q7: out bit); end reginf; architecture beh of reginf is begin -- clk为1时寄存d process begin wait until clk='1'; q1<=d; --利用clk上升沿传递信号; end process; -- clk为0时寄存d process begin wait until clk='0'; q2<=d; --利用clk下降沿传递信号; end process; -- 带异步清零,clk上升沿时寄存d process(clk,clr) begin if clr='1' then q3<='0'; elsif clk'event and clk='1' then q3<=d; end if; end process; -- 带异步清零,clk下降沿时寄存d process(clk,clr) begin if clr='1' then q4<='0'; elsif clk'event and clk='0' then q4<=d; end if; end process; --带异步预置高电平功能,clk上升沿时寄存d process(clk,pre) begin if pre='1' then q5<='1'; elsif clk'event and clk='1' then q5<=d; end if; end process; -- 带异步预置数功能,clk上升沿时寄存d process(clk,load,data) begin if load='1' then q6<=data; elsif clk'event and clk='1' then q6<=d; end if; end process; -- 带异步预置高电平和清零功能,clk上升沿时寄存d process(clk,clr,pre) begin if clr='1' then q7<='0'; elsif pre='1' then q7<='1'; elsif clk'event and clk='1' then q7<=d; end if; end process; end beh; 一般时序电路(状态机)的设计 Moore电路:输出完全由电路状态决定; Mealy电路:输出与外部输入直接相关;状态不变时输出可能 变化; Moore电路的设计思想 以状态转换图作为基础;对每一次触发条件,根据当前状态 和输入条件,决定下一状态;同时给出下一状态的输出; 例 简单的Moore状态机设计 设计思想:采用type语句对不同状态进行定义;再将输出与 状态建立对应关系; library ieee; use ieee.std_logic_1164.all; entity statmach is port(clk,input,reset: in std_logic; output: out std_logic); end statmach; architecture beh of statmach is type state_type is (s0,s1); signal st: state_type; begin process(clk) begin if reset='1' then st<=s0; elsif clk'event and clk='1' then case st is when s0=>st<=s1; when s1=> if input='1' then st<=s0; else st<=s1; end if; end case; end if; end process; output<='1' when st=s1 else'0'; end beh; 例 Moore状态机的设计 该状态机有5个状态,转换图如下所示:其中输入控制ID为 4位二进制数,对应为1位16进制数; 设计思路:采用二进制常数定义不同的状态;输出直接与状 态的后2位对应;先确定状态的变化,再将状态的后2位输 出; library ieee; use ieee.std_logic_1164.all; entity moore2 is port(clk,rst: in std_logic; id: in std_logic_vector(3 downto 0); y: out std_logic_vector(1 downto 0)); end moore2; architecture beh of moore2 is signal st: std_logic_vector(2 downto 0); constant s0:std_logic_vector(2 downto 0):="000"; constant s1:std_logic_vector(2 downto 0):="010"; constant s2:std_logic_vector(2 downto 0):="011"; constant s3:std_logic_vector(2 downto 0):="110"; constant s4:std_logic_vector(2 downto 0):="111"; begin process(clk,rst) begin if rst='1' then st<=s0; elsif clk'event and clk='1' then case st is when s0=> if id=x"3" then st<=s1;else st<=s0;end if; when s1=> st<=s2; when s2=> if id=x"7" then st<=s3;else st<=s2;end if; when s3=> if id=x"7" then st<=s0; elsif id=x"9" then st<=s4;else st<=s3; end if; when s4=> if id=x"b" then st<=s0;else st<=s4;end if; when others=>st<=s0; end case; end if; end process; y<=st(1 downto 0); end beh; 课堂作业: 设计一个JK flip-flop,该电路要点为: 名称 jkff 输入端 j k clk clr 输出端 q qn 状态方程: qkqjq n += +1