上升沿(rising_edge)在时钟(clk)中不可综合化。

3

我正在学习并使用VHDL编程Lattice FPGA,以模拟74HCT245的功能。以下是我的代码。

我一直收到"语句不可综合,因为在NOT(时钟边缘)条件下它不保持其值。VHDL-1242" 错误提示。

 entity HCT541 is
  port (Clk       : in    std_logic;
        A         : inout std_logic_vector(15 downto 0) := "1011101010111010";
        BA        : out   std_logic_vector(15 downto 0);
        n_OE, DIR : in    std_logic;
        M_D       : inout std_logic_vector(15 downto 0) := "0000000000000001";
        D         : inout std_logic_vector(15 downto 0) := "1011101010111010";
        BD        : inout std_logic_vector(15 downto 0) := "1011101010111010");
end HCT541;

architecture df of HCT541 is
  signal n_OE_1, n_OE_2 : std_logic := '0';
begin

  process(Clk, n_OE, DIR)
  begin

    if ((BD = "ZZZZZZZZZZZZZZZZ" or D = "ZZZZZZZZZZZZZZZZ") and n_OE = '0') then
      BD <= "0000000000000000";
      D  <= M_D;
    end if;

    M_D <= M_D + '1';

    CLK1 : if(rising_edge(Clk)) then

      if(n_OE_1 = '0' and n_OE_2 = '0') then
        A  <= A - '1';
        BA <= A;
      else
        BA <= "ZZZZZZZZZZZZZZZZ";
      end if;

      if (n_OE = '0' and DIR = '1') then
        D  <= M_D;
        BD <= D;
      elsif (n_OE = '0' and DIR = '0') then
        BD <= BD - '1';
        D  <= BD;
      elsif (n_OE = '1') then
        BD <= "ZZZZZZZZZZZZZZZZ";
        D  <= "ZZZZZZZZZZZZZZZZ";
      end if;

    end if CLK1;

  end process;

end df;

有什么想法吗?

使用rising_edge有什么问题吗?


1
准则:始终将三态逻辑与任何触发器逻辑分开编码。 - Jim Lewis
rising_edge(clk) 是没问题的。问题在于 if rising_edge(clk) 之前的部分。 - user1818839
2个回答

3
一些指导原则:
  1. 先画出所需硬件的图像,然后编写代码。
  2. 硬件只能检查1和0,所以Z的检查存在问题。
  3. 只在组合过程中驱动三态门。否则会有很多意外和错误。
  4. 许多FPGA没有内部三态门,因此仅支持主输出。

解释@Jonathan Drolet关于“混合组合过程和同步过程”的评论。从输出角度考虑。

理想情况下,您的同步过程应该是这种形式:

SyncProc : process (Clk) is
begin
  -- do not do logic here
  if rising_edge(Clk) then
   -- do synch stuff.  
   -- logic is ok in here
  end if ; 
  -- do not do logic here
end process SyncProc ; 

你的组合过程最理想的形式应该是:

CombProc : process (sig1, sig2, ...) is
begin
  -- do logic stuff here
  -- do not do clocks here
end process CombProc ; 

一些工具可以让你做更多的事情。

2
由于您发布的格式很难阅读,我无法确定具体情况。看起来您在 rising_edge(clk) 语句中以及它之外都指定了 BD,这是不可能的。BD 要么是一个寄存器,要么不是。
不要将组合进程与同步进程混合使用。虽然从 VHDL 规范上来说没有问题,但容易出现像您遇到的错误。基本上,一个对 clk 敏感的进程不应该对任何其他信号敏感,除非是异步复位信号。
将您的进程分为两个部分:一个对 n_OE 和 DIR 敏感,另一个对 CLK 敏感。您会发现您在两个进程中都指定了 BD,这在综合中通常是错误的,可能会导致一个信号有多个驱动器。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接