在综合过程中,如果我真的想要锁存器,我应该关心 "found latch" 警告吗?
During synthesis, should I care about the "found latch" warnings if I actually want the latches?
假设我有以下状态机:
....
if state_a then
output_a <= '0';
next_state <= state_b;
elsif state_b then
output_a < '0';
if cond then
output_b <= '1';
next_state <= state_a;
else
next_state <= state_b;
end if;
end if;
......
我不希望 output_b 发生变化,除非在 state_b 中再次分配。然而,当我尝试综合这段代码时,大多数综合工具都会说一些类似的话:
warning: found 1-bit latch for signal "output_b". latches aren't
recommended for FPGA design because it might result in timing
problems.
我应该担心这个吗?如果是这样,为什么以及有哪些替代方案?
正在关注 Xilinx:
If latch inference is intended, you can safely ignore this message. However, some inefficient coding styles can lead to accidental latch inference. You should analyse your code to see if this result is intended.
避免闩锁推断的一些技巧:
- 确保任何 "if / else if" 语句都有一个结束 "else" 子句,
- 在每种情况下分配给所有相同的输出,
- 在 case 语句中包含所有可能的情况(但请注意
WHEN OTHERS
子句始终有效,但会产生无关的逻辑)。
如果你有不完整的 if/elsif 或时钟进程中的 case 语句,那绝对是无害的。
if rising_edge(clk)
if a then
out <= b;
end if;
end if;
这意味着你有带某种反馈的触发器,或者像在这种情况下,你有带时钟使能引脚的触发器,这样更好。
如果您在非时钟进程中有不完整的 if/elsif 或 case 语句 - 它是一个闩锁,在大多数情况下是:
- 你并不真正想要的东西;
- 指出设计不佳且可以通过重新设计避免的内容。
如果您完成了您的小示例,有人可以帮助您重新设计它。现在信息不够了。
您遇到的问题源于您(大概)使用的 FSM 编码风格。正如其他人所指出的那样,不可能猜测您想要代码做什么,因为您没有提供足够的代码来解决这个问题,所以我提出了一种可能的解释,假设您真的想以某种方式更改 output_a一次(复位后)output_b 的锁存应该在 FSM 状态转换的同时发生。
每个 FSM 样式使用 2 个进程,我们的代码没有给出闩锁警告:
----
signal CLK, RESET, cond : std_logic;
type state_t is (a,b);
signal state, state_next : state_t;
signal ouput_a, output_b, output_b_next : std_logic;
----
FSM_clock: process(all)
begin
if rising_edge(CLK) then
if RESET then
state <= a;
output_b <= '0';
else
state <= state_next;
output_b <= output_b_next;
end if;
end if;
end process;
FSM_next: process(all)
begin
state_next <= state;
output_b_next <= output_b;
output_a <= '0';
case state is
when a =>
state_next <= b;
when b =>
output_a <= '1';
if cond then
output_b_next <= '1';
state_next <= a;
else
state_next <= b;
end if;
end case;
end process;
假设我有以下状态机:
....
if state_a then
output_a <= '0';
next_state <= state_b;
elsif state_b then
output_a < '0';
if cond then
output_b <= '1';
next_state <= state_a;
else
next_state <= state_b;
end if;
end if;
......
我不希望 output_b 发生变化,除非在 state_b 中再次分配。然而,当我尝试综合这段代码时,大多数综合工具都会说一些类似的话:
warning: found 1-bit latch for signal "output_b". latches aren't recommended for FPGA design because it might result in timing problems.
我应该担心这个吗?如果是这样,为什么以及有哪些替代方案?
正在关注 Xilinx:
If latch inference is intended, you can safely ignore this message. However, some inefficient coding styles can lead to accidental latch inference. You should analyse your code to see if this result is intended.
避免闩锁推断的一些技巧:
- 确保任何 "if / else if" 语句都有一个结束 "else" 子句,
- 在每种情况下分配给所有相同的输出,
- 在 case 语句中包含所有可能的情况(但请注意
WHEN OTHERS
子句始终有效,但会产生无关的逻辑)。
如果你有不完整的 if/elsif 或时钟进程中的 case 语句,那绝对是无害的。
if rising_edge(clk)
if a then
out <= b;
end if;
end if;
这意味着你有带某种反馈的触发器,或者像在这种情况下,你有带时钟使能引脚的触发器,这样更好。
如果您在非时钟进程中有不完整的 if/elsif 或 case 语句 - 它是一个闩锁,在大多数情况下是:
- 你并不真正想要的东西;
- 指出设计不佳且可以通过重新设计避免的内容。
如果您完成了您的小示例,有人可以帮助您重新设计它。现在信息不够了。
您遇到的问题源于您(大概)使用的 FSM 编码风格。正如其他人所指出的那样,不可能猜测您想要代码做什么,因为您没有提供足够的代码来解决这个问题,所以我提出了一种可能的解释,假设您真的想以某种方式更改 output_a一次(复位后)output_b 的锁存应该在 FSM 状态转换的同时发生。
每个 FSM 样式使用 2 个进程,我们的代码没有给出闩锁警告:
----
signal CLK, RESET, cond : std_logic;
type state_t is (a,b);
signal state, state_next : state_t;
signal ouput_a, output_b, output_b_next : std_logic;
----
FSM_clock: process(all)
begin
if rising_edge(CLK) then
if RESET then
state <= a;
output_b <= '0';
else
state <= state_next;
output_b <= output_b_next;
end if;
end if;
end process;
FSM_next: process(all)
begin
state_next <= state;
output_b_next <= output_b;
output_a <= '0';
case state is
when a =>
state_next <= b;
when b =>
output_a <= '1';
if cond then
output_b_next <= '1';
state_next <= a;
else
state_next <= b;
end if;
end case;
end process;