【发布时间】:2012-08-02 01:16:09
【问题描述】:
如果我有一个包含值2**MAX - 1 的unsigned(MAX downto 0),VHDL (87|93|200X) 标准是否定义了当我将其加一时会发生什么? (或者,类似地,当我从零减一时?)
【问题讨论】:
标签: standards vhdl integer-overflow
如果我有一个包含值2**MAX - 1 的unsigned(MAX downto 0),VHDL (87|93|200X) 标准是否定义了当我将其加一时会发生什么? (或者,类似地,当我从零减一时?)
【问题讨论】:
标签: standards vhdl integer-overflow
简答:
没有溢出处理,溢出进位只是丢失了。因此,结果只是您的操作 模 2^MAX 的整数结果。
更长的答案:
numeric_std 包是标准包,但它不是 VHDL 标准 (87,93,200X) 的核心。
供参考:numeric_std.vhd
+ 操作符最后调用了ADD_UNSIGNED (L, R : unsigned; C : std_logic) 函数(带有C = '0')。请注意,任何整数/自然操作数都首先转换为unsigned。
函数的定义是:
function ADD_UNSIGNED (L, R : unsigned; C : std_logic) return unsigned is
constant L_left : integer := L'length-1;
alias XL : unsigned(L_left downto 0) is L;
alias XR : unsigned(L_left downto 0) is R;
variable RESULT : unsigned(L_left downto 0);
variable CBIT : std_logic := C;
begin
for i in 0 to L_left loop
RESULT(i) := CBIT xor XL(i) xor XR(i);
CBIT := (CBIT and XL(i)) or (CBIT and XR(i)) or (XL(i) and XR(i));
end loop;
return RESULT;
end ADD_UNSIGNED;
如您所见,如果CBIT='1'(进位位)用于i = L_left,则会发生“溢出”。结果位RESULT(i)正常计算,忽略最后一个carry bot值。
【讨论】:
我遇到了希望 unsigned 在 C 或 Verilog 中溢出/下溢的问题,这就是我想出的(result 和 delta 是 unsigned):
result <= unsigned(std_logic_vector(resize(('1' & result) - delta, result'length))); -- proper underflow
result <= unsigned(std_logic_vector(resize(('0' & result) + delta, result'length))); -- proper overflow
对于溢出'0' & result 生成一个unsigned,它大1 位,以便能够正确容纳加法的值。然后通过resize 命令删除MSB,这会产生正确的溢出值。下溢也一样。
【讨论】:
对于等于 7 的 MAX 值,将 1 添加到 2**7 - 1 (127) 将得到值 2**7 (128)。
最大无符号值由无符号数组类型的长度决定:
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity foo is
end entity;
architecture faa of foo is
constant MAX: natural := 7;
signal somename: unsigned (MAX downto 0) := (others => '1');
begin
UNLABELED:
process
begin
report "somename'length = " & integer'image(somename'length);
report "somename maximum value = " &integer'image(to_integer(somename));
wait;
end process;
end architecture;
聚合 (others => '1') 表示 somename 的每个元素中的一个“1”,这是一个无符号数组类型,表示可能的最大二进制值。
这给出了:
foo.vhdl:15:9:@0ms:(报告说明): somename'length = 8
foo.vhdl:16:9:@0ms:(report note): somename 最大值 = 255
长度为8,无符号数组类型可表示的数值范围为0到2**8 - 1(255),最大可能值大于2**7(128)且没有溢出。
在一个较新的问题VHDL modulo 2^32 addition 中注意到了这一点。在您接受的答案的上下文中,它假定您的意思是长度而不是最左边的值。
从零开始递减的结果是 2**8 - 1 (255) (MAX = 7)。下溢或上溢取决于您的数学信仰。
感谢 Jonathan Drolet 在链接的较新问题中指出这一点。
【讨论】: