VHDL-脉动阵列:单元格阵列中的单个单元格在仿真中的行为不同

问题描述

我目前正在尝试在VHDL中编写一个基本的脉动数组,以乘以2个3x3矩阵,即AxB。我首先编写一个计算结果= a0 * b0 + a1 * b1 + a2 * b2的单元格。这个很好用。单个单元格的VHDL代码如下:

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.numeric_std.ALL;


entity sys_cell is
    port 
    (   
        clk,reset : in std_ulogic; --active low
        a_in,b_in  : in    integer;
        a_out,b_out : out integer;
        
        result : out integer
    );
end sys_cell;


architecture sys_cell_behave of sys_cell is
                    
    signal counter : unsigned(3 downto 0) := "0000";
    signal sign_a_out,sign_b_out,sign_result : integer := 0;
begin

    result <= sign_result;

    counter_process : process (clk,reset)
    begin
        if (reset = '0') then
            counter <= "0000";
        elsif (rising_edge(clk)) then
            counter <= counter + 1;
        else
            NULL;
        end if;
    end process counter_process;
    
    result_process : process (counter)
    begin
        case(counter) is
            when "0000" =>
                sign_result <= 0;
            when others =>
                sign_result <= sign_result + (a_in * b_in);
        end case;
    end process result_process;
    
    output_process : process (counter)
    begin
        case(counter) is
            when "0000" =>
                a_out <= 0;
                b_out <= 0;
            when "0001" =>
                sign_a_out <= a_in;
                sign_b_out <= b_in;
            when others =>
                a_out <= sign_a_out;
                b_out <= sign_b_out;
                sign_a_out <= a_in;
                sign_b_out <= b_in;
        end case;
    end process output_process;
    
end sys_cell_behave;

Simulation of one cell

下一步,我将9个单元格放到一个数组中。 3x3数组的代码如下:

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.numeric_std.ALL;


entity sys_array is
    port 
    (
        a0,a1,a2  :   in integer;
        b0,b1,b2  :   in integer;
        
        c00,c01,c02,c10,c11,c12,c20,c21,c22 :   out integer;
        
        reset,clk  :   in std_ulogic
    );
end sys_array;


architecture sys_array_behave of sys_array is
                    
    component sys_cell is
        port 
        (
            clk,reset : in std_ulogic; --active low
            a_in,b_in  : in    integer;
            a_out,b_out : out integer;
            
            result : out integer            
        );
    end component sys_cell;
    
    signal a_out_00,a_out_01,a_out_02,a_out_10,a_out_11,a_out_12,a_out_20,a_out_21,a_out_22 :   integer := 0;   
    signal b_out_00,b_out_01,b_out_02,b_out_10,b_out_11,b_out_12,b_out_20,b_out_21,b_out_22 :   integer := 0;
    
begin
    -- oben links
    sys_cell_00 : sys_cell
    port map
    (
        clk,reset,a0,b0,a_out_00,b_out_00,c00 
    );
    
    -- oben mitte
    sys_cell_01 : sys_cell
    port map
    (
        clk,c01
    );
    
    -- oben rechts
    sys_cell_02 : sys_cell
    port map
    (
        clk,b2,open,c02
    );
    
    -- mitte links
    sys_cell_10 : sys_cell
    port map
    (
        clk,c10
    );
    
    -- mitte mitte
    sys_cell_11 : sys_cell
    port map
    (
        clk,c11
    );
    
    -- mitte rechts
    sys_cell_12 : sys_cell
    port map
    (
        clk,c12     
    );
    
    -- unten links
    sys_cell_20 : sys_cell
    port map
    (
        clk,a2,c20
    );
    
    -- unten mitte
    sys_cell_21 : sys_cell
    port map
    (
        clk,c21
    );
    
    -- unten rechts
    sys_cell_22 : sys_cell
    port map
    (
        clk,c22
    );
            
    
end sys_array_behave;

在模拟中出现的问题是,除第一个单元格外,每个单元格的计算结果都是错误的。我添加了模拟图片。红线分隔sys_cell_00和sys_cell_01的信号。蓝色箭头指示这两个单元格的不同行为。为什么sys_cell_00计算结果而sys_cell_01不计算结果?唯一不同的信号是计数器值。但是“ result_process”中的vhdl代码应使其行为相同。 Simulation of the cell array

解决方法

我已经重写了代码,现在可以使用了。作为一个基本的开始,我现在有以下代码:

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.numeric_std.ALL;


entity sys_cell is
    port 
    (   
        clk,reset : in std_ulogic; --active low
        a_in,b_in  : in    integer;
        a_out,b_out : out integer;
        
        result : out integer
    );
end sys_cell;


architecture sys_cell_behave of sys_cell is
                    
    signal sign_result : integer := 0;

begin
    process(clk)
    begin
        if(reset = '1') then
            if (rising_edge(clk)) then
                sign_result <= sign_result + a_in * b_in;
                a_out <= a_in;
                b_out <= b_in;
            else 
                NULL;
            end if;
        else
            a_out <= 0;
            b_out <= 0;
            result <= 0;
            sign_result <= 0;
        end if;
        result <= sign_result;
    end process;
    
end sys_cell_behave;

3x3阵列的代码未更改