OpenCores
URL https://opencores.org/ocsvn/cpu_lecture/cpu_lecture/trunk

Subversion Repositories cpu_lecture

[/] [cpu_lecture/] [trunk/] [src/] [opc_deco.vhd] - Diff between revs 2 and 10

Go to most recent revision | Show entire file | Details | Blame | View Log

Rev 2 Rev 10
Line 87... Line 87...
        Q_WE_F    <= '0';
        Q_WE_F    <= '0';
        Q_WE_M    <= "00";
        Q_WE_M    <= "00";
        Q_WE_XYZS <= '0';
        Q_WE_XYZS <= '0';
 
 
        case I_OPC(15 downto 10) is
        case I_OPC(15 downto 10) is
            when "000000" =>
            when "000000" =>                            -- 0000 00xx xxxx xxxx
                case I_OPC(9 downto 8) is
                case I_OPC(9 downto 8) is
                    when "00" =>
                    when "00" =>
                        --
                        --
                        -- 0000 0000 0000 0000 - NOP
                        -- 0000 0000 0000 0000 - NOP
                        -- 0000 0000 001v vvvv - INTERRUPT
                        -- 0000 0000 001v vvvv - INTERRUPT
Line 159... Line 159...
                --
                --
                Q_ALU_OP <= ALU_SBC;
                Q_ALU_OP <= ALU_SBC;
                Q_WE_D <= '0' & I_OPC(11);  -- write Rd if SBC.
                Q_WE_D <= '0' & I_OPC(11);  -- write Rd if SBC.
                Q_WE_F <= '1';
                Q_WE_F <= '1';
 
 
            when "000011" =>
            when "000011" =>                            -- 0000 11xx xxxx xxxx
                --
                --
                -- 0000 11rd dddd rrrr - ADD
                -- 0000 11rd dddd rrrr - ADD
                --
                --
                Q_ALU_OP <= ALU_ADD;
                Q_ALU_OP <= ALU_ADD;
                Q_WE_D <= "01";
                Q_WE_D <= "01";
                Q_WE_F <= '1';
                Q_WE_F <= '1';
 
 
            when "000100" => -- CPSE
            when "000100" =>                            -- 0001 00xx xxxx xxxx
                Q_ALU_OP <= ALU_SUB;
                Q_ALU_OP <= ALU_SUB;
                Q_RD_M <= I_T0;
                Q_RD_M <= I_T0;
                if (I_T0 = '0') then        -- second cycle.
                if (I_T0 = '0') then        -- second cycle.
                    Q_PC_OP <= PC_SKIP_Z;
                    Q_PC_OP <= PC_SKIP_Z;
                end if;
                end if;
