gpt4 book ai didi

vhdl - 从同一语句分配两个信号

转载 作者:行者123 更新时间:2023-12-04 02:24:28 25 4
gpt4 key购买 nike

我是 VHDL 的新手,我正在尝试实现一个在 ABEL 中看起来像的真值表:

Truth-table
([C2.FB, C1.FB, C0.FB, DISABLE] -> [A, B])
[ X , X , X , 1 ] -> [0, 0];
[ 0 , 0 , 0 , 0 ] -> [0, 3];
[ 0 , 0 , 1 , 0 ] -> [3, 5];
[ 0 , 1 , 0 , 0 ] -> [5, 6];
[ 0 , 1 , 1 , 0 ] -> [6, 7];
[ 1 , 0 , 0 , 0 ] -> [7, 6];
[ 1 , 0 , 1 , 0 ] -> [6, 5];
[ 1 , 1 , 0 , 0 ] -> [5, 3];
[ 1 , 1 , 1 , 0 ] -> [3, 0];

据我所知,VHDL 中没有对真值表的真正支持,但也许“with select 语句”已经很接近了?

with C select
A <= std_logic_vector(to_unsigned(0, A'length)) when "000",
std_logic_vector(to_unsigned(3, A'length)) when "001",
std_logic_vector(to_unsigned(5, A'length)) when "010",
std_logic_vector(to_unsigned(6, A'length)) when "011",
...

是否可以在同一条语句中同时对 A 和 B 进行赋值?例如:

A,B  <= 0,3 when "000",
3,5 when "001",
...

还是我必须做几条陈述(对于长表来说很烦人)?我该如何处理 DISABLE 信号?有没有更好更聪明的方法来做到这一点?

感谢您的帮助!

最佳答案

如果有预定义的 VHDL 机制,为什么要使用真值表...?

B <= "000" when (disable = '1') else A;
C <= "000" when (disable = '1') else not A;

或者如果需要作为整数结果

B <= 0 when (disable = '1') else to_integer(unsigned(A));
C <= 0 when (disable = '1') else to_integer(unsigned(not A));

改进 1:

你可以这样写一个函数 mux(...) 或称它为 ite(...)(if-then-else 的缩写):

function ite(condition : boolean; a : std_logic_vector; b : std_logic_vector) return std_logic_vector is
begin
if (cond = true) then
return a;
else
return b;
end if;
end function;

现在你可以把上面的语句写得更短一些:

B <= ite((disable = '1'), "000", A);
C <= ite((disable = '1'), "000", not A);

改进 2:

用基本的 bool 运算计算结果。您可以将禁用信号放大到与 A 宽度一样多的位,然后使用合取运算符。 (这也称为“A is gated by disable”或门电路)。

B <= (A'range => disable) and A;
C <= (A'range => disable) and not A;

我的示例现在使用类型转换(您的示例将 std_logic_vector 作为输入和输出)。如果需要,请随意添加转换函数,如 unsigned(..) 或 to_integer(..)。


真值表/ROM

如果你真的想实现真值表,我建议使用 ROM。所以定义一个常量,其内容由 es 函数(预)计算。然后将您的输入用作 ROM 地址,并将选定的输出用作结果。

这里是一个使用整数作为结果的例子

subtype t_uint3 : integer range 0 to 7;
type t_uint3_vector is array (natural range <>) of t_uint3;
constant B_TRUTH_TABLE : t_uint3_vector(7 downto 0) := (0, 1, 2, 3, 4, 5, 6, 7);
constant C_TRUTH_TABLE : t_uint3_vector(7 downto 0) := (7, 6, 5, 4, 3, 2, 1, 0);

B <= B_TRUTH_TABLE(to_integer(unsigned(A)));
C <= C_TRUTH_TABLE(to_integer(unsigned(A)));

此示例现在具有禁用功能。要添加它,请将 ROM 与上述语句之一结合使用。


使用函数进行预计算:将元素列表 (0, 1, ..., 7) 替换为如下函数:

function precalc_B_ROM return t_uint3_vector is
variable result : t_uint3_vector(7 downto 0);
begin
for i in result'range loop
result(i) := i;
end loop;
return result;
end function;

function precalc_C_ROM return t_uint3_vector is
variable result : t_uint3_vector(7 downto 0);
begin
for i in result'range loop
result(i) := result'high - i; -- reverse numbers
end loop;
return result;
end function;

constant B_TRUTH_TABLE : t_uint3_vector(7 downto 0) := precalc_B_ROM;
constant C_TRUTH_TABLE : t_uint3_vector(7 downto 0) := precalc_C_ROM;

编辑1

计算多个结果的组合过程。

process(inA, inB, ...)
begin
-- default assignments
outX <= '0';
outY <= '0';
outZ <= '0';

case (inA & inB) is
when "00" =>
outY <= '1';
outZ <= '1';
when "01" =>
outX <= '1';
outY <= '1';
[...]
when others =>
outZ <= '1';
end case;
end process;

(默认赋值减少了 when 语句和时钟进程中的代码行,阻碍了生成锁存器的综合。)

因此,如果您返回一条记录并将结果拆分为子结果,或者如果您使用具有多个分配的案例,那么这是一个编码问题。

附录提供的 ROM 也可以返回一条记录。 => 1) 定义您的结果记录; 2)将这条记录打包成一个新的数组/向量类型; 3)定义一个新类型的ROM; 4) 通过地址访问ROMs条目->结果就是你请求的记录。

关于vhdl - 从同一语句分配两个信号,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24207176/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com