library ieee; use ieee.std_logic_1164.all; use ieee.numeric_std.all; use work.gen_pkg.all; entity alu is port ( sys_clk : in std_logic; sys_res_n : in std_logic; opcode : in alu_ops; op1 : in csigned; op2 : in csigned; op3 : out csigned; do_calc : in std_logic; ack : in std_logic; calc_done : out std_logic ); end entity alu; architecture beh of alu is type ALU_STATE is (SIDLE, SADD, SSUB, SMUL, SDIV, SDONE); signal state, state_next : ALU_STATE; signal done_intern : std_logic; begin -- sync process(sys_clk, sys_res_n) begin if sys_res_n = '0' then state <= SIDLE; elsif rising_edge(sys_clk) then state <= state_next; end if; end process; -- next state process(state, opcode, done_intern) begin -- set a default value for next state state_next <= state; -- next state berechnen case state is when SIDLE => case opcode is when ADD => state_next <= SADD; when SUB => state_next <= SSUB; when MUL => state_next <= SMUL; when DIV => state_next <= SDIV; when others => state_next <= SIDLE; end case; when SADD => if done_intern = '1' then state_next <= SDONE; end if; when SSUB => if done_intern = '1' then state_next <= SDONE; end if; when SMUL => if done_intern = '1' then state_next <= SDONE; end if; when SDIV => if done_intern = '1' then state_next <= SDONE; end if; when SDONE => if ack = '1' then state_next <= SIDLE; end if; end case; end process; -- output process(state) begin op3 <= (others => '0'); calc_done <= '0'; case state is when SIDLE => done_intern <= '0'; when SADD => op3 <= op1 + op2; done_intern <= '1'; when SSUB => op3 <= op1 - op2; done_intern <= '1'; when SMUL => op3 <= op1 * op2; done_intern <= '1'; when SDIV => op3 <= op1 / op2; done_intern <= '1'; when SDONE => done_intern <= '1'; calc_done <= '1'; end case; end process; end architecture beh;