Guest
Hi,
I'm trying to write a piece of VHDL code for multiply-and-accumulate.
I'm not a VHDL coder, so I'm having trouble with this simple process. I
have Xilinx generated vhdl code to start with, which already has read
(SLAVE_REG_READ_PROC) and write (SLAVE_REG_WRITE_PROC) processes. Now
I'm adding a process called MUL_AND_ACC_PROC, which does
multiply-and-accumulate for me. In C, my code would be:
product (reg2) = reg0 * reg1;
accum (reg3) = reg3 + reg2;
I'm using software accessible register to write to reg0 and reg1, and
hoping to find accum after n sets of reg0 and reg1. My vhdl code looks
as follows:
------------------------------------------------------------------------------
-- Architecture section
------------------------------------------------------------------------------
architecture IMP of user_logic is
--USER signal declarations added here, as needed for user logic
------------------------------------------
-- Signals for user logic slave model s/w accessible register example
------------------------------------------
signal slv_reg0 : std_logic_vector(0 to
C_DWIDTH-1);
signal slv_reg1 : std_logic_vector(0 to
C_DWIDTH-1);
signal slv_reg2 : std_logic_vector(0 to
C_DWIDTH-1);
signal slv_reg3 : std_logic_vector(0 to
C_DWIDTH-1);
signal slv_reg_write_select : std_logic_vector(0 to 3);
signal slv_reg_read_select : std_logic_vector(0 to 3);
signal slv_ip2bus_data : std_logic_vector(0 to
C_DWIDTH-1);
signal slv_read_ack : std_logic;
signal slv_write_ack : std_logic;
begin
--USER logic implementation added here
MUL_AND_ACC_PROC : process( Bus2IP_Clk, slv_reg0, slv_reg1 ) is
begin
if Bus2IP_Clk'event and Bus2IP_Clk = '1' then
if Bus2IP_Reset = '1' then
slv_reg2 <= (others => '0');
slv_reg3 <= (others => '0');
else
slv_reg2 <= slv_reg0 * slv_Reg1;
slv_reg3 <= slv_reg3 + slv_reg2;
end if;
end if;
end process MUL_AND_ACC_PROC;
------------------------------------------
-- Example code to read/write user logic slave model s/w accessible
registers
--
-- Note:
-- The example code presented here is to show you one way of
reading/writing
-- software accessible registers implemented in the user logic slave
model.
-- Each bit of the Bus2IP_WrCE/Bus2IP_RdCE signals is configured to
correspond
-- to one software accessible register by the top level template. For
example,
-- if you have four 32 bit software accessible registers in the user
logic, you
-- are basically operating on the following memory mapped registers:
--
-- Bus2IP_WrCE or Memory Mapped
-- Bus2IP_RdCE Register
-- "1000" C_BASEADDR + 0x0
-- "0100" C_BASEADDR + 0x4
-- "0010" C_BASEADDR + 0x8
-- "0001" C_BASEADDR + 0xC
--
------------------------------------------
slv_reg_write_select <= Bus2IP_WrCE(0 to 3);
slv_reg_read_select <= Bus2IP_RdCE(0 to 3);
slv_write_ack <= Bus2IP_WrCE(0) or Bus2IP_WrCE(1) or
Bus2IP_WrCE(2) or Bus2IP_WrCE(3);
slv_read_ack <= Bus2IP_RdCE(0) or Bus2IP_RdCE(1) or
Bus2IP_RdCE(2) or Bus2IP_RdCE(3);
-- implement slave model register(s)
SLAVE_REG_WRITE_PROC : process( Bus2IP_Clk ) is
begin
if Bus2IP_Clk'event and Bus2IP_Clk = '1' then
if Bus2IP_Reset = '1' then
slv_reg0 <= (others => '0');
slv_reg1 <= (others => '0');
else
case slv_reg_write_select is
when "1000" => slv_reg0 <= Bus2IP_Data(0 to 31);
when "0100" => slv_reg1 <= Bus2IP_Data(0 to 31);
when others => null;
end case;
end if;
end if;
end process SLAVE_REG_WRITE_PROC;
-- implement slave model register read mux
SLAVE_REG_READ_PROC : process( slv_reg_read_select, slv_reg0,
slv_reg1, slv_reg2, slv_reg3 ) is
begin
case slv_reg_read_select is
when "1000" => slv_ip2bus_data <= slv_reg0;
when "0100" => slv_ip2bus_data <= slv_reg1;
when "0010" => slv_ip2bus_data <= slv_reg2;
when "0001" => slv_ip2bus_data <= slv_reg3;
when others => slv_ip2bus_data <= (others => '0');
end case;
end process SLAVE_REG_READ_PROC;
------------------------------------------
-- Example code to drive IP to Bus signals
------------------------------------------
IP2Bus_Data <= slv_ip2bus_data;
IP2Bus_Ack <= slv_write_ack or slv_read_ack;
IP2Bus_Error <= '0';
IP2Bus_Retry <= '0';
IP2Bus_ToutSup <= '0';
end IMP;
I only included the three processes. In this Xilinx generated code, I
only modified SLAVE_REG_WRITE_PROC and added MUL_AND_ACCUM process. I
keep getting 0s for reg2 and reg3 in my C program. Can anyone point out
what I've done wrong? Thanks!
I'm trying to write a piece of VHDL code for multiply-and-accumulate.
I'm not a VHDL coder, so I'm having trouble with this simple process. I
have Xilinx generated vhdl code to start with, which already has read
(SLAVE_REG_READ_PROC) and write (SLAVE_REG_WRITE_PROC) processes. Now
I'm adding a process called MUL_AND_ACC_PROC, which does
multiply-and-accumulate for me. In C, my code would be:
product (reg2) = reg0 * reg1;
accum (reg3) = reg3 + reg2;
I'm using software accessible register to write to reg0 and reg1, and
hoping to find accum after n sets of reg0 and reg1. My vhdl code looks
as follows:
------------------------------------------------------------------------------
-- Architecture section
------------------------------------------------------------------------------
architecture IMP of user_logic is
--USER signal declarations added here, as needed for user logic
------------------------------------------
-- Signals for user logic slave model s/w accessible register example
------------------------------------------
signal slv_reg0 : std_logic_vector(0 to
C_DWIDTH-1);
signal slv_reg1 : std_logic_vector(0 to
C_DWIDTH-1);
signal slv_reg2 : std_logic_vector(0 to
C_DWIDTH-1);
signal slv_reg3 : std_logic_vector(0 to
C_DWIDTH-1);
signal slv_reg_write_select : std_logic_vector(0 to 3);
signal slv_reg_read_select : std_logic_vector(0 to 3);
signal slv_ip2bus_data : std_logic_vector(0 to
C_DWIDTH-1);
signal slv_read_ack : std_logic;
signal slv_write_ack : std_logic;
begin
--USER logic implementation added here
MUL_AND_ACC_PROC : process( Bus2IP_Clk, slv_reg0, slv_reg1 ) is
begin
if Bus2IP_Clk'event and Bus2IP_Clk = '1' then
if Bus2IP_Reset = '1' then
slv_reg2 <= (others => '0');
slv_reg3 <= (others => '0');
else
slv_reg2 <= slv_reg0 * slv_Reg1;
slv_reg3 <= slv_reg3 + slv_reg2;
end if;
end if;
end process MUL_AND_ACC_PROC;
------------------------------------------
-- Example code to read/write user logic slave model s/w accessible
registers
--
-- Note:
-- The example code presented here is to show you one way of
reading/writing
-- software accessible registers implemented in the user logic slave
model.
-- Each bit of the Bus2IP_WrCE/Bus2IP_RdCE signals is configured to
correspond
-- to one software accessible register by the top level template. For
example,
-- if you have four 32 bit software accessible registers in the user
logic, you
-- are basically operating on the following memory mapped registers:
--
-- Bus2IP_WrCE or Memory Mapped
-- Bus2IP_RdCE Register
-- "1000" C_BASEADDR + 0x0
-- "0100" C_BASEADDR + 0x4
-- "0010" C_BASEADDR + 0x8
-- "0001" C_BASEADDR + 0xC
--
------------------------------------------
slv_reg_write_select <= Bus2IP_WrCE(0 to 3);
slv_reg_read_select <= Bus2IP_RdCE(0 to 3);
slv_write_ack <= Bus2IP_WrCE(0) or Bus2IP_WrCE(1) or
Bus2IP_WrCE(2) or Bus2IP_WrCE(3);
slv_read_ack <= Bus2IP_RdCE(0) or Bus2IP_RdCE(1) or
Bus2IP_RdCE(2) or Bus2IP_RdCE(3);
-- implement slave model register(s)
SLAVE_REG_WRITE_PROC : process( Bus2IP_Clk ) is
begin
if Bus2IP_Clk'event and Bus2IP_Clk = '1' then
if Bus2IP_Reset = '1' then
slv_reg0 <= (others => '0');
slv_reg1 <= (others => '0');
else
case slv_reg_write_select is
when "1000" => slv_reg0 <= Bus2IP_Data(0 to 31);
when "0100" => slv_reg1 <= Bus2IP_Data(0 to 31);
when others => null;
end case;
end if;
end if;
end process SLAVE_REG_WRITE_PROC;
-- implement slave model register read mux
SLAVE_REG_READ_PROC : process( slv_reg_read_select, slv_reg0,
slv_reg1, slv_reg2, slv_reg3 ) is
begin
case slv_reg_read_select is
when "1000" => slv_ip2bus_data <= slv_reg0;
when "0100" => slv_ip2bus_data <= slv_reg1;
when "0010" => slv_ip2bus_data <= slv_reg2;
when "0001" => slv_ip2bus_data <= slv_reg3;
when others => slv_ip2bus_data <= (others => '0');
end case;
end process SLAVE_REG_READ_PROC;
------------------------------------------
-- Example code to drive IP to Bus signals
------------------------------------------
IP2Bus_Data <= slv_ip2bus_data;
IP2Bus_Ack <= slv_write_ack or slv_read_ack;
IP2Bus_Error <= '0';
IP2Bus_Retry <= '0';
IP2Bus_ToutSup <= '0';
end IMP;
I only included the three processes. In this Xilinx generated code, I
only modified SLAVE_REG_WRITE_PROC and added MUL_AND_ACCUM process. I
keep getting 0s for reg2 and reg3 in my C program. Can anyone point out
what I've done wrong? Thanks!