📄 fpu.vhd
字号:
-- Exponent (-126 to 127 with a bias of 127) -- Physical 0/logical -127 is reserved for zero/denormalized ex_ExpA_1 <= ex_a(IEEE754_SINGLE_EXP_POS); ex_ExpB_1 <= ex_b(IEEE754_SINGLE_EXP_POS); -- Mantissa/Fraction ex_MantA_1 <= ex_a(IEEE754_SINGLE_MANT_POS); ex_MantB_1 <= ex_b(IEEE754_SINGLE_MANT_POS); ----------------------------------------------------------------------------- -- Stage 2 -- Determine the difference in exponents and which value is greater ----------------------------------------------------------------------------- -- Are the mantissas zero --ex_MantA_Zero_2_cmb <= (ex_MantA_1 = FPU_MANT_ZERO); --ex_MantB_Zero_2_cmb <= (ex_MantB_1 = FPU_MANT_ZERO); ex_MantA_Zero_2 : carry_compare_const generic map ( C_TARGET => C_TARGET, Size => ex_MantA_1'length, B_Vec => FPU_MANT_ZERO) port map ( A_Vec => ex_MantA_1, Carry_In => '1', Carry_Out => ex_MantA_Zero_2_cmb_s); ex_MantA_Zero_2_cmb <= (ex_MantA_Zero_2_cmb_s = '1'); ex_MantB_Zero_2 : carry_compare_const generic map ( C_TARGET => C_TARGET, Size => ex_MantB_1'length, B_Vec => FPU_MANT_ZERO) port map ( A_Vec => ex_MantB_1, Carry_In => '1', Carry_Out => ex_MantB_Zero_2_cmb_s); ex_MantB_Zero_2_cmb <= (ex_MantB_Zero_2_cmb_s = '1'); -- Are the exponents zero ex_ExpA_Zero_2_cmb <= (ex_ExpA_1 = FPU_EXP_ZERO); ex_ExpB_Zero_2_cmb <= (ex_ExpB_1 = FPU_EXP_ZERO); -- Are the exponents all ones ex_ExpA_Ones_2_cmb <= (ex_ExpA_1 = FPU_EXP_ONES); ex_ExpB_Ones_2_cmb <= (ex_ExpB_1 = FPU_EXP_ONES); ----------------------------------------------------------------------------- -- For addition and subtraction -- -- Doing a compare and absolute on the exponents -- Doing a subtract (ExpB_1 - ExpA_1) ----------------------------------------------------------------------------- ---------------------------------------- -- ex_Exp_AsubB_PROC -- Subtract the exponents -- Old name: Exp_Diff_1 ---------------------------------------- ex_Exp_AsubB_PROC : process (ex_ExpA_1, ex_ExpB_1) is variable temp_1 : Exp_Plus2_T; variable temp_2 : Exp_Plus2_T; begin -- process ex_Exp_AsubB_PROC temp_1 := "00" & ex_ExpA_1; temp_2 := "00" & ex_ExpB_1; ex_Exp_AsubB_2_i <= std_logic_vector(unsigned(temp_1) - unsigned(temp_2)); end process ex_Exp_AsubB_PROC; ex_Exp_AsubB_2_cmb <= ex_Exp_AsubB_2_i(ex_Exp_AsubB_2_i'left+2 to ex_Exp_AsubB_2_i'right); -- Is exponent B greater than A? -- Exp_Sub_Carry(0) = '0' ex_Exp_BgtA_2_cmb <= (ex_Exp_AsubB_2_i(ex_Exp_AsubB_2_i'left) = '1'); -- Are the exponents equal? -- Exp_Equal_Carry(0) = '1' -- ex_Exp_Equal_2_cmb <= (ex_ExpA_1 = ex_ExpB_1); ex_Exp_Equal_2 : carry_compare generic map ( C_TARGET => C_TARGET, Size => ex_ExpA_1'length) port map ( A_Vec => ex_ExpA_1, B_Vec => ex_ExpB_1, Carry_In => '1', Carry_Out => ex_Exp_Equal_2_cmb_s); ex_Exp_Equal_2_cmb <= (ex_Exp_Equal_2_cmb_s = '1'); -- Absolute value of subtract -- Abs(ex_ExpA_1 - ex_ExpB_1); -- Align_1 -- Need the extra bits in ex_Exp_AsubB_2_i ex_Exp_absAsubB_2_cmb_i <= std_logic_vector(abs(signed(ex_Exp_AsubB_2_i))); ex_Exp_absAsubB_2_cmb <= ex_Exp_absAsubB_2_cmb_i(ex_Exp_AsubB_2_i'left+2 to ex_Exp_AsubB_2_i'right); -- Subtract the mantissas -- Mant_Sub_Res -- ex_Mant_AsubB_2_cmb <= std_logic_vector(unsigned(ex_MantA_1) - unsigned(ex_MantB_1)); -- Is mantissa B greater than A? -- ex_Mant_BgtA_2_cmb <= (ex_Mant_AsubB_2_cmb(ex_Mant_AsubB_2_cmb'left) = '1'); ex_Mant_BgtA_2_cmb <= unsigned(ex_MantB_1) > unsigned(ex_MantA_1); -- Are the mantissas and exponents equal? -- Mant_Sub_Is_Zero -- Is the subtract 0 -- ex_Mant_Equal_2_cmb <= (ex_MantA_1 = ex_MantB_1); -- ex_Exp_Mant_Equal_2_cmb <= (ex_MantA_1 = ex_MantB_1) and ex_Exp_Equal_2_cmb; ex_Exp_Mant_Equal_2 : carry_compare generic map ( C_TARGET => C_TARGET, Size => ex_MantA_1'length) port map ( A_Vec => ex_MantA_1, B_Vec => ex_MantB_1, Carry_In => ex_Exp_Equal_2_cmb_s, Carry_Out => ex_Exp_Mant_Equal_2_cmb_s); ex_Exp_Mant_Equal_2_cmb <= (ex_Exp_Mant_Equal_2_cmb_s = '1'); -- Is B greater than A (ignoring sign)? ex_absBgtA_2_cmb <= (ex_Exp_Equal_2_cmb and ex_Mant_BgtA_2_cmb) or (not ex_Exp_Equal_2_cmb and ex_Exp_BgtA_2_cmb); -- Is either operand zero? ex_A_Zero_2_cmb <= ex_ExpA_Zero_2_cmb and ex_MantA_Zero_2_cmb; ex_B_Zero_2_cmb <= ex_ExpB_Zero_2_cmb and ex_MantB_Zero_2_cmb; -- Is either operand a Nan? ex_A_NaN_2_cmb <= ex_ExpA_Ones_2_cmb and not ex_MantA_Zero_2_cmb; ex_B_NaN_2_cmb <= ex_ExpB_Ones_2_cmb and not ex_MantB_Zero_2_cmb; ----------------------------------------------------------------------------- -- MEM Stage -- extra cycles are spent here ----------------------------------------------------------------------------- ---------------------------------------- -- MEM_ADD_Op_REG -- MEM stage 2 is add operation? ---------------------------------------- MEM_ADD_Op_2_REG : process (Clk) is begin -- process MEM_ADD_Op_2_REG if Clk'event and Clk = '1' then if Reset = '1' then mem_add_op_2 <= false; elsif EX_PipeRun and EX_Start_FPU then mem_add_op_2 <= ex_add_op; end if; end if; end process MEM_ADD_Op_2_REG; ---------------------------------------- -- MEM_SUB_Op_REG -- MEM stage 2 is subtract operation? ---------------------------------------- MEM_SUB_Op_2_REG : process (Clk) is begin -- process MEM_SUB_Op_2_REG if Clk'event and Clk = '1' then if Reset = '1' then mem_sub_op_2 <= false; elsif EX_PipeRun and EX_Start_FPU then mem_sub_op_2 <= ex_sub_op; end if; end if; end process MEM_SUB_Op_2_REG; ---------------------------------------- -- MEM_ADDSUB_Sel_REG -- MEM stage 2 is add or subtract operation? ---------------------------------------- MEM_ADDSUB_Sel_2_REG : process (Clk) is begin -- process MEM_ADDSUB_Sel_2_REG if Clk'event and Clk = '1' then if Reset = '1' then mem_addsub_sel_2 <= '0'; elsif EX_PipeRun and EX_Start_FPU then -- FPU_OP_ADDSUB_POS: 1 for subtract mem_addsub_sel_2 <= ex_fpu_op_1(FPU_OP_ADDSUB_POS); end if; end if; end process MEM_ADDSUB_Sel_2_REG; ---------------------------------------- -- MEM_CMP_Op_REG -- MEM stage 2 is compare operation? ---------------------------------------- MEM_CMP_Op_2_REG : process (Clk) is begin -- process MEM_CMP_Op_2_REG if Clk'event and Clk = '1' then if Reset = '1' then mem_cmp_op_2 <= false; elsif EX_PipeRun and EX_Start_FPU then mem_cmp_op_2 <= ex_cmp_op; end if; end if; end process MEM_CMP_Op_2_REG; ---------------------------------------- -- MEM_CMP_Cond_REG -- MEM stage 2 comparison condition ---------------------------------------- MEM_CMP_Cond_2_REG : process (Clk) is begin -- process MEM_CMP_Cond_2_REG if Clk'event and Clk = '1' then if Reset = '1' then mem_cmp_cond_2 <= (others => '0'); elsif EX_PipeRun and EX_Start_FPU then mem_cmp_cond_2 <= EX_FPU_Cond; end if; end if; end process MEM_CMP_Cond_2_REG; ---------------------------------------- -- MEM_MUL_Op_2_REG -- MEM stage 2 is multiply operation? ---------------------------------------- MEM_MUL_Op_2_REG : process (Clk) is begin -- process MEM_MUL_Op_2_REG if Clk'event and Clk = '1' then if Reset = '1' then mem_mul_op_2 <= false; elsif EX_PipeRun and EX_Start_FPU then mem_mul_op_2 <= ex_mul_op; end if; end if; end process MEM_MUL_Op_2_REG; ---------------------------------------- -- MEM_DIV_Op_2_REG -- MEM stage 2 is divide operation? ---------------------------------------- MEM_DIV_Op_2_REG : process (Clk) is begin -- process MEM_DIV_Op_2_REG if Clk'event and Clk = '1' then if Reset = '1' then mem_div_op_2 <= false; mem_sqrt_op_2 <= false; mem_flt_op_2 <= false; mem_int_op_2 <= false; mem_float_operation_2 <= false; elsif EX_PipeRun and EX_Start_FPU then mem_float_operation_2 <= EX_Start_FPU; mem_div_op_2 <= ex_div_op; mem_sqrt_op_2 <= ex_sqrt_op; mem_flt_op_2 <= ex_flt_op; mem_int_op_2 <= ex_int_op; end if; end if; end process MEM_DIV_Op_2_REG; ---------------------------------------- -- MEM_Sign_2_REG -- MEM stage 2 signs ---------------------------------------- MEM_Sign_2_REG : process (Clk) is begin -- process MEM_Sign_2_REG if Clk'event and Clk = '1' then if Reset = '1' then mem_SignA_2 <= '0'; mem_SignB_2 <= '0'; elsif EX_PipeRun then mem_SignA_2 <= ex_SignA_1; mem_SignB_2 <= ex_SignB_1; end if; end if; end process MEM_Sign_2_REG; ---------------------------------------- -- MEM_Stage2_Exp_absAsubB_REG -- MEM stage exponents --- abs(A - B) -- Old name: Align_2 ---------------------------------------- MEM_Stage2_Exp_absAsubB_REG : process (Clk) is begin -- MEM_Stage2_Exp_absAsubB_REG if Clk'event and Clk = '1' then -- rising clock edge if Reset = '1' then mem_Exp_absAsubB_2 <= (others => '0'); elsif (EX_PipeRun) then mem_Exp_absAsubB_2 <= ex_Exp_absAsubB_2_cmb; end if; end if; end process MEM_Stage2_Exp_absAsubB_REG; ---------------------------------------- -- Stage2_Mant -- Add the implicit bit ---------------------------------------- Stage2_Mant_Implicit : process (Clk) is begin -- process Stage2_Mant if Clk'event and Clk = '1' then -- rising clock edge if Reset = '1' then mem_MantA_2 <= (others => '0'); mem_MantB_2 <= (others => '0'); elsif (EX_PipeRun) then mem_MantA_2(mem_MantA_2'left+1 to mem_MantA_2'right) <= ex_MantA_1; mem_MantB_2(mem_MantB_2'left+1 to mem_MantB_2'right) <= ex_MantB_1; -- FPU_MANT_IMPL_POS if (ex_ExpA_Zero_2_cmb) then mem_MantA_2(mem_MantA_2'left) <= '0'; else mem_MantA_2(mem_MantA_2'left) <= '1'; end if; if (ex_ExpB_Zero_2_cmb) then mem_MantB_2(mem_MantB_2'left) <= '0'; else mem_MantB_2(mem_MantB_2'left) <= '1'; end if; end if; end if; end process Stage2_Mant_Implicit; ---------------------------------------- -- Stage2_Input_Types -- Determine input operand types: -- NaN, denormalized, infinity, zero ---------------------------------------- Stage2_Input_Types : process (clk) is begin -- process Stage2_Types if Clk'event and Clk = '1' then -- rising clock edge if Reset = '1' then mem_QNanA_2 <= false; mem_QNanB_2 <= false; mem_SNanA_2 <= false; mem_SNanB_2 <= false; mem_DeNormA_2 <= false; mem_DeNormB_2 <= false; mem_InfA_2 <= false; mem_InfB_2 <= false; mem_ZeroA_2 <= false; mem_ZeroB_2 <= false; elsif (EX_PipeRun) then
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -