diff options
| author | 2026-03-02 09:25:23 +1100 | |
|---|---|---|
| committer | 2026-03-02 09:25:23 +1100 | |
| commit | 366b485b037b404a4a71f1caa77a4cacb83e17ef (patch) | |
| tree | 5a952cf72bc53d6c1032738f21725e8ae55f152e /src/devices/cpu/powerpc/ppcfe.cpp | |
| parent | ac492c02708b92ce76400214204a4fa9713d0a1a (diff) | |
Allow recompiling CPU cores to define their own opcode descriptions.
The base opcode description now only has the parts that are used by the
base recompiler front-end. CPU cores are free to define their own
extensions as they see fit without being limited to pre-defined fields.
The base recompiler front-end is now a template, eliminating the virtual
member functions. It no longer has any dependencies on libemu, which
paves the way to decoupling the recompiler front-ends and allowing the
instruction analysis to be tested without the rest of the emulator.
Also added a compile-time option to disable ASTAT flag update elision in
the SHARC recompiler, and fixed some recompiler front-end bugs.
Diffstat (limited to 'src/devices/cpu/powerpc/ppcfe.cpp')
| -rw-r--r-- | src/devices/cpu/powerpc/ppcfe.cpp | 240 |
1 files changed, 154 insertions, 86 deletions
diff --git a/src/devices/cpu/powerpc/ppcfe.cpp b/src/devices/cpu/powerpc/ppcfe.cpp index 1e8fb105ee1..1819d906ba7 100644 --- a/src/devices/cpu/powerpc/ppcfe.cpp +++ b/src/devices/cpu/powerpc/ppcfe.cpp @@ -10,41 +10,44 @@ #include "emu.h" #include "ppcfe.h" + #include "ppccom.h" +#include "cpu/drcfe.ipp" + //************************************************************************** // MACROS //************************************************************************** -#define GPR_USED(desc, x) do { (desc).regin[0] |= REGFLAG_R(x); } while (0) -#define GPR_USED_OR_ZERO(desc, x) do { (desc).regin[0] |= ((x) == 0 ? 0 : REGFLAG_R(x)); } while (0) -#define GPR_MODIFIED(desc, x) do { (desc).regout[0] |= REGFLAG_R(x); } while (0) +#define GPR_USED(desc, x) do { (desc).regin.set(REG_BIT_R0 + x); } while (0) +#define GPR_USED_OR_ZERO(desc, x) do { if (x) GPR_USED((desc), x); } while (0) +#define GPR_MODIFIED(desc, x) do { (desc).regout.set(REG_BIT_R0 + x); } while (0) -#define FPR_USED(desc, x) do { (desc).regin[1] |= REGFLAG_FR(x); } while (0) -#define FPR_MODIFIED(desc, x) do { (desc).regout[1] |= REGFLAG_FR(x); } while (0) +#define FPR_USED(desc, x) do { (desc).regin.set(REG_BIT_FR0 + x); } while (0) +#define FPR_MODIFIED(desc, x) do { (desc).regout.set(REG_BIT_FR0 + x); } while (0) -#define CR_USED(desc, x) do { (desc).regin[2] |= REGFLAG_CR(x); } while (0) -#define CR_BIT_USED(desc, x) do { (desc).regin[2] |= REGFLAG_CR_BIT(x); } while (0) -#define CR_MODIFIED(desc, x) do { (desc).regout[2] |= REGFLAG_CR(x); } while (0) -#define CR_BIT_MODIFIED(desc, x) do { (desc).regout[2] |= REGFLAG_CR_BIT(x); } while (0) +#define CR_USED(desc, x) do { CR_BIT_USED((desc), (x * 4) + 0); CR_BIT_USED((desc), (x * 4) + 1); CR_BIT_USED((desc), (x * 4) + 2); CR_BIT_USED((desc), (x * 4) + 3); } while (0) +#define CR_BIT_USED(desc, x) do { (desc).regin.set(64 + 31 - x); } while (0) +#define CR_MODIFIED(desc, x) do { CR_BIT_MODIFIED((desc), (x * 4) + 0); CR_BIT_MODIFIED((desc), (x * 4) + 1); CR_BIT_MODIFIED((desc), (x * 4) + 2); CR_BIT_MODIFIED((desc), (x * 4) + 3); } while (0) +#define CR_BIT_MODIFIED(desc, x) do { (desc).regout.set(64 + 31 - x); } while (0) -#define XER_CA_USED(desc) do { (desc).regin[3] |= REGFLAG_XER_CA; } while (0) -#define XER_OV_USED(desc) do { (desc).regin[3] |= REGFLAG_XER_OV; } while (0) -#define XER_SO_USED(desc) do { (desc).regin[3] |= REGFLAG_XER_SO; } while (0) -#define XER_COUNT_USED(desc) do { (desc).regin[3] |= REGFLAG_XER_COUNT; } while (0) -#define XER_CA_MODIFIED(desc) do { (desc).regout[3] |= REGFLAG_XER_CA; } while (0) -#define XER_OV_MODIFIED(desc) do { (desc).regout[3] |= REGFLAG_XER_OV; } while (0) -#define XER_SO_MODIFIED(desc) do { (desc).regout[3] |= REGFLAG_XER_SO; } while (0) -#define XER_COUNT_MODIFIED(desc) do { (desc).regout[3] |= REGFLAG_XER_COUNT; } while (0) +#define XER_CA_USED(desc) do { (desc).regin.set(REG_BIT_XER_CA); } while (0) +#define XER_OV_USED(desc) do { (desc).regin.set(REG_BIT_XER_OV); } while (0) +#define XER_SO_USED(desc) do { (desc).regin.set(REG_BIT_XER_SO); } while (0) +#define XER_COUNT_USED(desc) do { (desc).regin.set(REG_BIT_XER_COUNT); } while (0) +#define XER_CA_MODIFIED(desc) do { (desc).regout.set(REG_BIT_XER_CA); } while (0) +#define XER_OV_MODIFIED(desc) do { (desc).regout.set(REG_BIT_XER_OV); } while (0) +#define XER_SO_MODIFIED(desc) do { (desc).regout.set(REG_BIT_XER_SO); } while (0) +#define XER_COUNT_MODIFIED(desc) do { (desc).regout.set(REG_BIT_XER_COUNT); } while (0) -#define CTR_USED(desc) do { (desc).regin[3] |= REGFLAG_CTR; } while (0) -#define CTR_MODIFIED(desc) do { (desc).regout[3] |= REGFLAG_CTR; } while (0) -#define LR_USED(desc) do { (desc).regin[3] |= REGFLAG_LR; } while (0) -#define LR_MODIFIED(desc) do { (desc).regout[3] |= REGFLAG_LR; } while (0) +#define CTR_USED(desc) do { (desc).regin.set(REG_BIT_CTR); } while (0) +#define CTR_MODIFIED(desc) do { (desc).regout.set(REG_BIT_CTR); } while (0) +#define LR_USED(desc) do { (desc).regin.set(REG_BIT_LR); } while (0) +#define LR_MODIFIED(desc) do { (desc).regout.set(REG_BIT_LR); } while (0) -#define FPSCR_USED(desc, x) do { (desc).regin[3] |= REGFLAG_FPSCR(x); } while (0) -#define FPSCR_MODIFIED(desc, x) do { (desc).regout[3] |= REGFLAG_FPSCR(x); } while (0) +#define FPSCR_USED(desc, x) do { (desc).regin.set(REG_BIT_FPSCR0 + x); } while (0) +#define FPSCR_MODIFIED(desc, x) do { (desc).regout.set(REG_BIT_FPSCR0 + x); } while (0) @@ -57,11 +60,22 @@ //------------------------------------------------- ppc_device::frontend::frontend(ppc_device &ppc, uint32_t window_start, uint32_t window_end, uint32_t max_sequence) - : drc_frontend(ppc, window_start, window_end, max_sequence) + : drc_frontend_base(ppc.space_config(AS_PROGRAM)->page_shift(), window_start, window_end, max_sequence) , m_ppc(ppc) { } +ppc_device::frontend::~frontend() +{ +} + +ppc_device::opcode_desc const *ppc_device::frontend::describe_code(offs_t startpc) +{ + return do_describe_code( + [this] (opcode_desc &desc, opcode_desc const *prev) { return describe(desc, prev); }, + startpc); +} + //------------------------------------------------- // describe - build a description of a single @@ -70,7 +84,6 @@ ppc_device::frontend::frontend(ppc_device &ppc, uint32_t window_start, uint32_t bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) { - uint32_t op, opswitch; int regnum; // compute the physical PC @@ -78,19 +91,23 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) { // uh-oh: a page fault; leave the description empty and just if this is the first instruction, leave it empty and // mark as needing to validate; otherwise, just end the sequence here - desc.flags |= OPFLAG_VALIDATE_TLB | OPFLAG_CAN_CAUSE_EXCEPTION | OPFLAG_COMPILER_PAGE_FAULT | OPFLAG_VIRTUAL_NOOP | OPFLAG_END_SEQUENCE; + desc.set_validate_tlb(); + desc.set_can_cause_exception(); + desc.set_compiler_page_fault(); + desc.set_virtual_noop(); + desc.set_end_sequence(); return true; } // fetch the opcode - op = desc.opptr.l[0] = m_ppc.m_pr32(desc.physpc); + const uint32_t op = desc.opptr = m_ppc.m_pr32(desc.physpc); // all instructions are 4 bytes and default to a single cycle each desc.length = 4; desc.cycles = 1; // parse the instruction - opswitch = op >> 26; + const uint32_t opswitch = op >> 26; switch (opswitch) { case 0x02: // TDI - 64-bit only @@ -101,7 +118,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) case 0x03: // TWI GPR_USED(desc, G_RA(op)); - desc.flags |= OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); if (is_603_class()) desc.cycles = 2; // 603 return true; @@ -162,7 +179,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) { CR_BIT_USED(desc, G_BI(op)); // branch folding - if (prev == nullptr || prev->regout[2] == 0) + if (prev == nullptr || REGFLAG_CR(prev->regout) == 0) desc.cycles = 0; } if (!(G_BO(op) & 0x04)) @@ -173,9 +190,14 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) if (op & M_LK) LR_MODIFIED(desc); if ((G_BO(op) & 0x14) == 0x14) - desc.flags |= OPFLAG_IS_UNCONDITIONAL_BRANCH | OPFLAG_END_SEQUENCE; + { + desc.set_is_unconditional_branch(); + desc.set_end_sequence(); + } else - desc.flags |= OPFLAG_IS_CONDITIONAL_BRANCH; + { + desc.set_is_conditional_branch(); + } desc.targetpc = (int16_t)(G_BD(op) << 2) + ((op & M_AA) ? 0 : desc.pc); if (desc.targetpc == desc.pc && desc.cycles == 0) desc.cycles = 1; @@ -184,7 +206,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) case 0x11: // SC if (!(m_ppc.m_cap & (PPCCAP_OEA | PPCCAP_4XX))) return false; - desc.flags |= OPFLAG_WILL_CAUSE_EXCEPTION; + desc.set_will_cause_exception(); if (is_601_class()) desc.cycles = 16; // 601 else if (is_603_class()) @@ -196,7 +218,8 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) case 0x12: // Bx if (op & M_LK) LR_MODIFIED(desc); - desc.flags |= OPFLAG_IS_UNCONDITIONAL_BRANCH | OPFLAG_END_SEQUENCE; + desc.set_is_unconditional_branch(); + desc.set_end_sequence(); desc.targetpc = ((int32_t)(G_LI(op) << 8) >> 6) + ((op & M_AA) ? 0 : desc.pc); // branch folding if (desc.targetpc != desc.pc) @@ -263,7 +286,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) case 0x2a: // LHA GPR_USED_OR_ZERO(desc, G_RA(op)); GPR_MODIFIED(desc, G_RD(op)); - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); return true; case 0x21: // LWZU @@ -275,7 +298,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) GPR_USED(desc, G_RA(op)); GPR_MODIFIED(desc, G_RD(op)); GPR_MODIFIED(desc, G_RA(op)); - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); return true; case 0x24: // STW @@ -283,7 +306,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) case 0x2c: // STH GPR_USED_OR_ZERO(desc, G_RA(op)); GPR_USED(desc, G_RS(op)); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); return true; case 0x25: // STWU @@ -294,7 +317,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) GPR_USED(desc, G_RA(op)); GPR_USED(desc, G_RS(op)); GPR_MODIFIED(desc, G_RA(op)); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); return true; case 0x2e: // LMW @@ -305,7 +328,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) if (regnum != G_RA(op) || ((m_ppc.m_cap & PPCCAP_4XX) && regnum == 31)) GPR_MODIFIED(desc, regnum); } - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); desc.cycles = 32 - G_RD(op); return true; @@ -313,7 +336,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) GPR_USED_OR_ZERO(desc, G_RA(op)); for (regnum = G_RS(op); regnum < 32; regnum++) GPR_USED(desc, regnum); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); desc.cycles = 32 - G_RS(op); return true; @@ -323,7 +346,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) return false; GPR_USED_OR_ZERO(desc, G_RA(op)); FPR_MODIFIED(desc, G_RD(op)); - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); return true; case 0x31: // LFSU @@ -335,7 +358,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) GPR_USED(desc, G_RA(op)); GPR_MODIFIED(desc, G_RA(op)); FPR_MODIFIED(desc, G_RD(op)); - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); return true; case 0x34: // STFS @@ -344,7 +367,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) return false; GPR_USED_OR_ZERO(desc, G_RA(op)); FPR_USED(desc, G_RS(op)); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); return true; case 0x35: // STFSU @@ -356,7 +379,7 @@ bool ppc_device::frontend::describe(opcode_desc &desc, const opcode_desc *prev) GPR_USED(desc, G_RA(op)); GPR_MODIFIED(desc, G_RA(op)); FPR_USED(desc, G_RS(op)); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); return true; case 0x3b: // 0x3b group @@ -386,7 +409,7 @@ bool ppc_device::frontend::describe_13(uint32_t op, opcode_desc &desc, const opc CR_USED(desc, G_CRFS(op)); CR_MODIFIED(desc, G_CRFD(op)); // CR logical folding - if (prev == nullptr || prev->regout[2] == 0) + if (prev == nullptr || REGFLAG_CR(prev->regout) == 0) desc.cycles = 0; return true; @@ -402,9 +425,14 @@ bool ppc_device::frontend::describe_13(uint32_t op, opcode_desc &desc, const opc if (op & M_LK) LR_MODIFIED(desc); if ((G_BO(op) & 0x14) == 0x14) - desc.flags |= OPFLAG_IS_UNCONDITIONAL_BRANCH | OPFLAG_END_SEQUENCE; + { + desc.set_is_unconditional_branch(); + desc.set_end_sequence(); + } else - desc.flags |= OPFLAG_IS_CONDITIONAL_BRANCH; + { + desc.set_is_conditional_branch(); + } desc.targetpc = BRANCH_TARGET_DYNAMIC; return true; @@ -420,14 +448,18 @@ bool ppc_device::frontend::describe_13(uint32_t op, opcode_desc &desc, const opc CR_BIT_USED(desc, G_CRBB(op)); CR_BIT_MODIFIED(desc, G_CRBD(op)); // CR logical folding - if (prev == nullptr || prev->regout[2] == 0) + if (prev == nullptr || REGFLAG_CR(prev->regout) == 0) desc.cycles = 0; return true; case 0x032: // RFI if (!(m_ppc.m_cap & (PPCCAP_OEA | PPCCAP_4XX))) return false; - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CHANGE_MODES | OPFLAG_IS_UNCONDITIONAL_BRANCH | OPFLAG_END_SEQUENCE | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_is_unconditional_branch(); + desc.set_can_cause_exception(); + desc.set_end_sequence(); + desc.set_privileged(); + desc.set_can_change_modes(); desc.targetpc = BRANCH_TARGET_DYNAMIC; if (is_601_class()) desc.cycles = 13; // 601 @@ -440,7 +472,11 @@ bool ppc_device::frontend::describe_13(uint32_t op, opcode_desc &desc, const opc case 0x033: // RFCI if (!(m_ppc.m_cap & PPCCAP_4XX)) return false; - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CHANGE_MODES | OPFLAG_IS_UNCONDITIONAL_BRANCH | OPFLAG_END_SEQUENCE | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_is_unconditional_branch(); + desc.set_can_cause_exception(); + desc.set_end_sequence(); + desc.set_privileged(); + desc.set_can_change_modes(); desc.targetpc = BRANCH_TARGET_DYNAMIC; return true; @@ -460,9 +496,14 @@ bool ppc_device::frontend::describe_13(uint32_t op, opcode_desc &desc, const opc if (op & M_LK) LR_MODIFIED(desc); if ((G_BO(op) & 0x14) == 0x14) - desc.flags |= OPFLAG_IS_UNCONDITIONAL_BRANCH | OPFLAG_END_SEQUENCE; + { + desc.set_is_unconditional_branch(); + desc.set_end_sequence(); + } else - desc.flags |= OPFLAG_IS_CONDITIONAL_BRANCH; + { + desc.set_is_conditional_branch(); + } desc.targetpc = BRANCH_TARGET_DYNAMIC; return true; } @@ -523,7 +564,7 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc case 0x004: // TW GPR_USED(desc, G_RA(op)); GPR_USED(desc, G_RB(op)); - desc.flags |= OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); if (is_603_class()) desc.cycles = 2; // 603 return true; @@ -736,7 +777,7 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc GPR_USED_OR_ZERO(desc, G_RA(op)); GPR_USED(desc, G_RB(op)); GPR_MODIFIED(desc, G_RD(op)); - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); return true; case 0x018: // SLWx @@ -800,7 +841,8 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc return false; GPR_USED_OR_ZERO(desc, G_RA(op)); GPR_USED(desc, G_RB(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x037: // LWZUX @@ -813,7 +855,7 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc GPR_USED(desc, G_RB(op)); GPR_MODIFIED(desc, G_RD(op)); GPR_MODIFIED(desc, G_RA(op)); - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); return true; case 0x153: // MFSPR @@ -831,7 +873,10 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc XER_SO_USED(desc); } if (spr & 0x010) - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + { + desc.set_can_cause_exception(); + desc.set_privileged(); + } if ((m_ppc.m_cap & PPCCAP_4XX) && spr == SPR4XX_TBLU) desc.cycles = POWERPC_COUNT_READ_TBL; else if ((m_ppc.m_cap & PPCCAP_VEA) && spr == SPRVEA_TBL_R) @@ -842,20 +887,24 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc case 0x053: // MFMSR GPR_MODIFIED(desc, G_RD(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION | OPFLAG_CAN_EXPOSE_EXTERNAL_INT; + desc.set_can_cause_exception(); + desc.set_can_expose_external_int(); + desc.set_privileged(); if (is_601_class()) desc.cycles = 2; // 601 return true; case 0x253: // MFSR GPR_MODIFIED(desc, G_RD(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x293: // MFSRIN GPR_USED(desc, G_RB(op)); GPR_MODIFIED(desc, G_RD(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x173: // MFTB @@ -900,7 +949,10 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc case 0x092: // MTMSR GPR_USED(desc, G_RS(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION | OPFLAG_CAN_CHANGE_MODES | OPFLAG_END_SEQUENCE; + desc.set_can_cause_exception(); + desc.set_end_sequence(); + desc.set_privileged(); + desc.set_can_change_modes(); if (is_601_class()) desc.cycles = 17; // 601 else if (is_603_class()) @@ -911,7 +963,8 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc if (!(m_ppc.m_cap & PPCCAP_OEA)) return false; GPR_USED(desc, G_RS(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x1d3: // MTSPR @@ -929,7 +982,10 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc XER_SO_MODIFIED(desc); } if (spr & 0x010) - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + { + desc.set_can_cause_exception(); + desc.set_privileged(); + } return true; case 0x1b6: // ECOWX @@ -945,7 +1001,7 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc GPR_USED_OR_ZERO(desc, G_RA(op)); GPR_USED(desc, G_RB(op)); GPR_USED(desc, G_RS(op)); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); return true; case 0x0b7: // STWUX @@ -957,7 +1013,7 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc GPR_USED(desc, G_RB(op)); GPR_USED(desc, G_RS(op)); GPR_MODIFIED(desc, G_RA(op)); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); return true; case 0x0f2: // MTSRIN @@ -965,27 +1021,31 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc return false; GPR_USED(desc, G_RS(op)); GPR_USED(desc, G_RB(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x132: // TLBIE if (!(m_ppc.m_cap & PPCCAP_OEA)) return false; GPR_USED(desc, G_RB(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x172: // TLBIA if (!(m_ppc.m_cap & PPCCAP_OEA) || (m_ppc.m_cap & PPCCAP_603_MMU)) return false; - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x3d2: // TLBLD case 0x3f2: // TLBLI if (!(m_ppc.m_cap & PPCCAP_603_MMU) && !is_602_class()) return false; - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x200: // MCRXR @@ -1004,7 +1064,7 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc XER_COUNT_USED(desc); for (regnum = 0; regnum < 32; regnum++) GPR_MODIFIED(desc, regnum); - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); return true; case 0x217: // LFSX @@ -1014,13 +1074,14 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc GPR_USED_OR_ZERO(desc, G_RA(op)); GPR_USED(desc, G_RB(op)); FPR_MODIFIED(desc, G_RD(op)); - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); return true; case 0x236: // TLBSYNC if (!(m_ppc.m_cap & PPCCAP_OEA)) return false; - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x256: // SYNC @@ -1041,14 +1102,14 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc GPR_USED(desc, G_RB(op)); GPR_MODIFIED(desc, G_RA(op)); FPR_MODIFIED(desc, G_RD(op)); - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); return true; case 0x255: // LSWI GPR_USED_OR_ZERO(desc, G_RA(op)); for (regnum = 0; regnum < ((G_NB(op) - 1) & 0x1f) + 1; regnum += 4) GPR_MODIFIED(desc, (G_RD(op) + regnum / 4) % 32); - desc.flags |= OPFLAG_READS_MEMORY; + desc.set_reads_memory(); desc.cycles = (((G_NB(op) - 1) & 0x1f) + 1 + 3) / 4; return true; @@ -1058,14 +1119,14 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc XER_COUNT_USED(desc); for (regnum = 0; regnum < 32; regnum++) GPR_USED(desc, regnum); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); return true; case 0x2d5: // STSWI GPR_USED_OR_ZERO(desc, G_RA(op)); for (regnum = 0; regnum < ((G_NB(op) - 1) & 0x1f) + 1; regnum += 4) GPR_USED(desc, (G_RD(op) + regnum / 4) % 32); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); desc.cycles = (((G_NB(op) - 1) & 0x1f) + 1 + 3) / 4; return true; @@ -1077,7 +1138,7 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc GPR_USED_OR_ZERO(desc, G_RA(op)); GPR_USED(desc, G_RB(op)); FPR_USED(desc, G_RS(op)); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); return true; case 0x2b7: // STFSUX @@ -1090,7 +1151,7 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc GPR_USED(desc, G_RB(op)); GPR_MODIFIED(desc, G_RA(op)); FPR_USED(desc, G_RS(op)); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); return true; case 0x338: // SRAWIx @@ -1109,7 +1170,7 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc return false; GPR_USED_OR_ZERO(desc, G_RA(op)); GPR_USED(desc, G_RB(op)); - desc.flags |= OPFLAG_WRITES_MEMORY; + desc.set_writes_memory(); return true; case 0x106: // ICBT @@ -1119,7 +1180,8 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc return false; GPR_USED_OR_ZERO(desc, G_RA(op)); GPR_USED(desc, G_RB(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x1e6: // DCREAD @@ -1129,42 +1191,48 @@ bool ppc_device::frontend::describe_1f(uint32_t op, opcode_desc &desc, const opc GPR_USED_OR_ZERO(desc, G_RA(op)); GPR_USED(desc, G_RB(op)); GPR_MODIFIED(desc, G_RT(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x143: // MFDCR if (!(m_ppc.m_cap & PPCCAP_4XX)) return false; GPR_MODIFIED(desc, G_RD(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION; + desc.set_can_cause_exception(); + desc.set_privileged(); return true; case 0x1c3: // MTDCR if (!(m_ppc.m_cap & PPCCAP_4XX)) return false; GPR_USED(desc, G_RS(op)); - desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION | OPFLAG_CAN_EXPOSE_EXTERNAL_INT; + desc.set_can_cause_exception(); + desc.set_can_expose_external_int(); + desc.set_privileged(); return true; case 0x083: // WRTEE if (!(m_ppc.m_cap & PPCCAP_4XX)) return false; GPR_USED(desc, G_RS(op)); - desc.flags |= OPFLAG_CAN_EXPOSE_EXTERNAL_INT; + desc.set_can_expose_external_int(); return true; case 0x0a3: // WRTEEI if (!(m_ppc.m_cap & PPCCAP_4XX)) return false; if (op & MSR_EE) - desc.flags |= OPFLAG_CAN_EXPOSE_EXTERNAL_INT; + desc.set_can_expose_external_int(); return true; case 0x254: // ESA case 0x274: // DSA if (!is_602_class()) return false; - desc.flags |= OPFLAG_CAN_CHANGE_MODES | OPFLAG_CAN_CAUSE_EXCEPTION | OPFLAG_END_SEQUENCE; + desc.set_can_cause_exception(); + desc.set_end_sequence(); + desc.set_can_change_modes(); return true; case 0x14b: // DIV (POWER) |
