条件语句中从unsigned到std_logic_vector的VHDL许可转换

时间:2016-10-04 21:24:37

标签: vhdl

我想知道为什么在条件语句中执行从unsigned到std_logic_vector的错误转换时没有出现警告/错误

todo

而在通常的其他矢量情感中检测到它。

--Naturally wrong when input length is not 4, will always be false
if  input = std_logic_vector(to_unsigned(pattern_int,4)) then 

带有工作语法的简化代码(MVCE)如下所示:

Link to EDA PlayGround(包含“dut”及其测试平台的代码)

-- for this you will get a warning, e.g vector truncated
temp <= std_logic_vector(to_unsigned(pattern_int,4));

测试平台,以便问题真的完整(它已经在EDA Playground上提供,但不幸的是你必须注册才能播放它...)

library IEEE;
use IEEE.std_logic_1164.all;
use IEEE.numeric_std.all;

entity vector_test is
port (  CLOCK   : in std_logic;
        RESET   : in std_logic;
        INPUT   : in std_logic_vector(7 downto 0);
        OUTPUT  : out std_logic);
end entity;

architecture rtl of vector_test is
    constant pattern_int : integer := 16#80#;
    --signal temp : std_logic_vector(7 downto 0);
    begin
        process(CLOCK,RESET,INPUT)
            begin
                -- for this you will get a warning, e.g vector truncated
                --temp <= std_logic_vector(to_unsigned(pattern_int,4));
                if RESET = '1' then
                    output <= '0';
                elsif rising_edge(CLOCK) then 
                    --Naturally wrong, output will alway be 0
                    --if  input = std_logic_vector(to_unsigned(pattern_int,4)) then 
                    if  input = std_logic_vector(to_unsigned(pattern_int,input'length)) then 
                        output <= '1';
                    else
                        output <= '0';
                    end if;
                end if;
        end process;
end architecture;

1 个答案:

答案 0 :(得分:2)

我想知道为什么在条件语句中执行从unsigned到std_logic_vector的错误转换时没有收到警告/错误

IEEE Std 1076-2008 9.2.3关系运算符第3和第4段:

  

为文件类型和受保护类型以外的所有类型定义了相等和不等式运算符(=和/ =)。如果两个操作数相等,则等于运算符返回值TRUE,否则返回值FALSE。如果两个操作数相等,则不等式运算符返回值FALSE,否则返回值TRUE。

     

当且仅当值相同时,相同类型的两个标量值相等。 相同类型的两个复合值相等,当且仅当左操作数的每个元素都存在右操作数的匹配元素,反之亦然,并且匹配元素的值相等,如预定义所给定的元素类型的等于运算符。特别是,两个相同类型的空数组总是相等的。当且仅当它们都指定相同的对象或者它们都等于访问类型的空值时,访问类型的两个值是相等的。

如果两个std_logic_vector值的长度不匹配,则相等测试将返回FALSE。在端口中声明的INPUT的长度是8.转换为std_logic_vector的无符号的长度是4(来自to_unsigned的第二个参数,自然指定返回的无符号的长度)。

如果您将作业取消注释为temp并运行代码,则会在模拟过程中收到错误消息。

14.7.3.4信号更新第1和第2段:

  

对于标量信号S,驱动值和有效值都应属于信号的子类型。对于复合信号R,对R的子类型执行隐式子类型转换;对于R的每个元素,在驱动和有效值中都应有匹配元素,反之亦然。

     

为了在给定的模拟周期内更新信号,内核过程首先确定该信号的驱动和有效值。然后,内核进程使用新确定的驱动值更新包含驱动值的变量。内核还使用新确定的有效值更新包含信号当前值的变量,如下所示:

     
    

a)如果S是标量信号,则S的有效值用于更新S的当前值。检查S的有效值是否属于S的子类型。如果此子类型出现错误检查失败。最后,S的有效值被分配给表示信号当前值的变量。

         

b)如果S是复合信号(包括数组的切片),则S的有效值被隐式转换为S的子类型。子类型转换检查S的每个元素是否存在匹配元素的有效值,反之亦然。如果此检查失败,则会发生错误。此子类型转换的结果将分配给表示S的当前值的变量。

  

在更新信号时,对条件的评估没有被定义为错误,要求右侧表达式中存在匹配元素,并且失败。

将关系相等性的数组值与空数组进行比较并获得FALSE返回值完全有效。

在以下错误中报告的第19行是未取消注释的临时分配:

  

ghdl -a vector_test.vhdl
  ghdl -e vector_test
  ghdl -r vector_test
  ../../src/ieee/numeric_std-body.v93:2151:7:@0ms:(警告警告):NUMERIC_STD.TO_UNSIGNED:向量截断的向量
  ./vector_test:error:vector_test.vhdl的绑定检查失败:19
  ./vector_test:error:模拟失败

除了由14.7.3.4(12.6.2信号值的传播,-1993中的第12段)规定的绑定检查失败错误之外,我们还看到来自包numeric_std函数to_unsigned的警告报告除零以外的除法余数:

  function TO_UNSIGNED (ARG, SIZE : NATURAL) return UNRESOLVED_UNSIGNED is
    variable RESULT : UNRESOLVED_UNSIGNED(SIZE-1 downto 0);
    variable I_VAL  : NATURAL := ARG;
  begin
    if (SIZE < 1) then return NAU;
    end if;
    for I in 0 to RESULT'left loop
      if (I_VAL mod 2) = 0 then
        RESULT(I) := '0';
      else RESULT(I) := '1';
      end if;
      I_VAL          := I_VAL/2;
    end loop;
    if not(I_VAL = 0) then
      assert NO_WARNING
        report "NUMERIC_STD.TO_UNSIGNED: vector truncated"
        severity warning;
    end if;
    return RESULT;
  end function TO_UNSIGNED;

这是因为提供的SIZE参数(4)不足以包含转换为二进制的常量pattern_int16#80#的自然值,这需要8位SIZE。

能够使用顶级端口执行vector_test取决于实现。

14.2拟定设计实体第7段:

  

实现可以允许(但不是必须)允许设计层次结构的根设计实体具有泛型和端口。如果实现允许这些顶级接口对象,它可能会限制其允许的表单(即,是否允许它们是接口类型,子程序,包或对象),并且在接口对象的情况下,它们允许的类型和模式以实现定义的方式。

简单地说,对于某些模拟器,您的代码是MCVE,而对于其他模拟器则不是。您的测试平台可能包含在您的问题中。我们看到运行ghdl的错误发生在if语句之外,并且条件评估了CLOCK的上升沿。