为什么推断的闩锁不好?


22

我的编译器抱怨组合循环(always @(*)在Verilog中为)中推断出的闩锁。还告诉我,最好避免使用推断出的闩锁。

推断的闩锁到底有什么问题?它们无疑使组合循环更易于编写。


包括您正在做的事的HDL示例将是一件好事
shuckc

我注意到这个问题最近被引用了两次。对于不是这样的专家,请注意,除了Oli Glaser的答案以外,所有答案都是错误和/或无益的某种组合。
EML 2015年

除非应该确切知道自己在做什么,否则应该避免推断的闩锁,而通常应该避免透明的闩锁。万无一失)。
彼得·格林

Answers:


20

“锁存器”与“触发器”的不同之处在于,FF仅响应于时钟沿改变其输出。锁存器可以响应于时钟以外的其他情况来更改其输出。例如,SR锁存器具有一个设置和一个复位输入,如果其中一个处于活动状态,则输出可以更改。SR-FF仅在还存在时钟沿时才响应置位或复位。

在FPGA中,您希望逻辑完全同步。这意味着所有存储元件(如FF)都由单个时钟源提供时钟。与该时钟异步的任何东西都必须非常小心地对待,否则会发生时序错误。

闩锁基本上是异步存储元素。它没有时钟输入,因此无法与任何时钟同步。我应该注意,有带有异步复位和复位输入的FF,对它们的处理应与普通锁存器相同。

深入探讨锁存器可能导致的所有时序问题,远远超出了此处的范围,但是让我举一个例子:

假设您有一个SR锁存器,并且希望每次8位计数器达到某个值时都对其进行设置。我不确定Verilog代码是什么,但是在VHDL中代码是:count = 11010010“时设置<='1',否则为'0';该设置信号进入SR-Latch上的设置输入。

生成的逻辑纯粹是组合的。“与”门,“或”门和逆变器(或LUT)的混合。但是通过该组合逻辑的信号路径并不总是完美的,“设置”信号可能会出现毛刺。通过一组特定门的信号路径所花费的时间可能会长于另一组门,导致设置的输出在输出稳定到最终状态之前的一小段时间内处于活动状态。

此输出故障可能会导致我们的SR锁存器被设置,即使本来不应该这样做。如果我们从SR锁存器切换到SR-FF,并从与计数器相同的时钟开始计时,则SR-FF将等待一个完整的时钟周期,然后再更改状态。本质上,它将在查看设置信号之前等待设置信号建立。

如果通过组合逻辑的设置信号路径只是以不同的方式布线(导致不同的延迟),则毛刺行为也会改变。该逻辑可能工作正常,但是由于您更改了完全不相关的内容,因此该逻辑的路由方式有所不同,因此会弹出错误。温度和电压也会改变信号时序,因此会改变毛刺行为。

时间上不确定,这就是为什么您应该避免逻辑中的闩锁。FF的使用更加安全。这就是为什么编译器会警告您有关锁存器的原因,因为很容易错误地创建锁存器,并且您可能根本不希望它存在。

当然,有时需要锁存器。仅在绝对需要时,您仅需很少使用它们,然后必须正确设计逻辑,以免出现小故障。


我希望,如果有人用Verilog或其他语言明确指定一个锁存器,并且设计一个电路使其能够与馈入该锁存器的组合延迟的任意组合一起正常工作(意味着生成信号的任何组合将用于锁存器将以这样的方式进行操作:即使使用零延迟逻辑路径和最大延迟逻辑路径的最坏情况组合,仍然可以满足锁存器的时序要求),合成器仍应产生一个工作电路锁存器本身具有非负延迟。但是,如果...
超级猫2012年

...使用组合逻辑和反馈而未指定任何必须具有非负延迟的节点,几乎任何事情都可能发生。我知道同步逻辑比异步逻辑更容易设计,但是许多设备在睡眠时需要关闭时钟以节省功耗,而又不会完全死机。拥有一个完全同步的设备,但与每个引脚相关联的几个逻辑输出可能会很有趣,这些逻辑输出用于“如果引脚为高电平则运行”和“如果引脚为低电平则运行”,以及在以下情况下生成时钟的能力:任何需要指示的引脚。
2012年