Line 183... Line 183...
                --
                --
                Q_ALU_OP <= ALU_SUB;
                Q_ALU_OP <= ALU_SUB;
                Q_WE_D <= '0' & I_OPC(11);  -- write Rd if SUB.
                Q_WE_D <= '0' & I_OPC(11);  -- write Rd if SUB.
                Q_WE_F <= '1';
                Q_WE_F <= '1';
 
 
            when "000111" =>
            when "000111" =>                            -- 0001 11xx xxxx xxxx
                --
                --
                -- 0001 11rd dddd rrrr - ADC
                -- 0001 11rd dddd rrrr - ADC
                --
                --
                Q_ALU_OP <= ALU_ADC;
                Q_ALU_OP <= ALU_ADC;
                Q_WE_D <= "01";
                Q_WE_D <= "01";
                Q_WE_F <= '1';
                Q_WE_F <= '1';
 
 
            when "001000" =>
            when "001000" =>                            -- 0010 00xx xxxx xxxx
                --
                --
                -- 0010 00rd dddd rrrr - AND
                -- 0010 00rd dddd rrrr - AND
                --
                --
                Q_ALU_OP <= ALU_AND;
                Q_ALU_OP <= ALU_AND;
                Q_WE_D <= "01";
                Q_WE_D <= "01";
                Q_WE_F <= '1';
                Q_WE_F <= '1';
 
 
            when "001001" =>
            when "001001" =>                            -- 0010 01xx xxxx xxxx
                --
                --
                -- 0010 01rd dddd rrrr - EOR
                -- 0010 01rd dddd rrrr - EOR
                --
                --
                Q_ALU_OP <= ALU_EOR;
                Q_ALU_OP <= ALU_EOR;
                Q_WE_D <= "01";
                Q_WE_D <= "01";
                Q_WE_F <= '1';
                Q_WE_F <= '1';
 
 
            when "001010" => -- OR
            when "001010" =>                            -- 0010 10xx xxxx xxxx
                --
                --
                -- 0010 10rd dddd rrrr - OR
                -- 0010 10rd dddd rrrr - OR
                --
                --
                Q_ALU_OP <= ALU_OR;
                Q_ALU_OP <= ALU_OR;
                Q_WE_D <= "01";
                Q_WE_D <= "01";
                Q_WE_F <= '1';
                Q_WE_F <= '1';
 
 
            when "001011" =>
            when "001011" =>                            -- 0010 11xx xxxx xxxx
                --
                --
                -- 0010 11rd dddd rrrr - MOV
                -- 0010 11rd dddd rrrr - MOV
                --
                --
                Q_ALU_OP <= ALU_R_MV_Q;
                Q_ALU_OP <= ALU_R_MV_Q;
                Q_WE_D <= "01";
                Q_WE_D <= "01";
Line 291... Line 291...
                end if;
                end if;
 
 
                Q_RD_M <= not I_OPC(9);             -- '1'  if LDD
                Q_RD_M <= not I_OPC(9);             -- '1'  if LDD
                Q_WE_M <= '0' & I_OPC(9);           -- "01" if STD
                Q_WE_M <= '0' & I_OPC(9);           -- "01" if STD
 
 
            when "100100" =>
            when "100100" =>                            -- 1001 00xx xxxx xxxx
                Q_IMM <= I_OPC(31 downto 16);   -- absolute address for LDS/STS
                Q_IMM <= I_OPC(31 downto 16);   -- absolute address for LDS/STS
                if (I_OPC(9) = '0') then        -- LDD / POP
                if (I_OPC(9) = '0') then        -- LDD / POP
                    --
                    --
                    -- 1001 00-0d dddd 0000 - LDS
                    -- 1001 00-0d dddd 0000 - LDS
                    -- 1001 00-0d dddd 0001 - LD Rd, Z+
                    -- 1001 00-0d dddd 0001 - LD Rd, Z+
Line 357... Line 357...
                        when "1111" => Q_AMOD <= AMOD_dSP;
                        when "1111" => Q_AMOD <= AMOD_dSP;
                        when others =>
                        when others =>
                    end case;
                    end case;
                end if;
                end if;
 
 
            when "100101" =>
            when "100101" =>                            -- 1001 01xx xxxx xxxx
                if (I_OPC(9) = '0') then
                if (I_OPC(9) = '0') then                -- 1001 010
                    if (I_OPC(3) = '0') then
                    if (I_OPC(3) = '0') then            -- 1001 010x xxxx 0xxx
                        --
                        --
                        --  1001 010d dddd 0000 - COM
                        --  1001 010d dddd 0000 - COM
                        --  1001 010d dddd 0001 - NEG
                        --  1001 010d dddd 0001 - NEG
                        --  1001 010d dddd 0010 - SWAP
                        --  1001 010d dddd 0010 - SWAP
                        --  1001 010d dddd 0011 - INC
                        --  1001 010d dddd 0011 - INC
