如果我从敏感列表中删除 NS,会有什么不同吗?

Is there any difference if I remove NS from sensitivity list?

我正在阅读 Free Range VHDL 这本书,这里是第 8 章的示例。

-- library declaration
library IEEE;
use IEEE.std_logic_1164.all;
-- entity
entity my_fsm1 is
    port (  TOG_EN  : in  std_logic;
            CLK,CLR : in  std_logic;
                 Z1 : out std_logic);
end my_fsm1;
-- architecture
architecture fsm1 of my_fsm1 is
   type state_type is (ST0,ST1);
   signal PS,NS : state_type;
begin
   sync_proc: process(CLK,NS,CLR)
   begin
     -- take care of the asynchronous input
     if (CLR = '1') then
        PS <= ST0;
     elsif (rising_edge(CLK)) then
        PS <= NS;
     end if;
   end process sync_proc;

   comb_proc: process(PS,TOG_EN)
   begin
      Z1 <= '0';        -- pre-assign output
      case PS is
         when ST0 =>    -- items regarding state ST0
            Z1 <= '0';  -- Moore output
            if (TOG_EN = '1') then NS <= ST1;
            else  NS <= ST0;
            end if;
         when ST1 =>    -- items regarding state ST1
            Z1 <= '1';  -- Moore output
            if (TOG_EN = '1') then NS <= ST0;
            else  NS <= ST1;
            end if;
         when others => -- the catch-all condition
            Z1 <= '0';  -- arbitrary; it should never
            NS <= ST0;  -- make it to these two statements
      end case;
   end process comb_proc;
end fsm1;

如果我从 sync_proc 的敏感列表中删除 NS 有什么不同吗?

sync_proc: process(CLK,NS,CLR)
begin
-- take care of the asynchronous input
  if (CLR = '1') then
    PS <= ST0;
  elsif (rising_edge(CLK)) then
    PS <= NS;
  end if;
end process sync_proc;

在检查了这个问题之后,这被认为是重复的,而且它的答案缺乏关于信号何时属于灵敏度列表的任何权威参考,可能值得一问该信息来自何处?

您可能会注意到 Free Range VHDL 仅提及 wait 作为 VHDL 中的保留字。远不止于此。 VHDL标准(IEEE Std 1076-2008 10.3 Process statement)中描述的一个过程语句告诉我们:

If a process sensitivity list appears following the reserved word process, then the process statement is assumed to contain an implicit wait statement as the last statement of the process statement part; this implicit wait statement is of the form

wait on sensitivity_list ;

然后继续讨论10.2 Wait语句的规则如何应用于由保留字all.

组成的敏感列表

syn_proc from architecture fsm1 of entity my_fsm1 from Free Range VHDL 清单 7.1 示例 18 的解决方案具有符合规则的敏感度列表在 10.2 Wait 语句中找到隐式生成的敏感度。

但是,这并不是完整的权限集。还有 IEEE Std 1076.6-2004(RTL Synthesis,现已撤回)6.1.3.1 Edge-sensitive storage from a process with sensitivity list and one clock:

d) The process sensitivity list includes the clock and any signal controlling an <async_assignment>.

其中 在 6.13 建模边缘敏感存储元素中定义:

<async_assignment>. An assignment to a signal or variable that is not controlled by <clock_edge> in any execution path.

并且 由约定 (1.4) 定义为在 6.1.2 时钟边沿规范中找到的 BNF 中定义的 clock_edge 的一种形式。

(翻译:d)以上意思就是你读到的意思。)

这告诉我们这里需要什么信号。对过程敏感列表中不需要的信号没有任何限制。然而,它们的效果可以从 IEEE Std 1076-2008 10.2 Wait 语句中看出:

The suspended process also resumes as a result of an event occurring on any signal in the sensitivity set of the wait statement. If such an event occurs, the condition in the condition clause is evaluated. If the value of the condition is FALSE, the process suspends again. Such repeated suspension does not involve the recalculation of the timeout interval.

等待语句:

wait_statement ::=
    [ label : ] wait [ sensitivity_clause ] [ condition_clause ] [ timeout_clause ] ;

如果您知道条件子句是可选的,如上方括号所示,它会有所帮助:

The condition clause specifies a condition that shall be met for the process to continue execution. If no condition clause appears, the condition clause until TRUE is assumed.

这意味着进程将针对进程敏感列表中任何信号上的任何事件恢复,并将遍历它的顺序语句。

通过对信号 NS 上的事件执行 sync_proc,在仿真期间不会对设计层次结构的状态造成损害。受制于条件的 if 语句中的赋值语句都不会执行。您还可以注意到,这同样适用于 CLK 下降沿上的事件。

配对敏感列表中的objective是为了尽量减少进程不必要的恢复次数。设计模型越大越复杂,仿真进行的速度就越慢,尤其是拖延不必要的恢复和暂停。

在过程灵敏度列表中显示的三个信号中,只有三个 二进制值 转换是感兴趣的,并且 none 信号 NS。 NS的当前值在CLK的上升沿赋值给PS。

进程在特定的等待语句中挂起和恢复。具有敏感列表的进程不应包含显式等待语句 (10.3),这意味着它将只有一个等待语句,即隐式等待语句。

你的第一个关于 VHDL 的问题似乎超出了本书 Free Range VHDL 可以提供的答案的限制。

彼得·阿申登 (Peter Ashenden) The Designer's Guide to VHDL, 3rd edition 关于这个主题的更好的恳求。

这里传达的意思是,不知道怎么做就不知道为什么。

我们总是在灵敏度列表中使用带有时钟和复位的过程块来描述序列circuit.And在灵敏度列表中使用带有每个驱动器信号的过程块来描述组合电路。

有时灵敏度列表只对仿真很重要,但如果您忘记了一个信号或在灵敏度列表中添加了太多信号,您可能会得到错误的仿真结果。大多数情况下,如果您的逻辑正确,真正的 FPGA 功能将正常工作。

但它可能会导致一些问题。

例如,如果您在带有敏感度 (b) 的 always 块中描述像 a=b&c 这样的函数;但是你忘了c。那么在你的模拟中,当 c 改变时 a 不会改变。但是在真正的FPGA中的电路,将是函数a=b&c的正确描述。并且你在合成代码时可能会收到警告。

你可以称之为‘pre-sim 和 post-sim 不一致’。

真正可怕的是你的 pre-sim 是正确的,但你的 post-sim 是错误的。这可能会导致 FPGA 功能不正确。

所以我建议你在写VHDL代码的时候,先描述电路,而不是描述功能。