这种功能将减轻对异步逻辑的大部分需求,因为在设备休眠时到达的输入可以为内部振荡器和电路加电,时间恰好足以处理和确认该输入。这样的功能比具有单个“唤醒”引脚的通用性要强得多,但是单唤醒设计似乎是常态。我所描述的多重唤醒方法会消耗过多的硅吗?与芯片上的所有其他芯片相比,我认为硅的需求将很小。
2012年

13

是什么使推断出的闩锁?
对于组合逻辑,电路的输出仅是输入的函数,并且不应包含任何存储器或内部状态(锁存器)。

在Verilog中,如果在always块中未为其分配值,则变量将保留其先前值。必须创建一个锁存器来存储此当前值。

不完整的if-else语句将生成锁存器。一个的if-else语句被认为是“不完整的”,如果输出状态不适合所有可能的输入条件定义。对于不完整的case语句或没有default: item 的case语句也是如此。

为什么推断的闩锁不好?
推断的锁存器可以充当“警告信号”,表明逻辑设计可能未按预期实现。设计中可能缺少关键的 if-else case语句。

闩锁会导致计时问题和比赛条件。它们可能导致组合反馈-输出路由回输入-这可能是不可预测的。

为了避免创建推断的闩锁:

  • 包含ifcase语句的所有分支
  • 为每个分支中的每个输出信号分配一个值
  • 在过程开始时使用默认分配,因此将分配每个信号。

P. Chu撰写的“通过Verilog实例进行FPGA原型设计”部分解释了某些内容


2
“通过Verilog示例编写FPGA原型”是一本不错的书,可以学习实用的Verilog for Synthesis。从基本的组合到基本的顺序,它都有一些很好的示例设计,最终导致有用的设计,例如UART,VGA,软核处理器(Picoblaze),甚至是Pong游戏。它还涵盖了基本的测试平台和模拟。@Randomblue,如果还没有的话,应该抓取一个副本。我相信他也做了VHDL版本。
奥利·格拉瑟

8

锁存器很难在FPGA或CPLD中使用,因此很多人只是完全避免使用它们。原因之一是许多FPGA没有内置锁存器,因此它们是由逻辑门制成的-这可能会引起讨厌的时序问题。
另外,使用闩锁时,您无法控制时序延迟和竞赛条件(除非存在本机元素)

我建议不要使用锁存器,除非您绝对不能没有它们(例如借用时间来满足所需的最大时钟频率),并使用编码技术来降低意外推断锁存器的可能性。


6

通过使用组合逻辑和反馈构建的顺序逻辑设计通常会做出一个假设,这在使用物理门时似乎是合理的:门的输出不会响应输入的更改而更改,直到输入实际更改之后的某个时间。在某些情况下,使用真实门时可能无法满足该假设(例如,如果快速NOR门和快速反相器均由从VSS缓慢上升到VDD的信号驱动,并且反相器在1.2V电压下切换而NOR直到1.7伏时,门才会切换,或非门可能会在看到缓慢上升的信号变高之前看到反相器的输出变低),但是通常可以通过在每次缓慢变化时添加一个缓冲器来解决此类问题信号被路由到多个目的地。不幸,

问题是,除非另有明确指示,否则FPGA编译器可能会用具有相同稳态行为但时序可能完全不同的完全不同的电路随意替换组合电路。例如,假设一个复杂的组合函数F接受六个输入U到Z。F被直接馈送到电路P,(F NAND Z)被馈送到电路Q。编译器可能意识到馈给Q的值仅取决于当Z为高时,F可以计算出与F相似的函数F',只是假定Z高。然后可以向Q馈送(F'NAND Z)而不是(F NAND Z)。P的最有效实现将完全有可能具有五个门延迟,而Q的最有效实现将只有两个。从而,

如果电路具有组合反馈回路,则FPGA编译器将必须添加物理信号节点,这些物理信号节点在物理上会具有正延迟(在现实世界中不会存在零延迟反馈回路),但无法保证这样的节点将被添加到使电路表现出所需的必要位置。甚至也不能保证对设计的微小更改不会导致编译器从碰巧在现实世界中起作用的任意位置更改为碰巧会失败的其他任意位置。


By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.