Line 381... Line 381...
                            when "111"  => Q_ALU_OP <= ALU_ROR;
                            when "111"  => Q_ALU_OP <= ALU_ROR;
                            when others =>
                            when others =>
                        end case;
                        end case;
                        Q_WE_D <= "01";
                        Q_WE_D <= "01";
                        Q_WE_F <= '1';
                        Q_WE_F <= '1';
                    else
                    else                                -- 1001 010x xxxx 1xxx
                        case I_OPC(2 downto 0) is
                        case I_OPC(2 downto 0) is
                            when "000"  =>
                            when "000"  =>              -- 1001 010x xxxx 1000
                                if (I_OPC(8)) = '0' then
                                if I_OPC(8) = '0' then  -- 1001 0100 xxxx 1000
                                    --
                                    --
                                    --  1001 0100 0sss 1000 - BSET
                                    --  1001 0100 0sss 1000 - BSET
                                    --  1001 0100 1sss 1000 - BCLR
                                    --  1001 0100 1sss 1000 - BCLR
                                    --
                                    --
                                    Q_BIT(3 downto 0) <= I_OPC(7 downto 4);
                                    Q_BIT(3 downto 0) <= I_OPC(7 downto 4);
                                    Q_ALU_OP <= ALU_SREG;
                                    Q_ALU_OP <= ALU_SREG;
                                    Q_WE_F <= '1';
                                    Q_WE_F <= '1';
                                else
                                else                    -- 1001 0101 xxxx 1000
                                    --
                                    --
                                    --  1001 0101 0000 1000 - RET
                                    --  1001 0101 0000 1000 - RET
                                    --  1001 0101 0001 1000 - RETI
                                    --  1001 0101 0001 1000 - RETI
                                    --  1001 0101 1000 1000 - SLEEP
                                    --  1001 0101 1000 1000 - SLEEP
                                    --  1001 0101 1001 1000 - BREAK
                                    --  1001 0101 1001 1000 - BREAK
Line 444... Line 444...
 
 
                                        when others =>
                                        when others =>
                                    end case;
                                    end case;
                                end if;
                                end if;
 
 
                            when "001"  =>
                            when "001" =>               -- 1001 010x xxxx 1001
                                --
                                --
                                --  1001 0100 0000 1001 IJMP
                                --  1001 0100 0000 1001 IJMP
                                --  1001 0100 0001 1001 EIJMP   -- not mega8
                                --  1001 0100 0001 1001 EIJMP   -- not mega8
                                --  1001 0101 0000 1001 ICALL
                                --  1001 0101 0000 1001 ICALL
                                --  1001 0101 0001 1001 EICALL   -- not mega8
                                --  1001 0101 0001 1001 EICALL   -- not mega8
Line 459... Line 459...
                                    Q_AMOD <= AMOD_ddSP;
                                    Q_AMOD <= AMOD_ddSP;
                                    Q_WE_M <= "11";
                                    Q_WE_M <= "11";
                                    Q_WE_XYZS <= '1';
                                    Q_WE_XYZS <= '1';
                                end if;
                                end if;
 
 
                            when "010"  =>
                            when "010"  =>               -- 1001 010x xxxx 1010
                                --
                                --
                                --  1001 010d dddd 1010 - DEC
                                --  1001 010d dddd 1010 - DEC
                                --
                                --
                                Q_ALU_OP <= ALU_DEC;
                                Q_ALU_OP <= ALU_DEC;
                                Q_WE_D <= "01";
                                Q_WE_D <= "01";
                                Q_WE_F <= '1';
                                Q_WE_F <= '1';
 
 
                            when "011"  =>
                            when "011"  =>               -- 1001 010x xxxx 1011
                                --
                                --
                                --  1001 0100 KKKK 1011 - DES   -- not mega8
                                --  1001 0100 KKKK 1011 - DES   -- not mega8
                                --
                                --
 
 
                            when "100" | "101"  =>
                            when "100" | "101"  =>
