什么';在vhdl中转换固定到标准逻辑向量的正确方法是什么?

什么';在vhdl中转换固定到标准逻辑向量的正确方法是什么?,vhdl,Vhdl,我试图将一个sfixed(从ieee.fixed_pkg)转换为std_logic_vector,我想知道正确的语法是什么,为什么下面的内容(显然是错误的)。我尝试编译以下3种体系结构: library ieee; use ieee.std_logic_1164.all; use ieee.fixed_pkg.all; entity test is port (input: in sfixed(0 downto -7) := x"00"; output: out

我试图将一个sfixed(从ieee.fixed_pkg)转换为std_logic_vector,我想知道正确的语法是什么,为什么下面的内容(显然是错误的)。我尝试编译以下3种体系结构:

library ieee;
    use ieee.std_logic_1164.all;
    use ieee.fixed_pkg.all;

entity test is
    port (input: in sfixed(0 downto -7) := x"00";
    output: out std_logic_vector(7 downto 0) := x"00");
end;    
架构a:

architecture a of test is begin 
    output <= std_logic_vector(input);
end;
但是架构c编译,同时仍然给我警告信息:

Warning: [...] Index value -7 (of type std.STANDARD.NATURAL) is out of range 0 to 2147483647.

所以我的问题是:什么是正确的方式来转换它,为什么上面发布的三种体系结构之间有任何区别?

有趣的是,这实际上可能是VHDL语言本身规范中的一个灰色区域。同样有问题的转换也针对开源模拟器

问题的实质是,
输入
被声明为
sfixed(0到-7)
,而
标准逻辑向量
的定义要求其索引为
自然
,即正整数或0

因此,将类型转换为无约束的标准逻辑向量

output <= std_logic_vector(input);
我不能保证Altera会接受同样的解决方案,但我有理由相信它会接受,它更明显地是有效的VHDL。我还没有尝试将
output
声明为您需要的端口

据我们所知,根据VHDL语言参考手册(LRM)的信函,ghdl(通常对VHDL的解释是严格的)拒绝这种结构是正确的,因此“错误”报告已经关闭


但是,,已经向VHDL标准委员会寻求进一步的澄清,如果可以证明它完全可以防止困扰某些其他语言的数组边界错误和缓冲区溢出,则可能会在将来放宽该规则。

类型强制转换具有负索引的sfixed所导致的范围问题@BrianDrmmond讨论的std_逻辑_向量是标准制定过程中发现的一个问题。对于GHDL以外的模拟器来说,这也是一个真正的问题

因此,包提供了类型转换函数来处理这个问题。要将sfixed或ufixed转换为标准逻辑向量,请使用To slv和To std逻辑向量:

  output <= to_slv(input);

