2016-01-26 72 views
0

我是VHDL的新手,我正在尝试写一个左移位器,它需要一个32位值和一个5位值。左移位器然后试图通过移出左边的5位数字指定的位数并将右边的多个零移出来来执行32位值的逻辑左移。我不明白为什么数组表示法不起作用。 1 < < 1的结果产生20000000而不是00000002.有人可以解释我要去哪里出错吗?下面的代码:为什么VHDL不能移动工作?

SIGNAL lshiftOutput : STD_LOGIC_VECTOR(31 downto 0); 

COMPONENT Lshift32 
    Port(a : in STD_LOGIC_VECTOR(31 downto 0); 
      b : in STD_LOGIC_VECTOR(4 downto 0); 
      lshiftOutput : out STD_LOGIC_VECTOR(31 downto 0)); 
END COMPONENT; 

PROCESS( a, b, opcode, adderOutput, subtractOutput, xorOutput, lshiftOutput, rshiftOutput) 
BEGIN 
    IF opcode = "0000" THEN 
     result <= x"00000000"; 
    ELSIF opcode = "0001" THEN 
     result <= adderOutput; 
    ELSIF opcode = "0010" THEN 
     result <= subtractOutput; 
    ELSIF opcode = "0011" THEN 
     result <= NOT a; 
    ELSIF opcode = "0100" THEN 
     result <= a AND b; 
    ELSIF opcode = "0101" THEN 
     result <= a OR b; 
    ELSIF opcode = "0110" THEN 
     result <= xorOutput; 
    ELSIF opcode = "0111" THEN 
     result <= lshiftOutput; 
    ELSIF opcode = "1000" THEN 
     result <= rshiftOutput; 
    END IF; 
END PROCESS; 

LIBRARY ieee; 
USE ieee.std_logic_unsigned.ALL; 
USE ieee.std_logic_1164.ALL; 
USE ieee.numeric_std.ALL; 


ENTITY Lshift32 IS 
    Port(a : in STD_LOGIC_VECTOR (31 downto 0); 
      b : in STD_LOGIC_VECTOR (4 downto 0); 
      lshiftOutput : out STD_LOGIC_VECTOR (31 downto 0)); 
END Lshift32; 

ARCHITECTURE Lshift32Architecture of Lshift32 IS 
BEGIN 
    PROCESS(a, b) 
    VARIABLE shiftAmount : INTEGER := 0; 
    BEGIN 
     shiftAmount := to_integer(b(4 downto 0)); 
     -- Shift left 
     lshiftOutput <= a(31-shiftAmount downto 0) & (shiftAmount-1 downto 0 => '0'); 
    END PROCESS; 
END Lshift32Architecture; 

该试验台是这样的:

-- Shift Left ------------------------------------------------------- 
WAIT FOR 9 ns; 
op <= "0111"; 
-- 1 << 1 
input_a <= x"00000001"; 
input_b <= x"00000001"; 
WAIT FOR 1 ns; 
IF (output /= x"00000002") THEN 
    ASSERT false REPORT "1 << 1 has incorrect result" severity error; 
END IF; 
+0

包括其余的代码,包括库/使用条款和据称给你这个结果的测试台。由于错误的移位距离可能会产生这种结果,因此您可能需要添加显示“shiftAmount”的“报告”语句。 –

+0

“测试平台”(a)不完整,(b)测试与“Lshift32”实体完全不同的内容。发布你正在抱怨的实体的单元测试 - 而不是其他的东西。 –

回答

1

布赖恩问你提供的一个Minimal, Complete, and Verifiable example,您编辑的代码没有做到这一点。而对于要求的原因是,它可以创建一个围绕您最初提供的代码部分的MCVE,它得到正确的答案:

library ieee; -- added 
use ieee.std_logic_1164.all; -- added 
use ieee.numeric_std_unsigned.all; -- added 

entity lshift32 is 
    port(a : in std_logic_vector (31 downto 0); 
      b : in std_logic_vector (4 downto 0); 
      lshiftoutput : out std_logic_vector (31 downto 0)); 
end entity lshift32; 

architecture lshift32architecture of lshift32 is 
begin 
    process(a, b) 
    variable shiftamount : integer := 0; 
    begin 
     shiftamount := to_integer(b(4 downto 0)); 
     -- shift left 

     lshiftoutput <= a(31-shiftamount downto 0) & (shiftamount-1 downto 0 => '0'); 
    end process; 
end architecture lshift32architecture; 

library ieee; 
use ieee.std_logic_1164.all; 
use ieee.numeric_std_unsigned.all; 

entity lshift32_tb is 
end entity; 

architecture foo of lshift32_tb is 
    signal a: std_logic_vector (31 downto 0) := (others => '0'); 
    signal b: std_logic_vector (4 downto 0) := (others => '0'); 
    signal lshiftoutput: std_logic_vector (31 downto 0); 
begin 

DUT: 
    entity work.lshift32 
     port map (
      a => a, 
      b => b, 
      lshiftoutput => lshiftoutput 
     ); 

SIMULIS: 
    process 
    begin 
     wait for 10 ns; 
     a(0) <= '1'; -- 1 
     b(0) <= '1'; -- 1 
     wait for 10 ns; 
     wait; 
    end process; 

ANALYSIS: 
    process (lshiftoutput) 
    variable shiftamount: integer; 
    begin 
     if now > 0 ns then 
      shiftamount := to_integer(b); 
      report "ShiftAmount = " & integer'image(shiftamount); 
      report "lshiftOutput = " & to_string(lshiftoutput); 
     end if; 
    end process; 
end architecture; 

并运行上述测试平台提供了:

ghdl -a --std = 08 lshift.vhdl
ghdl -e --std = 08 lshift32_tb
ghdl -r lshift32_tb
lshift.vhdl:60:13:@ 10ns的:(报告注):ShiftAmount = 1
lshift.vhdl:61:13:@ 10ns:(report n注意:lshiftOutput = 00000000000000000000000000000010

而且你的执行失败说你的测试平台的上下文子句(使用子句)或有问题。

请注意,您正在使用none标准软件包std_logic_unsigned和IEEE标准软件包numeric_std。你真的不应该混搭,可能会有意想不到的后果。

软件包numeric_std_unsigned可用于符合IEEE Std 1076-2008标准的VHDL实现。如果使用先前版本的VHDL标准,则可以使用软件包numeric_std并键入convert b以作为传递到to_integer的表达式的无符号数。

对于随此答案提供的测试台,您还会发现未提供针对std_logic_vector的to_string。没有看到你的整个测试平台,它很可能是功能性的。

如果你想证明的答案提供测试平台的作品在非-2008修订环境:

function to_string (inp: std_logic_vector) return string is 
    variable image_str: string (1 to inp'length); 
    alias input_str: std_logic_vector (1 to inp'length) is inp; 
begin 
    for i in input_str'range loop 
     image_str(i) := character'VALUE(std_ulogic'IMAGE(input_str(i))); 
    end loop; 
    return image_str; 
end function; 

功能可以提供作为架构声明项。

+0

是的代码实际上是功能。对不起,我没有给出更清楚的描述。 –