Line 479... Line 479...
                                --  1001 010k kkkk 110k - JMP (k = 0 for 16 bit)
                                --  1001 010k kkkk 110k - JMP (k = 0 for 16 bit)
                                --  kkkk kkkk kkkk kkkk
                                --  kkkk kkkk kkkk kkkk
                                --
                                --
                                Q_PC_OP <= PC_LD_I;
                                Q_PC_OP <= PC_LD_I;
 
 
                            when "110" | "111"  =>
                            when "110" | "111"  =>      -- 1001 010x xxxx 111x
                                --
                                --
                                --  1001 010k kkkk 111k - CALL (k = 0)
                                --  1001 010k kkkk 111k - CALL (k = 0)
                                --  kkkk kkkk kkkk kkkk
                                --  kkkk kkkk kkkk kkkk
                                --
                                --
                                Q_ALU_OP <= ALU_PC_2;
                                Q_ALU_OP <= ALU_PC_2;
Line 493... Line 493...
                                Q_WE_XYZS <= '1';
                                Q_WE_XYZS <= '1';
 
 
                            when others =>
                            when others =>
                        end case;
                        end case;
                    end if;
                    end if;
                else
                else            -- 1001 011
                    --
                    --
                    --  1001 0110 KKdd KKKK - ADIW
                    --  1001 0110 KKdd KKKK - ADIW
                    --  1001 0111 KKdd KKKK - SBIW
                    --  1001 0111 KKdd KKKK - SBIW
                    --
                    --
                    if (I_OPC(8) = '0') then    Q_ALU_OP <= ALU_ADIW;
                    if (I_OPC(8) = '0') then    Q_ALU_OP <= ALU_ADIW;
Line 510... Line 510...
 
 
                    Q_WE_D <= "11";
                    Q_WE_D <= "11";
                    Q_WE_F <= '1';
                    Q_WE_F <= '1';
                end if; -- I_OPC(9) = 0/1
                end if; -- I_OPC(9) = 0/1
 
 
            when "100110" =>
            when "100110" =>                            -- 1001 10xx xxxx xxxx
                --
                --
                --  1001 1000 AAAA Abbb - CBI
                --  1001 1000 AAAA Abbb - CBI
                --  1001 1001 AAAA Abbb - SBIC
                --  1001 1001 AAAA Abbb - SBIC
                --  1001 1010 AAAA Abbb - SBI
                --  1001 1010 AAAA Abbb - SBI
                --  1001 1011 AAAA Abbb - SBIS
                --  1001 1011 AAAA Abbb - SBIS
Line 535... Line 535...
                    if (I_T0 = '0') then        -- second cycle.
                    if (I_T0 = '0') then        -- second cycle.
                        Q_PC_OP <= PC_SKIP_T;
                        Q_PC_OP <= PC_SKIP_T;
                    end if;
                    end if;
                end if;
                end if;
 
 
            when "100111" => -- MUL
            when "100111" =>                            -- 1001 11xx xxxx xxxx
                --
                --
                --  1001 11rd dddd rrrr - MUL
                --  1001 11rd dddd rrrr - MUL
                --
                --
                 Q_ALU_OP <= ALU_MULT;
                 Q_ALU_OP <= ALU_MULT;
                 Q_IMM(7 downto 5) <= "000"; --  -MUL UU;
                 Q_IMM(7 downto 5) <= "000"; --  -MUL UU;
                 Q_WE_01 <= '1';
                 Q_WE_01 <= '1';
                 Q_WE_F <= '1';
                 Q_WE_F <= '1';
 
 
            when "101100" | "101101" =>
            when "101100" | "101101" =>                 -- 1011 0xxx xxxx xxxx
                --
                --
                -- 1011 0AAd dddd AAAA - IN
                -- 1011 0AAd dddd AAAA - IN
                --
                --
                Q_RSEL <= RS_DIN;
                Q_RSEL <= RS_DIN;
                Q_AMOD <= AMOD_ABS;
                Q_AMOD <= AMOD_ABS;
