URL
https://opencores.org/ocsvn/rv01_riscv_core/rv01_riscv_core/trunk
Subversion Repositories rv01_riscv_core
[/] [rv01_riscv_core/] [trunk/] [VHDL/] [RV01_resmux_ix2.vhd] - Rev 2
Compare with Previous | Blame | View Log
----------------------------------------------------------------- -- -- ----------------------------------------------------------------- -- -- -- Copyright (C) 2016 Stefano Tonello -- -- -- -- This source file may be used and distributed without -- -- restriction provided that this copyright statement is not -- -- removed from the file and that any derivative work contains -- -- the original copyright notice and the associated disclaimer.-- -- -- -- THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY -- -- EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED -- -- TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS -- -- FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR -- -- OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, -- -- INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES -- -- (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE -- -- GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR -- -- BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -- -- LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -- -- (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT -- -- OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE -- -- POSSIBILITY OF SUCH DAMAGE. -- -- -- ----------------------------------------------------------------- --------------------------------------------------------------- -- RV01 result mux (IX2 stage) --------------------------------------------------------------- library IEEE; use IEEE.std_logic_1164.all; use IEEE.numeric_std.all; library work; use work.RV01_CONSTS_PKG.all; use work.RV01_TYPES_PKG.all; use work.RV01_FUNCS_PKG.all; use work.RV01_IDEC_PKG.all; entity RV01_RESMUX_IX2 is generic( PXE : std_logic := '1'; DXE : std_logic := '1'; NW : natural := 2 ); port( OPA0_V_i : in std_logic; OPA1_V_i : in std_logic; OPA0_i : in SDWORD_T; OPA1_i : in SDWORD_T; OPB0_V_i : in std_logic; OPB1_V_i : in std_logic; OPB0_i : in SDWORD_T; OPB1_i : in SDWORD_T; DRD0_V_i : in std_logic; DRD1_V_i : in std_logic; DRD0_i : in SDWORD_T; DRD1_i : in SDWORD_T; DDAT0_i : in std_logic_vector(SDLEN-1 downto 0); DDAT1_i : in std_logic_vector(SDLEN-1 downto 0); PA0_ALU_RES_i : in SDWORD_T; PA1_ALU_RES_i : in SDWORD_T; PB0_RES_i : in SDWORD_T; PC1P4_i : in unsigned(SDLEN-1 downto 0); PASEL0_i : in std_logic_vector(4-1 downto 0); PASEL1_i : in std_logic_vector(4-1 downto 0); FWDE_i : in std_logic_vector(NW-1 downto 0); INSTR_i : in DEC_INSTR_VEC_T(NW-1 downto 0); IX3_DRD0_i : in SDWORD_T; IX3_DRD1_i : in SDWORD_T; IX3_V_i : in std_logic_vector(NW-1 downto 0); IX3_INSTR_i : in DEC_INSTR_VEC_T(NW-1 downto 0); FWDX_o : out std_logic_vector(NW-1 downto 0); PA0_RES_o : out SDWORD_T; PA1_RES_o : out SDWORD_T; OPA0_V_o : out std_logic; OPA1_V_o : out std_logic; OPA0_o : out SDWORD_T; OPA1_o : out SDWORD_T; OPB0_V_o : out std_logic; OPB1_V_o : out std_logic; OPB0_o : out SDWORD_T; OPB1_o : out SDWORD_T; DRD0_o : out SDWORD_T; DRD1_o : out SDWORD_T ); end RV01_RESMUX_IX2; architecture ARC of RV01_RESMUX_IX2 is component RV01_PIPE_A_RMX_X2 is generic( NW : natural := 2 ); port( OPA_V_i : in std_logic; OPB_V_i : in std_logic; OPA_i : in SDWORD_T; OPB_i : in SDWORD_T; INSTR_i : in DEC_INSTR_T; IX3_V_i : in std_logic_vector(NW-1 downto 0); IX3_INSTR_i : in DEC_INSTR_VEC_T(NW-1 downto 0); IX3_RES0_i : in SDWORD_T; IX3_RES1_i : in SDWORD_T; OPA_V_o : out std_logic; OPB_V_o : out std_logic; OPA_o : out SDWORD_T; OPB_o : out SDWORD_T ); end component; signal PA0_RES : SDWORD_T; signal PA1_RES : SDWORD_T; signal NOLD0_RES : SDWORD_T; signal NOLD1_RES : SDWORD_T; begin ------------------------------------------- -- Delayed execution disabled ------------------------------------------- GDX2_0 : if(DXE = '0') generate PA0_RES <= to_signed(DDAT0_i) when (PASEL0_i(3) = '1') else DRD0_i; GPX_0_1 : if(PXE = '1') generate PA1_RES <= to_signed(DDAT1_i) when (PASEL1_i(3) = '1') else DRD1_i; end generate; -- GPX_0_1 GPX_0_0 : if(PXE = '0') generate PA1_RES <= (others => '0'); end generate; -- GPX_0_0 -- Pipe #0 result can be provided by pipe-A #0 or pipe-B. DRD0_o <= to_signed(DDAT0_i) when (PASEL0_i(3) = '1' and FWDE_i(0) = '1') else DRD0_i when DRD0_V_i = '1' else PB0_RES_i; -- Pipe #1 result can be provided by pipe-A #0 or -- by jal/jalr return address (for slot #0 this is -- supplied by pipe-B). GPX_1_1 : if(PXE = '1') generate DRD1_o <= to_signed(DDAT1_i) when (PASEL1_i(3) = '1' and FWDE_i(1) = '1') else DRD1_i when DRD1_V_i = '1' else to_signed(PC1P4_i); end generate; -- GPX_1_1 GPX_1_0 : if(PXE = '0') generate DRD1_o <= (others => '0'); end generate; -- GPX_1_0 OPA0_V_o <= '0'; OPB0_V_o <= '0'; OPA0_o <= (others => '0'); OPB0_o <= (others => '0'); OPA1_V_o <= '0'; OPB1_V_o <= '0'; OPA1_o <= (others => '0'); OPB1_o <= (others => '0'); end generate; -- GDX2_0 ------------------------------------------- -- Delayed execution enabled ------------------------------------------- GDX2_1 : if(DXE = '1') generate -- Note: IX2_PA*_RES are used for forwarding! -- Code re-written for timing optimization PA0_RES <= to_signed(DDAT0_i) when (PASEL0_i(3) = '1') else NOLD0_RES; -- "no-load" result NOLD0_RES <= PA0_ALU_RES_i when (PASEL0_i(0) = '1' or PASEL0_i(2) = '1') else DRD0_i; GPX_1_1 : if(PXE = '1') generate -- Code re-written for timing optimization PA1_RES <= to_signed(DDAT1_i) when (PASEL1_i(3) = '1') else NOLD1_RES; -- "no-load" result NOLD1_RES <= PA1_ALU_RES_i when (PASEL1_i(0) = '1' or PASEL1_i(2) = '1') else DRD1_i; end generate; -- GPX_1_1 GPX_1_0 : if(PXE = '0') generate PA1_RES <= (others => '0'); end generate; -- GPX_1_0 -- Pipe #0 result can be provided by pipe-A #0, pipe-B -- and divider unit. DRD0_o <= PA0_RES when FWDE_i(0) = '1' else DRD0_i when DRD0_V_i = '1' else PB0_RES_i; -- Pipe #1 result can be provided by pipe-A #0 or -- by jal/jalr return address (for slot #0 this is -- supplied by pipe-B). GPX_2_1 : if(PXE = '1') generate DRD1_o <= PA1_RES when FWDE_i(1) = '1' else DRD1_i when DRD1_V_i = '1' else to_signed(PC1P4_i); end generate; -- GPX_2_1 GPX_2_0 : if(PXE = '0') generate DRD1_o <= (others => '0'); end generate; -- GPX_2_0 U_PA0RMX_X2: RV01_PIPE_A_RMX_X2 generic map( NW => NW ) port map( OPA_V_i => OPA0_V_i, OPB_V_i => OPB0_V_i, OPA_i => OPA0_i, OPB_i => OPB0_i, INSTR_i => INSTR_i(0), IX3_V_i => IX3_V_i, IX3_INSTR_i => IX3_INSTR_i, IX3_RES0_i => IX3_DRD0_i, IX3_RES1_i => IX3_DRD1_i, OPA_V_o => OPA0_V_o, OPB_V_o => OPB0_V_o, OPA_o => OPA0_o, OPB_o => OPB0_o ); GPX_3_1 : if(PXE = '1') generate U_PA1RMX_X2: RV01_PIPE_A_RMX_X2 generic map( NW => NW ) port map( OPA_V_i => OPA1_V_i, OPB_V_i => OPB1_V_i, OPA_i => OPA1_i, OPB_i => OPB1_i, INSTR_i => INSTR_i(1), IX3_V_i => IX3_V_i, IX3_INSTR_i => IX3_INSTR_i, IX3_RES0_i => IX3_DRD0_i, IX3_RES1_i => IX3_DRD1_i, OPA_V_o => OPA1_V_o, OPB_V_o => OPB1_V_o, OPA_o => OPA1_o, OPB_o => OPB1_o ); end generate; -- GPX_3_1 GPX_3_0 : if(PXE = '0') generate OPA1_V_o <= '0'; OPB1_V_o <= '0'; OPA1_o <= (others => '0'); OPB1_o <= (others => '0'); end generate; -- GPX_3_0 end generate; -- GDX2_1 PA0_RES_o <= PA0_RES; PA1_RES_o <= PA1_RES; FWDX_o(0) <= '1'; FWDX_o(1) <= PXE; end ARC;