VHDL 找到运算符“=”的“0”定义

VHDL found '0' definition of operator "="

我在我的 VHDL 代码中遇到此错误:找到运算符“=”的“0”个定义,无法确定“=”的精确重载匹配定义

这是我的代码:

library IEEE;
Use IEEE.STD_LOGIC_1164.ALL;

entity simpleMux is
    Port ( i0 : in  STD_LOGIC;
           i1 : in  STD_LOGIC;
           i2 : in  STD_LOGIC;
           i3 : in  STD_LOGIC;
           s : in  STD_LOGIC_VECTOR(1 downto 0);
           o : out  STD_LOGIC);
end simpleMux;

architecture Behavioral of simpleMux is

begin

o <= i0 when (s = "00") else
        i1 when (s = "01") else
        i2 when (s = "02") else
        i3 when (s = "03");

end Behavioral;

具体问题出在哪里?

信号s是std_logic_vector类型,它只是一个std_logic类型的数组。请记住,std_logic 只能假定值 0 和 1(以及其他一些未定义的值)。因此,您只能在 std_logic_vector 中使用值,例如“00”、“10”等。您正在与无效的值“02”和“03”进行比较。

相反,你的表达应该是:

o <= i0 when (s = "00") else
     i1 when (s = "01") else
     i2 when (s = "10") else
     i3 when (s = "11");

这旨在为 anderswb 的答案添加一个替代方案,并证明您可以在表示二进制值的数组类型和表示该数组类型中的值表达式的数字文字之间进行比较。

它还提供了一个机会来指出有关在具有比“9”和“1”更多的元素基类型的类型中评估表达式的内容。

可以修改您的设计并将数值与 s:

进行比较
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;

entity simplemux is
    port ( 
        i0:  in   std_logic;
        i1:  in   std_logic;
        i2:  in   std_logic;
        i3:  in   std_logic;
        s:   in   std_logic_vector(1 downto 0);
        o:   out  std_logic
    );
end entity simplemux;

architecture foo of simplemux is
begin
    o <=    i0 when unsigned(s) = 0 else
            i1 when unsigned(s) = 1 else
            i2 when unsigned(s) = 2 else
            i3 when unsigned(s) = 3 else
            'X';
end architecture;

这依赖于 s 到 unsigned 类型的类型转换。您还可以在端口声明中提供 s 作为 unsigned 以避免类型转换,并在关联列表中进行类型转换(实例化 simplemux 的端口映射)。

在包 numeric_std 中,定义了一个“=”函数,用于重载等于运算符,其签名为 [unsigned, natural return boolean]。

这允许将适用于无符号数的数值与无符号数进行比较。

这将分析,阐述和模拟。请注意,我在最后添加了一个额外的 else 来处理元值。为什么可以用一个简单的测试平台来演示,该测试平台不初始化任何输入到 simplemux 的值:

library ieee;
use ieee.std_logic_1164.all;

entity tb_simplemux is
end entity;

architecture fum of tb_simplemux is
    signal i0, i1, i2, i3: std_logic;  -- default value = 'U'
    signal s:              std_logic_vector (1 downto 0); -- default "UU"
    signal o:              std_logic;
begin
DUT:
    entity work.simplemux
        port map (
            i0 => i0,
            i1 => i1,
            i2 => i2,
            i3 => i3,
            s  => s,
            o  => o
        );
MONITOR:        
    process
    begin
        wait on o;
        report "o = " & std_logic'image(o);
    end process;

STIMULUS:
    process
    begin
        wait;
    end process;
end architecture;

如果我们分析和详细说明,那么运行 测试平台:

ghdl -r tb_simplemux
../../../src/ieee/numeric_std-body.v93:1710:7:@0ms:(assertion warning): NUMERIC_STD."=": metavalue detected, returning FALSE
../../../src/ieee/numeric_std-body.v93:1710:7:@0ms:(assertion warning): NUMERIC_STD."=": metavalue detected, returning FALSE
../../../src/ieee/numeric_std-body.v93:1710:7:@0ms:(assertion warning): NUMERIC_STD."=": metavalue detected, returning FALSE
../../../src/ieee/numeric_std-body.v93:1710:7:@0ms:(assertion warning): NUMERIC_STD."=": metavalue detected, returning FALSE
simplemux.vhdl:50:9:@0ms:(report note): o = 'X'

MONITOR 进程中的 wait on o; 消除了默认值 o(即 'U')的显示。将其注释掉并添加带有 s 的敏感度列表,您会看到:

...
simplemux.vhdl:49:9:@0ms:(report note): o = 'U'
simplemux.vhdl:49:9:@0ms:(report note): o = 'X'

o 的默认值也会显示。

s 上使用元值,您的 simplemux 实际上不会在模拟期间为 o 分配任何值,但会合成得很好(只考虑二进制表示值)。

'X' 表明 s 上有一个用于模拟目的的元值。

我们可以在测试台的 STIMULUS 过程中将不同的值分配给 i0i1i2i3(例如“9”、“1” ,'L' 和 'H',后两者映射到合成中的二进制值),然后通过向量 s 的二进制值,在分配之间有延迟,并证明 simplemux 是功能性的。您还可以将一个输入值设置为不同于其他输入值,并通过 s 的二进制值进行选通以显示选择了正确的输入,对每个输入都这样做。

这里的重点是std_ulogic,std_logic的基类型,std_logic_vector或unsigned的元素类型的基类型是一个多级值逻辑信号,提供的不仅仅是用于模拟目的的二进制信息,我们可以在故障排除中使用其他信息。

我们可以编写仿真模型,告诉我们有关模型正在做什么的信息(例如来自“=”的断言警告),同时仍能正确合成。