Line 559... Line 559...
                Q_IMM(4) <= I_OPC(9);
                Q_IMM(4) <= I_OPC(9);
                Q_IMM(6 downto 5) <= "01" + ('0' & I_OPC(10 downto 10));
                Q_IMM(6 downto 5) <= "01" + ('0' & I_OPC(10 downto 10));
 
 
                Q_WE_D <= "01";
                Q_WE_D <= "01";
 
 
            when "101110" | "101111" =>
            when "101110" | "101111" =>                 -- 1011 1xxx xxxx xxxx
                --
                --
                -- 1011 1AAr rrrr AAAA - OUT
                -- 1011 1AAr rrrr AAAA - OUT
                --
                --
                Q_ALU_OP <= ALU_D_MV_Q;
                Q_ALU_OP <= ALU_D_MV_Q;
                Q_AMOD <= AMOD_ABS;
                Q_AMOD <= AMOD_ABS;
Line 604... Line 604...
                Q_RSEL <= RS_IMM;
                Q_RSEL <= RS_IMM;
                Q_DDDDD <= '1' & I_OPC(7 downto 4);     -- 16..31
                Q_DDDDD <= '1' & I_OPC(7 downto 4);     -- 16..31
                Q_IMM(7 downto 0) <= I_OPC(11 downto 8) & I_OPC(3 downto 0);
                Q_IMM(7 downto 0) <= I_OPC(11 downto 8) & I_OPC(3 downto 0);
                Q_WE_D <= "01";
                Q_WE_D <= "01";
 
 
            when "111100" | "111101" =>
            when "111100" | "111101" =>                 -- 1111 0xxx xxxx xxxx
                --
                --
                -- 1111 00kk kkkk kbbb - BRBS
                -- 1111 00kk kkkk kbbb - BRBS
                -- 1111 01kk kkkk kbbb - BRBC
                -- 1111 01kk kkkk kbbb - BRBC
                --       v
                --       v
                -- bbb: status register bit
                -- bbb: status register bit
Line 617... Line 617...
                Q_JADR <= I_PC + (I_OPC(9) & I_OPC(9) & I_OPC(9) & I_OPC(9)
                Q_JADR <= I_PC + (I_OPC(9) & I_OPC(9) & I_OPC(9) & I_OPC(9)
                                & I_OPC(9) & I_OPC(9) & I_OPC(9) & I_OPC(9)
                                & I_OPC(9) & I_OPC(9) & I_OPC(9) & I_OPC(9)
                                & I_OPC(9) & I_OPC(9 downto 3)) + X"0001";
                                & I_OPC(9) & I_OPC(9 downto 3)) + X"0001";
                Q_PC_OP <= PC_BCC;
                Q_PC_OP <= PC_BCC;
 
 
            when "111110" =>
            when "111110" =>                            -- 1111 10xx xxxx xxxx
                --
                --
                -- 1111 100d dddd 0bbb - BLD
                -- 1111 100d dddd 0bbb - BLD
                -- 1111 101d dddd 0bbb - BST
                -- 1111 101d dddd 0bbb - BST
                --
                --
                if I_OPC(9) = '0' then  -- BLD: T flag to register
                if I_OPC(9) = '0' then  -- BLD: T flag to register
Line 633... Line 633...
                    Q_IMM(4 downto 0) <= I_OPC(8 downto 4);
                    Q_IMM(4 downto 0) <= I_OPC(8 downto 4);
                    Q_ALU_OP <= ALU_BIT_CS;
                    Q_ALU_OP <= ALU_BIT_CS;
                    Q_WE_F <= '1';
                    Q_WE_F <= '1';
                end if;
                end if;
 
 
            when "111111" =>
            when "111111" =>                            -- 1111 11xx xxxx xxxx
                --
                --
                -- 1111 110r rrrr 0bbb - SBRC
                -- 1111 110r rrrr 0bbb - SBRC
                -- 1111 111r rrrr 0bbb - SBRS
                -- 1111 111r rrrr 0bbb - SBRS
                --
                --
                -- like SBIC, but and general purpose regs instead of I/O regs.
                -- like SBIC, but and general purpose regs instead of I/O regs.

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.