我对vhdl还不熟悉,我正在尝试编写booth的乘法算法。我使用的是xilinx,当我合成代码时,会出现很多警告:
Upper已分配但从未使用,
Product已使用但从未分配,
LowerPrevLSB已分配但从未使用,
Lower已分配但从未使用,
A_2sComp已分配但从未使用,
Z的常数为0,
Product的常量值为0。
我认为我分配和编写的代码是正确的,但显然我不是。任何建议和帮助将不胜感激。

library IEEE;
use IEEE.NUMERIC_STD.ALL;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_arith.ALL;
use IEEE.STD_LOGIC_unsigned.ALL;

-- Uncomment the following library declaration if using
-- arithmetic functions with Signed or Unsigned values
--use IEEE.NUMERIC_STD.ALL;

-- Uncomment the following library declaration if instantiating
-- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;

-- X * Y = Z
entity BoothMultiplier is
    generic
    (
        numBits_X : integer := 8;
        numBits_Y : integer := 8
    );
    port
    (
        CLK : in std_logic;
        X : in std_logic_vector((numBits_X - 1) downto 0);
        Y : in std_logic_vector((numBits_Y - 1) downto 0);
        Z : out std_logic_vector((numBits_X + numBits_Y - 1) downto 0)
    );

end BoothMultiplier;

architecture Behavioral of BoothMultiplier is

    -- Two's Complement Function
    function TwosComplement(inputNum : std_logic_vector) return std_logic_vector;

    function TwosComplement(inputNum : std_logic_vector) return std_logic_vector is
        variable temp : std_logic_vector(inputNum'range);
        begin
            temp := (not inputNum) + 1;
            return temp;
    end TwosComplement;
    -- End Two's Complement Function

    -- MIN Function
    function MIN(Left, Right : integer) return integer;

    function MIN(Left, Right : integer) return integer is
    begin
        if Left < Right then return Left;
        else return Right;
        end if;
    end Min;
    -- End MIN Function

    -- MAX Function
    function MAX(Left, Right : integer) return integer;

    function MAX(Left, Right : integer) return integer is
    begin
        if Left > Right then return Left;
        else return Right;
        end if;
    end MAX;
    -- End MAX Function

    -- Signals
    signal Upper : std_logic_vector(MAX(numBits_X, numBits_Y) - 1 downto 0)
                    := (others => '0');
    signal Lower : std_logic_vector(MIN(numBits_X, numBits_Y) - 1 downto 0)
                    := (others => '0');
    signal LowerPrevLSB : std_logic := '0';
    signal Product : std_logic_vector(numBits_X + numBits_Y - 1 downto 0)
                        := (others => '0');
    signal A, A_2sComp : std_logic_vector(MAX(numBits_X, numBits_y) - 1 downto 0)
                := (others => '0');
    signal counter : integer := 0;
    -- End Signals

begin

    assert Z'length = (X'length + Y'length) report "Bad Product Length" severity failure;

    Lower <= X when (numBits_X <= numBits_Y) else Y;
    A <= X when (numBits_X > numBits_Y) else Y;
    A_2sComp <= TwosComplement(A);

    process(CLK)
    begin
        if rising_edge(CLK) then
            if (Lower(0) = '0' and LowerPrevLSB = '1') then
                Upper <= Upper + A;
            elsif (Lower(0) = '1' and LowerPrevLSB = '0') then
                Upper <= Upper + A_2sComp;
            end if;
            LowerPrevLSB <= Lower(0);
            Product <= Upper & Lower;
            for i in 0 to Product'length - 2 loop
                Product(i) <= Product(i+1);
            end loop;
            Product(Product'length-1) <= Product(Product'length-1);
            Upper <= Product(Product'length - 1 downto MIN(numBits_X, numBits_Y));
            Lower <= Product(MIN(numBits_X, numBits_Y) - 1 downto 0);
            counter <= counter + 1;
            if (counter = MIN(numBits_X, numBits_Y)) then
                Z <= Product;
            end if;
        end if;
    end process;

end Behavioral;

最佳答案

在vhdl中,一个进程中对同一信号的连续赋值会覆盖先前的赋值,因此:

if (Lower(0) = '0' and LowerPrevLSB = '1') then
    Upper <= Upper + A;
elsif (Lower(0) = '1' and LowerPrevLSB = '0') then
    Upper <= Upper + A_2sComp;
end if;
...
Upper <= Product(Product'length - 1 downto MIN(numBits_X, numBits_Y));

if块中的第一个赋值被完全忽略。如果查看代码,则会覆盖对ProductUpperLower的赋值。
我建议您先模拟您的设计,然后再使用Xilinx合成您的设计测试和调试会容易得多例如,您的counter信号永远不会重置,它将计数为2^31-1,然后包装为-2^31。在这种情况下,你的设计会怎样仿真很容易指出这些误差,留待以后综合!

关于algorithm - 展位乘法算法,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/30870422/

10-09 20:11