output固定包转换函数不是OP报告错误的解决方案,请参阅下面的函数转换为标准逻辑向量。请注意,“result”是一个std_ulogic_向量,通过执行操作数“arg”的类型转换来获得,与OP完全相同(OP使用的std_logic_向量除外)。定点软件包将产生与OP报告的错误相同的错误

  -- Conversion functions.  These are needed for synthesis where typically
  -- the only input and output type is a std_logic_vector.
  function to_sulv (
    arg : UNRESOLVED_ufixed)            -- fixed point vector
    return STD_ULOGIC_VECTOR is
    variable result : STD_ULOGIC_VECTOR (arg'length-1 downto 0);
  begin
    if arg'length < 1 then
      return NSLV;
    end if;
    result := STD_ULOGIC_VECTOR (arg);
    return result;
  end function to_sulv;
——转换函数。通常情况下,合成需要这些
--唯一的输入和输出类型是标准逻辑向量。
函数到sulv(
arg:未解决的_ufixed)--不动点向量
返回标准逻辑向量为
可变结果:标准逻辑向量(arg'length-1向下至0);
开始
如果arg'长度小于1,则
返回NSLV;
如果结束;
结果:=标准逻辑向量(arg);
返回结果;
终端功能至_sulv;

KJ

我发现这篇文章在使用David Bishop的fixed_pkg_c(github上的FPHDL)的GHDL 0.35(mcode,windows)中也面临同样的错误

注意,虽然这里的答案看起来是正确的;我必须在fixed_pkg_c中添加以下内容,以便让GHDL编译和模拟:

function to_sulv (
  arg : UNRESOLVED_sfixed)            -- fixed point vector
  return STD_ULOGIC_VECTOR is
  variable result : STD_ULOGIC_VECTOR (arg'length-1 downto 0);

  -- This was added
  subtype result_type is STD_ULOGIC_VECTOR (arg'length-1 downto 0);
  begin
  if arg'length < 1 then
    return NSLV;
  end if;
  --  originally: result := STD_ULOGIC_VECTOR (arg)
  result := result_type (arg);
  return result;
end function to_sulv;
功能到sulv(
arg:未解析的_sfixed)--不动点向量
返回标准逻辑向量为
可变结果:标准逻辑向量(arg'length-1向下至0);
--这是增加的
子类型结果类型为标准逻辑向量(arg'length-1至0);
开始
如果arg'长度小于1,则
返回NSLV;
如果结束;
--最初:结果:=标准逻辑向量(arg)
结果:=结果类型(arg);
返回结果;
终端功能至_sulv;
对于ufixed类型,to_sulv函数也需要进行相同的更改

我不知道为什么以前使用STD_ULOGIC_VECTOR的“类型转换”不起作用,我也没有花更多的时间考虑这个问题


如果其他人发现了这一点,请更新原始fixed_pkg_c文件是否在其原始实现中工作。

对受约束向量使用子类型,然后强制转换到该子类型确实有效。谢谢你的回答!我很高兴(c)愚弄了你的编译器,把一个“错误”变成了一个“警告”!啊!!所以问题很简单,就是定点软件包自己的解决方案没有得到足够的宣传!我同意这是一个比解决方法更好的答案。您的函数,上面的to_sulv,是固定点包中to_sulv的精确副本。更进一步,定点包中的to_slv调用了_sulv。为什么您认为在定点包中使用slv会产生相同的错误?在我的测试中没有。
-- declarations
subtype result_type is std_logic_vector (input'length-1 downto 0);
signal output : result_type;

-- assignment
output <= result_type (arg);
  output <= to_slv(input);
  signal a_sfixed : sfixed(0 downto -7) := x"00";
  signal a_slv    : std_logic_vector(7 downto 0) := x"00";

  a_sfixed <= to_sfixed(a_slv, 0, -7);
  . . . 
  a_sfixed <= to_sfixed(a_slv, a_sfixed);
  signal a_sfixed : sfixed(0 downto -7) := x"00";
  signal a_slv    : std_logic_vector(7 downto 0) := x"00";
  signal y_sfixed : sfixed(1 downto -7) := x"00";

  y_sfixed <= a_sfixed + to_sfixed(a_slv, 0, -7);
  -- Conversion functions.  These are needed for synthesis where typically
  -- the only input and output type is a std_logic_vector.
  function to_sulv (
    arg : UNRESOLVED_ufixed)            -- fixed point vector
    return STD_ULOGIC_VECTOR is
    variable result : STD_ULOGIC_VECTOR (arg'length-1 downto 0);
  begin
    if arg'length < 1 then
      return NSLV;
    end if;
    result := STD_ULOGIC_VECTOR (arg);
    return result;
  end function to_sulv;
function to_sulv (
  arg : UNRESOLVED_sfixed)            -- fixed point vector
  return STD_ULOGIC_VECTOR is
  variable result : STD_ULOGIC_VECTOR (arg'length-1 downto 0);

  -- This was added
  subtype result_type is STD_ULOGIC_VECTOR (arg'length-1 downto 0);
  begin
  if arg'length < 1 then
    return NSLV;
  end if;
  --  originally: result := STD_ULOGIC_VECTOR (arg)
  result := result_type (arg);
  return result;
end function to_sulv;