6

假设我需要一个信号来表示从 0 到 5 的数字;显然,这需要 3 位 std_logic 来表示(即如果 MAXVAL=5,则 bitwidth= { wcalc "floor(logtwo($MAXVAL))+1"})。

我知道我可以这样做:

SIGNAL myLogicVector : STD_LOGIC_VECTOR(2 downto 0) := 5; 

我将使用它明确指定三个 std_logic '位'的数组,并设置初始值;然后我可以使用 REPORT 打印出长度(在本例中为 3):

report("Bit width of myLogicVector is "& integer'image(myLogicVector'length));

到现在为止还挺好。但是,假设我使用整数(数字)类型:

SIGNAL myInteger : NATURAL range 0 to 5 := 5;

我猜这里的“编译器”(“合成器”)会自动推断它需要 3 位的存储长度,因为这个整数的值在 0 到 5 之间。如果是这样,我的问题是:是有可能以某种方式在报告中打印出这个位宽/长度/大小吗?

当然,诀窍是这样的:

report("Bit width of myInteger is "& integer'image(myInteger'length));

...将失败(例如,使用“ HDLParsers:3389 - 属性的前缀长度必须是一个数组对象”),因为据我所知,所有这些属性都像'length并且'range仅适用于数组了解 VHDL 属性),而整数(自然)不是数组-它是一个数字:) (VHDL向量整数转换问题

同样,我知道我可以使用 log2(从最大值计算无符号变量的宽度?) - 但我想快速查看(在合成期间)“合成器”有多少“位”分配给最终的综合设计,因此大约将使用多少最终 FPGA 资源(特别是如果我使用“泛型”以某种方式计算整数的特定最大值)。

好吧,提前感谢您的任何回复,干杯!

编辑:一些上下文:我使用的是 ISE Webpack 9.2;我正在尝试使用“通用”变量/常量作为参数,然后使用方程式计算计数器的最大值。我猜这个计算发生在“编译”时间(这将是 ISE 中的“合成” - 而不是“实施设计”),所以我希望报告消息出现在这里(事实上我得到了它们,对于 std_logic_vector 正确的,在综合日志中 - 但是,对于我来说,相同的报告消息也发生在行为模拟开始时,这很好)。

这些报告消息的目标是确保我的方程式都正常,并且合成器不会尝试推断 32 位计数器 - 即使我只想从 0 计数到 5 :)

4

5 回答 5

6

原则上,VHDL 整数的表示是未定义的。

在实践中,您通常可以假设综合工具将使用 2 的补码表示,同时考虑范围约束。因此,范围约束和实现的位宽之间的关系是直截了当的,即使从 VHDL 中报告位宽不是。

于 2011-03-05T12:17:11.497 回答
2

我猜这里的“编译器”(“合成器”)会自动推断它需要 3 位的存储长度,因为这个整数的值在 0 到 5 之间

根据规范,它应该,但不是必需的。来自 IEEE 1076.6-2004:

1.3 术语

“应”一词表示为符合标准而必须严格遵守的强制性要求,不允许偏离(必须等于)。应该使用这个词 来表示某种行动是首选的,但不一定是必需的;

8.3.1.2 整数类型

建议综合工具应将具有整数子类型指示的信号或变量转换为相应的位向量。如果范围不包含负值,则该项目应具有无符号二进制表示。如果范围包含一个或多个负值,则该项目应具有二进制补码实现。向量应具有与这些表示一致的最小宽度。

综合工具应支持整数类型以及正、负和无约束(通用)整数,其边界在 –2 147 483 648 到 +2 147 483 647 范围内(成功映射 32 位二进制补码数字的范围)

示例: “INTEGER 范围 9 到 10”应使用 4 位的等效向量长度合成,就像它已使用“INTEGER 范围 0 到 15”的子类型指示定义一样。

我可以肯定地说,至少有一个综合工具不会这种方式使用范围,因为我必须调试形式验证错误比较。

对于赛灵思 FPGA,XST 综合报告将告诉哪些存储元件有未使用的位,但不是简单的连线。

于 2011-03-04T16:26:34.990 回答
-1

是否有可能在报告中以某种方式打印出这个位宽/长度/大小?

基础数学:

位宽 = ceil(log2(my_integer + 1))

但是VHDL需要更多的努力......

内联代码:

use ieee.math_real.all;
...
report "Bit width of myInteger is " & integer'image(integer(ceil(log2(real(myInteger) + real(1)))));

作为一个函数:

use ieee.math_real.all;
...
-- Returns the bit width of i as a positive integer.
function BitWidth(constant i: in positive) return positive is
begin
    return positive(ceil(log2(real(i) + real(1))));  -- Add one to prevent errors when i = 2**n
end function;

-- Overload for returning the string representation of the bit width of i.
function BitWidth(constant i: in positive) return string is
    variable bit_width: positive := BitWidth(i);
begin
    return positive'image(bit_width);
end function;

signal myInteger: positive := 8;
...
report "Bit width of myInteger is " & BitWidth(myInteger);

您可以将这些函数放在一个辅助函数包中。

于 2020-12-15T14:20:51.513 回答
-2

这可以解决如下:

首先,声明一个新的(子)类型,表示应该用于的范围myInteger。(然后声明myInteger为这种类型的信号,而不是直接的整数范围)。

然后,使用声明的范围作为索引范围声明一个虚拟数组类型,然后'length使用that

subtype myInteger_range is natural range 0 to 5;
signal myInteger : myInteger_range;
type myInteger_dummy_array is array (myInteger_range) of boolean; -- or whatever
report integer'image(myInteger_dummy_array'length); --> "6"
于 2016-09-16T21:19:56.380 回答
-3

你总是可以使用:

report("myInteger 的位宽是 "& integer'image(myInteger'left - myInteger'Right));

于 2015-03-19T19:42:17.530 回答