VHDL 进程中的多个非嵌套 if 语句是一种不好的做法吗?
Are multiple non-nested if statements inside a VHDL process a bad practice?
我使用 VHDL 几个月,有时我会使用 非嵌套 if 语句来构建这种过程,当我希望按顺序评估某些条件时:
process(clk)
begin
if rising_edge(clk) then
if CONDITION1 then
(some instructions)
end if;
if CONDITION2 then
(some instructions)
end if;
end if;
end process;
好像在仿真和综合上都很好,但是网上找例子的时候几乎没见过这种结构。
我对这些语句的顺序执行表示怀疑,但 IEEE 标准 VHDL 语言参考手册 Std 1076-2008 指出:
Sequential statements are used to define algorithms for the execution
of a subprogram or process; they execute in the order in which they
appear.
并且 if
语句在顺序语句列表中。
为什么我找不到更多这样的例子?这是一种不好的做法吗?
是的,这是合法的,而且是的,赋值是顺序的。请记住,信号赋值是给它们的最后一个值,所以最后的 if
"wins"。所以下面两段代码在功能上是一样的。
process(clk)
begin
if rising_edge(clk) then
if cond1 then
--do something
end if;
if cond2 then
-- do something else
end if;
end if;
end process;
-- same as this:
process(clk)
begin
if rising_edge(clk) then
if cond2 then
-- do soemthing else
elsif cond1 then
-- do something
end if;
end if;
end process;
这有实际用途。传统流程模板已重置为 if..else
设置:
-- sync process
if srst then
a <= '0';
b <= '0';
else
--do something with a and b
end if;
这很好,但是您强迫 a
和 b
总是先有一个 link。如果您忘记将 b
放在 srst 分支中,您会将 srst 连接到 b 的使能引脚,因为您在代码中说当 srst 处于活动状态时无法锁存 b 寄存器。这会强制您将所有寄存器放在您可能不想要的重置分支中。因此,要在不创建使能 link 的情况下允许同一进程中的复位和非复位信号,您可以使用双 if:
--sync process
--do some logic with A and B here
if srst then -- reset wins
a <= '0';
-- B has no link to reset
end if;
这不是您在 Internet 上常见的样式(可能是因为旧教程总是教授 if..else
样式)。但是,使用 "traditional" 方法在开发代码中发现 srst 和启用引脚之间的意外时序 links 是很常见的。
我使用 VHDL 几个月,有时我会使用 非嵌套 if 语句来构建这种过程,当我希望按顺序评估某些条件时:
process(clk)
begin
if rising_edge(clk) then
if CONDITION1 then
(some instructions)
end if;
if CONDITION2 then
(some instructions)
end if;
end if;
end process;
好像在仿真和综合上都很好,但是网上找例子的时候几乎没见过这种结构。 我对这些语句的顺序执行表示怀疑,但 IEEE 标准 VHDL 语言参考手册 Std 1076-2008 指出:
Sequential statements are used to define algorithms for the execution of a subprogram or process; they execute in the order in which they appear.
并且 if
语句在顺序语句列表中。
为什么我找不到更多这样的例子?这是一种不好的做法吗?
是的,这是合法的,而且是的,赋值是顺序的。请记住,信号赋值是给它们的最后一个值,所以最后的 if
"wins"。所以下面两段代码在功能上是一样的。
process(clk)
begin
if rising_edge(clk) then
if cond1 then
--do something
end if;
if cond2 then
-- do something else
end if;
end if;
end process;
-- same as this:
process(clk)
begin
if rising_edge(clk) then
if cond2 then
-- do soemthing else
elsif cond1 then
-- do something
end if;
end if;
end process;
这有实际用途。传统流程模板已重置为 if..else
设置:
-- sync process
if srst then
a <= '0';
b <= '0';
else
--do something with a and b
end if;
这很好,但是您强迫 a
和 b
总是先有一个 link。如果您忘记将 b
放在 srst 分支中,您会将 srst 连接到 b 的使能引脚,因为您在代码中说当 srst 处于活动状态时无法锁存 b 寄存器。这会强制您将所有寄存器放在您可能不想要的重置分支中。因此,要在不创建使能 link 的情况下允许同一进程中的复位和非复位信号,您可以使用双 if:
--sync process
--do some logic with A and B here
if srst then -- reset wins
a <= '0';
-- B has no link to reset
end if;
这不是您在 Internet 上常见的样式(可能是因为旧教程总是教授 if..else
样式)。但是,使用 "traditional" 方法在开发代码中发现 srst 和启用引脚之间的意外时序 links 是很常见的。