diff options
author | 2019-03-25 23:13:40 +0100 | |
---|---|---|
committer | 2019-03-25 23:13:40 +0100 | |
commit | b380514764cf857469bae61c11143a19f79a74c5 (patch) | |
tree | 63c8012e262618f08a332da31dd714281aa2c5ed /src/devices/cpu/mips/mips1.h | |
parent | c24473ddff715ecec2e258a6eb38960cf8c8e98e (diff) |
Revert "conflict resolution (nw)"
This reverts commit c24473ddff715ecec2e258a6eb38960cf8c8e98e, reversing
changes made to 009cba4fb8102102168ef32870892438327f3705.
Diffstat (limited to 'src/devices/cpu/mips/mips1.h')
-rw-r--r-- | src/devices/cpu/mips/mips1.h | 208 |
1 files changed, 80 insertions, 128 deletions
diff --git a/src/devices/cpu/mips/mips1.h b/src/devices/cpu/mips/mips1.h index 3ae34e4b69f..d77bdef3cdb 100644 --- a/src/devices/cpu/mips/mips1.h +++ b/src/devices/cpu/mips/mips1.h @@ -9,8 +9,21 @@ class mips1core_device_base : public cpu_device { public: + // floating point coprocessor revision numbers recognised by RISC/os 4.52 and IRIX + enum fpu_rev_t : u32 + { + MIPS_R2360 = 0x0100, // MIPS R2360 Floating Point Board + MIPS_R2010 = 0x0200, // MIPS R2010 VLSI Floating Point Chip + MIPS_R2010A = 0x0310, // MIPS R2010A VLSI Floating Point Chip + MIPS_R3010 = 0x0320, // MIPS R3010 VLSI Floating Point Chip + MIPS_R3010A = 0x0330, // MIPS R3010A VLSI Floating Point Chip + MIPS_R3010Av4 = 0x0340, // MIPS R3010A VLSI Floating Point Chip + MIPS_R6010 = 0x0400, // MIPS R6010 Floating Point Chip + }; + // device configuration void set_endianness(endianness_t endianness) { m_endianness = endianness; } + void set_fpurev(u32 revision) { m_hasfpu = true; m_fpurev = revision; } // input lines template <unsigned Coprocessor> auto in_brcond() { return m_in_brcond[Coprocessor].bind(); } @@ -18,40 +31,53 @@ public: protected: mips1core_device_base(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, u32 cpurev, size_t icache_size, size_t dcache_size); - enum registers : unsigned + enum registers { - MIPS1_R0 = 0, - MIPS1_COP0 = 32, - MIPS1_F0 = 64, + // general purpose cpu registers + MIPS1_R0, MIPS1_R1, MIPS1_R2, MIPS1_R3, MIPS1_R4, MIPS1_R5, MIPS1_R6, MIPS1_R7, + MIPS1_R8, MIPS1_R9, MIPS1_R10, MIPS1_R11, MIPS1_R12, MIPS1_R13, MIPS1_R14, MIPS1_R15, + MIPS1_R16, MIPS1_R17, MIPS1_R18, MIPS1_R19, MIPS1_R20, MIPS1_R21, MIPS1_R22, MIPS1_R23, + MIPS1_R24, MIPS1_R25, MIPS1_R26, MIPS1_R27, MIPS1_R28, MIPS1_R29, MIPS1_R30, MIPS1_R31, - MIPS1_PC = 80, + // other cpu registers MIPS1_HI, MIPS1_LO, - MIPS1_FCR30, - MIPS1_FCR31, + MIPS1_PC, + + // coprocessor 0 registers + MIPS1_COP0_INDEX, // reg 0, tlb only + MIPS1_COP0_RANDOM, // reg 1, tlb only + MIPS1_COP0_ENTRYLO, // reg 2, tlb only + MIPS1_COP0_BUSCTRL, // reg 2, r3041 only + MIPS1_COP0_CONFIG, // reg 3, r3041/r3071/r3081 only + MIPS1_COP0_CONTEXT, // reg 4, tlb only + MIPS1_COP0_BADVADDR, // reg 8 + MIPS1_COP0_COUNT, // reg 9, r3041 only + MIPS1_COP0_ENTRYHI, // reg 10, tlb only + MIPS1_COP0_PORTSIZE, // reg 10, r3041 only + MIPS1_COP0_COMPARE, // reg 11, r3041 only + MIPS1_COP0_SR, // reg 12 + MIPS1_COP0_CAUSE, // reg 13 + MIPS1_COP0_EPC, // reg 14 + MIPS1_COP0_PRID, // reg 15 }; - enum exception : u32 + enum exception : int { - EXCEPTION_INTERRUPT = 0x00000000, - EXCEPTION_TLBMOD = 0x00000004, - EXCEPTION_TLBLOAD = 0x00000008, - EXCEPTION_TLBSTORE = 0x0000000c, - EXCEPTION_ADDRLOAD = 0x00000010, - EXCEPTION_ADDRSTORE = 0x00000014, - EXCEPTION_BUSINST = 0x00000018, - EXCEPTION_BUSDATA = 0x0000001c, - EXCEPTION_SYSCALL = 0x00000020, - EXCEPTION_BREAK = 0x00000024, - EXCEPTION_INVALIDOP = 0x00000028, - EXCEPTION_BADCOP = 0x0000002c, - EXCEPTION_OVERFLOW = 0x00000030, - EXCEPTION_TRAP = 0x00000034, - - EXCEPTION_BADCOP0 = 0x0000002c, - EXCEPTION_BADCOP1 = 0x1000002c, - EXCEPTION_BADCOP2 = 0x2000002c, - EXCEPTION_BADCOP3 = 0x3000002c, + EXCEPTION_INTERRUPT = 0, + EXCEPTION_TLBMOD = 1, + EXCEPTION_TLBLOAD = 2, + EXCEPTION_TLBSTORE = 3, + EXCEPTION_ADDRLOAD = 4, + EXCEPTION_ADDRSTORE = 5, + EXCEPTION_BUSINST = 6, + EXCEPTION_BUSDATA = 7, + EXCEPTION_SYSCALL = 8, + EXCEPTION_BREAK = 9, + EXCEPTION_INVALIDOP = 10, + EXCEPTION_BADCOP = 11, + EXCEPTION_OVERFLOW = 12, + EXCEPTION_TRAP = 13, }; enum cop0_reg : u8 @@ -101,29 +127,6 @@ protected: SR_COP1 = 0x20000000, // coprocessor 1 usable SR_COP2 = 0x40000000, // coprocessor 2 usable SR_COP3 = 0x80000000, // coprocessor 3 usable - - SR_KUIE = 0x0000003f, // all interrupt enable and user mode bits - SR_KUIEpc = 0x0000000f, // previous and current interrupt enable and user mode bits - SR_KUIEop = 0x0000003c, // old and previous interrupt enable and user mode bits - SR_IM = 0x0000ff00, // all interrupt mask bits - }; - - enum cause_mask : u32 - { - CAUSE_EXCCODE = 0x0000007c, // exception code - CAUSE_IPSW0 = 0x00000100, // software interrupt 0 pending - CAUSE_IPSW1 = 0x00000200, // software interrupt 1 pending - CAUSE_IPEX0 = 0x00000400, // external interrupt 0 pending - CAUSE_IPEX1 = 0x00000800, // external interrupt 1 pending - CAUSE_IPEX2 = 0x00001000, // external interrupt 2 pending - CAUSE_IPEX3 = 0x00002000, // external interrupt 3 pending - CAUSE_IPEX4 = 0x00004000, // external interrupt 4 pending - CAUSE_IPEX5 = 0x00008000, // external interrupt 5 pending - CAUSE_IP = 0x0000ff00, // interrupt pending - CAUSE_CE = 0x30000000, // co-processor error - CAUSE_BD = 0x80000000, // branch delay - - CAUSE_IPEX = 0x0000fc00, // external interrupt pending }; enum entryhi_mask : u32 @@ -155,7 +158,7 @@ protected: virtual u32 execute_max_cycles() const override { return 40; } virtual u32 execute_input_lines() const override { return 6; } virtual void execute_run() override; - virtual void execute_set_input(int inputnum, int state) override; + virtual void execute_set_input(int inputnum, int state) override { set_irq_line(inputnum, state); } // device_memory_interface overrides virtual space_config_vector memory_space_config() const override; @@ -168,18 +171,25 @@ protected: void dcache_map(address_map &map); // interrupts - void generate_exception(u32 exception, bool refill = false); + void generate_exception(int exception, bool refill = false); void check_irqs(); + void set_irq_line(int irqline, int state); // cop0 + virtual u32 get_cop0_reg(int const index); + void set_cop0_reg(int const index, u32 const data); virtual void handle_cop0(u32 const op); - virtual u32 get_cop0_reg(unsigned const reg); - virtual void set_cop0_reg(unsigned const reg, u32 const data); - // other coprocessors - virtual void handle_cop1(u32 const op); - virtual void handle_cop2(u32 const op); - virtual void handle_cop3(u32 const op); + // cop1 + void set_cop1_creg(int const index, u32 const data); + void handle_cop1(u32 const op); + + // generic coprocessor implementation + template <unsigned Coprocessor> void handle_cop(u32 const op); + template <unsigned Coprocessor> u32 get_cop_reg(int const index) { return m_cpr[Coprocessor][index]; } + template <unsigned Coprocessor> void set_cop_reg(int const index, u32 const data) { m_cpr[Coprocessor][index] = data; } + template <unsigned Coprocessor> u32 get_cop_creg(int const index) { return m_ccr[Coprocessor][index]; } + template <unsigned Coprocessor> void set_cop_creg(int const index, u32 const data) { m_ccr[Coprocessor][index] = data; } // load/store left/right opcodes void lwl(u32 const op); @@ -188,13 +198,9 @@ protected: void swr(u32 const op); // memory accessors - template <typename T, typename U> std::enable_if_t<std::is_convertible<U, std::function<void(T)>>::value, void> load(u32 address, U &&apply); - template <typename T, typename U> std::enable_if_t<std::is_convertible<U, T>::value, void> store(u32 address, U data, T mem_mask = ~T(0)); - bool fetch(u32 address, std::function<void(u32)> &&apply); - - // debug helpers - std::string debug_string(u32 string_pointer, unsigned const limit = 0); - std::string debug_string_array(u32 array_pointer); + template <typename T, typename U> std::enable_if_t<std::is_convertible<U, std::function<void(T)>>::value, void> load(u32 program_address, U &&apply); + template <typename T, typename U> std::enable_if_t<std::is_convertible<U, T>::value, void> store(u32 program_address, U data); + bool fetch(u32 program_address, std::function<void(u32)> &&apply); // address spaces const address_space_config m_program_config_be; @@ -206,16 +212,19 @@ protected: // configuration u32 m_cpurev; + bool m_hasfpu; + u32 m_fpurev; endianness_t m_endianness; // core registers u32 m_pc; - u32 m_r[32]; u32 m_hi; u32 m_lo; + u32 m_r[32]; - // cop0 registers - u32 m_cop0[32]; + // COP registers + u32 m_cpr[4][32]; + u32 m_ccr[4][32]; // internal stuff int m_icount; @@ -239,54 +248,9 @@ protected: class mips1_device_base : public mips1core_device_base { -public: - // floating point coprocessor revision numbers recognised by RISC/os 4.52 and IRIX - enum fpu_rev_t : u32 - { - MIPS_R2360 = 0x0100, // MIPS R2360 Floating Point Board - MIPS_R2010 = 0x0200, // MIPS R2010 VLSI Floating Point Chip - MIPS_R2010A = 0x0310, // MIPS R2010A VLSI Floating Point Chip - MIPS_R3010 = 0x0320, // MIPS R3010 VLSI Floating Point Chip - MIPS_R3010A = 0x0330, // MIPS R3010A VLSI Floating Point Chip - MIPS_R3010Av4 = 0x0340, // MIPS R3010A VLSI Floating Point Chip - MIPS_R6010 = 0x0400, // MIPS R6010 Floating Point Chip - }; - - void set_fpu(u32 revision, unsigned interrupt = 3) { m_fcr0 = revision; m_fpu_irq = interrupt; } - protected: mips1_device_base(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, u32 cpurev, size_t icache_size, size_t dcache_size); - enum cp1_fcr31_mask : u32 - { - FCR31_RM = 0x00000003, // rounding mode - - FCR31_FI = 0x00000004, // inexact operation flag - FCR31_FU = 0x00000008, // underflow flag - FCR31_FO = 0x00000010, // overflow flag - FCR31_FZ = 0x00000020, // divide by zero flag - FCR31_FV = 0x00000040, // invalid operation flag - - FCR31_EI = 0x00000080, // inexact operation enable - FCR31_EU = 0x00000100, // underflow enable - FCR31_EO = 0x00000200, // overflow enable - FCR31_EZ = 0x00000400, // divide by zero enable - FCR31_EV = 0x00000800, // invalid operation enable - - FCR31_CI = 0x00001000, // inexact operation cause - FCR31_CU = 0x00002000, // underflow cause - FCR31_CO = 0x00004000, // overflow cause - FCR31_CZ = 0x00008000, // divide by zero cause - FCR31_CV = 0x00010000, // invalid operation cause - FCR31_CE = 0x00020000, // unimplemented operation cause - - FCR31_C = 0x00800000, // condition - - FCR31_FM = 0x0000007c, // flag mask - FCR31_EM = 0x00000f80, // enable mask - FCR31_CM = 0x0001f000, // cause mask (except unimplemented) - }; - // device_t overrides virtual void device_start() override; virtual void device_reset() override; @@ -294,24 +258,12 @@ protected: // device_memory_interface overrides virtual bool memory_translate(int spacenum, int intention, offs_t &address) override; + virtual u32 get_cop0_reg(int idx) override; virtual void handle_cop0(u32 const op) override; - virtual u32 get_cop0_reg(unsigned const reg) override; - - virtual void handle_cop1(u32 const op) override; - virtual void set_cop1_reg(unsigned const reg, u64 const data); private: u64 m_reset_time; u32 m_tlb[64][2]; // 0 is hi, 1 is lo - unsigned m_tlb_mru[3][64]; - - // cop1 registers - u64 m_f[16]; - u32 m_fcr0; - u32 m_fcr30; - u32 m_fcr31; - - unsigned m_fpu_irq; }; class r2000_device : public mips1_device_base @@ -365,13 +317,13 @@ public: r3052e_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); }; -class r3071_device : public mips1_device_base +class r3071_device : public mips1core_device_base { public: r3071_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock, size_t icache_size = 16384, size_t dcache_size = 4096); }; -class r3081_device : public mips1_device_base +class r3081_device : public mips1core_device_base { public: r3081_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock, size_t icache_size = 16384, size_t dcache_size = 4096); |