4

如何实现具有“无关”输入并直接表示“无关”的 VHDL 函数?

自由范围 VHDL的练习 4.8-2a要求我:

...编写使用...选择的信号分配实现这些功能的 VHDL 模型。

a) F (A, B, C, D) = A'CD' + B'C + BCD'

此代码有效:

library ieee;
use ieee.std_logic_1164.all;

entity funca_selected is
  port (
    a: in std_ulogic;
    b: in std_ulogic;
    c: in std_ulogic;
    d: in std_ulogic;
    x: out std_ulogic);
end entity;

architecture rtl of funca_selected is
  signal s: std_ulogic_vector(3 downto 0);
begin
  s <= a & b & c & d;
  with s select x <=
    '1' when "0010" | "0110" | "0011" | "1010" | "1011" | "1110",
    '0' when others;
end architecture;

然而,它是函数定义的不良表示。我想使用“无关”输入对其进行编码,以便代码更接近定义。这将减少工作量,并且更容易正确。我试过这个:

  with s select x <=
    '1' when "0-10" | "-01-" | "-110",
    '0' when others;

这不起作用:当我的测试台执行此功能时,结果始终为“0”。

我正在使用 GHDL 版本 0.29+gcc4.3.i386。

VHDL 函数如何表示“无关”输入?

4

4 回答 4

4

使用上划线符号(如 A̅),练习 4.8-2a 中的函数是:

F(A, B, C, D) = A̅CD̅ + B̅C + BCD̅

GHDL最多仅支持 VHDL-2000(根据GHDL 特性),因此没有任何 VHDL-2008 比较操作与无关('-')检查可用。GHDL 的另一个表达式是表达式:

x <= ((not a) and c and (not d)) or
     ((not b) and c) or
     (b and c and (not d));

但是,如果工具中提供了 VHDL-2008,则检查无关紧要的 ?= 运算符可用作:

x <= (s ?= "0-10") or (s ?= "-01-") or (s ?= "-110");

请注意,此表达式还将 VHDL-2008 隐式布尔值应用于 std_logic 转换。

或者一个案例?,它也检查无关紧要,可以用作:

process (s) is
begin
  case? s is
    when "0010" | "0110" | "0011" | "1010" | "1011" | "1110" => x <= '1';
    when others => x <= '0';
  end case?;
end process;

有没有用?VHDL-2008 中的运算符用于并发类似案例的分配。

有关 VHDL-2008 功能的更多信息,这里有一篇不错的论文VHDL-2008: Why It Matters

于 2013-07-28T20:47:08.767 回答
2

我在 Xilinx ISE 14.6 中尝试了两个版本的逻辑,两个版本都可以工作,但有一些警告。首先,当我将“无关”版本的 RTL 原理图与显式版本进行比较时,“无关”版本更简单且更优化。“无关”版本有四个逻辑门,每个门的最大输入线为三线。显式版本有七个逻辑门,每个门的最大输入线为六线。

当我测试两个版本时,我有四个不同的模拟选项:行为、翻译后、地图后和路线后。在行为模型中,“不关心”版本输出是一条平线,就像您所说的那样,“不关心”版本似乎不起作用,但是,在所有其他三个模拟选项中,两个版本都可以正常工作并输出是相同的。所以看起来行为模型不知道如何处理 VHDL 代码的“无关”部分,但代码是可综合的,并且在 VHDL 代码中使用“无关”是非常有价值的。

于 2014-04-27T19:31:57.493 回答
1

VHDL 中的比较是一个非常纯粹的逐元素精确匹配。这是 VHDL 的愚蠢之处之一,它得到了扩展以在 VHDL-2008 中修复它,带有case?语句和=?运算符

http://www.doulos.com/knowhow/vhdl_designers_guide/vhdl_2008/vhdl_200x_small/#matchcase

不幸的是,GHDL 不支持 VHDL-2008,因此您必须使用该std_match功能,我认为这也排除了使用with..select.

于 2013-07-28T20:23:28.210 回答
1

是的,ghdl 只能指望符合 IEEE Std 1076-1993 标准,而且那里有一两个洞。

当我们意识到不需要第一项 (A̅CD̅) 时,该函数可能会更简单,结果不依赖于它。输出中从未发现第一个乘积项。

无论所选信号分配的评估目标是表达式。您可以使用 MortenZdk 的并发信号赋值语句中的表达式:

library ieee;
use ieee.std_logic_1164.all;

entity f_test is
end;
architecture test of f_test is

    subtype vector is  std_logic_vector (3 downto 0);
    type    vectorstream is array (0 to 15) of vector;

    constant stimulous: vectorstream  :=(
    x"0",x"1",x"2",x"3",x"4",X"5",x"6",x"7",
    x"8",x"9",x"A",x"B",x"C",x"D",x"E",X"F"
    );

    signal index: integer range 0 to 15;

    signal a,b,c,d: std_logic;

    signal x:   std_logic;

begin
Test_Vectors:
    process
        variable TV: std_logic_vector(3 downto 0);
    begin
        -- first term is valid
        for i in vectorstream'range loop

                index <= (i);   -- make vector index  visible in waveform
                TV  := vector(stimulous(i));
                a <= TV(3); b <= TV(2); c <= TV(1); d <= TV(0);  
                wait for 10 ns;                      
            end loop;

            wait;  -- ends simulation

    end process;
EVALUATE:  -- "the code more closely matches the definition"

    with TO_X01(
                ( not a           and c and not d) or  -- b is don't care
                (           not b and c          ) or  -- a, d are don't care
                (               b and c and not d)     -- a is don't care
               ) select x <= '1' when '1',
                             '0' when '0',
                             'X' when 'X';  -- equivalent of 'else 'X' in 
                                            -- concurrent signal assignment

end;

TO_X01 被称为强度剥离器,来自包 std_logic_1164,计算结果为“X”、“0”或“1”。

选定的信号分配具有等效的条件信号分配,并且两者都可以表示为过程,这就是它们的模拟方式。

ghdl -a f_test.vhdl
ghdl -r f_test --wave=f_test.ghw
open f_test.ghw

gtkwave 模拟结果

您可以添加到 stimulous,允许演示在映射到类型 X01 的 std_Logic_1164 包中为“and”和“or”指定的 stdlogic_table 中指定的其他元素值,以减少所选信号分配语句中的选择数量。

另请注意,在 select x <= '1' when '1' 时,第一个 '1' 指的是 std_logic 值,而第二个 '1' 指的是 X01 类型的值。

您可以注释掉 A̅CD̅ 的第一个乘积项行,以证明它对结果 x 没有影响。

于 2013-07-28T23:08:18.550 回答