Previous 199869 Revisions Next

r31143 Monday 30th June, 2014 at 20:38:12 UTC by Wilbert Pol
powerpc: Modernised cpu core (nw)
[src/emu/cpu/powerpc]ppc.c ppc.h ppccom.c ppccom.h ppcdrc.c ppcfe.c ppcfe.h
[src/emu/drivers]testcpu.c
[src/mame/drivers]cobra.c firebeat.c gticlub.c hornet.c konamim2.c model3.c nwk-tr.c taitopjc.c taitotz.c triforce.c ultrsprt.c viper.c zr107.c
[src/mess/drivers]dm7000.c
[src/mess/includes]dm7000.h

trunk/src/emu/cpu/powerpc/ppcfe.c
r31142r31143
5656//  ppc_frontend - constructor
5757//-------------------------------------------------
5858
59ppc_frontend::ppc_frontend(powerpc_state &state, UINT32 window_start, UINT32 window_end, UINT32 max_sequence)
60   : drc_frontend(*state.device, window_start, window_end, max_sequence),
61      m_context(state)
59ppc_frontend::ppc_frontend(ppc_device *ppc, UINT32 window_start, UINT32 window_end, UINT32 max_sequence)
60   : drc_frontend(*ppc, window_start, window_end, max_sequence),
61   m_ppc(ppc)
6262{
6363}
6464
r31142r31143
7474   int regnum;
7575
7676   // compute the physical PC
77   if (!ppccom_translate_address(&m_context, AS_PROGRAM, TRANSLATE_FETCH, &desc.physpc))
77   if (!m_ppc->memory_translate(AS_PROGRAM, TRANSLATE_FETCH, desc.physpc))
7878   {
7979      // uh-oh: a page fault; leave the description empty and just if this is the first instruction, leave it empty and
8080      // mark as needing to validate; otherwise, just end the sequence here
r31142r31143
8383   }
8484
8585   // fetch the opcode
86   op = desc.opptr.l[0] = m_context.direct->read_decrypted_dword(desc.physpc, m_context.codexor);
86   op = desc.opptr.l[0] = m_ppc->m_direct->read_decrypted_dword(desc.physpc, m_ppc->m_codexor);
8787
8888   // all instructions are 4 bytes and default to a single cycle each
8989   desc.length = 4;
r31142r31143
172172         return true;
173173
174174      case 0x11:  // SC
175         if (!(m_context.cap & (PPCCAP_OEA | PPCCAP_4XX)))
175         if (!(m_ppc->m_cap & (PPCCAP_OEA | PPCCAP_4XX)))
176176            return false;
177177         desc.flags |= OPFLAG_WILL_CAUSE_EXCEPTION;
178178         if (is_601_class())
r31142r31143
305305
306306      case 0x30:  // LFS
307307      case 0x32:  // LFD
308         if (!(m_context.cap & PPCCAP_FPU))
308         if (!(m_ppc->m_cap & PPCCAP_FPU))
309309            return false;
310310         GPR_USED_OR_ZERO(desc, G_RA(op));
311311         FPR_MODIFIED(desc, G_RD(op));
r31142r31143
314314
315315      case 0x31:  // LFSU
316316      case 0x33:  // LFDU
317         if (!(m_context.cap & PPCCAP_FPU))
317         if (!(m_ppc->m_cap & PPCCAP_FPU))
318318            return false;
319319         if (G_RA(op) == 0)
320320            return false;
r31142r31143
326326
327327      case 0x34:  // STFS
328328      case 0x36:  // STFD
329         if (!(m_context.cap & PPCCAP_FPU))
329         if (!(m_ppc->m_cap & PPCCAP_FPU))
330330            return false;
331331         GPR_USED_OR_ZERO(desc, G_RA(op));
332332         FPR_USED(desc, G_RS(op));
r31142r31143
335335
336336      case 0x35:  // STFSU
337337      case 0x37:  // STFDU
338         if (!(m_context.cap & PPCCAP_FPU))
338         if (!(m_ppc->m_cap & PPCCAP_FPU))
339339            return false;
340340         if (G_RA(op) == 0)
341341            return false;
r31142r31143
411411         return true;
412412
413413      case 0x032: // RFI
414         if (!(m_context.cap & (PPCCAP_OEA | PPCCAP_4XX)))
414         if (!(m_ppc->m_cap & (PPCCAP_OEA | PPCCAP_4XX)))
415415            return false;
416416         desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CHANGE_MODES | OPFLAG_IS_UNCONDITIONAL_BRANCH | OPFLAG_END_SEQUENCE | OPFLAG_CAN_CAUSE_EXCEPTION;
417417         desc.targetpc = BRANCH_TARGET_DYNAMIC;
r31142r31143
424424         return true;
425425
426426      case 0x033: // RFCI
427         if (!(m_context.cap & PPCCAP_4XX))
427         if (!(m_ppc->m_cap & PPCCAP_4XX))
428428            return false;
429429         desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CHANGE_MODES | OPFLAG_IS_UNCONDITIONAL_BRANCH | OPFLAG_END_SEQUENCE | OPFLAG_CAN_CAUSE_EXCEPTION;
430430         desc.targetpc = BRANCH_TARGET_DYNAMIC;
431431         return true;
432432
433433      case 0x096: // ISYNC
434         if (!(m_context.cap & (PPCCAP_VEA | PPCCAP_4XX)))
434         if (!(m_ppc->m_cap & (PPCCAP_VEA | PPCCAP_4XX)))
435435            return false;
436436         if (is_601_class())
437437            desc.cycles = 6;    // 601
r31142r31143
709709         return true;
710710
711711      case 0x136: // ECIWX
712         if (!(m_context.cap & PPCCAP_VEA))
712         if (!(m_ppc->m_cap & PPCCAP_VEA))
713713            return false;
714714      case 0x014: // LWARX
715715      case 0x017: // LWZX
r31142r31143
774774      case 0x116: // DCBT
775775      case 0x2f6: // DCBA
776776      case 0x3d6: // ICBI
777         if (!(m_context.cap & (PPCCAP_VEA | PPCCAP_4XX)))
777         if (!(m_ppc->m_cap & (PPCCAP_VEA | PPCCAP_4XX)))
778778            return false;
779779         GPR_USED_OR_ZERO(desc, G_RA(op));
780780         GPR_USED(desc, G_RB(op));
781781         return true;
782782
783783      case 0x1d6: // DCBI
784         if (!(m_context.cap & (PPCCAP_OEA | PPCCAP_4XX)))
784         if (!(m_ppc->m_cap & (PPCCAP_OEA | PPCCAP_4XX)))
785785            return false;
786786         GPR_USED_OR_ZERO(desc, G_RA(op));
787787         GPR_USED(desc, G_RB(op));
r31142r31143
817817         }
818818         if (spr & 0x010)
819819            desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION;
820         if ((m_context.cap & PPCCAP_4XX) && spr == SPR4XX_TBLU)
820         if ((m_ppc->m_cap & PPCCAP_4XX) && spr == SPR4XX_TBLU)
821821            desc.cycles = POWERPC_COUNT_READ_TBL;
822         else if ((m_context.cap & PPCCAP_VEA) && spr == SPRVEA_TBL_R)
822         else if ((m_ppc->m_cap & PPCCAP_VEA) && spr == SPRVEA_TBL_R)
823823            desc.cycles = POWERPC_COUNT_READ_TBL;
824         else if ((m_context.cap & PPCCAP_OEA) && spr == SPROEA_DEC)
824         else if ((m_ppc->m_cap & PPCCAP_OEA) && spr == SPROEA_DEC)
825825            desc.cycles = POWERPC_COUNT_READ_DEC;
826826         return true;
827827
r31142r31143
844844         return true;
845845
846846      case 0x173: // MFTB
847         if (!(m_context.cap & PPCCAP_VEA))
847         if (!(m_ppc->m_cap & PPCCAP_VEA))
848848            return false;
849849         GPR_MODIFIED(desc, G_RD(op));
850850         spr = compute_spr(G_SPR(op));
r31142r31143
893893         return true;
894894
895895      case 0x0d2: // MTSR
896         if (!(m_context.cap & PPCCAP_OEA))
896         if (!(m_ppc->m_cap & PPCCAP_OEA))
897897            return false;
898898         GPR_USED(desc, G_RS(op));
899899         desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION;
r31142r31143
918918         return true;
919919
920920      case 0x1b6: // ECOWX
921         if (!(m_context.cap & PPCCAP_VEA))
921         if (!(m_ppc->m_cap & PPCCAP_VEA))
922922            return false;
923923      case 0x096: // STWCX.
924924      case 0x097: // STWX
r31142r31143
945945         return true;
946946
947947      case 0x0f2: // MTSRIN
948         if (!(m_context.cap & PPCCAP_OEA))
948         if (!(m_ppc->m_cap & PPCCAP_OEA))
949949            return false;
950950         GPR_USED(desc, G_RS(op));
951951         GPR_USED(desc, G_RB(op));
r31142r31143
953953         return true;
954954
955955      case 0x132: // TLBIE
956         if (!(m_context.cap & PPCCAP_OEA))
956         if (!(m_ppc->m_cap & PPCCAP_OEA))
957957            return false;
958958         GPR_USED(desc, G_RB(op));
959959         desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION;
960960         return true;
961961
962962      case 0x172: // TLBIA
963         if (!(m_context.cap & PPCCAP_OEA) || (m_context.cap & PPCCAP_603_MMU))
963         if (!(m_ppc->m_cap & PPCCAP_OEA) || (m_ppc->m_cap & PPCCAP_603_MMU))
964964            return false;
965965         desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION;
966966         return true;
967967
968968      case 0x3d2: // TLBLD
969969      case 0x3f2: // TLBLI
970         if (!(m_context.cap & PPCCAP_603_MMU) && !is_602_class())
970         if (!(m_ppc->m_cap & PPCCAP_603_MMU) && !is_602_class())
971971            return false;
972972         desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION;
973973         return true;
r31142r31143
993993
994994      case 0x217: // LFSX
995995      case 0x257: // LFDX
996         if (!(m_context.cap & PPCCAP_FPU))
996         if (!(m_ppc->m_cap & PPCCAP_FPU))
997997            return false;
998998         GPR_USED_OR_ZERO(desc, G_RA(op));
999999         GPR_USED(desc, G_RB(op));
r31142r31143
10021002         return true;
10031003
10041004      case 0x236: // TLBSYNC
1005         if (!(m_context.cap & PPCCAP_OEA))
1005         if (!(m_ppc->m_cap & PPCCAP_OEA))
10061006            return false;
10071007         desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION;
10081008         return true;
r31142r31143
10111011         return true;
10121012
10131013      case 0x356: // EIEIO
1014         if (!(m_context.cap & (PPCCAP_VEA | PPCCAP_4XX)))
1014         if (!(m_ppc->m_cap & (PPCCAP_VEA | PPCCAP_4XX)))
10151015            return false;
10161016         return true;
10171017
10181018      case 0x237: // LFSUX
10191019      case 0x277: // LFDUX
1020         if (!(m_context.cap & PPCCAP_FPU))
1020         if (!(m_ppc->m_cap & PPCCAP_FPU))
10211021            return false;
10221022         if (G_RA(op) == 0)
10231023            return false;
r31142r31143
10561056      case 0x297: // STFSX
10571057      case 0x2d7: // STFDX
10581058      case 0x3d7: // STFIWX
1059         if (!(m_context.cap & PPCCAP_FPU))
1059         if (!(m_ppc->m_cap & PPCCAP_FPU))
10601060            return false;
10611061         GPR_USED_OR_ZERO(desc, G_RA(op));
10621062         GPR_USED(desc, G_RB(op));
r31142r31143
10661066
10671067      case 0x2b7: // STFSUX
10681068      case 0x2f7: // STFDUX
1069         if (!(m_context.cap & PPCCAP_FPU))
1069         if (!(m_ppc->m_cap & PPCCAP_FPU))
10701070            return false;
10711071         if (G_RA(op) == 0)
10721072            return false;
r31142r31143
10891089         return true;
10901090
10911091      case 0x3f6: // DCBZ
1092         if (!(m_context.cap & (PPCCAP_VEA | PPCCAP_4XX)))
1092         if (!(m_ppc->m_cap & (PPCCAP_VEA | PPCCAP_4XX)))
10931093            return false;
10941094         GPR_USED_OR_ZERO(desc, G_RA(op));
10951095         GPR_USED(desc, G_RB(op));
r31142r31143
10991099      case 0x106: // ICBT
11001100      case 0x1c6: // DCCCI
11011101      case 0x3c6: // ICCCI
1102         if (!(m_context.cap & PPCCAP_4XX))
1102         if (!(m_ppc->m_cap & PPCCAP_4XX))
11031103            return false;
11041104         GPR_USED_OR_ZERO(desc, G_RA(op));
11051105         GPR_USED(desc, G_RB(op));
r31142r31143
11081108
11091109      case 0x1e6: // DCREAD
11101110      case 0x3e6: // ICREAD
1111         if (!(m_context.cap & PPCCAP_4XX))
1111         if (!(m_ppc->m_cap & PPCCAP_4XX))
11121112            return false;
11131113         GPR_USED_OR_ZERO(desc, G_RA(op));
11141114         GPR_USED(desc, G_RB(op));
r31142r31143
11171117         return true;
11181118
11191119      case 0x143: // MFDCR
1120         if (!(m_context.cap & PPCCAP_4XX))
1120         if (!(m_ppc->m_cap & PPCCAP_4XX))
11211121            return false;
11221122         GPR_MODIFIED(desc, G_RD(op));
11231123         desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION;
11241124         return true;
11251125
11261126      case 0x1c3: // MTDCR
1127         if (!(m_context.cap & PPCCAP_4XX))
1127         if (!(m_ppc->m_cap & PPCCAP_4XX))
11281128            return false;
11291129         GPR_USED(desc, G_RS(op));
11301130         desc.flags |= OPFLAG_PRIVILEGED | OPFLAG_CAN_CAUSE_EXCEPTION | OPFLAG_CAN_EXPOSE_EXTERNAL_INT;
11311131         return true;
11321132
11331133      case 0x083: // WRTEE
1134         if (!(m_context.cap & PPCCAP_4XX))
1134         if (!(m_ppc->m_cap & PPCCAP_4XX))
11351135            return false;
11361136         GPR_USED(desc, G_RS(op));
11371137         desc.flags |= OPFLAG_CAN_EXPOSE_EXTERNAL_INT;
11381138         return true;
11391139
11401140      case 0x0a3: // WRTEEI
1141         if (!(m_context.cap & PPCCAP_4XX))
1141         if (!(m_ppc->m_cap & PPCCAP_4XX))
11421142            return false;
11431143         if (op & MSR_EE)
11441144            desc.flags |= OPFLAG_CAN_EXPOSE_EXTERNAL_INT;
r31142r31143
11661166{
11671167   UINT32 opswitch = (op >> 1) & 0x1f;
11681168
1169   if (!(m_context.cap & PPCCAP_FPU))
1169   if (!(m_ppc->m_cap & PPCCAP_FPU))
11701170      return false;
11711171
11721172   switch (opswitch)
r31142r31143
12421242{
12431243   UINT32 opswitch = (op >> 1) & 0x3ff;
12441244
1245   if (!(m_context.cap & PPCCAP_FPU))
1245   if (!(m_ppc->m_cap & PPCCAP_FPU))
12461246      return false;
12471247
12481248   if (opswitch & 0x10)
trunk/src/emu/cpu/powerpc/ppcfe.h
r31142r31143
1111#ifndef __PPCFE_H__
1212#define __PPCFE_H__
1313
14#include "ppccom.h"
14#include "ppc.h"
1515#include "cpu/drcfe.h"
1616
1717
r31142r31143
4949{
5050public:
5151   // construction/destruction
52   ppc_frontend(powerpc_state &state, UINT32 window_start, UINT32 window_end, UINT32 max_sequence);
52   ppc_frontend(ppc_device *ppc, UINT32 window_start, UINT32 window_end, UINT32 max_sequence);
5353
5454protected:
5555   // required overrides
r31142r31143
5858private:
5959   // inlines
6060   UINT32 compute_spr(UINT32 spr) const { return ((spr >> 5) | (spr << 5)) & 0x3ff; }
61   bool is_403_class() const { return (m_context.flavor == PPC_MODEL_403GA || m_context.flavor == PPC_MODEL_403GB || m_context.flavor == PPC_MODEL_403GC || m_context.flavor == PPC_MODEL_403GCX || m_context.flavor == PPC_MODEL_405GP); }
62   bool is_601_class() const { return (m_context.flavor == PPC_MODEL_601); }
63   bool is_602_class() const { return (m_context.flavor == PPC_MODEL_602); }
64   bool is_603_class() const { return (m_context.flavor == PPC_MODEL_603 || m_context.flavor == PPC_MODEL_603E || m_context.flavor == PPC_MODEL_603EV || m_context.flavor == PPC_MODEL_603R); }
61   bool is_403_class() const { return (m_ppc->m_flavor == ppc_device::PPC_MODEL_403GA || m_ppc->m_flavor == ppc_device::PPC_MODEL_403GB || m_ppc->m_flavor == ppc_device::PPC_MODEL_403GC || m_ppc->m_flavor == ppc_device::PPC_MODEL_403GCX || m_ppc->m_flavor == ppc_device::PPC_MODEL_405GP); }
62   bool is_601_class() const { return (m_ppc->m_flavor == ppc_device::PPC_MODEL_601); }
63   bool is_602_class() const { return (m_ppc->m_flavor == ppc_device::PPC_MODEL_602); }
64   bool is_603_class() const { return (m_ppc->m_flavor == ppc_device::PPC_MODEL_603 || m_ppc->m_flavor == ppc_device::PPC_MODEL_603E || m_ppc->m_flavor == ppc_device::PPC_MODEL_603EV || m_ppc->m_flavor == ppc_device::PPC_MODEL_603R); }
6565
6666   // internal helpers
6767   bool describe_13(UINT32 op, opcode_desc &desc, const opcode_desc *prev);
r31142r31143
7070   bool describe_3f(UINT32 op, opcode_desc &desc, const opcode_desc *prev);
7171
7272   // internal state
73   powerpc_state &m_context;
73   ppc_device *m_ppc;
7474};
7575
7676
trunk/src/emu/cpu/powerpc/ppcdrc.c
r31142r31143
1616
1717#include "emu.h"
1818#include "debugger.h"
19#include "ppc.h"
1920#include "ppccom.h"
2021#include "ppcfe.h"
2122#include "cpu/drcfe.h"
r31142r31143
2930
3031
3132/***************************************************************************
32    DEBUGGING
33***************************************************************************/
34
35#define LOG_UML                         (0)
36#define LOG_NATIVE                      (0)
37
38#define DISABLE_FLAG_OPTIMIZATIONS      (0)
39#define DISABLE_FAST_REGISTERS          (0)
40#define SINGLE_INSTRUCTION_MODE         (0)
41
42#define PRINTF_EXCEPTIONS               (0)
43#define PRINTF_MMU                      (0)
44
45#define PROBE_ADDRESS                   ~0
46
47
48
49/***************************************************************************
5033    CONSTANTS
5134***************************************************************************/
5235
r31142r31143
6144#define MODE_PROTECTION                 0x02        /* 4XX */
6245#define MODE_USER                       0x04
6346
64/* size of the execution code cache */
65#define CACHE_SIZE                      (32 * 1024 * 1024)
66
67/* compilation boundaries -- how far back/forward does the analysis extend? */
68#define COMPILE_BACKWARDS_BYTES         128
69#define COMPILE_FORWARDS_BYTES          512
70#define COMPILE_MAX_INSTRUCTIONS        ((COMPILE_BACKWARDS_BYTES/4) + (COMPILE_FORWARDS_BYTES/4))
71#define COMPILE_MAX_SEQUENCE            64
72
7347/* exit codes */
7448#define EXECUTE_OUT_OF_CYCLES           0
7549#define EXECUTE_MISSING_CODE            1
r31142r31143
8256    MACROS
8357***************************************************************************/
8458
85#define R32(reg)                ppc->impstate->regmap[reg]
86#define R32Z(reg)               (((reg) == 0) ? parameter(0) : ppc->impstate->regmap[reg])
87#define F64(reg)                ppc->impstate->fdregmap[reg]
88#define CR32(reg)               mem(&ppc->cr[reg])
89#define FPSCR32                 mem(&ppc->fpscr)
90#define MSR32                   mem(&ppc->msr)
91#define XERSO32                 mem(&ppc->xerso)
92#define SR32(reg)               mem(&ppc->sr[reg])
93#define SPR32(reg)              mem(&ppc->spr[reg])
59#define R32(reg)                m_regmap[reg]
60#define R32Z(reg)               (((reg) == 0) ? parameter(0) : m_regmap[reg])
61#define F64(reg)                m_fdregmap[reg]
62#define CR32(reg)               mem(&m_core->cr[reg])
63#define FPSCR32                 mem(&m_core->fpscr)
64#define MSR32                   mem(&m_core->msr)
65#define XERSO32                 mem(&m_core->xerso)
66#define SR32(reg)               mem(&m_core->sr[reg])
67#define SPR32(reg)              mem(&m_core->spr[reg])
9468
9569#define CRMASK(reg)             (0xf0000000 >> ((reg) * 4))
9670
r31142r31143
12296
12397
12498/***************************************************************************
125    STRUCTURES & TYPEDEFS
126***************************************************************************/
127
128/* fast RAM info */
129struct fast_ram_info
130{
131   offs_t              start;                      /* start of the RAM block */
132   offs_t              end;                        /* end of the RAM block */
133   UINT8               readonly;                   /* TRUE if read-only */
134   void *              base;                       /* base in memory where the RAM lives */
135};
136
137
138/* hotspot info */
139struct hotspot_info
140{
141   offs_t              pc;                         /* PC to consider */
142   UINT32              opcode;                     /* required opcode at that PC */
143   UINT32              cycles;                     /* number of cycles to eat when hit */
144};
145
146
147/* internal compiler state */
148struct compiler_state
149{
150   UINT32              cycles;                     /* accumulated cycles */
151   UINT8               checkints;                  /* need to check interrupts before next instruction */
152   UINT8               checksoftints;              /* need to check software interrupts before next instruction */
153   code_label  labelnum;                   /* index for local labels */
154};
155
156
157/* PowerPC implementation state */
158struct ppcimp_state
159{
160   /* core state */
161   drc_cache *         cache;                      /* pointer to the DRC code cache */
162   drcuml_state *      drcuml;                     /* DRC UML generator state */
163   ppc_frontend *      drcfe;                      /* pointer to the DRC front-end state */
164   UINT32              drcoptions;                 /* configurable DRC options */
165
166   /* parameters for subroutines */
167   UINT32              mode;                       /* current global mode */
168   const char *        format;                     /* format string for printing */
169   UINT32              arg0;                       /* print_debug argument 1 */
170   UINT32              arg1;                       /* print_debug argument 2 */
171   UINT32              updateaddr;                 /* update address storage */
172   UINT32              swcount;                    /* counter for sw instructions */
173   UINT32              tempaddr;                   /* temporary address storage */
174   drcuml_ireg         tempdata;                   /* temporary data storage */
175   double              fp0;                        /* floating point 0 */
176
177   /* tables */
178   UINT8               fpmode[4];                  /* FPU mode table */
179   UINT8               sz_cr_table[32];            /* SZ CR table */
180   UINT8               cmp_cr_table[32];           /* CMP CR table */
181   UINT8               cmpl_cr_table[32];          /* CMPL CR table */
182   UINT8               fcmp_cr_table[32];          /* FCMP CR table */
183
184   /* internal stuff */
185   UINT8               cache_dirty;                /* true if we need to flush the cache */
186
187   /* register mappings */
188   parameter   regmap[32];                 /* parameter to register mappings for all 32 integer registers */
189   parameter   fdregmap[32];               /* parameter to register mappings for all 32 floating point registers */
190
191   /* subroutines */
192   code_handle *   entry;                      /* entry point */
193   code_handle *   nocode;                     /* nocode exception handler */
194   code_handle *   out_of_cycles;              /* out of cycles exception handler */
195   code_handle *   tlb_mismatch;               /* tlb mismatch handler */
196   code_handle *   swap_tgpr;                  /* swap TGPR handler */
197   code_handle *   lsw[8][32];                 /* lsw entries */
198   code_handle *   stsw[8][32];                /* stsw entries */
199   code_handle *   read8[8];                   /* read byte */
200   code_handle *   write8[8];                  /* write byte */
201   code_handle *   read16[8];                  /* read half */
202   code_handle *   read16mask[8];              /* read half */
203   code_handle *   write16[8];                 /* write half */
204   code_handle *   write16mask[8];             /* write half */
205   code_handle *   read32[8];                  /* read word */
206   code_handle *   read32align[8];             /* read word aligned */
207   code_handle *   read32mask[8];              /* read word */
208   code_handle *   write32[8];                 /* write word */
209   code_handle *   write32align[8];            /* write word aligned */
210   code_handle *   write32mask[8];             /* write word */
211   code_handle *   read64[8];                  /* read double */
212   code_handle *   read64mask[8];              /* read double */
213   code_handle *   write64[8];                 /* write double */
214   code_handle *   write64mask[8];             /* write double */
215   code_handle *   exception[EXCEPTION_COUNT]; /* array of exception handlers */
216   code_handle *   exception_norecover[EXCEPTION_COUNT];   /* array of exception handlers */
217
218   /* fast RAM */
219   UINT32              fastram_select;
220   fast_ram_info       fastram[PPC_MAX_FASTRAM];
221
222   /* hotspots */
223   UINT32              hotspot_select;
224   hotspot_info        hotspot[PPC_MAX_HOTSPOTS];
225};
226
227
228
229/***************************************************************************
230    FUNCTION PROTOTYPES
231***************************************************************************/
232
233static void code_flush_cache(powerpc_state *ppc);
234static void code_compile_block(powerpc_state *ppc, UINT8 mode, offs_t pc);
235
236static void cfunc_printf_exception(void *param);
237static void cfunc_printf_probe(void *param);
238
239static void static_generate_entry_point(powerpc_state *ppc);
240static void static_generate_nocode_handler(powerpc_state *ppc);
241static void static_generate_out_of_cycles(powerpc_state *ppc);
242static void static_generate_tlb_mismatch(powerpc_state *ppc);
243static void static_generate_exception(powerpc_state *ppc, UINT8 exception, int recover, const char *name);
244static void static_generate_memory_accessor(powerpc_state *ppc, int mode, int size, int iswrite, int ismasked, const char *name, code_handle *&handleptr, code_handle *masked);
245static void static_generate_swap_tgpr(powerpc_state *ppc);
246static void static_generate_lsw_entries(powerpc_state *ppc, int mode);
247static void static_generate_stsw_entries(powerpc_state *ppc, int mode);
248
249static void generate_update_mode(powerpc_state *ppc, drcuml_block *block);
250static void generate_update_cycles(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, parameter, int allow_exception);
251static void generate_checksum_block(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *seqhead, const opcode_desc *seqlast);
252static void generate_sequence_instruction(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
253static int generate_opcode(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
254static int generate_instruction_13(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
255static int generate_instruction_1f(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
256static int generate_instruction_3b(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
257static int generate_instruction_3f(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
258
259static void log_add_disasm_comment(drcuml_block *block, UINT32 pc, UINT32 op);
260static const char *log_desc_flags_to_string(UINT32 flags);
261static void log_register_list(drcuml_state *drcuml, const char *string, const UINT32 *reglist, const UINT32 *regnostarlist);
262static void log_opcode_desc(drcuml_state *drcuml, const opcode_desc *desclist, int indent);
263
264
265
266/***************************************************************************
267    PRIVATE GLOBAL VARIABLES
268***************************************************************************/
269
270/* lookup table for FP modes */
271static const UINT8 fpmode_source[4] =
272{
273   ROUND_ROUND,
274   ROUND_TRUNC,
275   ROUND_CEIL,
276   ROUND_FLOOR
277};
278
279/* flag lookup table for SZ */
280static const UINT8 sz_cr_table_source[32] =
281{
282   /* ..... */ 0x4,
283   /* ....C */ 0x4,
284   /* ...V. */ 0x4,
285   /* ...VC */ 0x4,
286   /* ..Z.. */ 0x2,
287   /* ..Z.C */ 0x2,
288   /* ..ZV. */ 0x2,
289   /* ..ZVC */ 0x2,
290   /* .S... */ 0x8,
291   /* .S..C */ 0x8,
292   /* .S.V. */ 0x8,
293   /* .S.VC */ 0x8,
294   /* .SZ.. */ 0x2,
295   /* .SZ.C */ 0x2,
296   /* .SZV. */ 0x2,
297   /* .SZVC */ 0x2,
298   /* U.... */ 0x4,
299   /* U...C */ 0x4,
300   /* U..V. */ 0x4,
301   /* U..VC */ 0x4,
302   /* U.Z.. */ 0x2,
303   /* U.Z.C */ 0x2,
304   /* U.ZV. */ 0x2,
305   /* U.ZVC */ 0x2,
306   /* US... */ 0x8,
307   /* US..C */ 0x8,
308   /* US.V. */ 0x8,
309   /* US.VC */ 0x8,
310   /* USZ.. */ 0x2,
311   /* USZ.C */ 0x2,
312   /* USZV. */ 0x2,
313   /* USZVC */ 0x2
314};
315
316/* flag lookup table for CMP */
317static const UINT8 cmp_cr_table_source[32] =
318{
319   /* ..... */ 0x4,
320   /* ....C */ 0x4,
321   /* ...V. */ 0x8,
322   /* ...VC */ 0x8,
323   /* ..Z.. */ 0x2,
324   /* ..Z.C */ 0x2,
325   /* ..ZV. */ 0x2,
326   /* ..ZVC */ 0x2,
327   /* .S... */ 0x8,
328   /* .S..C */ 0x8,
329   /* .S.V. */ 0x4,
330   /* .S.VC */ 0x4,
331   /* .SZ.. */ 0x2,
332   /* .SZ.C */ 0x2,
333   /* .SZV. */ 0x2,
334   /* .SZVC */ 0x2,
335   /* U.... */ 0x4,
336   /* U...C */ 0x4,
337   /* U..V. */ 0x8,
338   /* U..VC */ 0x8,
339   /* U.Z.. */ 0x2,
340   /* U.Z.C */ 0x2,
341   /* U.ZV. */ 0x2,
342   /* U.ZVC */ 0x2,
343   /* US... */ 0x8,
344   /* US..C */ 0x8,
345   /* US.V. */ 0x4,
346   /* US.VC */ 0x4,
347   /* USZ.. */ 0x2,
348   /* USZ.C */ 0x2,
349   /* USZV. */ 0x2,
350   /* USZVC */ 0x2
351};
352
353/* flag lookup table for CMPL */
354static const UINT8 cmpl_cr_table_source[32] =
355{
356   /* ..... */ 0x4,
357   /* ....C */ 0x8,
358   /* ...V. */ 0x4,
359   /* ...VC */ 0x8,
360   /* ..Z.. */ 0x2,
361   /* ..Z.C */ 0x2,
362   /* ..ZV. */ 0x2,
363   /* ..ZVC */ 0x2,
364   /* .S... */ 0x4,
365   /* .S..C */ 0x8,
366   /* .S.V. */ 0x4,
367   /* .S.VC */ 0x8,
368   /* .SZ.. */ 0x2,
369   /* .SZ.C */ 0x2,
370   /* .SZV. */ 0x2,
371   /* .SZVC */ 0x2,
372   /* U.... */ 0x4,
373   /* U...C */ 0x8,
374   /* U..V. */ 0x4,
375   /* U..VC */ 0x8,
376   /* U.Z.. */ 0x2,
377   /* U.Z.C */ 0x2,
378   /* U.ZV. */ 0x2,
379   /* U.ZVC */ 0x2,
380   /* US... */ 0x4,
381   /* US..C */ 0x8,
382   /* US.V. */ 0x4,
383   /* US.VC */ 0x8,
384   /* USZ.. */ 0x2,
385   /* USZ.C */ 0x2,
386   /* USZV. */ 0x2,
387   /* USZVC */ 0x2
388};
389
390/* flag lookup table for FCMP */
391static const UINT8 fcmp_cr_table_source[32] =
392{
393   /* ..... */ 0x4,
394   /* ....C */ 0x8,
395   /* ...V. */ 0x4,
396   /* ...VC */ 0x8,
397   /* ..Z.. */ 0x2,
398   /* ..Z.C */ 0xa,
399   /* ..ZV. */ 0x2,
400   /* ..ZVC */ 0xa,
401   /* .S... */ 0x4,
402   /* .S..C */ 0x8,
403   /* .S.V. */ 0x4,
404   /* .S.VC */ 0x8,
405   /* .SZ.. */ 0x2,
406   /* .SZ.C */ 0xa,
407   /* .SZV. */ 0x2,
408   /* .SZVC */ 0xa,
409   /* U.... */ 0x5,
410   /* U...C */ 0x9,
411   /* U..V. */ 0x5,
412   /* U..VC */ 0x9,
413   /* U.Z.. */ 0x3,
414   /* U.Z.C */ 0xb,
415   /* U.ZV. */ 0x3,
416   /* U.ZVC */ 0xb,
417   /* US... */ 0x5,
418   /* US..C */ 0x9,
419   /* US.V. */ 0x5,
420   /* US.VC */ 0x9,
421   /* USZ.. */ 0x3,
422   /* USZ.C */ 0xb,
423   /* USZV. */ 0x3,
424   /* USZVC */ 0xb
425};
426
427
428
429/***************************************************************************
43099    INLINE FUNCTIONS
431100***************************************************************************/
432101
433INLINE powerpc_state *get_safe_token(device_t *device)
434{
435   assert(device != NULL);
436   assert(device->type() == PPC403GA ||
437         device->type() == PPC403GCX ||
438         device->type() == PPC405GP ||
439         device->type() == PPC601 ||
440         device->type() == PPC602 ||
441         device->type() == PPC603 ||
442         device->type() == PPC603E ||
443         device->type() == PPC603R ||
444         device->type() == PPC604 ||
445         device->type() == MPC8240);
446   return *(powerpc_state **)downcast<legacy_cpu_device *>(device)->token();
447}
448
449102/*-------------------------------------------------
450103    alloc_handle - allocate a handle if not
451104    already allocated
452105-------------------------------------------------*/
453106
454INLINE void alloc_handle(drcuml_state *drcuml, code_handle **handleptr, const char *name)
107inline void ppc_device::alloc_handle(drcuml_state *drcuml, code_handle **handleptr, const char *name)
455108{
456109   if (*handleptr == NULL)
457110      *handleptr = drcuml->handle_alloc(name);
r31142r31143
463116    registers
464117-------------------------------------------------*/
465118
466INLINE void load_fast_iregs(powerpc_state *ppc, drcuml_block *block)
119inline void ppc_device::load_fast_iregs(drcuml_block *block)
467120{
468121   int regnum;
469122
470   for (regnum = 0; regnum < ARRAY_LENGTH(ppc->impstate->regmap); regnum++)
471      if (ppc->impstate->regmap[regnum].is_int_register())
472         UML_MOV(block, ireg(ppc->impstate->regmap[regnum].ireg() - REG_I0), mem(&ppc->r[regnum]));
123   for (regnum = 0; regnum < ARRAY_LENGTH(m_regmap); regnum++)
124   {
125      if (m_regmap[regnum].is_int_register())
126      {
127         UML_MOV(block, ireg(m_regmap[regnum].ireg() - REG_I0), mem(&m_core->r[regnum]));
128      }
129   }
473130}
474131
475132
r31142r31143
478135    registers
479136-------------------------------------------------*/
480137
481INLINE void save_fast_iregs(powerpc_state *ppc, drcuml_block *block)
138void ppc_device::save_fast_iregs(drcuml_block *block)
482139{
483140   int regnum;
484141
485   for (regnum = 0; regnum < ARRAY_LENGTH(ppc->impstate->regmap); regnum++)
486      if (ppc->impstate->regmap[regnum].is_int_register())
487         UML_MOV(block, mem(&ppc->r[regnum]), ireg(ppc->impstate->regmap[regnum].ireg() - REG_I0));
142   for (regnum = 0; regnum < ARRAY_LENGTH(m_regmap); regnum++)
143   {
144      if (m_regmap[regnum].is_int_register())
145      {
146         UML_MOV(block, mem(&m_core->r[regnum]), ireg(m_regmap[regnum].ireg() - REG_I0));
147      }
148   }
488149}
489150
490151
r31142r31143
493154    for an rlw* instruction
494155-------------------------------------------------*/
495156
496INLINE UINT32 compute_rlw_mask(UINT8 mb, UINT8 me)
157inline UINT32 ppc_device::compute_rlw_mask(UINT8 mb, UINT8 me)
497158{
498159   if (mb <= me)
499160      return (0xffffffff >> mb) & (0xffffffff << (31 - me));
r31142r31143
507168    for a mtcrf/mfcrf instruction
508169-------------------------------------------------*/
509170
510INLINE UINT32 compute_crf_mask(UINT8 crm)
171inline UINT32 ppc_device::compute_crf_mask(UINT8 crm)
511172{
512173   UINT32 mask = 0;
513174   if (crm & 0x80) mask |= 0xf0000000;
r31142r31143
527188    SPR field of an opcode
528189-------------------------------------------------*/
529190
530INLINE UINT32 compute_spr(UINT32 spr)
191inline UINT32 ppc_device::compute_spr(UINT32 spr)
531192{
532193   return ((spr >> 5) | (spr << 5)) & 0x3ff;
533194}
r31142r31143
539200***************************************************************************/
540201
541202/*-------------------------------------------------
542    ppcdrc_init - initialize the processor
543-------------------------------------------------*/
544
545static void ppcdrc_init(powerpc_flavor flavor, UINT32 cap, int tb_divisor, legacy_cpu_device *device, device_irq_acknowledge_delegate irqcallback)
546{
547   powerpc_state *ppc;
548   drcbe_info beinfo;
549   UINT32 flags = 0;
550   drc_cache *cache;
551   int regnum;
552
553   /* allocate enough space for the cache and the core */
554   cache = auto_alloc(device->machine(), drc_cache(CACHE_SIZE + sizeof(*ppc)));
555
556   /* allocate the core from the near cache */
557   *(powerpc_state **)device->token() = ppc = (powerpc_state *)cache->alloc_near(sizeof(*ppc));
558   memset(ppc, 0, sizeof(*ppc));
559
560   /* initialize the core */
561   ppccom_init(ppc, flavor, cap, tb_divisor, device, irqcallback);
562
563   /* allocate the implementation-specific state from the full cache */
564   ppc->impstate = (ppcimp_state *)cache->alloc_near(sizeof(*ppc->impstate));
565   memset(ppc->impstate, 0, sizeof(*ppc->impstate));
566   ppc->impstate->cache = cache;
567
568   /* initialize the UML generator */
569   if (LOG_UML)
570      flags |= DRCUML_OPTION_LOG_UML;
571   if (LOG_NATIVE)
572      flags |= DRCUML_OPTION_LOG_NATIVE;
573   ppc->impstate->drcuml = auto_alloc(device->machine(), drcuml_state(*device, *cache, flags, 8, 32, 2));
574
575   /* add symbols for our stuff */
576   ppc->impstate->drcuml->symbol_add(&ppc->pc, sizeof(ppc->pc), "pc");
577   ppc->impstate->drcuml->symbol_add(&ppc->icount, sizeof(ppc->icount), "icount");
578   for (regnum = 0; regnum < 32; regnum++)
579   {
580      char buf[10];
581      sprintf(buf, "r%d", regnum);
582      ppc->impstate->drcuml->symbol_add(&ppc->r[regnum], sizeof(ppc->r[regnum]), buf);
583      sprintf(buf, "fpr%d", regnum);
584      ppc->impstate->drcuml->symbol_add(&ppc->f[regnum], sizeof(ppc->r[regnum]), buf);
585   }
586   for (regnum = 0; regnum < 8; regnum++)
587   {
588      char buf[10];
589      sprintf(buf, "cr%d", regnum);
590      ppc->impstate->drcuml->symbol_add(&ppc->cr[regnum], sizeof(ppc->cr[regnum]), buf);
591   }
592   ppc->impstate->drcuml->symbol_add(&ppc->xerso, sizeof(ppc->xerso), "xerso");
593   ppc->impstate->drcuml->symbol_add(&ppc->fpscr, sizeof(ppc->fpscr), "fpscr");
594   ppc->impstate->drcuml->symbol_add(&ppc->msr, sizeof(ppc->msr), "msr");
595   ppc->impstate->drcuml->symbol_add(&ppc->sr, sizeof(ppc->sr), "sr");
596   ppc->impstate->drcuml->symbol_add(&ppc->spr[SPR_XER], sizeof(ppc->spr[SPR_XER]), "xer");
597   ppc->impstate->drcuml->symbol_add(&ppc->spr[SPR_LR], sizeof(ppc->spr[SPR_LR]), "lr");
598   ppc->impstate->drcuml->symbol_add(&ppc->spr[SPR_CTR], sizeof(ppc->spr[SPR_CTR]), "ctr");
599   ppc->impstate->drcuml->symbol_add(&ppc->spr, sizeof(ppc->spr), "spr");
600   ppc->impstate->drcuml->symbol_add(&ppc->dcr, sizeof(ppc->dcr), "dcr");
601   ppc->impstate->drcuml->symbol_add(&ppc->param0, sizeof(ppc->param0), "param0");
602   ppc->impstate->drcuml->symbol_add(&ppc->param1, sizeof(ppc->param1), "param1");
603   ppc->impstate->drcuml->symbol_add(&ppc->irq_pending, sizeof(ppc->irq_pending), "irq_pending");
604   ppc->impstate->drcuml->symbol_add(&ppc->impstate->mode, sizeof(ppc->impstate->mode), "mode");
605   ppc->impstate->drcuml->symbol_add(&ppc->impstate->arg0, sizeof(ppc->impstate->arg0), "arg0");
606   ppc->impstate->drcuml->symbol_add(&ppc->impstate->arg1, sizeof(ppc->impstate->arg1), "arg1");
607   ppc->impstate->drcuml->symbol_add(&ppc->impstate->updateaddr, sizeof(ppc->impstate->updateaddr), "updateaddr");
608   ppc->impstate->drcuml->symbol_add(&ppc->impstate->swcount, sizeof(ppc->impstate->swcount), "swcount");
609   ppc->impstate->drcuml->symbol_add(&ppc->impstate->tempaddr, sizeof(ppc->impstate->tempaddr), "tempaddr");
610   ppc->impstate->drcuml->symbol_add(&ppc->impstate->tempdata, sizeof(ppc->impstate->tempdata), "tempdata");
611   ppc->impstate->drcuml->symbol_add(&ppc->impstate->fp0, sizeof(ppc->impstate->fp0), "fp0");
612   ppc->impstate->drcuml->symbol_add(&ppc->impstate->fpmode, sizeof(ppc->impstate->fpmode), "fpmode");
613   ppc->impstate->drcuml->symbol_add(&ppc->impstate->sz_cr_table, sizeof(ppc->impstate->sz_cr_table), "sz_cr_table");
614   ppc->impstate->drcuml->symbol_add(&ppc->impstate->cmp_cr_table, sizeof(ppc->impstate->cmp_cr_table), "cmp_cr_table");
615   ppc->impstate->drcuml->symbol_add(&ppc->impstate->cmpl_cr_table, sizeof(ppc->impstate->cmpl_cr_table), "cmpl_cr_table");
616   ppc->impstate->drcuml->symbol_add(&ppc->impstate->fcmp_cr_table, sizeof(ppc->impstate->fcmp_cr_table), "fcmp_cr_table");
617
618   /* initialize the front-end helper */
619   ppc->impstate->drcfe = auto_alloc(device->machine(), ppc_frontend(*ppc, COMPILE_BACKWARDS_BYTES, COMPILE_FORWARDS_BYTES, SINGLE_INSTRUCTION_MODE ? 1 : COMPILE_MAX_SEQUENCE));
620
621   /* initialize the implementation state tables */
622   memcpy(ppc->impstate->fpmode, fpmode_source, sizeof(fpmode_source));
623   memcpy(ppc->impstate->sz_cr_table, sz_cr_table_source, sizeof(sz_cr_table_source));
624   memcpy(ppc->impstate->cmp_cr_table, cmp_cr_table_source, sizeof(cmp_cr_table_source));
625   memcpy(ppc->impstate->cmpl_cr_table, cmpl_cr_table_source, sizeof(cmpl_cr_table_source));
626   memcpy(ppc->impstate->fcmp_cr_table, fcmp_cr_table_source, sizeof(fcmp_cr_table_source));
627
628   /* compute the register parameters */
629   for (regnum = 0; regnum < 32; regnum++)
630   {
631      ppc->impstate->regmap[regnum] = mem(&ppc->r[regnum]);
632      ppc->impstate->fdregmap[regnum] = mem(&ppc->f[regnum]);
633   }
634
635   /* if we have registers to spare, assign r0, r1, r2 to leftovers */
636   if (!DISABLE_FAST_REGISTERS)
637   {
638      ppc->impstate->drcuml->get_backend_info(beinfo);
639      if (beinfo.direct_iregs > 5)
640         ppc->impstate->regmap[0] = I5;
641      if (beinfo.direct_iregs > 6)
642         ppc->impstate->regmap[1] = I6;
643      if (beinfo.direct_iregs > 7)
644         ppc->impstate->regmap[2] = I7;
645   }
646
647   /* mark the cache dirty so it is updated on next execute */
648   ppc->impstate->cache_dirty = TRUE;
649}
650
651
652/*-------------------------------------------------
653    ppcdrc_reset - reset the processor
654-------------------------------------------------*/
655
656static CPU_RESET( ppcdrc )
657{
658   powerpc_state *ppc = get_safe_token(device);
659
660   /* reset the common code and mark the cache dirty */
661   ppccom_reset(ppc);
662   ppc->impstate->mode = 0;
663   ppc->impstate->cache_dirty = TRUE;
664}
665
666
667/*-------------------------------------------------
668203    ppcdrc_execute - execute the CPU for the
669204    specified number of cycles
670205-------------------------------------------------*/
671206
672static CPU_EXECUTE( ppcdrc )
207void ppc_device::execute_run()
673208{
674   powerpc_state *ppc = get_safe_token(device);
675   drcuml_state *drcuml = ppc->impstate->drcuml;
676209   int execute_result;
677210
678211   /* reset the cache if dirty */
679   if (ppc->impstate->cache_dirty)
680      code_flush_cache(ppc);
681   ppc->impstate->cache_dirty = FALSE;
212   if (m_cache_dirty)
213      code_flush_cache();
214   m_cache_dirty = FALSE;
682215
683216   /* execute */
684217   do
685218   {
686219      /* run as much as we can */
687      execute_result = drcuml->execute(*ppc->impstate->entry);
220      execute_result = m_drcuml->execute(*m_entry);
688221
689222      /* if we need to recompile, do it */
690223      if (execute_result == EXECUTE_MISSING_CODE)
691         code_compile_block(ppc, ppc->impstate->mode, ppc->pc);
224         code_compile_block(m_core->mode, m_core->pc);
692225      else if (execute_result == EXECUTE_UNMAPPED_CODE)
693         fatalerror("Attempted to execute unmapped code at PC=%08X\n", ppc->pc);
226         fatalerror("Attempted to execute unmapped code at PC=%08X\n", m_core->pc);
694227      else if (execute_result == EXECUTE_RESET_CACHE)
695         code_flush_cache(ppc);
228         code_flush_cache();
696229
697230   } while (execute_result != EXECUTE_OUT_OF_CYCLES);
698231}
699232
700233
701234/*-------------------------------------------------
702    ppcdrc_exit - cleanup from execution
703-------------------------------------------------*/
704
705static CPU_EXIT( ppcdrc )
706{
707   powerpc_state *ppc = get_safe_token(device);
708   ppccom_exit(ppc);
709
710   /* clean up the DRC */
711   auto_free(device->machine(), ppc->impstate->drcfe);
712   auto_free(device->machine(), ppc->impstate->drcuml);
713   auto_free(device->machine(), ppc->impstate->cache);
714}
715
716
717/*-------------------------------------------------
718    ppcdrc_translate - perform virtual-to-physical
719    address translation
720-------------------------------------------------*/
721
722static CPU_TRANSLATE( ppcdrc )
723{
724   powerpc_state *ppc = get_safe_token(device);
725   return ppccom_translate_address(ppc, space, intention, address);
726}
727
728
729/*-------------------------------------------------
730    ppcdrc_dasm - disassemble an instruction
731-------------------------------------------------*/
732
733static CPU_DISASSEMBLE( ppcdrc )
734{
735   powerpc_state *ppc = get_safe_token(device);
736   return ppccom_dasm(ppc, buffer, pc, oprom, opram);
737}
738
739
740/*-------------------------------------------------
741    ppcdrc_set_info - set information about a given
742    CPU instance
743-------------------------------------------------*/
744
745static CPU_SET_INFO( ppcdrc )
746{
747   powerpc_state *ppc = get_safe_token(device);
748
749   /* --- everything is handled generically --- */
750   ppccom_set_info(ppc, state, info);
751}
752
753
754/*-------------------------------------------------
755    ppcdrc_get_info - return information about a given
756    CPU instance
757-------------------------------------------------*/
758
759static CPU_GET_INFO( ppcdrc )
760{
761   powerpc_state *ppc = (device != NULL && device->token() != NULL) ? get_safe_token(device) : NULL;
762   switch (state)
763   {
764      /* --- the following bits of info are returned as 64-bit signed integers --- */
765      case CPUINFO_INT_CONTEXT_SIZE:                  info->i = sizeof(powerpc_state *);              break;
766      case CPUINFO_INT_PREVIOUSPC:                    /* not implemented */                           break;
767
768      /* --- the following bits of info are returned as pointers to data or functions --- */
769      case CPUINFO_FCT_SET_INFO:                      info->setinfo = CPU_SET_INFO_NAME(ppcdrc);      break;
770      case CPUINFO_FCT_INIT:                          /* provided per-CPU */                          break;
771      case CPUINFO_FCT_RESET:                         info->reset = CPU_RESET_NAME(ppcdrc);           break;
772      case CPUINFO_FCT_EXIT:                          info->exit = CPU_EXIT_NAME(ppcdrc);             break;
773      case CPUINFO_FCT_EXECUTE:                       info->execute = CPU_EXECUTE_NAME(ppcdrc);       break;
774      case CPUINFO_FCT_DISASSEMBLE:                   info->disassemble = CPU_DISASSEMBLE_NAME(ppcdrc);break;
775      case CPUINFO_FCT_TRANSLATE:                     info->translate = CPU_TRANSLATE_NAME(ppcdrc);   break;
776
777      /* --- the following bits of info are returned as NULL-terminated strings --- */
778      case CPUINFO_STR_SOURCE_FILE:                       strcpy(info->s, __FILE__);                      break;
779
780      /* --- everything else is handled generically --- */
781      default:                                        ppccom_get_info(ppc, state, info);              break;
782   }
783}
784
785
786/*-------------------------------------------------
787235    ppcdrc_set_options - configure DRC options
788236-------------------------------------------------*/
789237
790void ppcdrc_set_options(device_t *device, UINT32 options)
238void ppc_device::ppcdrc_set_options(UINT32 options)
791239{
792   powerpc_state *ppc = get_safe_token(device);
793   ppc->impstate->drcoptions = options;
240   m_drcoptions = options;
794241}
795242
796243
r31142r31143
799246    region
800247-------------------------------------------------*/
801248
802void ppcdrc_add_fastram(device_t *device, offs_t start, offs_t end, UINT8 readonly, void *base)
249void ppc_device::ppcdrc_add_fastram(offs_t start, offs_t end, UINT8 readonly, void *base)
803250{
804   powerpc_state *ppc = get_safe_token(device);
805   if (ppc->impstate->fastram_select < ARRAY_LENGTH(ppc->impstate->fastram))
251   if (m_fastram_select < ARRAY_LENGTH(m_fastram))
806252   {
807      ppc->impstate->fastram[ppc->impstate->fastram_select].start = start;
808      ppc->impstate->fastram[ppc->impstate->fastram_select].end = end;
809      ppc->impstate->fastram[ppc->impstate->fastram_select].readonly = readonly;
810      ppc->impstate->fastram[ppc->impstate->fastram_select].base = base;
811      ppc->impstate->fastram_select++;
253      m_fastram[m_fastram_select].start = start;
254      m_fastram[m_fastram_select].end = end;
255      m_fastram[m_fastram_select].readonly = readonly;
256      m_fastram[m_fastram_select].base = base;
257      m_fastram_select++;
812258   }
813259}
814260
r31142r31143
817263    ppcdrc_add_hotspot - add a new hotspot
818264-------------------------------------------------*/
819265
820void ppcdrc_add_hotspot(device_t *device, offs_t pc, UINT32 opcode, UINT32 cycles)
266void ppc_device::ppcdrc_add_hotspot(offs_t pc, UINT32 opcode, UINT32 cycles)
821267{
822   powerpc_state *ppc = get_safe_token(device);
823   if (ppc->impstate->hotspot_select < ARRAY_LENGTH(ppc->impstate->hotspot))
268   if (m_hotspot_select < ARRAY_LENGTH(m_hotspot))
824269   {
825      ppc->impstate->hotspot[ppc->impstate->hotspot_select].pc = pc;
826      ppc->impstate->hotspot[ppc->impstate->hotspot_select].opcode = opcode;
827      ppc->impstate->hotspot[ppc->impstate->hotspot_select].cycles = cycles;
828      ppc->impstate->hotspot_select++;
270      m_hotspot[m_hotspot_select].pc = pc;
271      m_hotspot[m_hotspot_select].opcode = opcode;
272      m_hotspot[m_hotspot_select].cycles = cycles;
273      m_hotspot_select++;
829274   }
830275}
831276
r31142r31143
840285    regenerate static code
841286-------------------------------------------------*/
842287
843static void code_flush_cache(powerpc_state *ppc)
288void ppc_device::code_flush_cache()
844289{
845   drcuml_state *drcuml = ppc->impstate->drcuml;
846   int mode;
847
848290   /* empty the transient cache contents */
849   drcuml->reset();
291   m_drcuml->reset();
850292
851293   try
852294   {
853295      /* generate the entry point and out-of-cycles handlers */
854      static_generate_entry_point(ppc);
855      static_generate_nocode_handler(ppc);
856      static_generate_out_of_cycles(ppc);
857      static_generate_tlb_mismatch(ppc);
858      if (ppc->cap & PPCCAP_603_MMU)
859         static_generate_swap_tgpr(ppc);
296      static_generate_entry_point();
297      static_generate_nocode_handler();
298      static_generate_out_of_cycles();
299      static_generate_tlb_mismatch();
300      if (m_cap & PPCCAP_603_MMU)
301         static_generate_swap_tgpr();
860302
861303      /* append exception handlers for various types */
862      static_generate_exception(ppc, EXCEPTION_RESET,     TRUE,  "exception_reset");
863      static_generate_exception(ppc, EXCEPTION_MACHCHECK, TRUE,  "exception_machine_check");
864      static_generate_exception(ppc, EXCEPTION_DSI,       TRUE,  "exception_dsi");
865      static_generate_exception(ppc, EXCEPTION_ISI,       TRUE,  "exception_isi");
866      static_generate_exception(ppc, EXCEPTION_EI,        TRUE,  "exception_ei");
867      static_generate_exception(ppc, EXCEPTION_EI,        FALSE, "exception_ei_norecover");
868      static_generate_exception(ppc, EXCEPTION_ALIGN,     TRUE,  "exception_align");
869      static_generate_exception(ppc, EXCEPTION_PROGRAM,   TRUE,  "exception_program");
870      static_generate_exception(ppc, EXCEPTION_NOFPU,     TRUE,  "exception_fpu_unavailable");
871      static_generate_exception(ppc, EXCEPTION_DECREMENT, TRUE,  "exception_decrementer");
872      static_generate_exception(ppc, EXCEPTION_SYSCALL,   TRUE,  "exception_syscall");
873      static_generate_exception(ppc, EXCEPTION_TRACE,     TRUE,  "exception_trace");
874      static_generate_exception(ppc, EXCEPTION_FPASSIST,  TRUE,  "exception_floating_point_assist");
875      if (ppc->cap & PPCCAP_603_MMU)
304      static_generate_exception(EXCEPTION_RESET,     TRUE,  "exception_reset");
305      static_generate_exception(EXCEPTION_MACHCHECK, TRUE,  "exception_machine_check");
306      static_generate_exception(EXCEPTION_DSI,       TRUE,  "exception_dsi");
307      static_generate_exception(EXCEPTION_ISI,       TRUE,  "exception_isi");
308      static_generate_exception(EXCEPTION_EI,        TRUE,  "exception_ei");
309      static_generate_exception(EXCEPTION_EI,        FALSE, "exception_ei_norecover");
310      static_generate_exception(EXCEPTION_ALIGN,     TRUE,  "exception_align");
311      static_generate_exception(EXCEPTION_PROGRAM,   TRUE,  "exception_program");
312      static_generate_exception(EXCEPTION_NOFPU,     TRUE,  "exception_fpu_unavailable");
313      static_generate_exception(EXCEPTION_DECREMENT, TRUE,  "exception_decrementer");
314      static_generate_exception(EXCEPTION_SYSCALL,   TRUE,  "exception_syscall");
315      static_generate_exception(EXCEPTION_TRACE,     TRUE,  "exception_trace");
316      static_generate_exception(EXCEPTION_FPASSIST,  TRUE,  "exception_floating_point_assist");
317      if (m_cap & PPCCAP_603_MMU)
876318      {
877         static_generate_exception(ppc, EXCEPTION_ITLBMISS,  TRUE,  "exception_itlb_miss");
878         static_generate_exception(ppc, EXCEPTION_DTLBMISSL, TRUE,  "exception_dtlb_miss_load");
879         static_generate_exception(ppc, EXCEPTION_DTLBMISSS, TRUE,  "exception_dtlb_miss_store");
319         static_generate_exception(EXCEPTION_ITLBMISS,  TRUE,  "exception_itlb_miss");
320         static_generate_exception(EXCEPTION_DTLBMISSL, TRUE,  "exception_dtlb_miss_load");
321         static_generate_exception(EXCEPTION_DTLBMISSS, TRUE,  "exception_dtlb_miss_store");
880322      }
881323
882324      /* add subroutines for memory accesses */
883      for (mode = 0; mode < 8; mode++)
325      for (int mode = 0; mode < 8; mode++)
884326      {
885         static_generate_memory_accessor(ppc, mode, 1, FALSE, FALSE, "read8",       ppc->impstate->read8[mode],       NULL);
886         static_generate_memory_accessor(ppc, mode, 1, TRUE,  FALSE, "write8",      ppc->impstate->write8[mode],      NULL);
887         static_generate_memory_accessor(ppc, mode, 2, FALSE, TRUE,  "read16mask",  ppc->impstate->read16mask[mode],  NULL);
888         static_generate_memory_accessor(ppc, mode, 2, FALSE, FALSE, "read16",      ppc->impstate->read16[mode],      ppc->impstate->read16mask[mode]);
889         static_generate_memory_accessor(ppc, mode, 2, TRUE,  TRUE,  "write16mask", ppc->impstate->write16mask[mode], NULL);
890         static_generate_memory_accessor(ppc, mode, 2, TRUE,  FALSE, "write16",     ppc->impstate->write16[mode],     ppc->impstate->write16mask[mode]);
891         static_generate_memory_accessor(ppc, mode, 4, FALSE, TRUE,  "read32mask",  ppc->impstate->read32mask[mode],  NULL);
892         static_generate_memory_accessor(ppc, mode, 4, FALSE, FALSE, "read32align", ppc->impstate->read32align[mode], NULL);
893         static_generate_memory_accessor(ppc, mode, 4, FALSE, FALSE, "read32",      ppc->impstate->read32[mode],      ppc->impstate->read32mask[mode]);
894         static_generate_memory_accessor(ppc, mode, 4, TRUE,  TRUE,  "write32mask", ppc->impstate->write32mask[mode], NULL);
895         static_generate_memory_accessor(ppc, mode, 4, TRUE,  FALSE, "write32align",ppc->impstate->write32align[mode],NULL);
896         static_generate_memory_accessor(ppc, mode, 4, TRUE,  FALSE, "write32",     ppc->impstate->write32[mode],     ppc->impstate->write32mask[mode]);
897         static_generate_memory_accessor(ppc, mode, 8, FALSE, TRUE,  "read64mask",  ppc->impstate->read64mask[mode],  NULL);
898         static_generate_memory_accessor(ppc, mode, 8, FALSE, FALSE, "read64",      ppc->impstate->read64[mode],      ppc->impstate->read64mask[mode]);
899         static_generate_memory_accessor(ppc, mode, 8, TRUE,  TRUE,  "write64mask", ppc->impstate->write64mask[mode], NULL);
900         static_generate_memory_accessor(ppc, mode, 8, TRUE,  FALSE, "write64",     ppc->impstate->write64[mode],     ppc->impstate->write64mask[mode]);
901         static_generate_lsw_entries(ppc, mode);
902         static_generate_stsw_entries(ppc, mode);
327         static_generate_memory_accessor(mode, 1, FALSE, FALSE, "read8",       m_read8[mode],       NULL);
328         static_generate_memory_accessor(mode, 1, TRUE,  FALSE, "write8",      m_write8[mode],      NULL);
329         static_generate_memory_accessor(mode, 2, FALSE, TRUE,  "read16mask",  m_read16mask[mode],  NULL);
330         static_generate_memory_accessor(mode, 2, FALSE, FALSE, "read16",      m_read16[mode],      m_read16mask[mode]);
331         static_generate_memory_accessor(mode, 2, TRUE,  TRUE,  "write16mask", m_write16mask[mode], NULL);
332         static_generate_memory_accessor(mode, 2, TRUE,  FALSE, "write16",     m_write16[mode],     m_write16mask[mode]);
333         static_generate_memory_accessor(mode, 4, FALSE, TRUE,  "read32mask",  m_read32mask[mode],  NULL);
334         static_generate_memory_accessor(mode, 4, FALSE, FALSE, "read32align", m_read32align[mode], NULL);
335         static_generate_memory_accessor(mode, 4, FALSE, FALSE, "read32",      m_read32[mode],      m_read32mask[mode]);
336         static_generate_memory_accessor(mode, 4, TRUE,  TRUE,  "write32mask", m_write32mask[mode], NULL);
337         static_generate_memory_accessor(mode, 4, TRUE,  FALSE, "write32align",m_write32align[mode],NULL);
338         static_generate_memory_accessor(mode, 4, TRUE,  FALSE, "write32",     m_write32[mode],     m_write32mask[mode]);
339         static_generate_memory_accessor(mode, 8, FALSE, TRUE,  "read64mask",  m_read64mask[mode],  NULL);
340         static_generate_memory_accessor(mode, 8, FALSE, FALSE, "read64",      m_read64[mode],      m_read64mask[mode]);
341         static_generate_memory_accessor(mode, 8, TRUE,  TRUE,  "write64mask", m_write64mask[mode], NULL);
342         static_generate_memory_accessor(mode, 8, TRUE,  FALSE, "write64",     m_write64[mode],     m_write64mask[mode]);
343         static_generate_lsw_entries(mode);
344         static_generate_stsw_entries(mode);
903345      }
904346   }
905347   catch (drcuml_block::abort_compilation &)
r31142r31143
914356    given mode at the specified pc
915357-------------------------------------------------*/
916358
917static void code_compile_block(powerpc_state *ppc, UINT8 mode, offs_t pc)
359void ppc_device::code_compile_block(UINT8 mode, offs_t pc)
918360{
919   drcuml_state *drcuml = ppc->impstate->drcuml;
920361   compiler_state compiler = { 0 };
921362   const opcode_desc *seqhead, *seqlast;
922363   const opcode_desc *desclist;
r31142r31143
926367   g_profiler.start(PROFILER_DRC_COMPILE);
927368
928369   /* get a description of this sequence */
929   desclist = ppc->impstate->drcfe->describe_code(pc);
370   desclist = m_drcfe->describe_code(pc);
930371   if (LOG_UML || LOG_NATIVE)
931      log_opcode_desc(drcuml, desclist, 0);
372      log_opcode_desc(m_drcuml, desclist, 0);
932373
933374   bool succeeded = false;
934375   while (!succeeded)
r31142r31143
936377      try
937378      {
938379         /* start the block */
939         block = drcuml->begin_block(4096);
380         block = m_drcuml->begin_block(4096);
940381
941382         /* loop until we get through all instruction sequences */
942383         for (seqhead = desclist; seqhead != NULL; seqhead = seqlast->next())
r31142r31143
955396            assert(seqlast != NULL);
956397
957398            /* if we don't have a hash for this mode/pc, or if we are overriding all, add one */
958            if (override || !drcuml->hash_exists(mode, seqhead->pc))
399            if (override || !m_drcuml->hash_exists(mode, seqhead->pc))
959400               UML_HASH(block, mode, seqhead->pc);                                             // hash    mode,pc
960401
961402            /* if we already have a hash, and this is the first sequence, assume that we */
r31142r31143
970411            else
971412            {
972413               UML_LABEL(block, seqhead->pc | 0x80000000);                                     // label   seqhead->pc | 0x80000000
973               UML_HASHJMP(block, ppc->impstate->mode, seqhead->pc, *ppc->impstate->nocode);
414               UML_HASHJMP(block, m_core->mode, seqhead->pc, *m_nocode);
974415                                                                           // hashjmp <mode>,seqhead->pc,nocode
975416               continue;
976417            }
977418
978419            /* validate this code block if we're not pointing into ROM */
979            if (ppc->program->get_write_ptr(seqhead->physpc) != NULL)
980               generate_checksum_block(ppc, block, &compiler, seqhead, seqlast);               // <checksum>
420            if (m_program->get_write_ptr(seqhead->physpc) != NULL)
421               generate_checksum_block(block, &compiler, seqhead, seqlast);               // <checksum>
981422
982423            /* label this instruction, if it may be jumped to locally */
983424            if (seqhead->flags & OPFLAG_IS_BRANCH_TARGET)
r31142r31143
985426
986427            /* iterate over instructions in the sequence and compile them */
987428            for (curdesc = seqhead; curdesc != seqlast->next(); curdesc = curdesc->next())
988               generate_sequence_instruction(ppc, block, &compiler, curdesc);                  // <instruction>
429               generate_sequence_instruction(block, &compiler, curdesc);                  // <instruction>
989430
990431            /* if we need to return to the start, do it */
991432            if (seqlast->flags & OPFLAG_RETURN_TO_START)
r31142r31143
996437               nextpc = seqlast->pc + (seqlast->skipslots + 1) * 4;
997438
998439            /* count off cycles and go there */
999            generate_update_cycles(ppc, block, &compiler, nextpc, TRUE);                    // <subtract cycles>
440            generate_update_cycles(block, &compiler, nextpc, TRUE);                    // <subtract cycles>
1000441
1001442            /* if the last instruction can change modes, use a variable mode; otherwise, assume the same mode */
1002443            if (seqlast->flags & OPFLAG_CAN_CHANGE_MODES)
1003               UML_HASHJMP(block, mem(&ppc->impstate->mode), nextpc, *ppc->impstate->nocode);// hashjmp <mode>,nextpc,nocode
444               UML_HASHJMP(block, mem(&m_core->mode), nextpc, *m_nocode);// hashjmp <mode>,nextpc,nocode
1004445            else if (seqlast->next() == NULL || seqlast->next()->pc != nextpc)
1005               UML_HASHJMP(block, ppc->impstate->mode, nextpc, *ppc->impstate->nocode);// hashjmp <mode>,nextpc,nocode
446               UML_HASHJMP(block, m_core->mode, nextpc, *m_nocode);// hashjmp <mode>,nextpc,nocode
1006447         }
1007448
1008449         /* end the sequence */
r31142r31143
1013454      catch (drcuml_block::abort_compilation &)
1014455      {
1015456         // flush the cache and try again
1016         code_flush_cache(ppc);
457         code_flush_cache();
1017458      }
1018459   }
1019460}
r31142r31143
1031472
1032473static void cfunc_printf_exception(void *param)
1033474{
1034   powerpc_state *ppc = (powerpc_state *)param;
1035   printf("Exception: type=%2d EPC=%08X MSR=%08X\n", ppc->param0, ppc->spr[SPROEA_SRR0], ppc->spr[SPROEA_SRR1]);
1036   cfunc_printf_probe(ppc);
475   ppc_device *ppc = (ppc_device *)param;
476   ppc->ppc_cfunc_printf_exception();
1037477}
1038478
479void ppc_device::ppc_cfunc_printf_exception()
480{
481   printf("Exception: type=%2d EPC=%08X MSR=%08X\n", m_core->param0, m_core->spr[SPROEA_SRR0], m_core->spr[SPROEA_SRR1]);
482   ppc_cfunc_printf_probe();
483}
1039484
485
1040486/*-------------------------------------------------
1041487    cfunc_printf_debug - generic printf for
1042488    debugging
r31142r31143
1044490
1045491static void cfunc_printf_debug(void *param)
1046492{
1047   powerpc_state *ppc = (powerpc_state *)param;
1048   printf(ppc->impstate->format, ppc->impstate->arg0, ppc->impstate->arg1);
493   ppc_device *ppc = (ppc_device *)param;
494   ppc->ppc_cfunc_printf_debug();
1049495}
1050496
497void ppc_device::ppc_cfunc_printf_debug()
498{
499   printf(m_core->format, m_core->arg0, m_arg1);
500}
1051501
502
1052503/*-------------------------------------------------
1053504    cfunc_printf_probe - print the current CPU
1054505    state and return
r31142r31143
1056507
1057508static void cfunc_printf_probe(void *param)
1058509{
1059   powerpc_state *ppc = (powerpc_state *)param;
1060   UINT32 pc = (UINT32)(FPTR)param;
510   ppc_device *ppc = (ppc_device *)param;
511   ppc->ppc_cfunc_printf_probe();
512}
1061513
1062   printf(" PC=%08X\n", pc);
514void ppc_device::ppc_cfunc_printf_probe()
515{
516   printf(" PC=%08X\n", m_core->pc);
1063517   printf(" r0=%08X  r1=%08X  r2=%08X  r3=%08X\n",
1064      ppc->r[0], ppc->r[1], ppc->r[2], ppc->r[3]);
518      m_core->r[0], m_core->r[1], m_core->r[2], m_core->r[3]);
1065519   printf(" r4=%08X  r5=%08X  r6=%08X  r7=%08X\n",
1066      ppc->r[4], ppc->r[5], ppc->r[6], ppc->r[7]);
520      m_core->r[4], m_core->r[5], m_core->r[6], m_core->r[7]);
1067521   printf(" r8=%08X  r9=%08X r10=%08X r11=%08X\n",
1068      ppc->r[8], ppc->r[9], ppc->r[10], ppc->r[11]);
522      m_core->r[8], m_core->r[9], m_core->r[10], m_core->r[11]);
1069523   printf("r12=%08X r13=%08X r14=%08X r15=%08X\n",
1070      ppc->r[12], ppc->r[13], ppc->r[14], ppc->r[15]);
524      m_core->r[12], m_core->r[13], m_core->r[14], m_core->r[15]);
1071525   printf("r16=%08X r17=%08X r18=%08X r19=%08X\n",
1072      ppc->r[16], ppc->r[17], ppc->r[18], ppc->r[19]);
526      m_core->r[16], m_core->r[17], m_core->r[18], m_core->r[19]);
1073527   printf("r20=%08X r21=%08X r22=%08X r23=%08X\n",
1074      ppc->r[20], ppc->r[21], ppc->r[22], ppc->r[23]);
528      m_core->r[20], m_core->r[21], m_core->r[22], m_core->r[23]);
1075529   printf("r24=%08X r25=%08X r26=%08X r27=%08X\n",
1076      ppc->r[24], ppc->r[25], ppc->r[26], ppc->r[27]);
530      m_core->r[24], m_core->r[25], m_core->r[26], m_core->r[27]);
1077531   printf("r28=%08X r29=%08X r30=%08X r31=%08X\n",
1078      ppc->r[28], ppc->r[29], ppc->r[30], ppc->r[31]);
532      m_core->r[28], m_core->r[29], m_core->r[30], m_core->r[31]);
1079533}
1080534
1081535
r31142r31143
1086540
1087541static void cfunc_unimplemented(void *param)
1088542{
1089   powerpc_state *ppc = (powerpc_state *)param;
1090   UINT32 opcode = ppc->impstate->arg0;
1091   fatalerror("PC=%08X: Unimplemented op %08X\n", ppc->pc, opcode);
543   ppc_device *ppc = (ppc_device *)param;
544   ppc->ppc_cfunc_unimplemented();
1092545}
1093546
547void ppc_device::ppc_cfunc_unimplemented()
548{
549   UINT32 opcode = m_core->arg0;
550   fatalerror("PC=%08X: Unimplemented op %08X\n", m_core->pc, opcode);
551}
1094552
553static void cfunc_ppccom_tlb_fill(void *param)
554{
555   ppc_device *ppc = (ppc_device *)param;
556   ppc->ppccom_tlb_fill();
557}
1095558
559static void cfunc_ppccom_update_fprf(void *param)
560{
561   ppc_device *ppc = (ppc_device *)param;
562   ppc->ppccom_update_fprf();
563}
564
565static void cfunc_ppccom_dcstore_callback(void *param)
566{
567   ppc_device *ppc = (ppc_device *)param;
568   ppc->ppccom_dcstore_callback();
569}
570
571static void cfunc_ppccom_execute_tlbie(void *param)
572{
573   ppc_device *ppc = (ppc_device *)param;
574   ppc->ppccom_execute_tlbie();
575}
576
577static void cfunc_ppccom_execute_tlbia(void *param)
578{
579   ppc_device *ppc = (ppc_device *)param;
580   ppc->ppccom_execute_tlbia();
581}
582
583static void cfunc_ppccom_execute_tlbl(void *param)
584{
585   ppc_device *ppc = (ppc_device *)param;
586   ppc->ppccom_execute_tlbl();
587}
588
589static void cfunc_ppccom_execute_mfspr(void *param)
590{
591   ppc_device *ppc = (ppc_device *)param;
592   ppc->ppccom_execute_mfspr();
593}
594
595static void cfunc_ppccom_execute_mftb(void *param)
596{
597   ppc_device *ppc = (ppc_device *)param;
598   ppc->ppccom_execute_mftb();
599}
600
601static void cfunc_ppccom_execute_mtspr(void *param)
602{
603   ppc_device *ppc = (ppc_device *)param;
604   ppc->ppccom_execute_mtspr();
605}
606
607static void cfunc_ppccom_tlb_flush(void *param)
608{
609   ppc_device *ppc = (ppc_device *)param;
610   ppc->ppccom_tlb_flush();
611}
612
613static void cfunc_ppccom_execute_mfdcr(void *param)
614{
615   ppc_device *ppc = (ppc_device *)param;
616   ppc->ppccom_execute_mfdcr();
617}
618
619static void cfunc_ppccom_execute_mtdcr(void *param)
620{
621   ppc_device *ppc = (ppc_device *)param;
622   ppc->ppccom_execute_mtdcr();
623}
624
625
1096626/***************************************************************************
1097627    STATIC CODEGEN
1098628***************************************************************************/
r31142r31143
1102632    static entry point
1103633-------------------------------------------------*/
1104634
1105static void static_generate_entry_point(powerpc_state *ppc)
635void ppc_device::static_generate_entry_point()
1106636{
1107   drcuml_state *drcuml = ppc->impstate->drcuml;
1108637   code_label skip = 1;
1109638   drcuml_block *block;
1110639
1111640   /* begin generating */
1112   block = drcuml->begin_block(20);
641   block = m_drcuml->begin_block(20);
1113642
1114643   /* forward references */
1115   alloc_handle(drcuml, &ppc->impstate->nocode, "nocode");
1116   alloc_handle(drcuml, &ppc->impstate->exception_norecover[EXCEPTION_EI], "exception_ei_norecover");
644   alloc_handle(m_drcuml, &m_nocode, "nocode");
645   alloc_handle(m_drcuml, &m_exception_norecover[EXCEPTION_EI], "exception_ei_norecover");
1117646
1118   alloc_handle(drcuml, &ppc->impstate->entry, "entry");
1119   UML_HANDLE(block, *ppc->impstate->entry);                                               // handle  entry
647   alloc_handle(m_drcuml, &m_entry, "entry");
648   UML_HANDLE(block, *m_entry);                                               // handle  entry
1120649
1121650   /* reset the FPU mode */
1122651   UML_AND(block, I0, FPSCR32, 3);                                             // and     i0,fpscr,3
1123   UML_LOAD(block, I0, &ppc->impstate->fpmode[0], I0, SIZE_BYTE, SCALE_x1);        // load    i0,fpmode,i0,byte
652   UML_LOAD(block, I0, &m_fpmode[0], I0, SIZE_BYTE, SCALE_x1);        // load    i0,fpmode,i0,byte
1124653   UML_SETFMOD(block, I0);                                                         // setfmod i0
1125654
1126655   /* load fast integer registers */
1127   load_fast_iregs(ppc, block);                                                            // <load fastregs>
656   load_fast_iregs(block);                                                            // <load fastregs>
1128657
1129658   /* check for interrupts */
1130   UML_TEST(block, mem(&ppc->irq_pending), ~0);                                        // test    [irq_pending],0
659   UML_TEST(block, mem(&m_core->irq_pending), ~0);                                        // test    [irq_pending],0
1131660   UML_JMPc(block, COND_Z, skip);                                                          // jmp     skip,Z
1132661   UML_TEST(block, MSR32, MSR_EE);                                                 // test    msr,MSR_EE
1133662   UML_JMPc(block, COND_Z, skip);                                                          // jmp     skip,Z
1134   UML_MOV(block, I0, mem(&ppc->pc));                                                  // mov     i0,pc
663   UML_MOV(block, I0, mem(&m_core->pc));                                                  // mov     i0,pc
1135664   UML_MOV(block, I1, 0);                                                      // mov     i1,0
1136   UML_CALLH(block, *ppc->impstate->exception_norecover[EXCEPTION_EI]);                        // callh   exception_norecover
665   UML_CALLH(block, *m_exception_norecover[EXCEPTION_EI]);                        // callh   exception_norecover
1137666   UML_LABEL(block, skip);                                                             // skip:
1138667
1139668   /* generate a hash jump via the current mode and PC */
1140   UML_HASHJMP(block, mem(&ppc->impstate->mode), mem(&ppc->pc), *ppc->impstate->nocode);   // hashjmp <mode>,<pc>,nocode
669   UML_HASHJMP(block, mem(&m_core->mode), mem(&m_core->pc), *m_nocode);   // hashjmp <mode>,<pc>,nocode
1141670
1142671   block->end();
1143672}
r31142r31143
1148677    exception handler for "out of code"
1149678-------------------------------------------------*/
1150679
1151static void static_generate_nocode_handler(powerpc_state *ppc)
680void ppc_device::static_generate_nocode_handler()
1152681{
1153   drcuml_state *drcuml = ppc->impstate->drcuml;
1154682   drcuml_block *block;
1155683
1156684   /* begin generating */
1157   block = drcuml->begin_block(10);
685   block = m_drcuml->begin_block(10);
1158686
1159687   /* generate a hash jump via the current mode and PC */
1160   alloc_handle(drcuml, &ppc->impstate->nocode, "nocode");
1161   UML_HANDLE(block, *ppc->impstate->nocode);                                              // handle  nocode
688   alloc_handle(m_drcuml, &m_nocode, "nocode");
689   UML_HANDLE(block, *m_nocode);                                              // handle  nocode
1162690   UML_GETEXP(block, I0);                                                              // getexp  i0
1163   UML_MOV(block, mem(&ppc->pc), I0);                                                  // mov     [pc],i0
1164   save_fast_iregs(ppc, block);                                                            // <save fastregs>
691   UML_MOV(block, mem(&m_core->pc), I0);                                                  // mov     [pc],i0
692   save_fast_iregs(block);                                                            // <save fastregs>
1165693   UML_EXIT(block, EXECUTE_MISSING_CODE);                                              // exit    EXECUTE_MISSING_CODE
1166694
1167695   block->end();
r31142r31143
1173701    out of cycles exception handler
1174702-------------------------------------------------*/
1175703
1176static void static_generate_out_of_cycles(powerpc_state *ppc)
704void ppc_device::static_generate_out_of_cycles()
1177705{
1178   drcuml_state *drcuml = ppc->impstate->drcuml;
1179706   drcuml_block *block;
1180707
1181708   /* begin generating */
1182   block = drcuml->begin_block(10);
709   block = m_drcuml->begin_block(10);
1183710
1184711   /* generate a hash jump via the current mode and PC */
1185   alloc_handle(drcuml, &ppc->impstate->out_of_cycles, "out_of_cycles");
1186   UML_HANDLE(block, *ppc->impstate->out_of_cycles);                                       // handle  out_of_cycles
712   alloc_handle(m_drcuml, &m_out_of_cycles, "out_of_cycles");
713   UML_HANDLE(block, *m_out_of_cycles);                                       // handle  out_of_cycles
1187714   UML_GETEXP(block, I0);                                                              // getexp  i0
1188   UML_MOV(block, mem(&ppc->pc), I0);                                                  // mov     <pc>,i0
1189   save_fast_iregs(ppc, block);                                                            // <save fastregs>
715   UML_MOV(block, mem(&m_core->pc), I0);                                                  // mov     <pc>,i0
716   save_fast_iregs(block);                                                            // <save fastregs>
1190717   UML_EXIT(block, EXECUTE_OUT_OF_CYCLES);                                         // exit    EXECUTE_OUT_OF_CYCLES
1191718
1192719   block->end();
r31142r31143
1198725    TLB mismatch handler
1199726-------------------------------------------------*/
1200727
1201static void static_generate_tlb_mismatch(powerpc_state *ppc)
728void ppc_device::static_generate_tlb_mismatch()
1202729{
1203   drcuml_state *drcuml = ppc->impstate->drcuml;
1204730   drcuml_block *block;
1205731   int isi, exit, label = 1;
1206732
1207733   /* forward references */
1208   alloc_handle(drcuml, &ppc->impstate->exception[EXCEPTION_ISI], "exception_isi");
1209   if (ppc->cap & PPCCAP_603_MMU)
1210      alloc_handle(drcuml, &ppc->impstate->exception[EXCEPTION_ITLBMISS], "exception_itlb_miss");
734   alloc_handle(m_drcuml, &m_exception[EXCEPTION_ISI], "exception_isi");
735   if (m_cap & PPCCAP_603_MMU)
736      alloc_handle(m_drcuml, &m_exception[EXCEPTION_ITLBMISS], "exception_itlb_miss");
1211737
1212738   /* begin generating */
1213   block = drcuml->begin_block(20);
739   block = m_drcuml->begin_block(20);
1214740
1215741   /* generate a hash jump via the current mode and PC */
1216   alloc_handle(drcuml, &ppc->impstate->tlb_mismatch, "tlb_mismatch");
1217   UML_HANDLE(block, *ppc->impstate->tlb_mismatch);                                            // handle  tlb_mismatch
742   alloc_handle(m_drcuml, &m_tlb_mismatch, "tlb_mismatch");
743   UML_HANDLE(block, *m_tlb_mismatch);                                            // handle  tlb_mismatch
1218744   UML_RECOVER(block, I0, MAPVAR_PC);                                                  // recover i0,PC
1219745   UML_SHR(block, I1, I0, 12);                                             // shr     i1,i0,12
1220   UML_LOAD(block, I2, (void *)vtlb_table(ppc->vtlb), I1, SIZE_DWORD, SCALE_x4);   // load    i2,[vtlb],i1,dword
1221   UML_MOV(block, mem(&ppc->param0), I0);                                              // mov     [param0],i0
1222   UML_MOV(block, mem(&ppc->param1), TRANSLATE_FETCH);                             // mov     [param1],TRANSLATE_FETCH
1223   UML_CALLC(block, (c_function)ppccom_tlb_fill, ppc);                                                 // callc   tlbfill,ppc
1224   UML_LOAD(block, I1, (void *)vtlb_table(ppc->vtlb), I1, SIZE_DWORD, SCALE_x4);   // load    i1,[vtlb],i1,dword
746   UML_LOAD(block, I2, (void *)vtlb_table(m_vtlb), I1, SIZE_DWORD, SCALE_x4);   // load    i2,[vtlb],i1,dword
747   UML_MOV(block, mem(&m_core->param0), I0);                                              // mov     [param0],i0
748   UML_MOV(block, mem(&m_core->param1), TRANSLATE_FETCH);                             // mov     [param1],TRANSLATE_FETCH
749   UML_CALLC(block, (c_function)cfunc_ppccom_tlb_fill, this);                                                 // callc   tlbfill,ppc
750   UML_LOAD(block, I1, (void *)vtlb_table(m_vtlb), I1, SIZE_DWORD, SCALE_x4);   // load    i1,[vtlb],i1,dword
1225751   UML_TEST(block, I1, VTLB_FETCH_ALLOWED);                                        // test    i1,VTLB_FETCH_ALLOWED
1226752   UML_JMPc(block, COND_Z, isi = label++);                                                 // jmp     isi,z
1227753   UML_CMP(block, I2, 0);                                                      // cmp     i2,0
1228754   UML_JMPc(block, COND_NZ, exit = label++);                                                   // jmp     exit,nz
1229   UML_HASHJMP(block, mem(&ppc->impstate->mode), I0, *ppc->impstate->nocode);          // hashjmp <mode>,i0,nocode
755   UML_HASHJMP(block, mem(&m_core->mode), I0, *m_nocode);          // hashjmp <mode>,i0,nocode
1230756   UML_LABEL(block, exit);                                                             // exit:
1231   UML_MOV(block, mem(&ppc->pc), I0);                                                  // mov     <pc>,i0
1232   save_fast_iregs(ppc, block);                                                            // <save fastregs>
757   UML_MOV(block, mem(&m_core->pc), I0);                                                  // mov     <pc>,i0
758   save_fast_iregs(block);                                                            // <save fastregs>
1233759   UML_EXIT(block, EXECUTE_MISSING_CODE);                                              // exit    EXECUTE_MISSING_CODE
1234760   UML_LABEL(block, isi);                                                              // isi:
1235   if (!(ppc->cap & PPCCAP_603_MMU))
761   if (!(m_cap & PPCCAP_603_MMU))
1236762   {
1237      UML_MOV(block, SPR32(SPROEA_DSISR), mem(&ppc->param0));                             // mov     [dsisr],[param0]
1238      UML_EXH(block, *ppc->impstate->exception[EXCEPTION_ISI], I0);                   // exh     isi,i0
763      UML_MOV(block, SPR32(SPROEA_DSISR), mem(&m_core->param0));                             // mov     [dsisr],[param0]
764      UML_EXH(block, *m_exception[EXCEPTION_ISI], I0);                   // exh     isi,i0
1239765   }
1240766   else
1241767   {
1242768      UML_MOV(block, SPR32(SPR603_IMISS), I0);                                        // mov     [imiss],i0
1243      UML_MOV(block, SPR32(SPR603_ICMP), mem(&ppc->mmu603_cmp));                          // mov     [icmp],[mmu603_cmp]
1244      UML_MOV(block, SPR32(SPR603_HASH1), mem(&ppc->mmu603_hash[0]));                     // mov     [hash1],[mmu603_hash][0]
1245      UML_MOV(block, SPR32(SPR603_HASH2), mem(&ppc->mmu603_hash[1]));                     // mov     [hash2],[mmu603_hash][1]
1246      UML_EXH(block, *ppc->impstate->exception[EXCEPTION_ITLBMISS], I0);              // exh     itlbmiss,i0
769      UML_MOV(block, SPR32(SPR603_ICMP), mem(&m_core->mmu603_cmp));                          // mov     [icmp],[mmu603_cmp]
770      UML_MOV(block, SPR32(SPR603_HASH1), mem(&m_core->mmu603_hash[0]));                     // mov     [hash1],[mmu603_hash][0]
771      UML_MOV(block, SPR32(SPR603_HASH2), mem(&m_core->mmu603_hash[1]));                     // mov     [hash2],[mmu603_hash][1]
772      UML_EXH(block, *m_exception[EXCEPTION_ITLBMISS], I0);              // exh     itlbmiss,i0
1247773   }
1248774
1249775   block->end();
r31142r31143
1255781    exception handler
1256782-------------------------------------------------*/
1257783
1258static void static_generate_exception(powerpc_state *ppc, UINT8 exception, int recover, const char *name)
784void ppc_device::static_generate_exception(UINT8 exception, int recover, const char *name)
1259785{
1260   drcuml_state *drcuml = ppc->impstate->drcuml;
1261   code_handle *&exception_handle = recover ? ppc->impstate->exception[exception] : ppc->impstate->exception_norecover[exception];
786   code_handle *&exception_handle = recover ? m_exception[exception] : m_exception_norecover[exception];
1262787   UINT32 vector = exception << 8;
1263788   code_label label = 1;
1264789   drcuml_block *block;
1265790
1266791   /* begin generating */
1267   block = drcuml->begin_block(1024);
792   block = m_drcuml->begin_block(1024);
1268793
1269794   /* add a global entry for this */
1270   alloc_handle(drcuml, &exception_handle, name);
795   alloc_handle(m_drcuml, &exception_handle, name);
1271796   UML_HANDLE(block, *exception_handle);                                                   // handle  name
1272797
1273798   /* exception parameter is expected to be the fault address in this case */
r31142r31143
1285810   }
1286811
1287812   /* OEA handling of SRR exceptions */
1288   if (ppc->cap & PPCCAP_OEA)
813   if (m_cap & PPCCAP_OEA)
1289814   {
1290815      UINT32 msrandmask = MSROEA_POW | MSR_EE | MSR_PR | MSROEA_FP | MSROEA_FE0 | MSROEA_SE | MSROEA_BE | MSROEA_FE1 | MSROEA_IR | MSROEA_DR | MSROEA_RI | MSR_LE;
1291816      UINT32 msrormask = 0;
r31142r31143
1296821      {
1297822         code_label not_decrementer;
1298823
1299         UML_TEST(block, mem(&ppc->irq_pending), 0x01);                              // test    [irq_pending],0x01
824         UML_TEST(block, mem(&m_core->irq_pending), 0x01);                              // test    [irq_pending],0x01
1300825         UML_JMPc(block, COND_NZ, not_decrementer = label++);                                // jmp     not_decrementer,nz
1301826         UML_MOV(block, I3, EXCEPTION_DECREMENT << 8);                           // mov     i3,EXCEPTION_DECREMENT << 8
1302         UML_AND(block, mem(&ppc->irq_pending), mem(&ppc->irq_pending), ~0x02);      // and     [irq_pending],[irq_pending],~0x02
827         UML_AND(block, mem(&m_core->irq_pending), mem(&m_core->irq_pending), ~0x02);      // and     [irq_pending],[irq_pending],~0x02
1303828         UML_LABEL(block, not_decrementer);                                          // not_decrementer:
1304829      }
1305830
r31142r31143
1313838         UML_GETEXP(block, I1);                                                      // getexp  i1
1314839         UML_OR(block, SPR32(SPROEA_SRR1), SPR32(SPROEA_SRR1), I1);                  // or      [srr1],[srr1],i1
1315840      }
1316      if (ppc->cap & PPCCAP_603_MMU)
841      if (m_cap & PPCCAP_603_MMU)
1317842      {
1318843         if (exception == EXCEPTION_ITLBMISS)
1319844            UML_OR(block, SPR32(SPROEA_SRR1), SPR32(SPROEA_SRR1), 0x00040000);      // or      [srr1],0x00040000
r31142r31143
1324849      }
1325850
1326851      /* update MSR */
1327      if (ppc->cap & PPCCAP_603_MMU)
852      if (m_cap & PPCCAP_603_MMU)
1328853      {
1329854         if (exception == EXCEPTION_ITLBMISS || exception == EXCEPTION_DTLBMISSL || exception == EXCEPTION_DTLBMISSS)
1330855            msrormask |= MSR603_TGPR;
r31142r31143
1336861      UML_OR(block, I2, I2, msrormask);                                   // or      i2,i2,ormask
1337862      UML_ROLINS(block, I2, I2, 16, MSR_LE);                          // rolins  i2,u2,16,MSR_LE
1338863      UML_MOV(block, MSR32, I2);                                                      // mov     [msr],i2
1339      if (ppc->cap & PPCCAP_603_MMU)
864      if (m_cap & PPCCAP_603_MMU)
1340865      {
1341866         UML_XOR(block, I0, I0, I2);                                     // xor     i0,i0,i2
1342867         UML_TEST(block, I0, MSR603_TGPR);                                       // test    i0,tgpr
1343         UML_CALLHc(block, COND_NZ, *ppc->impstate->swap_tgpr);                              // callh   swap_tgpr,nz
868         UML_CALLHc(block, COND_NZ, *m_swap_tgpr);                              // callh   swap_tgpr,nz
1344869      }
1345      generate_update_mode(ppc, block);                                                   // <update mode>
870      generate_update_mode(block);                                                   // <update mode>
1346871
1347872      /* determine our target PC */
1348      if (ppc->flavor == PPC_MODEL_602)
873      if (m_flavor == PPC_MODEL_602)
1349874         UML_MOV(block, I0, SPR32(SPR602_IBR));                                      // mov     i0,[ibr]
1350875      else
1351876         UML_MOV(block, I0, 0x00000000);                                     // mov     i0,0x00000000
r31142r31143
1355880   }
1356881
1357882   /* 4XX handling of exceptions */
1358   if (ppc->cap & PPCCAP_4XX)
883   if (m_cap & PPCCAP_4XX)
1359884   {
1360885      /* check registers to see the real source of our exception (EI exceptions only) */
1361886      UML_MOV(block, I3, vector);                                             // mov     i3,vector
r31142r31143
1397922      /* finish updating MSR */
1398923      UML_ROLINS(block, I2, I2, 16, MSR_LE);                          // rolins  i2,u2,16,MSR_LE
1399924      UML_MOV(block, MSR32, I2);                                                      // mov     [msr],i2
1400      generate_update_mode(ppc, block);                                                   // <update mode>
925      generate_update_mode(block);                                                   // <update mode>
1401926
1402927      /* program exception flags go to ESR */
1403928      if (exception == EXCEPTION_PROGRAM)
r31142r31143
1415940   if ((PRINTF_EXCEPTIONS && exception != EXCEPTION_EI && exception != EXCEPTION_SYSCALL) ||
1416941      (PRINTF_MMU && (exception == EXCEPTION_ISI || exception == EXCEPTION_DSI)))
1417942   {
1418      UML_MOV(block, mem(&ppc->param0), exception);                                   // mov     [param0],exception
1419      UML_CALLC(block, cfunc_printf_exception, ppc);                                      // callc   cfunc_printf_exception,ppc
943      UML_MOV(block, mem(&m_core->param0), exception);                                   // mov     [param0],exception
944      UML_CALLC(block, cfunc_printf_exception, this);                                      // callc   cfunc_printf_exception,ppc
1420945   }
1421946
1422947   /* adjust cycles */
1423   UML_SUB(block, mem(&ppc->icount), mem(&ppc->icount), I1);                           // sub     icount,icount,cycles
1424   UML_EXHc(block, COND_S, *ppc->impstate->out_of_cycles, I0);                         // exh     out_of_cycles,i0
1425   UML_HASHJMP(block, mem(&ppc->impstate->mode), I0, *ppc->impstate->nocode);          // hashjmp <mode>,i0,nocode
948   UML_SUB(block, mem(&m_core->icount), mem(&m_core->icount), I1);                           // sub     icount,icount,cycles
949   UML_EXHc(block, COND_S, *m_out_of_cycles, I0);                         // exh     out_of_cycles,i0
950   UML_HASHJMP(block, mem(&m_core->mode), I0, *m_nocode);          // hashjmp <mode>,i0,nocode
1426951
1427952   block->end();
1428953}
r31142r31143
1432957    static_generate_memory_accessor
1433958------------------------------------------------------------------*/
1434959
1435static void static_generate_memory_accessor(powerpc_state *ppc, int mode, int size, int iswrite, int ismasked, const char *name, code_handle *&handleptr, code_handle *masked)
960void ppc_device::static_generate_memory_accessor(int mode, int size, int iswrite, int ismasked, const char *name, code_handle *&handleptr, code_handle *masked)
1436961{
1437962   /* on entry, address is in I0; data for writes is in I1; masks are in I2 */
1438963   /* on exit, read result is in I0 */
1439964   /* routine trashes I0-I3 */
1440   drcuml_state *drcuml = ppc->impstate->drcuml;
1441   int fastxor = BYTE8_XOR_BE(0) >> (int)(ppc->device->space_config(AS_PROGRAM)->m_databus_width < 64);
965   int fastxor = BYTE8_XOR_BE(0) >> (int)(space_config(AS_PROGRAM)->m_databus_width < 64);
1442966   drcuml_block *block;
1443967   int translate_type;
1444968   int tlbreturn = 0;
r31142r31143
1454978      translate_type = iswrite ? TRANSLATE_WRITE : TRANSLATE_READ;
1455979
1456980   /* begin generating */
1457   block = drcuml->begin_block(1024);
981   block = m_drcuml->begin_block(1024);
1458982
1459983   /* add a global entry for this */
1460   alloc_handle(drcuml, &handleptr, name);
984   alloc_handle(m_drcuml, &handleptr, name);
1461985   UML_HANDLE(block, *handleptr);                                                          // handle  *handleptr
1462986
1463987   /* check for unaligned accesses and break into two */
1464988   if (!ismasked && size != 1)
1465989   {
1466990      /* in little-endian mode, anything misaligned generates an exception */
1467      if ((mode & MODE_LITTLE_ENDIAN) || masked == NULL || !(ppc->cap & PPCCAP_MISALIGNED))
991      if ((mode & MODE_LITTLE_ENDIAN) || masked == NULL || !(m_cap & PPCCAP_MISALIGNED))
1468992      {
1469993         UML_TEST(block, I0, size - 1);                                      // test    i0,size-1
1470994         UML_JMPc(block, COND_NZ, alignex = label++);                                        // jmp     alignex,nz
r31142r31143
14941018   }
14951019
14961020   /* general case: assume paging and perform a translation */
1497   if (((ppc->cap & PPCCAP_OEA) && (mode & MODE_DATA_TRANSLATION)) || (iswrite && (ppc->cap & PPCCAP_4XX) && (mode & MODE_PROTECTION)))
1021   if (((m_cap & PPCCAP_OEA) && (mode & MODE_DATA_TRANSLATION)) || (iswrite && (m_cap & PPCCAP_4XX) && (mode & MODE_PROTECTION)))
14981022   {
14991023      UML_SHR(block, I3, I0, 12);                                         // shr     i3,i0,12
1500      UML_LOAD(block, I3, (void *)vtlb_table(ppc->vtlb), I3, SIZE_DWORD, SCALE_x4);// load    i3,[vtlb],i3,dword
1024      UML_LOAD(block, I3, (void *)vtlb_table(m_vtlb), I3, SIZE_DWORD, SCALE_x4);// load    i3,[vtlb],i3,dword
15011025      UML_TEST(block, I3, (UINT64)1 << translate_type);                           // test    i3,1 << translate_type
15021026      UML_JMPc(block, COND_Z, tlbmiss = label++);                                         // jmp     tlbmiss,z
15031027      UML_LABEL(block, tlbreturn = label++);                                          // tlbreturn:
15041028      UML_ROLINS(block, I0, I3, 0, 0xfffff000);                       // rolins  i0,i3,0,0xfffff000
15051029   }
1506   else if (ppc->cap & PPCCAP_4XX)
1030   else if (m_cap & PPCCAP_4XX)
15071031      UML_AND(block, I0, I0, 0x7fffffff);                                 // and     i0,i0,0x7fffffff
15081032   UML_XOR(block, I0, I0, (mode & MODE_LITTLE_ENDIAN) ? (8 - size) : 0);   // xor     i0,i0,8-size
15091033
1510   if ((ppc->device->machine().debug_flags & DEBUG_FLAG_ENABLED) != 0)
1034   if ((machine().debug_flags & DEBUG_FLAG_ENABLED) != 0)
15111035      for (ramnum = 0; ramnum < PPC_MAX_FASTRAM; ramnum++)
1512         if (ppc->impstate->fastram[ramnum].base != NULL && (!iswrite || !ppc->impstate->fastram[ramnum].readonly))
1036         if (m_fastram[ramnum].base != NULL && (!iswrite || !m_fastram[ramnum].readonly))
15131037         {
1514            void *fastbase = (UINT8 *)ppc->impstate->fastram[ramnum].base - ppc->impstate->fastram[ramnum].start;
1038            void *fastbase = (UINT8 *)m_fastram[ramnum].base - m_fastram[ramnum].start;
15151039            UINT32 skip = label++;
15161040
1517            if (ppc->impstate->fastram[ramnum].end != 0xffffffff)
1041            if (m_fastram[ramnum].end != 0xffffffff)
15181042            {
1519               UML_CMP(block, I0, ppc->impstate->fastram[ramnum].end);         // cmp     i0,end
1043               UML_CMP(block, I0, m_fastram[ramnum].end);         // cmp     i0,end
15201044               UML_JMPc(block, COND_A, skip);                                              // ja      skip
15211045            }
1522            if (ppc->impstate->fastram[ramnum].start != 0x00000000)
1046            if (m_fastram[ramnum].start != 0x00000000)
15231047            {
1524               UML_CMP(block, I0, ppc->impstate->fastram[ramnum].start);           // cmp     i0,fastram_start
1048               UML_CMP(block, I0, m_fastram[ramnum].start);           // cmp     i0,fastram_start
15251049               UML_JMPc(block, COND_B, skip);                                              // jb      skip
15261050            }
15271051
r31142r31143
16611185      {
16621186         if (iswrite)
16631187         {
1664            UML_MOV(block, mem(&ppc->impstate->tempaddr), I0);                      // mov     [tempaddr],i0
1665            UML_MOV(block, mem(&ppc->impstate->tempdata.w.l), I1);                  // mov     [tempdata],i1
1188            UML_MOV(block, mem(&m_core->tempaddr), I0);                      // mov     [tempaddr],i0
1189            UML_MOV(block, mem(&m_core->tempdata.w.l), I1);                  // mov     [tempdata],i1
16661190            UML_SUB(block, I0, I0, 1);                                  // sub     i0,i0,1
16671191            UML_SHR(block, I1, I1, 8);                                  // shr     i1,i1,8
16681192            UML_MOV(block, I2, 0x00ff);                                     // mov     i2,0x00ff
16691193            UML_CALLH(block, *masked);                                                  // callh   masked
1670            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 1);               // add     i0,[tempaddr],1
1671            UML_SHL(block, I1, mem(&ppc->impstate->tempdata.w.l), 8);           // shl     i1,[tempdata],8
1194            UML_ADD(block, I0, mem(&m_core->tempaddr), 1);               // add     i0,[tempaddr],1
1195            UML_SHL(block, I1, mem(&m_core->tempdata.w.l), 8);           // shl     i1,[tempdata],8
16721196            UML_MOV(block, I2, 0xff00);                                     // mov     i2,0xff00
16731197            UML_CALLH(block, *masked);                                                  // callh   masked
16741198         }
16751199         else
16761200         {
1677            UML_MOV(block, mem(&ppc->impstate->tempaddr), I0);                      // mov     [tempaddr],i0
1201            UML_MOV(block, mem(&m_core->tempaddr), I0);                      // mov     [tempaddr],i0
16781202            UML_SUB(block, I0, I0, 1);                                  // sub     i0,i0,1
16791203            UML_MOV(block, I2, 0x00ff);                                     // mov     i2,0x00ff
16801204            UML_CALLH(block, *masked);                                                  // callh   masked
1681            UML_SHL(block, mem(&ppc->impstate->tempdata.w.l), I0, 8);           // shl     [tempdata],i0,8
1682            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 1);               // add     i0,[tempaddr],1
1205            UML_SHL(block, mem(&m_core->tempdata.w.l), I0, 8);           // shl     [tempdata],i0,8
1206            UML_ADD(block, I0, mem(&m_core->tempaddr), 1);               // add     i0,[tempaddr],1
16831207            UML_MOV(block, I2, 0xff00);                                     // mov     i2,0xff00
16841208            UML_CALLH(block, *masked);                                                  // callh   masked
16851209            UML_SHR(block, I0, I0, 8);                                  // shr     i0,i0,8
1686            UML_OR(block, I0, I0, mem(&ppc->impstate->tempdata.w.l));           // or      i0,i0,[tempdata]
1210            UML_OR(block, I0, I0, mem(&m_core->tempdata.w.l));           // or      i0,i0,[tempdata]
16871211         }
16881212      }
16891213      else if (size == 4)
r31142r31143
16911215         int offs2, offs3;
16921216         if (iswrite)
16931217         {
1694            UML_MOV(block, mem(&ppc->impstate->tempaddr), I0);                      // mov     [tempaddr],i0
1695            UML_MOV(block, mem(&ppc->impstate->tempdata.w.l), I1);                  // mov     [tempdata],i1
1218            UML_MOV(block, mem(&m_core->tempaddr), I0);                      // mov     [tempaddr],i0
1219            UML_MOV(block, mem(&m_core->tempdata.w.l), I1);                  // mov     [tempdata],i1
16961220            UML_TEST(block, I0, 2);                                         // test    i0,i0,2
16971221            UML_JMPc(block, COND_NZ, offs2 = label++);                                  // jnz     offs2
16981222            UML_SUB(block, I0, I0, 1);                                  // sub     i0,i0,1
16991223            UML_SHR(block, I1, I1, 8);                                  // shr     i1,i1,8
17001224            UML_MOV(block, I2, 0x00ffffff);                                 // mov     i2,0x00ffffff
17011225            UML_CALLH(block, *masked);                                                  // callh   masked
1702            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 3);               // add     i0,[tempaddr],3
1703            UML_SHL(block, I1, mem(&ppc->impstate->tempdata.w.l), 24);      // shl     i1,[tempdata],24
1226            UML_ADD(block, I0, mem(&m_core->tempaddr), 3);               // add     i0,[tempaddr],3
1227            UML_SHL(block, I1, mem(&m_core->tempdata.w.l), 24);      // shl     i1,[tempdata],24
17041228            UML_MOV(block, I2, 0xff000000);                                 // mov     i2,0xff000000
17051229            UML_CALLH(block, *masked);                                                  // callh   masked
17061230            UML_RET(block);                                                             // ret
r31142r31143
17111235            UML_SHR(block, I1, I1, 16);                                 // shr     i1,i1,16
17121236            UML_MOV(block, I2, 0x0000ffff);                                 // mov     i2,0x0000ffff
17131237            UML_CALLH(block, *masked);                                                  // callh   masked
1714            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 2);               // add     i0,[tempaddr],2
1715            UML_SHL(block, I1, mem(&ppc->impstate->tempdata.w.l), 16);      // shl     i1,[tempdata],16
1238            UML_ADD(block, I0, mem(&m_core->tempaddr), 2);               // add     i0,[tempaddr],2
1239            UML_SHL(block, I1, mem(&m_core->tempdata.w.l), 16);      // shl     i1,[tempdata],16
17161240            UML_MOV(block, I2, 0xffff0000);                                 // mov     i2,0xffff0000
17171241            UML_CALLH(block, *masked);                                                  // callh   masked
17181242            UML_RET(block);                                                             // ret
r31142r31143
17211245            UML_SHR(block, I1, I1, 24);                                 // shr     i1,i1,24
17221246            UML_MOV(block, I2, 0x000000ff);                                 // mov     i2,0x000000ff
17231247            UML_CALLH(block, *masked);                                                  // callh   masked
1724            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 1);               // add     i0,[tempaddr],1
1725            UML_SHL(block, I1, mem(&ppc->impstate->tempdata.w.l), 8);           // shl     i1,[tempdata],8
1248            UML_ADD(block, I0, mem(&m_core->tempaddr), 1);               // add     i0,[tempaddr],1
1249            UML_SHL(block, I1, mem(&m_core->tempdata.w.l), 8);           // shl     i1,[tempdata],8
17261250            UML_MOV(block, I2, 0xffffff00);                                 // mov     i2,0xffffff00
17271251            UML_CALLH(block, *masked);                                                  // callh   masked
17281252         }
17291253         else
17301254         {
1731            UML_MOV(block, mem(&ppc->impstate->tempaddr), I0);                      // mov     [tempaddr],i0
1255            UML_MOV(block, mem(&m_core->tempaddr), I0);                      // mov     [tempaddr],i0
17321256            UML_TEST(block, I0, 2);                                         // test    i0,i0,2
17331257            UML_JMPc(block, COND_NZ, offs2 = label++);                                  // jnz     offs2
17341258            UML_SUB(block, I0, I0, 1);                                  // sub     i0,i0,1
17351259            UML_MOV(block, I2, 0x00ffffff);                                 // mov     i2,0x00ffffff
17361260            UML_CALLH(block, *masked);                                                  // callh   masked
1737            UML_SHL(block, mem(&ppc->impstate->tempdata.w.l), I0, 8);           // shl     [tempdata],i0,8
1738            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 3);               // add     i0,[tempaddr],3
1261            UML_SHL(block, mem(&m_core->tempdata.w.l), I0, 8);           // shl     [tempdata],i0,8
1262            UML_ADD(block, I0, mem(&m_core->tempaddr), 3);               // add     i0,[tempaddr],3
17391263            UML_MOV(block, I2, 0xff000000);                                 // mov     i2,0xff000000
17401264            UML_CALLH(block, *masked);                                                  // callh   masked
17411265            UML_SHR(block, I0, I0, 24);                                 // shr     i0,i0,24
1742            UML_OR(block, I0, I0, mem(&ppc->impstate->tempdata.w.l));           // or      i0,i0,[tempdata]
1266            UML_OR(block, I0, I0, mem(&m_core->tempdata.w.l));           // or      i0,i0,[tempdata]
17431267            UML_RET(block);                                                             // ret
17441268            UML_LABEL(block, offs2);                                                // offs2:
17451269            UML_TEST(block, I0, 1);                                         // test    i0,i0,1
r31142r31143
17471271            UML_SUB(block, I0, I0, 2);                                  // sub     i0,i0,2
17481272            UML_MOV(block, I2, 0x0000ffff);                                 // mov     i2,0x0000ffff
17491273            UML_CALLH(block, *masked);                                                  // callh   masked
1750            UML_SHL(block, mem(&ppc->impstate->tempdata.w.l), I0, 16);      // shl     [tempdata],i0,16
1751            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 2);               // add     i0,[tempaddr],2
1274            UML_SHL(block, mem(&m_core->tempdata.w.l), I0, 16);      // shl     [tempdata],i0,16
1275            UML_ADD(block, I0, mem(&m_core->tempaddr), 2);               // add     i0,[tempaddr],2
17521276            UML_MOV(block, I2, 0xffff0000);                                 // mov     i2,0xffff0000
17531277            UML_CALLH(block, *masked);                                                  // callh   masked
17541278            UML_SHR(block, I0, I0, 16);                                 // shr     i0,i0,16
1755            UML_OR(block, I0, I0, mem(&ppc->impstate->tempdata.w.l));           // or      i0,i0,[tempdata]
1279            UML_OR(block, I0, I0, mem(&m_core->tempdata.w.l));           // or      i0,i0,[tempdata]
17561280            UML_RET(block);                                                             // ret
17571281            UML_LABEL(block, offs3);                                                // offs3:
17581282            UML_SUB(block, I0, I0, 3);                                  // sub     i0,i0,3
17591283            UML_MOV(block, I2, 0x000000ff);                                 // mov     i2,0x000000ff
17601284            UML_CALLH(block, *masked);                                                  // callh   masked
1761            UML_SHL(block, mem(&ppc->impstate->tempdata.w.l), I0, 24);      // shl     [tempdata],i0,24
1762            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 1);               // add     i0,[tempaddr],1
1285            UML_SHL(block, mem(&m_core->tempdata.w.l), I0, 24);      // shl     [tempdata],i0,24
1286            UML_ADD(block, I0, mem(&m_core->tempaddr), 1);               // add     i0,[tempaddr],1
17631287            UML_MOV(block, I2, 0xffffff00);                                 // mov     i2,0xffffff00
17641288            UML_CALLH(block, *masked);                                                  // callh   masked
17651289            UML_SHR(block, I0, I0, 8);                                  // shr     i0,i0,8
1766            UML_OR(block, I0, I0, mem(&ppc->impstate->tempdata.w.l));           // or      i0,i0,[tempdata]
1290            UML_OR(block, I0, I0, mem(&m_core->tempdata.w.l));           // or      i0,i0,[tempdata]
17671291         }
17681292      }
17691293      else if (size == 8)
17701294      {
17711295         if (iswrite)
17721296         {
1773            UML_MOV(block, mem(&ppc->impstate->tempaddr), I0);                      // mov     [tempaddr],i0
1774            UML_DMOV(block, mem(&ppc->impstate->tempdata.d), I1);                   // dmov    [tempdata],i1
1297            UML_MOV(block, mem(&m_core->tempaddr), I0);                      // mov     [tempaddr],i0
1298            UML_DMOV(block, mem(&m_core->tempdata.d), I1);                   // dmov    [tempdata],i1
17751299            UML_DSHR(block, I1, I1, 32);                                            // dshr    i1,i1,32
17761300            UML_DMOV(block, I2, U64(0x00000000ffffffff));                           // dmov    i2,0x00000000ffffffff
17771301            UML_CALLH(block, *masked);                                              // callh   masked
1778            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 4);                   // add     i0,[tempaddr],4
1779            UML_DSHL(block, I1, mem(&ppc->impstate->tempdata.d), 32);               // dshl    i1,[tempdata],32
1302            UML_ADD(block, I0, mem(&m_core->tempaddr), 4);                   // add     i0,[tempaddr],4
1303            UML_DSHL(block, I1, mem(&m_core->tempdata.d), 32);               // dshl    i1,[tempdata],32
17801304            UML_DMOV(block, I2, U64(0xffffffff00000000));                           // dmov    i2,0xffffffff00000000
17811305            UML_CALLH(block, *masked);                                              // callh   masked
17821306         }
17831307         else
17841308         {
1785            UML_MOV(block, mem(&ppc->impstate->tempaddr), I0);                      // mov     [tempaddr],i0
1309            UML_MOV(block, mem(&m_core->tempaddr), I0);                      // mov     [tempaddr],i0
17861310            UML_DMOV(block, I2, U64(0x00000000ffffffff));                           // mov     i2,0x00000000ffffffff
17871311            UML_CALLH(block, *masked);                                              // callh   masked
1788            UML_DSHL(block, mem(&ppc->impstate->tempdata.d), I0, 32);               // dshl    [tempdata],i0,32
1789            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 4);                   // add     i0,[tempaddr],4
1312            UML_DSHL(block, mem(&m_core->tempdata.d), I0, 32);               // dshl    [tempdata],i0,32
1313            UML_ADD(block, I0, mem(&m_core->tempaddr), 4);                   // add     i0,[tempaddr],4
17901314            UML_DMOV(block, I2, U64(0xffffffff00000000));                           // dmov    i2,0xffffffff00000000
17911315            UML_CALLH(block, *masked);                                              // callh   masked
17921316            UML_DSHR(block, I0, I0, 32);                                            // dshr    i0,i0,32
1793            UML_DOR(block, I0, I0, mem(&ppc->impstate->tempdata.d));                // dor     i0,i0,[tempdata]
1317            UML_DOR(block, I0, I0, mem(&m_core->tempdata.d));                // dor     i0,i0,[tempdata]
17941318         }
17951319      }
17961320      UML_RET(block);                                                                     // ret
r31142r31143
18011325   {
18021326      UML_LABEL(block, alignex);                                                      // alignex:
18031327      UML_RECOVER(block, SPR32(SPROEA_DSISR), MAPVAR_DSISR);                              // recover [dsisr],DSISR
1804      UML_EXH(block, *ppc->impstate->exception[EXCEPTION_ALIGN], I0);                 // exh     align,i0
1328      UML_EXH(block, *m_exception[EXCEPTION_ALIGN], I0);                 // exh     align,i0
18051329   }
18061330
18071331   /* handle a TLB miss */
18081332   if (tlbmiss != 0)
18091333   {
18101334      UML_LABEL(block, tlbmiss);                                                      // tlbmiss:
1811      UML_MOV(block, mem(&ppc->param0), I0);                                          // mov     [param0],i0
1812      UML_MOV(block, mem(&ppc->param1), translate_type);                              // mov     [param1],translate_type
1813      UML_CALLC(block, (c_function)ppccom_tlb_fill, ppc);                                             // callc   tlbfill,ppc
1335      UML_MOV(block, mem(&m_core->param0), I0);                                          // mov     [param0],i0
1336      UML_MOV(block, mem(&m_core->param1), translate_type);                              // mov     [param1],translate_type
1337      UML_CALLC(block, (c_function)cfunc_ppccom_tlb_fill, this);                                             // callc   tlbfill,ppc
18141338      UML_SHR(block, I3, I0, 12);                                         // shr     i3,i0,12
1815      UML_LOAD(block, I3, (void *)vtlb_table(ppc->vtlb), I3, SIZE_DWORD, SCALE_x4);// load    i3,[vtlb],i3,dword
1339      UML_LOAD(block, I3, (void *)vtlb_table(m_vtlb), I3, SIZE_DWORD, SCALE_x4);// load    i3,[vtlb],i3,dword
18161340      UML_TEST(block, I3, (UINT64)1 << translate_type);                           // test    i3,1 << translate_type
18171341      UML_JMPc(block, COND_NZ, tlbreturn);                                                    // jmp     tlbreturn,nz
18181342
18191343      /* 4XX case: protection exception */
1820      if (ppc->cap & PPCCAP_4XX)
1344      if (m_cap & PPCCAP_4XX)
18211345      {
18221346         UML_MOV(block, SPR32(SPR4XX_DEAR), I0);                                 // mov     [dear],i0
1823         UML_EXH(block, *ppc->impstate->exception[EXCEPTION_DSI], I0);               // exh     dsi,i0
1347         UML_EXH(block, *m_exception[EXCEPTION_DSI], I0);               // exh     dsi,i0
18241348      }
18251349
18261350      /* 603 case: TLBMISS exception */
1827      else if (ppc->cap & PPCCAP_603_MMU)
1351      else if (m_cap & PPCCAP_603_MMU)
18281352      {
18291353         UML_MOV(block, SPR32(SPR603_DMISS), I0);                                    // mov     [dmiss],i0
1830         UML_MOV(block, SPR32(SPR603_DCMP), mem(&ppc->mmu603_cmp));                      // mov     [dcmp],[mmu603_cmp]
1831         UML_MOV(block, SPR32(SPR603_HASH1), mem(&ppc->mmu603_hash[0]));                 // mov     [hash1],[mmu603_hash][0]
1832         UML_MOV(block, SPR32(SPR603_HASH2), mem(&ppc->mmu603_hash[1]));                 // mov     [hash2],[mmu603_hash][1]
1354         UML_MOV(block, SPR32(SPR603_DCMP), mem(&m_core->mmu603_cmp));                      // mov     [dcmp],[mmu603_cmp]
1355         UML_MOV(block, SPR32(SPR603_HASH1), mem(&m_core->mmu603_hash[0]));                 // mov     [hash1],[mmu603_hash][0]
1356         UML_MOV(block, SPR32(SPR603_HASH2), mem(&m_core->mmu603_hash[1]));                 // mov     [hash2],[mmu603_hash][1]
18331357         if (iswrite)
1834            UML_EXH(block, *ppc->impstate->exception[EXCEPTION_DTLBMISSS], I0);     // exh     dtlbmisss,i0
1358            UML_EXH(block, *m_exception[EXCEPTION_DTLBMISSS], I0);     // exh     dtlbmisss,i0
18351359         else
1836            UML_EXH(block, *ppc->impstate->exception[EXCEPTION_DTLBMISSL], I0);     // exh     dtlbmissl,i0
1360            UML_EXH(block, *m_exception[EXCEPTION_DTLBMISSL], I0);     // exh     dtlbmissl,i0
18371361      }
18381362
18391363      /* general case: DSI exception */
18401364      else
18411365      {
1842         UML_MOV(block, SPR32(SPROEA_DSISR), mem(&ppc->param0));                         // mov     [dsisr],[param0]
1843         UML_EXH(block, *ppc->impstate->exception[EXCEPTION_DSI], I0);               // exh     dsi,i0
1366         UML_MOV(block, SPR32(SPROEA_DSISR), mem(&m_core->param0));                         // mov     [dsisr],[param0]
1367         UML_EXH(block, *m_exception[EXCEPTION_DSI], I0);               // exh     dsi,i0
18441368      }
18451369   }
18461370
r31142r31143
18531377    subroutine to swap GPR0-3 with TGPR0-3
18541378-------------------------------------------------*/
18551379
1856static void static_generate_swap_tgpr(powerpc_state *ppc)
1380void ppc_device::static_generate_swap_tgpr()
18571381{
1858   drcuml_state *drcuml = ppc->impstate->drcuml;
18591382   drcuml_block *block;
18601383   int regnum;
18611384
18621385   /* begin generating */
1863   block = drcuml->begin_block(30);
1386   block = m_drcuml->begin_block(30);
18641387
18651388   /* generate a hash jump via the current mode and PC */
1866   alloc_handle(drcuml, &ppc->impstate->swap_tgpr, "swap_tgpr");
1867   UML_HANDLE(block, *ppc->impstate->swap_tgpr);                                           // handle  swap_tgpr
1389   alloc_handle(m_drcuml, &m_swap_tgpr, "swap_tgpr");
1390   UML_HANDLE(block, *m_swap_tgpr);                                           // handle  swap_tgpr
18681391   for (regnum = 0; regnum < 4; regnum++)
18691392   {
18701393      UML_MOV(block, I1, R32(regnum));                                                // mov     i1,r[regnum]
1871      UML_MOV(block, R32(regnum), mem(&ppc->mmu603_r[regnum]));                           // mov     r[regnum],mmu603_r[regnum]
1872      UML_MOV(block, mem(&ppc->mmu603_r[regnum]), I1);                                // mov     mmu603_r[regnum],i1
1394      UML_MOV(block, R32(regnum), mem(&m_core->mmu603_r[regnum]));                           // mov     r[regnum],mmu603_r[regnum]
1395      UML_MOV(block, mem(&m_core->mmu603_r[regnum]), I1);                                // mov     mmu603_r[regnum],i1
18731396   }
18741397   UML_RET(block);                                                                         // ret
18751398
r31142r31143
18831406    for each possible register
18841407-------------------------------------------------*/
18851408
1886static void static_generate_lsw_entries(powerpc_state *ppc, int mode)
1409void ppc_device::static_generate_lsw_entries(int mode)
18871410{
1888   drcuml_state *drcuml = ppc->impstate->drcuml;
18891411   drcuml_block *block;
18901412   int regnum;
18911413
18921414   /* begin generating */
1893   block = drcuml->begin_block(32 * 30);
1415   block = m_drcuml->begin_block(32 * 30);
18941416
18951417   /* iterate over all possible registers */
18961418   for (regnum = 0; regnum < 32; regnum++)
r31142r31143
18991421
19001422      /* allocate a handle */
19011423      sprintf(temp, "lsw%d", regnum);
1902      alloc_handle(drcuml, &ppc->impstate->lsw[mode][regnum], temp);
1903      UML_HANDLE(block, *ppc->impstate->lsw[mode][regnum]);                               // handle  lsw<regnum>
1424      alloc_handle(m_drcuml, &m_lsw[mode][regnum], temp);
1425      UML_HANDLE(block, *m_lsw[mode][regnum]);                               // handle  lsw<regnum>
19041426      UML_LABEL(block, regnum);                                                       // regnum:
1905      UML_ADD(block, I0, mem(&ppc->impstate->updateaddr), 0);                 // add     i0,[updateaddr],0
1906      UML_CALLH(block, *ppc->impstate->read8[mode]);                                      // callh   read8
1427      UML_ADD(block, I0, mem(&m_core->updateaddr), 0);                 // add     i0,[updateaddr],0
1428      UML_CALLH(block, *m_read8[mode]);                                      // callh   read8
19071429      UML_ROLAND(block, R32(regnum), I0, 24, 0xff000000);                 // roland  reg,i0,24,0xff000000
1908      UML_SUB(block, mem(&ppc->impstate->swcount), mem(&ppc->impstate->swcount), 1);  // sub     [swcount],[swcount],1
1430      UML_SUB(block, mem(&m_core->swcount), mem(&m_core->swcount), 1);  // sub     [swcount],[swcount],1
19091431      UML_RETc(block, COND_Z);                                                                // ret     z
1910      UML_ADD(block, I0, mem(&ppc->impstate->updateaddr), 1);                 // add     i0,[updateaddr],1
1911      UML_CALLH(block, *ppc->impstate->read8[mode]);                                      // callh   read8
1432      UML_ADD(block, I0, mem(&m_core->updateaddr), 1);                 // add     i0,[updateaddr],1
1433      UML_CALLH(block, *m_read8[mode]);                                      // callh   read8
19121434      UML_ROLAND(block, I0, I0, 16, 0x00ff0000);                      // roland  i0,i0,16,0x00ff0000
19131435      UML_OR(block, R32(regnum), R32(regnum), I0);                                    // or      reg,i0
1914      UML_SUB(block, mem(&ppc->impstate->swcount), mem(&ppc->impstate->swcount), 1);  // sub     [swcount],[swcount],1
1436      UML_SUB(block, mem(&m_core->swcount), mem(&m_core->swcount), 1);  // sub     [swcount],[swcount],1
19151437      UML_RETc(block, COND_Z);                                                                // ret     z
1916      UML_ADD(block, I0, mem(&ppc->impstate->updateaddr), 2);                 // add     i0,[updateaddr],2
1917      UML_CALLH(block, *ppc->impstate->read8[mode]);                                      // callh   read8
1438      UML_ADD(block, I0, mem(&m_core->updateaddr), 2);                 // add     i0,[updateaddr],2
1439      UML_CALLH(block, *m_read8[mode]);                                      // callh   read8
19181440      UML_ROLAND(block, I0, I0, 8, 0x0000ff00);                       // roland  i0,i0,8,0x0000ff00
19191441      UML_OR(block, R32(regnum), R32(regnum), I0);                                    // or      reg,i0
1920      UML_SUB(block, mem(&ppc->impstate->swcount), mem(&ppc->impstate->swcount), 1);  // sub     [swcount],[swcount],1
1442      UML_SUB(block, mem(&m_core->swcount), mem(&m_core->swcount), 1);  // sub     [swcount],[swcount],1
19211443      UML_RETc(block, COND_Z);                                                                // ret     z
1922      UML_ADD(block, I0, mem(&ppc->impstate->updateaddr), 3);                 // add     i0,[updateaddr],3
1923      UML_ADD(block, mem(&ppc->impstate->updateaddr), I0, 1);                 // add     [updateaddr],i0,1
1924      UML_CALLH(block, *ppc->impstate->read8[mode]);                                      // callh   read8
1444      UML_ADD(block, I0, mem(&m_core->updateaddr), 3);                 // add     i0,[updateaddr],3
1445      UML_ADD(block, mem(&m_core->updateaddr), I0, 1);                 // add     [updateaddr],i0,1
1446      UML_CALLH(block, *m_read8[mode]);                                      // callh   read8
19251447      UML_ROLAND(block, I0, I0, 0, 0x000000ff);                       // roland  i0,i0,0,0x000000ff
19261448      UML_OR(block, R32(regnum), R32(regnum), I0);                                    // or      reg,i0
1927      UML_SUB(block, mem(&ppc->impstate->swcount), mem(&ppc->impstate->swcount), 1);  // sub     [swcount],[swcount],1
1449      UML_SUB(block, mem(&m_core->swcount), mem(&m_core->swcount), 1);  // sub     [swcount],[swcount],1
19281450      UML_RETc(block, COND_Z);                                                                // ret     z
19291451      UML_JMP(block, (regnum + 1) % 32);                                                  // jmp     nextreg
19301452   }
r31142r31143
19391461    for each possible register
19401462-------------------------------------------------*/
19411463
1942static void static_generate_stsw_entries(powerpc_state *ppc, int mode)
1464void ppc_device::static_generate_stsw_entries(int mode)
19431465{
1944   drcuml_state *drcuml = ppc->impstate->drcuml;
19451466   drcuml_block *block;
1946   int regnum;
19471467
19481468   /* begin generating */
1949   block = drcuml->begin_block(32 * 30);
1469   block = m_drcuml->begin_block(32 * 30);
19501470
19511471   /* iterate over all possible registers */
1952   for (regnum = 0; regnum < 32; regnum++)
1472   for (int regnum = 0; regnum < 32; regnum++)
19531473   {
19541474      char temp[20];
19551475
19561476      /* allocate a handle */
19571477      sprintf(temp, "stsw%d", regnum);
1958      alloc_handle(drcuml, &ppc->impstate->stsw[mode][regnum], temp);
1959      UML_HANDLE(block, *ppc->impstate->stsw[mode][regnum]);                              // handle  stsw<regnum>
1478      alloc_handle(m_drcuml, &m_stsw[mode][regnum], temp);
1479      UML_HANDLE(block, *m_stsw[mode][regnum]);                              // handle  stsw<regnum>
19601480      UML_LABEL(block, regnum);                                                       // regnum:
1961      UML_ADD(block, I0, mem(&ppc->impstate->updateaddr), 0);                 // add     i0,[updateaddr],0
1481      UML_ADD(block, I0, mem(&m_core->updateaddr), 0);                 // add     i0,[updateaddr],0
19621482      UML_ROLAND(block, I1, R32(regnum), 8, 0xff);                            // roland  i1,regnum,8,0xff
1963      UML_CALLH(block, *ppc->impstate->write8[mode]);                                     // callh   write8
1964      UML_SUB(block, mem(&ppc->impstate->swcount), mem(&ppc->impstate->swcount), 1);  // sub     [swcount],[swcount],1
1483      UML_CALLH(block, *m_write8[mode]);                                     // callh   write8
1484      UML_SUB(block, mem(&m_core->swcount), mem(&m_core->swcount), 1);  // sub     [swcount],[swcount],1
19651485      UML_RETc(block, COND_Z);                                                                // ret     z
1966      UML_ADD(block, I0, mem(&ppc->impstate->updateaddr), 1);                 // add     i0,[updateaddr],1
1486      UML_ADD(block, I0, mem(&m_core->updateaddr), 1);                 // add     i0,[updateaddr],1
19671487      UML_ROLAND(block, I1, R32(regnum), 16, 0xff);                       // roland  i1,regnum,16,0xff
1968      UML_CALLH(block, *ppc->impstate->write8[mode]);                                     // callh   write8
1969      UML_SUB(block, mem(&ppc->impstate->swcount), mem(&ppc->impstate->swcount), 1);  // sub     [swcount],[swcount],1
1488      UML_CALLH(block, *m_write8[mode]);                                     // callh   write8
1489      UML_SUB(block, mem(&m_core->swcount), mem(&m_core->swcount), 1);  // sub     [swcount],[swcount],1
19701490      UML_RETc(block, COND_Z);                                                                // ret     z
1971      UML_ADD(block, I0, mem(&ppc->impstate->updateaddr), 2);                 // add     i0,[updateaddr],2
1491      UML_ADD(block, I0, mem(&m_core->updateaddr), 2);                 // add     i0,[updateaddr],2
19721492      UML_ROLAND(block, I1, R32(regnum), 24, 0xff);                       // roland  i1,regnum,24,0xff
1973      UML_CALLH(block, *ppc->impstate->write8[mode]);                                     // callh   write8
1974      UML_SUB(block, mem(&ppc->impstate->swcount), mem(&ppc->impstate->swcount), 1);  // sub     [swcount],[swcount],1
1493      UML_CALLH(block, *m_write8[mode]);                                     // callh   write8
1494      UML_SUB(block, mem(&m_core->swcount), mem(&m_core->swcount), 1);  // sub     [swcount],[swcount],1
19751495      UML_RETc(block, COND_Z);                                                                // ret     z
1976      UML_ADD(block, I0, mem(&ppc->impstate->updateaddr), 3);                 // add     i0,[updateaddr],3
1977      UML_ADD(block, mem(&ppc->impstate->updateaddr), I0, 1);                 // add     [updateaddr],i0,1
1496      UML_ADD(block, I0, mem(&m_core->updateaddr), 3);                 // add     i0,[updateaddr],3
1497      UML_ADD(block, mem(&m_core->updateaddr), I0, 1);                 // add     [updateaddr],i0,1
19781498      UML_ROLAND(block, I1, R32(regnum), 0, 0xff);                            // roland  i1,regnum,0,0xff
1979      UML_CALLH(block, *ppc->impstate->write8[mode]);                                     // callh   write8
1980      UML_SUB(block, mem(&ppc->impstate->swcount), mem(&ppc->impstate->swcount), 1);  // sub     [swcount],[swcount],1
1499      UML_CALLH(block, *m_write8[mode]);                                     // callh   write8
1500      UML_SUB(block, mem(&m_core->swcount), mem(&m_core->swcount), 1);  // sub     [swcount],[swcount],1
19811501      UML_RETc(block, COND_Z);                                                                // ret     z
19821502      UML_JMP(block, (regnum + 1) % 32);                                                  // jmp     nextreg
19831503   }
r31142r31143
19961516    on the MSR
19971517-------------------------------------------------*/
19981518
1999static void generate_update_mode(powerpc_state *ppc, drcuml_block *block)
1519void ppc_device::generate_update_mode(drcuml_block *block)
20001520{
20011521   /* LE in bit 0 of mode */
20021522   UML_AND(block, I0, MSR32, MSR_LE);                                          // and     i0,msr,MSR_LE
20031523
20041524   /* DR (OEA and 403GCX) in bit 1 of mode */
2005   if ((ppc->cap & PPCCAP_OEA) || ppc->flavor == PPC_MODEL_403GCX)
1525   if ((m_cap & PPCCAP_OEA) || m_flavor == PPC_MODEL_403GCX)
20061526   {
20071527      UML_ROLAND(block, I1, MSR32, 29, 0x02);                             // roland  i1,[msr],29,0x02
20081528      UML_OR(block, I0, I0, I1);                                          // or      i0,i0,i1
20091529   }
20101530
20111531   /* (4XX) in bit 1 of mode */
2012   if (ppc->cap & PPCCAP_4XX)
1532   if (m_cap & PPCCAP_4XX)
20131533   {
20141534      UML_ROLAND(block, I1, MSR32, 30, 0x02);                             // roland  i1,[msr],30,0x02
20151535      UML_OR(block, I0, I0, I1);                                          // or      i0,i0,i1
r31142r31143
20171537
20181538   /* PR in bit 2 of mode */
20191539   UML_ROLAND(block, I1, MSR32, 20, 0x04);                                 // roland  i1,[msr],20,0x04
2020   UML_OR(block, mem(&ppc->impstate->mode), I0, I1);                               // or      [mode],i0,i1
1540   UML_OR(block, mem(&m_core->mode), I0, I1);                               // or      [mode],i0,i1
20211541}
20221542
20231543
r31142r31143
20271547    an exception if out
20281548-------------------------------------------------*/
20291549
2030static void generate_update_cycles(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, parameter param, int allow_exception)
1550void ppc_device::generate_update_cycles(drcuml_block *block, compiler_state *compiler, parameter param, int allow_exception)
20311551{
20321552   /* check full interrupts if pending */
20331553   if (compiler->checkints)
r31142r31143
20351555      code_label skip;
20361556
20371557      compiler->checkints = FALSE;
2038      UML_TEST(block, mem(&ppc->irq_pending), ~0);                                    // test    [irq_pending],0
1558      UML_TEST(block, mem(&m_core->irq_pending), ~0);                                    // test    [irq_pending],0
20391559      UML_JMPc(block, COND_Z, skip = compiler->labelnum++);                                   // jmp     skip,Z
20401560      UML_TEST(block, MSR32, MSR_EE);                                             // test    [msr],MSR_EE
20411561      UML_JMPc(block, COND_Z, skip);                                                      // jmp     skip,Z
20421562      UML_MOV(block, I0, param);                                      // mov     i0,nextpc
20431563      UML_MOV(block, I1, compiler->cycles);                                       // mov     i1,cycles
2044      UML_CALLH(block, *ppc->impstate->exception_norecover[EXCEPTION_EI]);                    // callh   interrupt_norecover
1564      UML_CALLH(block, *m_exception_norecover[EXCEPTION_EI]);                    // callh   interrupt_norecover
20451565      UML_LABEL(block, skip);                                                         // skip:
20461566   }
20471567
20481568   /* account for cycles */
20491569   if (compiler->cycles > 0)
20501570   {
2051      UML_SUB(block, mem(&ppc->icount), mem(&ppc->icount), MAPVAR_CYCLES);                // sub     icount,icount,cycles
1571      UML_SUB(block, mem(&m_core->icount), mem(&m_core->icount), MAPVAR_CYCLES);                // sub     icount,icount,cycles
20521572      UML_MAPVAR(block, MAPVAR_CYCLES, 0);                                                // mapvar  cycles,0
20531573      if (allow_exception)
2054         UML_EXHc(block, COND_S, *ppc->impstate->out_of_cycles, param);      // exh     out_of_cycles,nextpc
1574         UML_EXHc(block, COND_S, *m_out_of_cycles, param);      // exh     out_of_cycles,nextpc
20551575   }
20561576   compiler->cycles = 0;
20571577}
r31142r31143
20621582    validate a sequence of opcodes
20631583-------------------------------------------------*/
20641584
2065static void generate_checksum_block(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *seqhead, const opcode_desc *seqlast)
1585void ppc_device::generate_checksum_block(drcuml_block *block, compiler_state *compiler, const opcode_desc *seqhead, const opcode_desc *seqlast)
20661586{
20671587   const opcode_desc *curdesc;
20681588   if (LOG_UML)
20691589      block->append_comment("[Validation for %08X]", seqhead->pc);                        // comment
20701590
20711591   /* loose verify or single instruction: just compare and fail */
2072   if (!(ppc->impstate->drcoptions & PPCDRC_STRICT_VERIFY) || seqhead->next() == NULL)
1592   if (!(m_drcoptions & PPCDRC_STRICT_VERIFY) || seqhead->next() == NULL)
20731593   {
20741594      if (!(seqhead->flags & OPFLAG_VIRTUAL_NOOP))
20751595      {
2076         void *base = ppc->direct->read_decrypted_ptr(seqhead->physpc, ppc->codexor);
1596         void *base = m_direct->read_decrypted_ptr(seqhead->physpc, m_codexor);
20771597         UML_LOAD(block, I0, base, 0, SIZE_DWORD, SCALE_x4);                 // load    i0,base,dword
20781598         UML_CMP(block, I0, seqhead->opptr.l[0]);                                // cmp     i0,*opptr
2079         UML_EXHc(block, COND_NE, *ppc->impstate->nocode, seqhead->pc);              // exne    nocode,seqhead->pc
1599         UML_EXHc(block, COND_NE, *m_nocode, seqhead->pc);              // exne    nocode,seqhead->pc
20801600      }
20811601   }
20821602
r31142r31143
20871607      for (curdesc = seqhead->next(); curdesc != seqlast->next(); curdesc = curdesc->next())
20881608         if (!(curdesc->flags & OPFLAG_VIRTUAL_NOOP))
20891609         {
2090            void *base = ppc->direct->read_decrypted_ptr(seqhead->physpc, ppc->codexor);
1610            void *base = m_direct->read_decrypted_ptr(seqhead->physpc, m_codexor);
20911611            UML_LOAD(block, I0, base, 0, SIZE_DWORD, SCALE_x4);             // load    i0,base,dword
20921612            UML_CMP(block, I0, curdesc->opptr.l[0]);                            // cmp     i0,*opptr
2093            UML_EXHc(block, COND_NE, *ppc->impstate->nocode, seqhead->pc);          // exne    nocode,seqhead->pc
1613            UML_EXHc(block, COND_NE, *m_nocode, seqhead->pc);          // exne    nocode,seqhead->pc
20941614         }
20951615#else
20961616      UINT32 sum = 0;
2097      void *base = ppc->direct->read_decrypted_ptr(seqhead->physpc, ppc->codexor);
1617      void *base = m_direct->read_decrypted_ptr(seqhead->physpc, m_codexor);
20981618      UML_LOAD(block, I0, base, 0, SIZE_DWORD, SCALE_x4);                     // load    i0,base,dword
20991619      sum += seqhead->opptr.l[0];
21001620      for (curdesc = seqhead->next(); curdesc != seqlast->next(); curdesc = curdesc->next())
21011621         if (!(curdesc->flags & OPFLAG_VIRTUAL_NOOP))
21021622         {
2103            base = ppc->direct->read_decrypted_ptr(curdesc->physpc, ppc->codexor);
1623            base = m_direct->read_decrypted_ptr(curdesc->physpc, m_codexor);
21041624            UML_LOAD(block, I1, base, 0, SIZE_DWORD, SCALE_x4);             // load    i1,base,dword
21051625            UML_ADD(block, I0, I0, I1);                                 // add     i0,i0,i1
21061626            sum += curdesc->opptr.l[0];
21071627         }
21081628      UML_CMP(block, I0, sum);                                                    // cmp     i0,sum
2109      UML_EXHc(block, COND_NE, *ppc->impstate->nocode, seqhead->pc);                  // exne    nocode,seqhead->pc
1629      UML_EXHc(block, COND_NE, *m_nocode, seqhead->pc);                  // exne    nocode,seqhead->pc
21101630#endif
21111631   }
21121632}
r31142r31143
21171637    for a single instruction in a sequence
21181638-------------------------------------------------*/
21191639
2120static void generate_sequence_instruction(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
1640void ppc_device::generate_sequence_instruction(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
21211641{
21221642   int hotnum;
21231643
r31142r31143
21331653
21341654   /* is this a hotspot? */
21351655   for (hotnum = 0; hotnum < PPC_MAX_HOTSPOTS; hotnum++)
2136      if (ppc->impstate->hotspot[hotnum].pc != 0 && desc->pc == ppc->impstate->hotspot[hotnum].pc && desc->opptr.l[0] == ppc->impstate->hotspot[hotnum].opcode)
1656      if (m_hotspot[hotnum].pc != 0 && desc->pc == m_hotspot[hotnum].pc && desc->opptr.l[0] == m_hotspot[hotnum].opcode)
21371657      {
2138         compiler->cycles += ppc->impstate->hotspot[hotnum].cycles;
1658         compiler->cycles += m_hotspot[hotnum].cycles;
21391659         break;
21401660      }
21411661
r31142r31143
21451665   /* if we want a probe, add it here */
21461666   if (desc->pc == PROBE_ADDRESS)
21471667   {
2148      UML_MOV(block, mem(&ppc->pc), desc->pc);                                        // mov     [pc],desc->pc
1668      UML_MOV(block, mem(&m_core->pc), desc->pc);                                        // mov     [pc],desc->pc
21491669      UML_CALLC(block, cfunc_printf_probe, (void *)(FPTR)desc->pc);                                       // callc   cfunc_printf_probe,desc->pc
21501670   }
21511671
21521672   /* if we are debugging, call the debugger */
2153   if ((ppc->device->machine().debug_flags & DEBUG_FLAG_ENABLED) != 0)
1673   if ((machine().debug_flags & DEBUG_FLAG_ENABLED) != 0)
21541674   {
2155      UML_MOV(block, mem(&ppc->pc), desc->pc);                                        // mov     [pc],desc->pc
2156      save_fast_iregs(ppc, block);                                                        // <save fastregs>
1675      UML_MOV(block, mem(&m_core->pc), desc->pc);                                        // mov     [pc],desc->pc
1676      save_fast_iregs(block);                                                        // <save fastregs>
21571677      UML_DEBUG(block, desc->pc);                                                 // debug   desc->pc
21581678   }
21591679
21601680   /* if we hit an unmapped address, fatal error */
21611681   if (desc->flags & OPFLAG_COMPILER_UNMAPPED)
21621682   {
2163      UML_MOV(block, mem(&ppc->pc), desc->pc);                                        // mov     [pc],desc->pc
2164      save_fast_iregs(ppc, block);                                                        // <save fastregs>
1683      UML_MOV(block, mem(&m_core->pc), desc->pc);                                        // mov     [pc],desc->pc
1684      save_fast_iregs(block);                                                        // <save fastregs>
21651685      UML_EXIT(block, EXECUTE_UNMAPPED_CODE);                                     // exit    EXECUTE_UNMAPPED_CODE
21661686   }
21671687
r31142r31143
21711691      if (PRINTF_MMU)
21721692      {
21731693         const char *text = "Compiler page fault @ %08X\n";
2174         UML_MOV(block, mem(&ppc->impstate->format), (FPTR)text);                    // mov     [format],text
2175         UML_MOV(block, mem(&ppc->impstate->arg0), desc->pc);                        // mov     [arg0],desc->pc
2176         UML_CALLC(block, cfunc_printf_debug, ppc);                                      // callc   printf_debug
1694         UML_MOV(block, mem(&m_core->format), (FPTR)text);                    // mov     [format],text
1695         UML_MOV(block, mem(&m_core->arg0), desc->pc);                        // mov     [arg0],desc->pc
1696         UML_CALLC(block, cfunc_printf_debug, this);                                      // callc   printf_debug
21771697      }
2178      UML_EXH(block, *ppc->impstate->tlb_mismatch, 0);                                // exh     tlb_mismatch,0
1698      UML_EXH(block, *m_tlb_mismatch, 0);                                // exh     tlb_mismatch,0
21791699   }
21801700
21811701   /* validate our TLB entry at this PC; if we fail, we need to handle it */
2182   if ((desc->flags & OPFLAG_VALIDATE_TLB) && (ppc->impstate->mode & MODE_DATA_TRANSLATION))
1702   if ((desc->flags & OPFLAG_VALIDATE_TLB) && (m_core->mode & MODE_DATA_TRANSLATION))
21831703   {
2184      const vtlb_entry *tlbtable = vtlb_table(ppc->vtlb);
1704      const vtlb_entry *tlbtable = vtlb_table(m_vtlb);
21851705
21861706      /* if we currently have a valid TLB read entry, we just verify */
21871707      if (tlbtable[desc->pc >> 12] != 0)
r31142r31143
21891709         if (PRINTF_MMU)
21901710         {
21911711            const char *text = "Checking TLB at @ %08X\n";
2192            UML_MOV(block, mem(&ppc->impstate->format), (FPTR)text);                // mov     [format],text
2193            UML_MOV(block, mem(&ppc->impstate->arg0), desc->pc);                    // mov     [arg0],desc->pc
2194            UML_CALLC(block, cfunc_printf_debug, ppc);                                  // callc   printf_debug
1712            UML_MOV(block, mem(&m_core->format), (FPTR)text);                // mov     [format],text
1713            UML_MOV(block, mem(&m_core->arg0), desc->pc);                    // mov     [arg0],desc->pc
1714            UML_CALLC(block, cfunc_printf_debug, this);                                  // callc   printf_debug
21951715         }
21961716         UML_LOAD(block, I0, &tlbtable[desc->pc >> 12], 0, SIZE_DWORD, SCALE_x4);// load    i0,tlbtable[desc->pc >> 12],dword
21971717         UML_CMP(block, I0, tlbtable[desc->pc >> 12]);                           // cmp     i0,*tlbentry
2198         UML_EXHc(block, COND_NE, *ppc->impstate->tlb_mismatch, 0);                  // exh     tlb_mismatch,0,NE
1718         UML_EXHc(block, COND_NE, *m_tlb_mismatch, 0);                  // exh     tlb_mismatch,0,NE
21991719      }
22001720
22011721      /* otherwise, we generate an unconditional exception */
r31142r31143
22041724         if (PRINTF_MMU)
22051725         {
22061726            const char *text = "No valid TLB @ %08X\n";
2207            UML_MOV(block, mem(&ppc->impstate->format), (FPTR)text);                // mov     [format],text
2208            UML_MOV(block, mem(&ppc->impstate->arg0), desc->pc);                    // mov     [arg0],desc->pc
2209            UML_CALLC(block, cfunc_printf_debug, ppc);                                  // callc   printf_debug
1727            UML_MOV(block, mem(&m_core->format), (FPTR)text);                // mov     [format],text
1728            UML_MOV(block, mem(&m_core->arg0), desc->pc);                    // mov     [arg0],desc->pc
1729            UML_CALLC(block, cfunc_printf_debug, this);                                  // callc   printf_debug
22101730         }
2211         UML_EXH(block, *ppc->impstate->tlb_mismatch, 0);                            // exh     tlb_mismatch,0
1731         UML_EXH(block, *m_tlb_mismatch, 0);                            // exh     tlb_mismatch,0
22121732      }
22131733   }
22141734
22151735   /* if this is an invalid opcode, generate the exception now */
22161736   if (desc->flags & OPFLAG_INVALID_OPCODE)
2217      UML_EXH(block, *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x80000);          // exh    exception_program,0x80000
1737      UML_EXH(block, *m_exception[EXCEPTION_PROGRAM], 0x80000);          // exh    exception_program,0x80000
22181738
22191739   /* if this is a privileged opcode in user mode, generate the exception */
2220   else if ((desc->flags & OPFLAG_PRIVILEGED) && (ppc->impstate->mode & MODE_USER))
2221      UML_EXH(block, *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x40000);          // exh    exception_program,0x40000
1740   else if ((desc->flags & OPFLAG_PRIVILEGED) && (m_core->mode & MODE_USER))
1741      UML_EXH(block, *m_exception[EXCEPTION_PROGRAM], 0x40000);          // exh    exception_program,0x40000
22221742
22231743   /* otherwise, unless this is a virtual no-op, it's a regular instruction */
22241744   else if (!(desc->flags & OPFLAG_VIRTUAL_NOOP))
22251745   {
22261746      /* compile the instruction */
2227      if (!generate_opcode(ppc, block, compiler, desc))
1747      if (!generate_opcode(block, compiler, desc))
22281748      {
2229         UML_MOV(block, mem(&ppc->pc), desc->pc);                                    // mov     [pc],desc->pc
2230         UML_MOV(block, mem(&ppc->impstate->arg0), desc->opptr.l[0]);                // mov     [arg0],*desc->opptr.l
2231         UML_CALLC(block, cfunc_unimplemented, ppc);                                     // callc   cfunc_unimplemented,ppc
1749         UML_MOV(block, mem(&m_core->pc), desc->pc);                                    // mov     [pc],desc->pc
1750         UML_MOV(block, mem(&m_core->arg0), desc->opptr.l[0]);                // mov     [arg0],*desc->opptr.l
1751         UML_CALLC(block, cfunc_unimplemented, this);                                     // callc   cfunc_unimplemented,ppc
22321752      }
22331753   }
22341754}
r31142r31143
22381758    generate_compute_flags - compute CR0 and/or XER flags
22391759------------------------------------------------------------------*/
22401760
2241static void generate_compute_flags(powerpc_state *ppc, drcuml_block *block, const opcode_desc *desc, int updatecr, UINT32 xermask, int invertcarry)
1761void ppc_device::generate_compute_flags(drcuml_block *block, const opcode_desc *desc, int updatecr, UINT32 xermask, int invertcarry)
22421762{
22431763   UINT32 xerflags;
22441764
r31142r31143
22601780   if (xermask == 0)
22611781   {
22621782      UML_GETFLGS(block, I0, FLAG_S | FLAG_Z);                                        // getflgs i0,sz
2263      UML_LOAD(block, I0, ppc->impstate->sz_cr_table, I0, SIZE_BYTE, SCALE_x1);   // load    i0,sz_cr_table,i0,byte
1783      UML_LOAD(block, I0, m_sz_cr_table, I0, SIZE_BYTE, SCALE_x1);   // load    i0,sz_cr_table,i0,byte
22641784      UML_OR(block, CR32(0), I0, XERSO32);                                            // or      [cr0],i0,[xerso]
22651785      return;
22661786   }
r31142r31143
22871807
22881808   /* tricky case: both */
22891809   UML_GETFLGS(block, I0, FLAG_S | FLAG_Z | xerflags);                             // getflgs i0,SZ | xerflags
2290   UML_LOAD(block, I1, ppc->impstate->sz_cr_table, I0, SIZE_BYTE, SCALE_x1);       // load    i1,sz_cr_table,i0,byte
1810   UML_LOAD(block, I1, m_sz_cr_table, I0, SIZE_BYTE, SCALE_x1);       // load    i1,sz_cr_table,i0,byte
22911811   if (invertcarry && (xermask & XER_CA))
22921812      UML_XOR(block, I0, I0, FLAG_C);                                     // xor     i0,i0,FLAG_C
22931813   UML_ROLINS(block, SPR32(SPR_XER), I0, 29, xermask);                     // rolins  [xer],i0,29,xermask
r31142r31143
23091829    generate_shift_flags - compute S/Z flags for shifts
23101830-------------------------------------------------------*/
23111831
2312static void generate_shift_flags(powerpc_state *ppc, drcuml_block *block, const opcode_desc *desc, UINT32 op)
1832void ppc_device::generate_shift_flags(drcuml_block *block, const opcode_desc *desc, UINT32 op)
23131833{
23141834   UML_CMP(block, R32(G_RA(op)), 0);               // cmp ra, #0
23151835   UML_SETc(block, COND_Z, I1);                     // set Z, i1
r31142r31143
23181838   UML_SHR(block, I2, R32(G_RA(op)), 28);          // shr i2, ra, #28
23191839   UML_AND(block, I2, I2, FLAG_S);                 // and i2, i2, FLAG_S (i2 now = FLAG_S)
23201840   UML_OR(block, I1, I1, I2);                      // or i1, i1, i2
2321   UML_LOAD(block, I0, ppc->impstate->sz_cr_table, I1, SIZE_BYTE, SCALE_x1);   // load    i0,sz_cr_table,i0,byte
1841   UML_LOAD(block, I0, m_sz_cr_table, I1, SIZE_BYTE, SCALE_x1);   // load    i0,sz_cr_table,i0,byte
23221842   UML_OR(block, CR32(0), I0, XERSO32);                                            // or      [cr0],i0,[xerso]
23231843}
23241844
r31142r31143
23271847    point status flags
23281848-------------------------------------------------*/
23291849
2330static void generate_fp_flags(powerpc_state *ppc, drcuml_block *block, const opcode_desc *desc, int updatefprf)
1850void ppc_device::generate_fp_flags(drcuml_block *block, const opcode_desc *desc, int updatefprf)
23311851{
23321852   /* for now, only handle the FPRF field */
23331853   if (updatefprf)
23341854   {
2335      UML_MOV(block, mem(&ppc->param0), G_RD(desc->opptr.l[0]));
2336      UML_CALLC(block, (c_function)ppccom_update_fprf, ppc);
1855      UML_MOV(block, mem(&m_core->param0), G_RD(desc->opptr.l[0]));
1856      UML_CALLC(block, (c_function)cfunc_ppccom_update_fprf, this);
23371857   }
23381858}
23391859
r31142r31143
23421862    branch
23431863-------------------------------------------------*/
23441864
2345static void generate_branch(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc, int source, UINT8 link)
1865void ppc_device::generate_branch(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc, int source, UINT8 link)
23461866{
23471867   compiler_state compiler_temp = *compiler;
2348   UINT32 *srcptr = &ppc->spr[source];
1868   UINT32 *srcptr = &m_core->spr[source];
23491869
23501870   /* set the link if needed */
23511871   if (link)
23521872   {
23531873      if (desc->targetpc == BRANCH_TARGET_DYNAMIC && source == SPR_LR)
23541874      {
2355         UML_MOV(block, mem(&ppc->impstate->tempaddr), mem(srcptr));                     // mov     [tempaddr],[lr]
2356         srcptr = &ppc->impstate->tempaddr;
1875         UML_MOV(block, mem(&m_core->tempaddr), mem(srcptr));                     // mov     [tempaddr],[lr]
1876         srcptr = &m_core->tempaddr;
23571877      }
23581878      UML_MOV(block, SPR32(SPR_LR), desc->pc + 4);                                    // mov     [lr],desc->pc + 4
23591879   }
r31142r31143
23611881   /* update the cycles and jump through the hash table to the target */
23621882   if (desc->targetpc != BRANCH_TARGET_DYNAMIC)
23631883   {
2364      generate_update_cycles(ppc, block, &compiler_temp, desc->targetpc, TRUE);       // <subtract cycles>
1884      generate_update_cycles(block, &compiler_temp, desc->targetpc, TRUE);       // <subtract cycles>
23651885      if (desc->flags & OPFLAG_INTRABLOCK_BRANCH)
23661886         UML_JMP(block, desc->targetpc | 0x80000000);                                    // jmp     desc->targetpc | 0x80000000
23671887      else
2368         UML_HASHJMP(block, ppc->impstate->mode, desc->targetpc, *ppc->impstate->nocode);
1888         UML_HASHJMP(block, m_core->mode, desc->targetpc, *m_nocode);
23691889                                                                     // hashjmp <mode>,desc->targetpc,nocode
23701890   }
23711891   else
23721892   {
2373      generate_update_cycles(ppc, block, &compiler_temp, mem(srcptr), TRUE);              // <subtract cycles>
2374      UML_HASHJMP(block, ppc->impstate->mode, mem(srcptr), *ppc->impstate->nocode);   // hashjmp <mode>,<rsreg>,nocode
1893      generate_update_cycles(block, &compiler_temp, mem(srcptr), TRUE);              // <subtract cycles>
1894      UML_HASHJMP(block, m_core->mode, mem(srcptr), *m_nocode);   // hashjmp <mode>,<rsreg>,nocode
23751895   }
23761896
23771897   /* update the label */
r31142r31143
23871907    branch based on the BO and BI fields
23881908-------------------------------------------------*/
23891909
2390static void generate_branch_bo(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc, UINT32 bo, UINT32 bi, int source, int link)
1910void ppc_device::generate_branch_bo(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc, UINT32 bo, UINT32 bi, int source, int link)
23911911{
23921912   int skip = compiler->labelnum++;
23931913
r31142r31143
24011921      UML_TEST(block, CR32(bi / 4), 8 >> (bi % 4));                                   // test  cr32(bi/4),8 >> (bi % 4)
24021922      UML_JMPc(block, (bo & 0x08) ? COND_Z : COND_NZ, skip);                                  // jmp   skip,z/nz
24031923   }
2404   generate_branch(ppc, block, compiler, desc, source, link);                              // <branch>
1924   generate_branch(block, compiler, desc, source, link);                              // <branch>
24051925   UML_LABEL(block, skip);                                                             // skip:
24061926}
24071927
r31142r31143
24111931    opcode
24121932-------------------------------------------------*/
24131933
2414static int generate_opcode(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
1934int ppc_device::generate_opcode(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
24151935{
24161936   UINT32 op = desc->opptr.l[0];
24171937   UINT32 opswitch = op >> 26;
2418   int regnum;
24191938
24201939   switch (opswitch)
24211940   {
r31142r31143
24281947      case 0x03:  /* TWI */
24291948         UML_CMP(block, R32(G_RA(op)), (INT16)G_SIMM(op));                           // cmp     ra,simm
24301949         if (G_TO(op) & 0x10)
2431            UML_EXHc(block, COND_L, *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,l
1950            UML_EXHc(block, COND_L, *m_exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,l
24321951         if (G_TO(op) & 0x08)
2433            UML_EXHc(block, COND_G, *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,g
1952            UML_EXHc(block, COND_G, *m_exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,g
24341953         if (G_TO(op) & 0x04)
2435            UML_EXHc(block, COND_E, *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,e
1954            UML_EXHc(block, COND_E, *m_exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,e
24361955         if (G_TO(op) & 0x02)
2437            UML_EXHc(block, COND_B,  *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,b
1956            UML_EXHc(block, COND_B,  *m_exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,b
24381957         if (G_TO(op) & 0x01)
2439            UML_EXHc(block, COND_A,  *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,a
1958            UML_EXHc(block, COND_A,  *m_exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,a
24401959         return TRUE;
24411960
24421961      case 0x07:  /* MULLI */
r31142r31143
24551974      case 0x0a:  /* CMPLI */
24561975         UML_CMP(block, R32(G_RA(op)), G_UIMM(op));                                  // cmp     ra,uimm
24571976         UML_GETFLGS(block, I0, FLAG_Z | FLAG_C);                                    // getflgs i0,zc
2458         UML_LOAD(block, I0, ppc->impstate->cmpl_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,cmpl_cr_table,i0,byte
1977         UML_LOAD(block, I0, m_cmpl_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,cmpl_cr_table,i0,byte
24591978         UML_OR(block, CR32(G_CRFD(op)), I0, XERSO32);                               // or      [crn],i0,[xerso]
24601979         return TRUE;
24611980
24621981      case 0x0b:  /* CMPI */
24631982         UML_CMP(block, R32(G_RA(op)), (INT16)G_SIMM(op));                           // cmp     ra,uimm
24641983         UML_GETFLGS(block, I0, FLAG_Z | FLAG_V | FLAG_C | FLAG_S);                          // getflgs i0,zvcs
2465         UML_LOAD(block, I0, ppc->impstate->cmp_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,cmp_cr_table,i0,byte
1984         UML_LOAD(block, I0, m_cmp_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,cmp_cr_table,i0,byte
24661985         UML_OR(block, CR32(G_CRFD(op)), I0, XERSO32);                               // or      [crn],i0,[xerso]
24671986         return TRUE;
24681987
24691988      case 0x08:  /* SUBFIC */
24701989         UML_SUB(block, R32(G_RD(op)), (INT16)G_SIMM(op), R32(G_RA(op)));            // sub     rd,simm,ra
2471         generate_compute_flags(ppc, block, desc, FALSE, XER_CA, TRUE);                  // <update flags>
1990         generate_compute_flags(block, desc, FALSE, XER_CA, TRUE);                  // <update flags>
24721991         return TRUE;
24731992
24741993      case 0x0c:  /* ADDIC */
24751994         UML_ADD(block, R32(G_RD(op)), R32(G_RA(op)), (INT16)G_SIMM(op));            // add     rd,ra,simm
2476         generate_compute_flags(ppc, block, desc, FALSE, XER_CA, FALSE);                 // <update flags>
1995         generate_compute_flags(block, desc, FALSE, XER_CA, FALSE);                 // <update flags>
24771996         return TRUE;
24781997
24791998      case 0x0d:  /* ADDIC. */
24801999         UML_ADD(block, R32(G_RD(op)), R32(G_RA(op)), (INT16)G_SIMM(op));            // add     rd,ra,simm
2481         generate_compute_flags(ppc, block, desc, TRUE, XER_CA, FALSE);                  // <update flags>
2000         generate_compute_flags(block, desc, TRUE, XER_CA, FALSE);                  // <update flags>
24822001         return TRUE;
24832002
24842003      case 0x10:  /* BCx */
2485         generate_branch_bo(ppc, block, compiler, desc, G_BO(op), G_BI(op), 0, op & M_LK);// <branch conditional>
2004         generate_branch_bo(block, compiler, desc, G_BO(op), G_BI(op), 0, op & M_LK);// <branch conditional>
24862005         return TRUE;
24872006
24882007      case 0x11:  /* SC */
24892008         UML_MAPVAR(block, MAPVAR_PC, desc->pc + 4);                                     // mapvar  PC,desc->pc+4
2490         UML_EXH(block, *ppc->impstate->exception[EXCEPTION_SYSCALL], 0);            // exh     syscall,0
2009         UML_EXH(block, *m_exception[EXCEPTION_SYSCALL], 0);            // exh     syscall,0
24912010         return TRUE;
24922011
24932012      case 0x12:  /* Bx */
2494         generate_branch(ppc, block, compiler, desc, 0, op & M_LK);                      // <branch>
2013         generate_branch(block, compiler, desc, 0, op & M_LK);                      // <branch>
24952014         return TRUE;
24962015
24972016      case 0x13:  /* 0x13 group */
2498         return generate_instruction_13(ppc, block, compiler, desc);                     // <group13>
2017         return generate_instruction_13(block, compiler, desc);                     // <group13>
24992018
25002019      case 0x14:  /* RLWIMIx */
25012020         UML_ROLINS(block, R32(G_RA(op)), R32(G_RS(op)), G_SH(op), compute_rlw_mask(G_MB(op), G_ME(op)));
25022021                                                                     // rolins ra,rs,sh,mask
25032022         if (op & M_RC)
2504            generate_compute_flags(ppc, block, desc, TRUE, 0, FALSE);                   // <update flags>
2023            generate_compute_flags(block, desc, TRUE, 0, FALSE);                   // <update flags>
25052024         return TRUE;
25062025
25072026      case 0x15:  /* RLWINMx */
25082027         UML_ROLAND(block, R32(G_RA(op)), R32(G_RS(op)), G_SH(op), compute_rlw_mask(G_MB(op), G_ME(op)));
25092028                                                                     // roland ra,rs,sh,mask
25102029         if (op & M_RC)
2511            generate_compute_flags(ppc, block, desc, TRUE, 0, FALSE);                   // <update flags>
2030            generate_compute_flags(block, desc, TRUE, 0, FALSE);                   // <update flags>
25122031         return TRUE;
25132032
25142033      case 0x17:  /* RLWNMx */
25152034         UML_ROLAND(block, R32(G_RA(op)), R32(G_RS(op)), R32(G_RB(op)), compute_rlw_mask(G_MB(op), G_ME(op)));
25162035                                                                     // roland ra,rs,rb,mask
25172036         if (op & M_RC)
2518            generate_compute_flags(ppc, block, desc, TRUE, 0, FALSE);                   // <update flags>
2037            generate_compute_flags(block, desc, TRUE, 0, FALSE);                   // <update flags>
25192038         return TRUE;
25202039
25212040      case 0x18:  /* ORI */
r31142r31143
25362055
25372056      case 0x1c:  /* ANDI. */
25382057         UML_AND(block, R32(G_RA(op)), R32(G_RS(op)), G_UIMM(op));                   // and     ra,rs,uimm
2539         generate_compute_flags(ppc, block, desc, TRUE, 0, FALSE);                       // <update flags>
2058         generate_compute_flags(block, desc, TRUE, 0, FALSE);                       // <update flags>
25402059         return TRUE;
25412060
25422061      case 0x1d:  /* ANDIS. */
25432062         UML_AND(block, R32(G_RA(op)), R32(G_RS(op)), G_UIMM(op) << 16);         // and  ra,rs,uimm << 16
2544         generate_compute_flags(ppc, block, desc, TRUE, 0, FALSE);                       // <update flags>
2063         generate_compute_flags(block, desc, TRUE, 0, FALSE);                       // <update flags>
25452064         return TRUE;
25462065
25472066      case 0x1f:  /* 0x1f group */
2548         return generate_instruction_1f(ppc, block, compiler, desc);                     // <group1f>
2067         return generate_instruction_1f(block, compiler, desc);                     // <group1f>
25492068
25502069      case 0x22:  /* LBZ */
25512070         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
25522071         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2553         UML_CALLH(block, *ppc->impstate->read8[ppc->impstate->mode]);                   // callh   read8
2072         UML_CALLH(block, *m_read8[m_core->mode]);                   // callh   read8
25542073         UML_AND(block, R32(G_RD(op)), I0, 0xff);                                // and     rd,i0,0xff
2555         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2074         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
25562075         return TRUE;
25572076
25582077      case 0x28:  /* LHZ */
25592078         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
25602079         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2561         UML_CALLH(block, *ppc->impstate->read16[ppc->impstate->mode]);                  // callh   read16
2080         UML_CALLH(block, *m_read16[m_core->mode]);                  // callh   read16
25622081         UML_AND(block, R32(G_RD(op)), I0, 0xffff);                          // and     rd,i0,0xffff
2563         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2082         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
25642083         return TRUE;
25652084
25662085      case 0x2a:  /* LHA */
25672086         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
25682087         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2569         UML_CALLH(block, *ppc->impstate->read16[ppc->impstate->mode]);                  // callh   read16
2088         UML_CALLH(block, *m_read16[m_core->mode]);                  // callh   read16
25702089         UML_SEXT(block, R32(G_RD(op)), I0, SIZE_WORD);                                  // sext    rd,i0,word
2571         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2090         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
25722091         return TRUE;
25732092
25742093      case 0x20:  /* LWZ */
25752094         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
25762095         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2577         UML_CALLH(block, *ppc->impstate->read32[ppc->impstate->mode]);                  // callh   read32
2096         UML_CALLH(block, *m_read32[m_core->mode]);                  // callh   read32
25782097         UML_MOV(block, R32(G_RD(op)), I0);                                          // mov     rd,i0
2579         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2098         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
25802099         return TRUE;
25812100
25822101      case 0x23:  /* LBZU */
25832102         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
2584         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2103         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
25852104         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2586         UML_CALLH(block, *ppc->impstate->read8[ppc->impstate->mode]);                   // callh   read8
2105         UML_CALLH(block, *m_read8[m_core->mode]);                   // callh   read8
25872106         UML_AND(block, R32(G_RD(op)), I0, 0xff);                                // and     rd,i0,0xff
2588         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2589         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2107         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2108         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
25902109         return TRUE;
25912110
25922111      case 0x29:  /* LHZU */
25932112         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
2594         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2113         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
25952114         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2596         UML_CALLH(block, *ppc->impstate->read16[ppc->impstate->mode]);                  // callh   read16
2115         UML_CALLH(block, *m_read16[m_core->mode]);                  // callh   read16
25972116         UML_AND(block, R32(G_RD(op)), I0, 0xffff);                          // and     rd,i0,0xffff
2598         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2599         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2117         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2118         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
26002119         return TRUE;
26012120
26022121      case 0x2b:  /* LHAU */
26032122         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
2604         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2123         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
26052124         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2606         UML_CALLH(block, *ppc->impstate->read16[ppc->impstate->mode]);                  // callh   read16
2125         UML_CALLH(block, *m_read16[m_core->mode]);                  // callh   read16
26072126         UML_SEXT(block, R32(G_RD(op)), I0, SIZE_WORD);                                  // sext    rd,i0,word
2608         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2609         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2127         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2128         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
26102129         return TRUE;
26112130
26122131      case 0x21:  /* LWZU */
26132132         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
2614         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2133         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
26152134         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2616         UML_CALLH(block, *ppc->impstate->read32[ppc->impstate->mode]);                  // callh   read32
2135         UML_CALLH(block, *m_read32[m_core->mode]);                  // callh   read32
26172136         UML_MOV(block, R32(G_RD(op)), I0);                                          // mov     rd,i0
2618         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2619         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2137         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2138         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
26202139         return TRUE;
26212140
26222141      case 0x26:  /* STB */
26232142         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
26242143         UML_AND(block, I1, R32(G_RS(op)), 0xff);                                // and     i1,rs,0xff
26252144         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2626         UML_CALLH(block, *ppc->impstate->write8[ppc->impstate->mode]);                  // callh   write8
2627         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2145         UML_CALLH(block, *m_write8[m_core->mode]);                  // callh   write8
2146         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
26282147         return TRUE;
26292148
26302149      case 0x2c:  /* STH */
26312150         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
26322151         UML_AND(block, I1, R32(G_RS(op)), 0xffff);                          // and     i1,rs,0xffff
26332152         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2634         UML_CALLH(block, *ppc->impstate->write16[ppc->impstate->mode]);                 // callh   write16
2635         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2153         UML_CALLH(block, *m_write16[m_core->mode]);                 // callh   write16
2154         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
26362155         return TRUE;
26372156
26382157      case 0x24:  /* STW */
26392158         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
26402159         UML_MOV(block, I1, R32(G_RS(op)));                                          // mov     i1,rs
26412160         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2642         UML_CALLH(block, *ppc->impstate->write32[ppc->impstate->mode]);                 // callh   write32
2643         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2161         UML_CALLH(block, *m_write32[m_core->mode]);                 // callh   write32
2162         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
26442163         return TRUE;
26452164
26462165      case 0x27:  /* STBU */
26472166         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
26482167         UML_AND(block, I1, R32(G_RS(op)), 0xff);                                // and     i1,rs,0xff
2649         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2168         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
26502169         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2651         UML_CALLH(block, *ppc->impstate->write8[ppc->impstate->mode]);                  // callh   write8
2652         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2653         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2170         UML_CALLH(block, *m_write8[m_core->mode]);                  // callh   write8
2171         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2172         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
26542173         return TRUE;
26552174
26562175      case 0x2d:  /* STHU */
26572176         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
26582177         UML_AND(block, I1, R32(G_RS(op)), 0xffff);                          // and     i1,rs,0xffff
2659         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2178         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
26602179         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2661         UML_CALLH(block, *ppc->impstate->write16[ppc->impstate->mode]);                 // callh   write16
2662         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2663         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2180         UML_CALLH(block, *m_write16[m_core->mode]);                 // callh   write16
2181         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2182         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
26642183         return TRUE;
26652184
26662185      case 0x25:  /* STWU */
26672186         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
26682187         UML_MOV(block, I1, R32(G_RS(op)));                                          // mov     i1,rs
2669         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2188         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
26702189         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2671         UML_CALLH(block, *ppc->impstate->write32[ppc->impstate->mode]);                 // callh   write32
2672         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2673         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2190         UML_CALLH(block, *m_write32[m_core->mode]);                 // callh   write32
2191         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2192         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
26742193         return TRUE;
26752194
26762195      case 0x2e:  /* LMW */
26772196         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2678         UML_MOV(block, mem(&ppc->impstate->tempaddr), R32Z(G_RA(op)));                  // mov     [tempaddr],ra
2679         for (regnum = G_RD(op); regnum < 32; regnum++)
2197         UML_MOV(block, mem(&m_core->tempaddr), R32Z(G_RA(op)));                  // mov     [tempaddr],ra
2198         for (int regnum = G_RD(op); regnum < 32; regnum++)
26802199         {
2681            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), (INT16)G_SIMM(op) + 4 * (regnum - G_RD(op)));
2200            UML_ADD(block, I0, mem(&m_core->tempaddr), (INT16)G_SIMM(op) + 4 * (regnum - G_RD(op)));
26822201                                                                     // add     i0,[tempaddr],simm + 4*(regnum-rd)
2683            UML_CALLH(block, *ppc->impstate->read32align[ppc->impstate->mode]);         // callh   read32align
2202            UML_CALLH(block, *m_read32align[m_core->mode]);         // callh   read32align
26842203            UML_MOV(block, R32(regnum), I0);                                        // mov     regnum,i0
26852204         }
2686         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2205         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
26872206         return TRUE;
26882207
26892208      case 0x2f:  /* STMW */
26902209         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2691         UML_MOV(block, mem(&ppc->impstate->tempaddr), R32Z(G_RA(op)));                  // mov     [tempaddr],ra
2692         for (regnum = G_RS(op); regnum < 32; regnum++)
2210         UML_MOV(block, mem(&m_core->tempaddr), R32Z(G_RA(op)));                  // mov     [tempaddr],ra
2211         for (int regnum = G_RS(op); regnum < 32; regnum++)
26932212         {
2694            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), (INT16)G_SIMM(op) + 4 * (regnum - G_RS(op)));
2213            UML_ADD(block, I0, mem(&m_core->tempaddr), (INT16)G_SIMM(op) + 4 * (regnum - G_RS(op)));
26952214                                                                     // add     i0,[tempaddr],simm + 4*(regnum-rs)
26962215            UML_MOV(block, I1, R32(regnum));                                        // mov     i1,regnum
2697            UML_CALLH(block, *ppc->impstate->write32align[ppc->impstate->mode]);            // callh   write32align
2216            UML_CALLH(block, *m_write32align[m_core->mode]);            // callh   write32align
26982217         }
2699         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2218         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
27002219         return TRUE;
27012220
27022221      case 0x30:  /* LFS */
27032222         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
27042223         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2705         UML_CALLH(block, *ppc->impstate->read32[ppc->impstate->mode]);                  // callh   read32
2706         UML_MOV(block, mem(&ppc->impstate->tempdata.w.l), I0);                      // mov     [tempdata],i0
2707         UML_FDFRFLT(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.w.l), SIZE_DWORD);   // fdfrflt fd,[tempdata],dword
2708         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2224         UML_CALLH(block, *m_read32[m_core->mode]);                  // callh   read32
2225         UML_MOV(block, mem(&m_core->tempdata.w.l), I0);                      // mov     [tempdata],i0
2226         UML_FDFRFLT(block, F64(G_RD(op)), mem(&m_core->tempdata.w.l), SIZE_DWORD);   // fdfrflt fd,[tempdata],dword
2227         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
27092228         return TRUE;
27102229
27112230      case 0x32:  /* LFD */
27122231         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
27132232         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2714         UML_CALLH(block, *ppc->impstate->read64[ppc->impstate->mode]);                  // callh   read64
2715         UML_DMOV(block, mem(&ppc->impstate->tempdata.d), I0);                       // dmov    [tempdata],i0
2716         UML_FDMOV(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.d));               // fdmov   fd,[tempdata]
2717         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2233         UML_CALLH(block, *m_read64[m_core->mode]);                  // callh   read64
2234         UML_DMOV(block, mem(&m_core->tempdata.d), I0);                       // dmov    [tempdata],i0
2235         UML_FDMOV(block, F64(G_RD(op)), mem(&m_core->tempdata.d));               // fdmov   fd,[tempdata]
2236         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
27182237         return TRUE;
27192238
27202239      case 0x31:  /* LFSU */
27212240         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
2722         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2241         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
27232242         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2724         UML_CALLH(block, *ppc->impstate->read32[ppc->impstate->mode]);                  // callh   read32
2725         UML_MOV(block, mem(&ppc->impstate->tempdata.w.l), I0);                      // mov     [tempdata],i0
2726         UML_FDFRFLT(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.w.l), SIZE_DWORD);   // fdfrflt fd,[tempdata],dword
2727         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2728         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2243         UML_CALLH(block, *m_read32[m_core->mode]);                  // callh   read32
2244         UML_MOV(block, mem(&m_core->tempdata.w.l), I0);                      // mov     [tempdata],i0
2245         UML_FDFRFLT(block, F64(G_RD(op)), mem(&m_core->tempdata.w.l), SIZE_DWORD);   // fdfrflt fd,[tempdata],dword
2246         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2247         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
27292248         return TRUE;
27302249
27312250      case 0x33:  /* LFDU */
27322251         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
2733         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2252         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
27342253         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2735         UML_CALLH(block, *ppc->impstate->read64[ppc->impstate->mode]);                  // callh   read64
2736         UML_DMOV(block, mem(&ppc->impstate->tempdata.d), I0);                       // dmov    [tempdata],i0
2737         UML_FDMOV(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.d));               // fdmov   fd,[tempdata]
2738         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2739         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2254         UML_CALLH(block, *m_read64[m_core->mode]);                  // callh   read64
2255         UML_DMOV(block, mem(&m_core->tempdata.d), I0);                       // dmov    [tempdata],i0
2256         UML_FDMOV(block, F64(G_RD(op)), mem(&m_core->tempdata.d));               // fdmov   fd,[tempdata]
2257         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2258         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
27402259         return TRUE;
27412260
27422261      case 0x34:  /* STFS */
27432262         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
2744         UML_FSFRFLT(block, mem(&ppc->impstate->tempdata.w.l), F64(G_RS(op)), SIZE_QWORD);   // fsfrflt [tempdata],rs,qword
2745         UML_MOV(block, I1, mem(&ppc->impstate->tempdata.w.l));                      // mov     i1,[tempdata]
2263         UML_FSFRFLT(block, mem(&m_core->tempdata.w.l), F64(G_RS(op)), SIZE_QWORD);   // fsfrflt [tempdata],rs,qword
2264         UML_MOV(block, I1, mem(&m_core->tempdata.w.l));                      // mov     i1,[tempdata]
27462265         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2747         UML_CALLH(block, *ppc->impstate->write32[ppc->impstate->mode]);                 // callh   write32
2748         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2266         UML_CALLH(block, *m_write32[m_core->mode]);                 // callh   write32
2267         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
27492268         return TRUE;
27502269
27512270      case 0x36:  /* STFD */
27522271         UML_ADD(block, I0, R32Z(G_RA(op)), (INT16)G_SIMM(op));              // add     i0,ra,simm
2753         UML_FDMOV(block, mem(&ppc->impstate->tempdata.d), F64(G_RS(op)));               // fdmov   [tempdata],rs
2754         UML_DMOV(block, I1, mem(&ppc->impstate->tempdata.d));                       // dmov    i1,[tempdata]
2272         UML_FDMOV(block, mem(&m_core->tempdata.d), F64(G_RS(op)));               // fdmov   [tempdata],rs
2273         UML_DMOV(block, I1, mem(&m_core->tempdata.d));                       // dmov    i1,[tempdata]
27552274         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMM(op));                                 // mapvar  dsisr,DSISR_IMM(op)
2756         UML_CALLH(block, *ppc->impstate->write64[ppc->impstate->mode]);                 // callh   write64
2757         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2275         UML_CALLH(block, *m_write64[m_core->mode]);                 // callh   write64
2276         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
27582277         return TRUE;
27592278
27602279      case 0x35:  /* STFSU */
27612280         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
2762         UML_FSFRFLT(block, mem(&ppc->impstate->tempdata.w.l), F64(G_RS(op)), SIZE_QWORD);   // fsfrflt [tempdata],rs,qword
2763         UML_MOV(block, I1, mem(&ppc->impstate->tempdata.w.l));                      // mov     i1,[tempdata]
2764         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2281         UML_FSFRFLT(block, mem(&m_core->tempdata.w.l), F64(G_RS(op)), SIZE_QWORD);   // fsfrflt [tempdata],rs,qword
2282         UML_MOV(block, I1, mem(&m_core->tempdata.w.l));                      // mov     i1,[tempdata]
2283         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
27652284         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2766         UML_CALLH(block, *ppc->impstate->write32[ppc->impstate->mode]);                 // callh   write32
2767         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2768         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2285         UML_CALLH(block, *m_write32[m_core->mode]);                 // callh   write32
2286         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2287         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
27692288         return TRUE;
27702289
27712290      case 0x37:  /* STFDU */
27722291         UML_ADD(block, I0, R32(G_RA(op)), (INT16)G_SIMM(op));                   // add     i0,ra,simm
2773         UML_FDMOV(block, mem(&ppc->impstate->tempdata.d), F64(G_RS(op)));               // fdmov   [tempdata],rs
2774         UML_DMOV(block, I1, mem(&ppc->impstate->tempdata.d));                       // dmov    i1,[tempdata]
2775         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2292         UML_FDMOV(block, mem(&m_core->tempdata.d), F64(G_RS(op)));               // fdmov   [tempdata],rs
2293         UML_DMOV(block, I1, mem(&m_core->tempdata.d));                       // dmov    i1,[tempdata]
2294         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
27762295         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IMMU(op));                                // mapvar  dsisr,DSISR_IMMU(op)
2777         UML_CALLH(block, *ppc->impstate->write64[ppc->impstate->mode]);                 // callh   write64
2778         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
2779         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2296         UML_CALLH(block, *m_write64[m_core->mode]);                 // callh   write64
2297         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2298         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
27802299         return TRUE;
27812300
27822301      case 0x3b:  /* 0x3b group */
2783         return generate_instruction_3b(ppc, block, compiler, desc);                     // <group3b>
2302         return generate_instruction_3b(block, compiler, desc);                     // <group3b>
27842303
27852304      case 0x3f:  /* 0x3f group */
2786         return generate_instruction_3f(ppc, block, compiler, desc);                     // <group3f>
2305         return generate_instruction_3f(block, compiler, desc);                     // <group3f>
27872306   }
27882307
27892308   return FALSE;
r31142r31143
27952314    the 0x13 group
27962315-------------------------------------------------*/
27972316
2798static int generate_instruction_13(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
2317int ppc_device::generate_instruction_13(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
27992318{
28002319   UINT32 op = desc->opptr.l[0];
28012320   UINT32 opswitch = (op >> 1) & 0x3ff;
r31142r31143
28032322   switch (opswitch)
28042323   {
28052324      case 0x010: /* BCLRx */
2806         generate_branch_bo(ppc, block, compiler, desc, G_BO(op), G_BI(op), SPR_LR, op & M_LK);// <branch conditional>
2325         generate_branch_bo(block, compiler, desc, G_BO(op), G_BI(op), SPR_LR, op & M_LK);// <branch conditional>
28072326         return TRUE;
28082327
28092328      case 0x210: /* BCCTRx */
2810         generate_branch_bo(ppc, block, compiler, desc, G_BO(op), G_BI(op), SPR_CTR, op & M_LK);
2329         generate_branch_bo(block, compiler, desc, G_BO(op), G_BI(op), SPR_CTR, op & M_LK);
28112330                                                                     // <branch conditional>
28122331         return TRUE;
28132332
r31142r31143
28852404         return TRUE;
28862405
28872406      case 0x032: /* RFI */
2888         if (ppc->cap & PPCCAP_OEA)
2407         if (m_cap & PPCCAP_OEA)
28892408         {
2890            if (!(ppc->cap & PPCCAP_603_MMU))
2409            if (!(m_cap & PPCCAP_603_MMU))
28912410               UML_ROLINS(block, MSR32, SPR32(SPROEA_SRR1), 0, 0x87c0ffff);    // rolins  [msr],[srr1],0,0x87c0ffff
28922411            else
28932412            {
r31142r31143
28962415                                                                     // rolins  [msr],[srr1],0,0x87c0ffff | MSR603_TGPR
28972416               UML_XOR(block, I0, I0, MSR32);                              // xor     i0,i0,[msr]
28982417               UML_TEST(block, I0, MSR603_TGPR);                               // test    i0,tgpr
2899               UML_CALLHc(block, COND_NZ, *ppc->impstate->swap_tgpr);                      // callh   swap_tgpr,nz
2418               UML_CALLHc(block, COND_NZ, *m_swap_tgpr);                      // callh   swap_tgpr,nz
29002419            }
29012420         }
2902         else if (ppc->cap & PPCCAP_4XX)
2421         else if (m_cap & PPCCAP_4XX)
29032422            UML_MOV(block, MSR32, SPR32(SPR4XX_SRR1));                                  // mov     [msr],[srr1]
2904         generate_update_mode(ppc, block);                                               // <update mode>
2423         generate_update_mode(block);                                               // <update mode>
29052424         compiler->checkints = TRUE;
2906         generate_update_cycles(ppc, block, compiler, SPR32(SPROEA_SRR0), TRUE);         // <subtract cycles>
2907         UML_HASHJMP(block, mem(&ppc->impstate->mode), SPR32(SPROEA_SRR0), *ppc->impstate->nocode);
2425         generate_update_cycles(block, compiler, SPR32(SPROEA_SRR0), TRUE);         // <subtract cycles>
2426         UML_HASHJMP(block, mem(&m_core->mode), SPR32(SPROEA_SRR0), *m_nocode);
29082427                                                                     // hashjmp mode,[srr0],nocode
29092428         return TRUE;
29102429
29112430      case 0x033: /* RFCI */
2912         assert(ppc->cap & PPCCAP_4XX);
2431         assert(m_cap & PPCCAP_4XX);
29132432         UML_MOV(block, MSR32, SPR32(SPR4XX_SRR3));                                      // mov     [msr],[srr3]
2914         generate_update_mode(ppc, block);                                               // <update mode>
2433         generate_update_mode(block);                                               // <update mode>
29152434         compiler->checkints = TRUE;
2916         generate_update_cycles(ppc, block, compiler, SPR32(SPR4XX_SRR2), TRUE);         // <subtract cycles>
2917         UML_HASHJMP(block, mem(&ppc->impstate->mode), SPR32(SPR4XX_SRR2), *ppc->impstate->nocode);
2435         generate_update_cycles(block, compiler, SPR32(SPR4XX_SRR2), TRUE);         // <subtract cycles>
2436         UML_HASHJMP(block, mem(&m_core->mode), SPR32(SPR4XX_SRR2), *m_nocode);
29182437                                                                     // hashjmp mode,[srr2],nocode
29192438         return TRUE;
29202439
r31142r31143
29322451    the 0x1f group
29332452-------------------------------------------------*/
29342453
2935static int generate_instruction_1f(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
2454int ppc_device::generate_instruction_1f(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
29362455{
29372456   UINT32 op = desc->opptr.l[0];
29382457   UINT32 opswitch = (op >> 1) & 0x3ff;
r31142r31143
29712490      case 0x004: /* TW */
29722491         UML_CMP(block, R32(G_RA(op)), R32(G_RB(op)));                                   // cmp     ra,rb
29732492         if (G_TO(op) & 0x10)
2974            UML_EXHc(block, COND_L, *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,l
2493            UML_EXHc(block, COND_L, *m_exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,l
29752494         if (G_TO(op) & 0x08)
2976            UML_EXHc(block, COND_G, *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,g
2495            UML_EXHc(block, COND_G, *m_exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,g
29772496         if (G_TO(op) & 0x04)
2978            UML_EXHc(block, COND_E, *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,e
2497            UML_EXHc(block, COND_E, *m_exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,e
29792498         if (G_TO(op) & 0x02)
2980            UML_EXHc(block, COND_B,  *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,b
2499            UML_EXHc(block, COND_B,  *m_exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,b
29812500         if (G_TO(op) & 0x01)
2982            UML_EXHc(block, COND_A,  *ppc->impstate->exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,a
2501            UML_EXHc(block, COND_A,  *m_exception[EXCEPTION_PROGRAM], 0x20000);// exh program,0x20000,a
29832502         return TRUE;
29842503
29852504      case 0x10a: /* ADDx */
29862505      case 0x30a: /* ADDOx */
29872506         UML_ADD(block, R32(G_RD(op)), R32(G_RA(op)), R32(G_RB(op)));                    // add     rd,ra,rb
2988         generate_compute_flags(ppc, block, desc, op & M_RC, ((op & M_OE) ? XER_OV : 0), FALSE);
2507         generate_compute_flags(block, desc, op & M_RC, ((op & M_OE) ? XER_OV : 0), FALSE);
29892508                                                                     // <update flags>
29902509         return TRUE;
29912510
29922511      case 0x00a: /* ADDCx */
29932512      case 0x20a: /* ADDCOx */
29942513         UML_ADD(block, R32(G_RD(op)), R32(G_RA(op)), R32(G_RB(op)));                    // add     rd,ra,rb
2995         generate_compute_flags(ppc, block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), FALSE);
2514         generate_compute_flags(block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), FALSE);
29962515                                                                     // <update flags>
29972516         return TRUE;
29982517
r31142r31143
30002519      case 0x28a: /* ADDEOx */
30012520         UML_CARRY(block, SPR32(SPR_XER), 29);                                       // carry   [xer],XER_CA
30022521         UML_ADDC(block, R32(G_RD(op)), R32(G_RA(op)), R32(G_RB(op)));                   // addc    rd,ra,rb
3003         generate_compute_flags(ppc, block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), FALSE);
2522         generate_compute_flags(block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), FALSE);
30042523                                                                     // <update flags>
30052524         return TRUE;
30062525
r31142r31143
30082527      case 0x2ca: /* ADDZEOx */
30092528         UML_CARRY(block, SPR32(SPR_XER), 29);                                       // carry   [xer],XER_CA
30102529         UML_ADDC(block, R32(G_RD(op)), R32(G_RA(op)), 0);                           // addc    rd,ra,0
3011         generate_compute_flags(ppc, block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), FALSE);
2530         generate_compute_flags(block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), FALSE);
30122531                                                                     // <update flags>
30132532         return TRUE;
30142533
r31142r31143
30162535      case 0x2ea: /* ADDMEOx */
30172536         UML_CARRY(block, SPR32(SPR_XER), 29);                                       // carry   [xer],XER_CA
30182537         UML_ADDC(block, R32(G_RD(op)), R32(G_RA(op)), (UINT32)-1);                          // addc    rd,ra,-1
3019         generate_compute_flags(ppc, block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), FALSE);
2538         generate_compute_flags(block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), FALSE);
30202539                                                                     // <update flags>
30212540         return TRUE;
30222541
30232542      case 0x028: /* SUBFx */
30242543      case 0x228: /* SUBFOx */
30252544         UML_SUB(block, R32(G_RD(op)), R32(G_RB(op)), R32(G_RA(op)));                    // sub     rd,rb,ra
3026         generate_compute_flags(ppc, block, desc, op & M_RC, (op & M_OE) ? XER_OV : 0, TRUE);
2545         generate_compute_flags(block, desc, op & M_RC, (op & M_OE) ? XER_OV : 0, TRUE);
30272546                                                                     // <update flags>
30282547         return TRUE;
30292548
30302549      case 0x008: /* SUBFCx */
30312550      case 0x208: /* SUBFCOx */
30322551         UML_SUB(block, R32(G_RD(op)), R32(G_RB(op)), R32(G_RA(op)));                    // sub     rd,rb,ra
3033         generate_compute_flags(ppc, block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), TRUE);
2552         generate_compute_flags(block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), TRUE);
30342553                                                                     // <update flags>
30352554         return TRUE;
30362555
r31142r31143
30392558         UML_XOR(block, I0, SPR32(SPR_XER), XER_CA);                         // xor     i0,[xer],XER_CA
30402559         UML_CARRY(block, I0, 29);                                               // carry   i0,XER_CA
30412560         UML_SUBB(block, R32(G_RD(op)), R32(G_RB(op)), R32(G_RA(op)));                   // subc    rd,rb,ra
3042         generate_compute_flags(ppc, block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), TRUE);
2561         generate_compute_flags(block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), TRUE);
30432562                                                                     // <update flags>
30442563         return TRUE;
30452564
r31142r31143
30482567         UML_XOR(block, I0, SPR32(SPR_XER), XER_CA);                         // xor     i0,[xer],XER_CA
30492568         UML_CARRY(block, I0, 29);                                               // carry   i0,XER_CA
30502569         UML_SUBB(block, R32(G_RD(op)), 0, R32(G_RA(op)));                           // subc    rd,0,ra
3051         generate_compute_flags(ppc, block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), TRUE);
2570         generate_compute_flags(block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), TRUE);
30522571                                                                     // <update flags>
30532572         return TRUE;
30542573
r31142r31143
30572576         UML_XOR(block, I0, SPR32(SPR_XER), XER_CA);                         // xor     i0,[xer],XER_CA
30582577         UML_CARRY(block, I0, 29);                                               // carry   i0,XER_CA
30592578         UML_SUBB(block, R32(G_RD(op)), (UINT32)-1, R32(G_RA(op)));                          // subc    rd,-1,ra
3060         generate_compute_flags(ppc, block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), TRUE);
2579         generate_compute_flags(block, desc, op & M_RC, XER_CA | ((op & M_OE) ? XER_OV : 0), TRUE);
30612580                                                                     // <update flags>
30622581         return TRUE;
30632582
30642583      case 0x068: /* NEGx */
30652584      case 0x268: /* NEGOx */
30662585         UML_SUB(block, R32(G_RD(op)), 0, R32(G_RA(op)));                            // sub     rd,0,ra
3067         generate_compute_flags(ppc, block, desc, op & M_RC, (op & M_OE) ? XER_OV : 0, TRUE);
2586         generate_compute_flags(block, desc, op & M_RC, (op & M_OE) ? XER_OV : 0, TRUE);
30682587                                                                     // <update flags>
30692588         return TRUE;
30702589
30712590      case 0x000: /* CMP */
30722591         UML_CMP(block, R32(G_RA(op)), R32(G_RB(op)));                                   // cmp     ra,rb
30732592         UML_GETFLGS(block, I0, FLAG_Z | FLAG_V | FLAG_C | FLAG_S);                          // getflgs i0,zvcs
3074         UML_LOAD(block, I0, ppc->impstate->cmp_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,cmp_cr_table,i0,byte
2593         UML_LOAD(block, I0, m_cmp_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,cmp_cr_table,i0,byte
30752594         UML_OR(block, CR32(G_CRFD(op)), I0, XERSO32);                               // or      [crn],i0,[xerso]
30762595         return TRUE;
30772596
30782597      case 0x020: /* CMPL */
30792598         UML_CMP(block, R32(G_RA(op)), R32(G_RB(op)));                                   // cmp     ra,rb
30802599         UML_GETFLGS(block, I0, FLAG_Z | FLAG_C);                                    // getflgs i0,zc
3081         UML_LOAD(block, I0, ppc->impstate->cmpl_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,cmpl_cr_table,i0,byte
2600         UML_LOAD(block, I0, m_cmpl_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,cmpl_cr_table,i0,byte
30822601         UML_OR(block, CR32(G_CRFD(op)), I0, XERSO32);                               // or      [crn],i0,[xerso]
30832602         return TRUE;
30842603
r31142r31143
30872606         if (op & M_RC)
30882607         {
30892608            UML_TEST(block, R32(G_RD(op)), ~0);                                 // test    rd,~0
3090            generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);              // <update flags>
2609            generate_compute_flags(block, desc, op & M_RC, 0, FALSE);              // <update flags>
30912610         }
30922611         return TRUE;
30932612
r31142r31143
30962615         if (op & M_RC)
30972616         {
30982617            UML_TEST(block, R32(G_RD(op)), ~0);                                 // test    rd,~0
3099            generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);              // <update flags>
2618            generate_compute_flags(block, desc, op & M_RC, 0, FALSE);              // <update flags>
31002619         }
31012620         return TRUE;
31022621
31032622      case 0x0eb: /* MULLWx */
31042623      case 0x2eb: /* MULLWOx */
31052624         UML_MULS(block, R32(G_RD(op)), R32(G_RD(op)), R32(G_RA(op)), R32(G_RB(op)));    // muls    rd,rd,ra,rb
3106         generate_compute_flags(ppc, block, desc, op & M_RC, ((op & M_OE) ? XER_OV : 0), FALSE);// <update flags>
2625         generate_compute_flags(block, desc, op & M_RC, ((op & M_OE) ? XER_OV : 0), FALSE);// <update flags>
31072626         return TRUE;
31082627
31092628      case 0x1cb: /* DIVWUx */
r31142r31143
31282647
31292648         UML_LABEL(block, compiler->labelnum++);             // 0:
31302649         UML_DIVU(block, R32(G_RD(op)), R32(G_RD(op)), R32(G_RA(op)), R32(G_RB(op)));    // divu    rd,rd,ra,rb
3131         generate_compute_flags(ppc, block, desc, op & M_RC, ((op & M_OE) ? XER_OV : 0), FALSE);// <update flags>
2650         generate_compute_flags(block, desc, op & M_RC, ((op & M_OE) ? XER_OV : 0), FALSE);// <update flags>
31322651
31332652         UML_LABEL(block, compiler->labelnum++);             // 1:
31342653         return TRUE;
r31142r31143
31812700
31822701         UML_LABEL(block, compiler->labelnum++);             // 2:
31832702         UML_DIVS(block, R32(G_RD(op)), R32(G_RD(op)), R32(G_RA(op)), R32(G_RB(op)));    // divs    rd,rd,ra,rb
3184         generate_compute_flags(ppc, block, desc, op & M_RC, ((op & M_OE) ? XER_OV : 0), FALSE);// <update flags>
2703         generate_compute_flags(block, desc, op & M_RC, ((op & M_OE) ? XER_OV : 0), FALSE);// <update flags>
31852704
31862705         UML_LABEL(block, compiler->labelnum++);             // 3:
31872706         return TRUE;
31882707
31892708      case 0x01c: /* ANDx */
31902709         UML_AND(block, R32(G_RA(op)), R32(G_RS(op)), R32(G_RB(op)));                    // and     ra,rs,rb
3191         generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);                  // <update flags>
2710         generate_compute_flags(block, desc, op & M_RC, 0, FALSE);                  // <update flags>
31922711         return TRUE;
31932712
31942713      case 0x03c: /* ANDCx */
31952714         UML_XOR(block, I0, R32(G_RB(op)), ~0);                              // xor     i0,rb,~0
31962715         UML_AND(block, R32(G_RA(op)), R32(G_RS(op)), I0);                           // and     ra,rs,i0
3197         generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);                  // <update flags>
2716         generate_compute_flags(block, desc, op & M_RC, 0, FALSE);                  // <update flags>
31982717         return TRUE;
31992718
32002719      case 0x1dc: /* NANDx */
32012720         UML_AND(block, I0, R32(G_RS(op)), R32(G_RB(op)));                           // and     i0,rs,rb
32022721         UML_XOR(block, R32(G_RA(op)), I0, ~0);                              // xor     ra,i0,~0
3203         generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);                  // <update flags>
2722         generate_compute_flags(block, desc, op & M_RC, 0, FALSE);                  // <update flags>
32042723         return TRUE;
32052724
32062725      case 0x1bc: /* ORx */
32072726         UML_OR(block, R32(G_RA(op)), R32(G_RS(op)), R32(G_RB(op)));                     // or      ra,rs,rb
3208         generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);                  // <update flags>
2727         generate_compute_flags(block, desc, op & M_RC, 0, FALSE);                  // <update flags>
32092728         return TRUE;
32102729
32112730      case 0x19c: /* ORCx */
32122731         UML_XOR(block, I0, R32(G_RB(op)), ~0);                              // xor     i0,rb,~0
32132732         UML_OR(block, R32(G_RA(op)), R32(G_RS(op)), I0);                            // or      ra,rs,i0
3214         generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);                  // <update flags>
2733         generate_compute_flags(block, desc, op & M_RC, 0, FALSE);                  // <update flags>
32152734         return TRUE;
32162735
32172736      case 0x07c: /* NORx */
32182737         UML_OR(block, I0, R32(G_RS(op)), R32(G_RB(op)));                            // or      i0,rs,rb
32192738         UML_XOR(block, R32(G_RA(op)), I0, ~0);                              // xor     ra,i0,~0
3220         generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);                  // <update flags>
2739         generate_compute_flags(block, desc, op & M_RC, 0, FALSE);                  // <update flags>
32212740         return TRUE;
32222741
32232742      case 0x13c: /* XORx */
32242743         UML_XOR(block, R32(G_RA(op)), R32(G_RS(op)), R32(G_RB(op)));                    // xor     ra,rs,rb
3225         generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);                  // <update flags>
2744         generate_compute_flags(block, desc, op & M_RC, 0, FALSE);                  // <update flags>
32262745         return TRUE;
32272746
32282747      case 0x11c: /* EQVx */
32292748         UML_XOR(block, I0, R32(G_RS(op)), R32(G_RB(op)));                           // xor     i0,rs,rb
32302749         UML_XOR(block, R32(G_RA(op)), I0, ~0);                              // xor     ra,i0,~0
3231         generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);                  // <update flags>
2750         generate_compute_flags(block, desc, op & M_RC, 0, FALSE);                  // <update flags>
32322751         return TRUE;
32332752
32342753      case 0x018: /* SLWx */
r31142r31143
32502769         // calculate S and Z flags
32512770         if (op & M_RC)
32522771         {
3253            generate_shift_flags(ppc, block, desc, op);
2772            generate_shift_flags(block, desc, op);
32542773         }
32552774
32562775         UML_LABEL(block, compiler->labelnum++);             // 1:
r31142r31143
32752794         // calculate S and Z flags
32762795         if (op & M_RC)
32772796         {
3278            generate_shift_flags(ppc, block, desc, op);
2797            generate_shift_flags(block, desc, op);
32792798         }
32802799
32812800         UML_LABEL(block, compiler->labelnum++);             // 1:
r31142r31143
33132832         // calculate S and Z flags
33142833         if (op & M_RC)
33152834         {
3316            generate_shift_flags(ppc, block, desc, op);
2835            generate_shift_flags(block, desc, op);
33172836         }
33182837         return TRUE;
33192838
r31142r31143
33302849         // calculate S and Z flags
33312850         if (op & M_RC)
33322851         {
3333            generate_shift_flags(ppc, block, desc, op);
2852            generate_shift_flags(block, desc, op);
33342853         }
33352854         return TRUE;
33362855
33372856      case 0x01a: /* CNTLZWx */
33382857         UML_LZCNT(block, R32(G_RA(op)), R32(G_RS(op)));                                 // lzcnt   ra,rs
33392858         if (op & M_RC)
3340            generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);              // <update flags>
2859            generate_compute_flags(block, desc, op & M_RC, 0, FALSE);              // <update flags>
33412860         return TRUE;
33422861
33432862      case 0x3ba: /* EXTSBx */
33442863         UML_SEXT(block, R32(G_RA(op)), R32(G_RS(op)), SIZE_BYTE);                           // sext    ra,rs,byte
33452864         if (op & M_RC)
3346            generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);              // <update flags>
2865            generate_compute_flags(block, desc, op & M_RC, 0, FALSE);              // <update flags>
33472866         return TRUE;
33482867
33492868      case 0x39a: /* EXTSHx */
33502869         UML_SEXT(block, R32(G_RA(op)), R32(G_RS(op)), SIZE_WORD);                           // sext    ra,rs,word
33512870         if (op & M_RC)
3352            generate_compute_flags(ppc, block, desc, op & M_RC, 0, FALSE);              // <update flags>
2871            generate_compute_flags(block, desc, op & M_RC, 0, FALSE);              // <update flags>
33532872         return TRUE;
33542873
33552874      case 0x057: /* LBZX */
33562875         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
33572876         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3358         UML_CALLH(block, *ppc->impstate->read8[ppc->impstate->mode]);                   // callh   read8
2877         UML_CALLH(block, *m_read8[m_core->mode]);                   // callh   read8
33592878         UML_AND(block, R32(G_RD(op)), I0, 0xff);                                // and     rd,i0,0xff
3360         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2879         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
33612880         return TRUE;
33622881
33632882      case 0x117: /* LHZX */
33642883         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
33652884         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3366         UML_CALLH(block, *ppc->impstate->read16[ppc->impstate->mode]);                  // callh   read16
2885         UML_CALLH(block, *m_read16[m_core->mode]);                  // callh   read16
33672886         UML_AND(block, R32(G_RD(op)), I0, 0xffff);                          // and     rd,i0,0xffff
3368         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2887         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
33692888         return TRUE;
33702889
33712890      case 0x157: /* LHAX */
33722891         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
33732892         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3374         UML_CALLH(block, *ppc->impstate->read16[ppc->impstate->mode]);                  // callh   read16
2893         UML_CALLH(block, *m_read16[m_core->mode]);                  // callh   read16
33752894         UML_SEXT(block, R32(G_RD(op)), I0, SIZE_WORD);                                  // sext    rd,i0,word
3376         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2895         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
33772896         return TRUE;
33782897
33792898      case 0x017: /* LWZX */
33802899         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
33812900         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3382         UML_CALLH(block, *ppc->impstate->read32[ppc->impstate->mode]);                  // callh   read32
2901         UML_CALLH(block, *m_read32[m_core->mode]);                  // callh   read32
33832902         UML_MOV(block, R32(G_RD(op)), I0);                                          // mov     rd,i0
3384         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2903         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
33852904         return TRUE;
33862905
33872906      case 0x217: /* LFSX */
33882907         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
33892908         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3390         UML_CALLH(block, *ppc->impstate->read32[ppc->impstate->mode]);                  // callh   read32
3391         UML_MOV(block, mem(&ppc->impstate->tempdata.w.l), I0);                      // mov     [tempdata],i0
3392         UML_FDFRFLT(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.w.l), SIZE_DWORD);   // fdfrflt fd,[tempdata],dword
3393         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2909         UML_CALLH(block, *m_read32[m_core->mode]);                  // callh   read32
2910         UML_MOV(block, mem(&m_core->tempdata.w.l), I0);                      // mov     [tempdata],i0
2911         UML_FDFRFLT(block, F64(G_RD(op)), mem(&m_core->tempdata.w.l), SIZE_DWORD);   // fdfrflt fd,[tempdata],dword
2912         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
33942913         return TRUE;
33952914
33962915      case 0x257: /* LFDX */
33972916         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
33982917         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3399         UML_CALLH(block, *ppc->impstate->read64[ppc->impstate->mode]);                  // callh   read64
3400         UML_DMOV(block, mem(&ppc->impstate->tempdata.d), I0);                       // dmov    [tempdata],i0
3401         UML_FDMOV(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.d));               // fdmov   fd,[tempdata]
3402         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2918         UML_CALLH(block, *m_read64[m_core->mode]);                  // callh   read64
2919         UML_DMOV(block, mem(&m_core->tempdata.d), I0);                       // dmov    [tempdata],i0
2920         UML_FDMOV(block, F64(G_RD(op)), mem(&m_core->tempdata.d));               // fdmov   fd,[tempdata]
2921         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34032922         return TRUE;
34042923
34052924      case 0x316: /* LHBRX */
34062925         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
34072926         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3408         UML_CALLH(block, *ppc->impstate->read16[ppc->impstate->mode]);                  // callh   read16
2927         UML_CALLH(block, *m_read16[m_core->mode]);                  // callh   read16
34092928         UML_BSWAP(block, I0, I0);                                               // bswap   i0,i0
34102929         UML_SHR(block, R32(G_RD(op)), I0, 16);                              // shr     rd,i0,16
3411         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2930         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34122931         return TRUE;
34132932
34142933      case 0x216: /* LWBRX */
34152934         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
34162935         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3417         UML_CALLH(block, *ppc->impstate->read32align[ppc->impstate->mode]);             // callh   read32align
2936         UML_CALLH(block, *m_read32align[m_core->mode]);             // callh   read32align
34182937         UML_BSWAP(block, R32(G_RD(op)), I0);                                        // bswap   rd,i0
3419         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2938         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34202939         return TRUE;
34212940
34222941      case 0x077: /* LBZUX */
34232942         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
3424         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2943         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
34252944         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDXU(op));                                // mapvar  dsisr,DSISR_IDXU(op)
3426         UML_CALLH(block, *ppc->impstate->read8[ppc->impstate->mode]);                   // callh   read8
2945         UML_CALLH(block, *m_read8[m_core->mode]);                   // callh   read8
34272946         UML_AND(block, R32(G_RD(op)), I0, 0xff);                                // and     rd,i0,0xff
3428         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3429         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2947         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2948         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34302949         return TRUE;
34312950
34322951      case 0x137: /* LHZUX */
34332952         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
3434         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2953         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
34352954         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDXU(op));                                // mapvar  dsisr,DSISR_IDXU(op)
3436         UML_CALLH(block, *ppc->impstate->read16[ppc->impstate->mode]);                  // callh   read16
2955         UML_CALLH(block, *m_read16[m_core->mode]);                  // callh   read16
34372956         UML_AND(block, R32(G_RD(op)), I0, 0xffff);                          // and     rd,i0,0xffff
3438         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3439         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2957         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2958         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34402959         return TRUE;
34412960
34422961      case 0x177: /* LHAUX */
34432962         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
3444         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2963         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
34452964         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDXU(op));                                // mapvar  dsisr,DSISR_IDXU(op)
3446         UML_CALLH(block, *ppc->impstate->read16[ppc->impstate->mode]);                  // callh   read16
2965         UML_CALLH(block, *m_read16[m_core->mode]);                  // callh   read16
34472966         UML_SEXT(block, R32(G_RD(op)), I0, SIZE_WORD);                                  // sext    rd,i0,word
3448         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3449         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2967         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2968         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34502969         return TRUE;
34512970
34522971      case 0x037: /* LWZUX */
34532972         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
3454         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2973         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
34552974         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDXU(op));                                // mapvar  dsisr,DSISR_IDXU(op)
3456         UML_CALLH(block, *ppc->impstate->read32[ppc->impstate->mode]);                  // callh   read32
2975         UML_CALLH(block, *m_read32[m_core->mode]);                  // callh   read32
34572976         UML_MOV(block, R32(G_RD(op)), I0);                                          // mov     rd,i0
3458         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3459         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2977         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2978         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34602979         return TRUE;
34612980
34622981      case 0x237: /* LFSUX */
34632982         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
3464         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2983         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
34652984         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3466         UML_CALLH(block, *ppc->impstate->read32[ppc->impstate->mode]);                  // callh   read32
3467         UML_MOV(block, mem(&ppc->impstate->tempdata.w.l), I0);                      // mov     [tempdata],i0
3468         UML_FDFRFLT(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.w.l), SIZE_DWORD);   // fdfrflt fd,[tempdata],dword
3469         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3470         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2985         UML_CALLH(block, *m_read32[m_core->mode]);                  // callh   read32
2986         UML_MOV(block, mem(&m_core->tempdata.w.l), I0);                      // mov     [tempdata],i0
2987         UML_FDFRFLT(block, F64(G_RD(op)), mem(&m_core->tempdata.w.l), SIZE_DWORD);   // fdfrflt fd,[tempdata],dword
2988         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
2989         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34712990         return TRUE;
34722991
34732992      case 0x277: /* LFDUX */
34742993         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
3475         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
2994         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
34762995         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3477         UML_CALLH(block, *ppc->impstate->read64[ppc->impstate->mode]);                  // callh   read64
3478         UML_DMOV(block, mem(&ppc->impstate->tempdata.d), I0);                       // dmov    [tempdata],i0
3479         UML_FDMOV(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.d));               // fdmov   fd,[tempdata]
3480         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3481         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
2996         UML_CALLH(block, *m_read64[m_core->mode]);                  // callh   read64
2997         UML_DMOV(block, mem(&m_core->tempdata.d), I0);                       // dmov    [tempdata],i0
2998         UML_FDMOV(block, F64(G_RD(op)), mem(&m_core->tempdata.d));               // fdmov   fd,[tempdata]
2999         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
3000         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34823001         return TRUE;
34833002
34843003      case 0x014: /* LWARX */
34853004         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
34863005         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3487         UML_CALLH(block, *ppc->impstate->read32align[ppc->impstate->mode]);             // callh   read32align
3006         UML_CALLH(block, *m_read32align[m_core->mode]);             // callh   read32align
34883007         UML_MOV(block, R32(G_RD(op)), I0);                                          // mov     rd,i0
3489         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3008         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34903009         return TRUE;
34913010
34923011      case 0x255: /* LSWI */
3493         UML_MOV(block, mem(&ppc->impstate->updateaddr), R32Z(G_RA(op)));                // mov     [updateaddr],ra
3494         UML_MOV(block, mem(&ppc->impstate->swcount), ((G_NB(op) - 1) & 0x1f) + 1);  // mov     [swcount],G_NB
3495         UML_CALLH(block, *ppc->impstate->lsw[ppc->impstate->mode][G_RD(op)]);           // call    lsw[rd]
3496         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3012         UML_MOV(block, mem(&m_core->updateaddr), R32Z(G_RA(op)));                // mov     [updateaddr],ra
3013         UML_MOV(block, mem(&m_core->swcount), ((G_NB(op) - 1) & 0x1f) + 1);  // mov     [swcount],G_NB
3014         UML_CALLH(block, *m_lsw[m_core->mode][G_RD(op)]);           // call    lsw[rd]
3015         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
34973016         return TRUE;
34983017
34993018      case 0x215: /* LSWX */
3500         UML_ADD(block, mem(&ppc->impstate->updateaddr), R32Z(G_RA(op)), R32(G_RB(op))); // add     [updateaddr],ra,rb
3501         UML_AND(block, mem(&ppc->impstate->swcount), SPR32(SPR_XER), 0x7f);     // and     [swcount],[xer],0x7f
3502         UML_SUB(block, mem(&ppc->icount), mem(&ppc->icount), mem(&ppc->impstate->swcount));// sub  icount,icount,[swcount]
3503         UML_CALLHc(block, COND_NZ, *ppc->impstate->lsw[ppc->impstate->mode][G_RD(op)]); // call    lsw[rd],nz
3504         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3019         UML_ADD(block, mem(&m_core->updateaddr), R32Z(G_RA(op)), R32(G_RB(op))); // add     [updateaddr],ra,rb
3020         UML_AND(block, mem(&m_core->swcount), SPR32(SPR_XER), 0x7f);     // and     [swcount],[xer],0x7f
3021         UML_SUB(block, mem(&m_core->icount), mem(&m_core->icount), mem(&m_core->swcount));// sub  icount,icount,[swcount]
3022         UML_CALLHc(block, COND_NZ, *m_lsw[m_core->mode][G_RD(op)]); // call    lsw[rd],nz
3023         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35053024         return TRUE;
35063025
35073026      case 0x136: /* ECIWX */
r31142r31143
35123031         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
35133032         UML_AND(block, I1, R32(G_RS(op)), 0xff);                                // and     i1,rs,0xff
35143033         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3515         UML_CALLH(block, *ppc->impstate->write8[ppc->impstate->mode]);                  // callh   write8
3516         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3034         UML_CALLH(block, *m_write8[m_core->mode]);                  // callh   write8
3035         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35173036         return TRUE;
35183037
35193038      case 0x197: /* STHX */
35203039         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
35213040         UML_AND(block, I1, R32(G_RS(op)), 0xffff);                          // and     i1,rs
35223041         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3523         UML_CALLH(block, *ppc->impstate->write16[ppc->impstate->mode]);                 // callh   write16
3524         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3042         UML_CALLH(block, *m_write16[m_core->mode]);                 // callh   write16
3043         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35253044         return TRUE;
35263045
35273046      case 0x097: /* STWX */
35283047         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
35293048         UML_MOV(block, I1, R32(G_RS(op)));                                          // mov     i1,rs
35303049         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3531         UML_CALLH(block, *ppc->impstate->write32[ppc->impstate->mode]);                 // callh   write32
3532         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3050         UML_CALLH(block, *m_write32[m_core->mode]);                 // callh   write32
3051         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35333052         return TRUE;
35343053
35353054      case 0x297: /* STFSX */
35363055         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
3537         UML_FSFRFLT(block, mem(&ppc->impstate->tempdata.w.l), F64(G_RS(op)), SIZE_QWORD);   // fsfrflt [tempdata],rs,qword
3538         UML_MOV(block, I1, mem(&ppc->impstate->tempdata.w.l));                      // mov     i1,[tempdata]
3056         UML_FSFRFLT(block, mem(&m_core->tempdata.w.l), F64(G_RS(op)), SIZE_QWORD);   // fsfrflt [tempdata],rs,qword
3057         UML_MOV(block, I1, mem(&m_core->tempdata.w.l));                      // mov     i1,[tempdata]
35393058         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3540         UML_CALLH(block, *ppc->impstate->write32[ppc->impstate->mode]);                 // callh   write32
3541         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3059         UML_CALLH(block, *m_write32[m_core->mode]);                 // callh   write32
3060         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35423061         return TRUE;
35433062
35443063      case 0x3d7: /* STFIWX */
35453064         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
3546         UML_FDMOV(block, mem(&ppc->impstate->tempdata.d), F64(G_RS(op)));               // fdmov   [tempdata],rs
3547         UML_MOV(block, I1, mem(&ppc->impstate->tempdata.w.l));                      // mov     i1,[tempdata.lo]
3065         UML_FDMOV(block, mem(&m_core->tempdata.d), F64(G_RS(op)));               // fdmov   [tempdata],rs
3066         UML_MOV(block, I1, mem(&m_core->tempdata.w.l));                      // mov     i1,[tempdata.lo]
35483067         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3549         UML_CALLH(block, *ppc->impstate->write32[ppc->impstate->mode]);                 // callh   write32
3550         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3068         UML_CALLH(block, *m_write32[m_core->mode]);                 // callh   write32
3069         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35513070         return TRUE;
35523071
35533072      case 0x2d7: /* STFDX */
35543073         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
3555         UML_FDMOV(block, mem(&ppc->impstate->tempdata.d), F64(G_RS(op)));               // fdmov   [tempdata],rs
3556         UML_DMOV(block, I1, mem(&ppc->impstate->tempdata.d));                       // dmov    i1,[tempdata]
3074         UML_FDMOV(block, mem(&m_core->tempdata.d), F64(G_RS(op)));               // fdmov   [tempdata],rs
3075         UML_DMOV(block, I1, mem(&m_core->tempdata.d));                       // dmov    i1,[tempdata]
35573076         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3558         UML_CALLH(block, *ppc->impstate->write64[ppc->impstate->mode]);                 // callh   write64
3559         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3077         UML_CALLH(block, *m_write64[m_core->mode]);                 // callh   write64
3078         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35603079         return TRUE;
35613080
35623081      case 0x396: /* STHBRX */
r31142r31143
35643083         UML_BSWAP(block, I1, R32(G_RS(op)));                                        // bswap   i1,rs
35653084         UML_SHR(block, I1, I1, 16);                                     // shr     i1,i1,16
35663085         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3567         UML_CALLH(block, *ppc->impstate->write16[ppc->impstate->mode]);                 // callh   write16
3568         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3086         UML_CALLH(block, *m_write16[m_core->mode]);                 // callh   write16
3087         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35693088         return TRUE;
35703089
35713090      case 0x296: /* STWBRX */
35723091         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
35733092         UML_BSWAP(block, I1, R32(G_RS(op)));                                        // bswap   i1,rs
35743093         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3575         UML_CALLH(block, *ppc->impstate->write32[ppc->impstate->mode]);                 // callh   write32
3576         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3094         UML_CALLH(block, *m_write32[m_core->mode]);                 // callh   write32
3095         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35773096         return TRUE;
35783097
35793098      case 0x0f7: /* STBUX */
35803099         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
35813100         UML_AND(block, I1, R32(G_RS(op)), 0xff);                                // and     i1,rs,0xff
3582         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
3101         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
35833102         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3584         UML_CALLH(block, *ppc->impstate->write8[ppc->impstate->mode]);                  // callh   write8
3585         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3586         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3103         UML_CALLH(block, *m_write8[m_core->mode]);                  // callh   write8
3104         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
3105         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35873106         return TRUE;
35883107
35893108      case 0x1b7: /* STHUX */
35903109         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
35913110         UML_AND(block, I1, R32(G_RS(op)), 0xffff);                          // and     i1,rs,0xffff
3592         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
3111         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
35933112         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3594         UML_CALLH(block, *ppc->impstate->write16[ppc->impstate->mode]);                 // callh   write16
3595         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3596         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3113         UML_CALLH(block, *m_write16[m_core->mode]);                 // callh   write16
3114         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
3115         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
35973116         return TRUE;
35983117
35993118      case 0x0b7: /* STWUX */
36003119         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
36013120         UML_MOV(block, I1, R32(G_RS(op)));                                          // mov     i1,rs
3602         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
3121         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
36033122         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDXU(op));                                // mapvar  dsisr,DSISR_IDXU(op)
3604         UML_CALLH(block, *ppc->impstate->write32[ppc->impstate->mode]);                 // callh   write32
3605         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3606         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3123         UML_CALLH(block, *m_write32[m_core->mode]);                 // callh   write32
3124         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
3125         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
36073126         return TRUE;
36083127
36093128      case 0x2b7: /* STFSUX */
36103129         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
3611         UML_FSFRFLT(block, mem(&ppc->impstate->tempdata.w.l), F64(G_RS(op)), SIZE_QWORD);   // fsfrflt [tempdata],rs,qword
3612         UML_MOV(block, I1, mem(&ppc->impstate->tempdata.w.l));                      // mov     i1,[tempdata]
3613         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
3130         UML_FSFRFLT(block, mem(&m_core->tempdata.w.l), F64(G_RS(op)), SIZE_QWORD);   // fsfrflt [tempdata],rs,qword
3131         UML_MOV(block, I1, mem(&m_core->tempdata.w.l));                      // mov     i1,[tempdata]
3132         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
36143133         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3615         UML_CALLH(block, *ppc->impstate->write32[ppc->impstate->mode]);                 // callh   write32
3616         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3617         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3134         UML_CALLH(block, *m_write32[m_core->mode]);                 // callh   write32
3135         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
3136         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
36183137         return TRUE;
36193138
36203139      case 0x2f7: /* STFDUX */
36213140         UML_ADD(block, I0, R32(G_RA(op)), R32(G_RB(op)));                           // add     i0,ra,rb
3622         UML_FDMOV(block, mem(&ppc->impstate->tempdata.d), F64(G_RS(op)));               // fdmov   [tempdata],rs
3623         UML_DMOV(block, I1, mem(&ppc->impstate->tempdata.d));                       // dmov    i1,[tempdata]
3624         UML_MOV(block, mem(&ppc->impstate->updateaddr), I0);                        // mov     [updateaddr],i0
3141         UML_FDMOV(block, mem(&m_core->tempdata.d), F64(G_RS(op)));               // fdmov   [tempdata],rs
3142         UML_DMOV(block, I1, mem(&m_core->tempdata.d));                       // dmov    i1,[tempdata]
3143         UML_MOV(block, mem(&m_core->updateaddr), I0);                        // mov     [updateaddr],i0
36253144         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3626         UML_CALLH(block, *ppc->impstate->write64[ppc->impstate->mode]);                 // callh   write64
3627         UML_MOV(block, R32(G_RA(op)), mem(&ppc->impstate->updateaddr));                 // mov     ra,[updateaddr]
3628         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3145         UML_CALLH(block, *m_write64[m_core->mode]);                 // callh   write64
3146         UML_MOV(block, R32(G_RA(op)), mem(&m_core->updateaddr));                 // mov     ra,[updateaddr]
3147         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
36293148         return TRUE;
36303149
36313150      case 0x096: /* STWCX. */
36323151         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
36333152         UML_MOV(block, I1, R32(G_RS(op)));                                          // mov     i1,rs
36343153         UML_MAPVAR(block, MAPVAR_DSISR, DSISR_IDX(op));                                 // mapvar  dsisr,DSISR_IDX(op)
3635         UML_CALLH(block, *ppc->impstate->write32align[ppc->impstate->mode]);                // callh   write32align
3636         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3154         UML_CALLH(block, *m_write32align[m_core->mode]);                // callh   write32align
3155         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
36373156
36383157         UML_CMP(block, I0, I0);                                             // cmp     i0,i0
36393158         UML_GETFLGS(block, I0, FLAG_Z | FLAG_C | FLAG_S);                           // getflgs i0,zcs
3640         UML_LOAD(block, I0, ppc->impstate->cmp_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,cmp_cr_table,i0,byte
3159         UML_LOAD(block, I0, m_cmp_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,cmp_cr_table,i0,byte
36413160         UML_OR(block, CR32(G_CRFD(op)), I0, XERSO32);                               // or      [crn],i0,[xerso]
36423161
3643         generate_compute_flags(ppc, block, desc, TRUE, 0, FALSE);                       // <update flags>
3162         generate_compute_flags(block, desc, TRUE, 0, FALSE);                       // <update flags>
36443163         return TRUE;
36453164
36463165      case 0x2d5: /* STSWI */
3647         UML_MOV(block, mem(&ppc->impstate->updateaddr), R32Z(G_RA(op)));                // mov     [updateaddr],ra
3648         UML_MOV(block, mem(&ppc->impstate->swcount), ((G_NB(op) - 1) & 0x1f) + 1);  // mov     [swcount],G_NB
3649         UML_CALLH(block, *ppc->impstate->stsw[ppc->impstate->mode][G_RD(op)]);          // call    stsw[rd]
3650         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3166         UML_MOV(block, mem(&m_core->updateaddr), R32Z(G_RA(op)));                // mov     [updateaddr],ra
3167         UML_MOV(block, mem(&m_core->swcount), ((G_NB(op) - 1) & 0x1f) + 1);  // mov     [swcount],G_NB
3168         UML_CALLH(block, *m_stsw[m_core->mode][G_RD(op)]);          // call    stsw[rd]
3169         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
36513170         return TRUE;
36523171
36533172      case 0x295: /* STSWX */
3654         UML_ADD(block, mem(&ppc->impstate->updateaddr), R32Z(G_RA(op)), R32(G_RB(op))); // add     [updateaddr],ra,rb
3655         UML_AND(block, mem(&ppc->impstate->swcount), SPR32(SPR_XER), 0x7f);     // and     [swcount],[xer],0x7f
3656         UML_SUB(block, mem(&ppc->icount), mem(&ppc->icount), mem(&ppc->impstate->swcount));// sub  icount,icount,[swcount]
3657         UML_CALLHc(block, COND_NZ, *ppc->impstate->stsw[ppc->impstate->mode][G_RD(op)]);    // call   stsw[rd]
3658         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3173         UML_ADD(block, mem(&m_core->updateaddr), R32Z(G_RA(op)), R32(G_RB(op))); // add     [updateaddr],ra,rb
3174         UML_AND(block, mem(&m_core->swcount), SPR32(SPR_XER), 0x7f);     // and     [swcount],[xer],0x7f
3175         UML_SUB(block, mem(&m_core->icount), mem(&m_core->icount), mem(&m_core->swcount));// sub  icount,icount,[swcount]
3176         UML_CALLHc(block, COND_NZ, *m_stsw[m_core->mode][G_RD(op)]);    // call   stsw[rd]
3177         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
36593178         return TRUE;
36603179
36613180      case 0x1b6: /* ECOWX */
r31142r31143
36643183
36653184      case 0x036: /* DCBST */
36663185         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
3667         UML_MOV(block, mem(&ppc->param0), I0);                                      // mov     [param0],i0
3668         UML_CALLC(block, (c_function)ppccom_dcstore_callback, ppc);
3186         UML_MOV(block, mem(&m_core->param0), I0);                                      // mov     [param0],i0
3187         UML_CALLC(block, (c_function)cfunc_ppccom_dcstore_callback, this);
36693188         return TRUE;
36703189
36713190      case 0x056: /* DCBF */
r31142r31143
36813200
36823201      case 0x3f6: /* DCBZ */
36833202         UML_ADD(block, I0, R32Z(G_RA(op)), R32(G_RB(op)));                          // add     i0,ra,rb
3684         UML_AND(block, mem(&ppc->impstate->tempaddr), I0, ~(ppc->cache_line_size - 1));
3203         UML_AND(block, mem(&m_core->tempaddr), I0, ~(m_cache_line_size - 1));
36853204                                                                     // and     [tempaddr],i0,~(cache_line_size - 1)
3686         for (item = 0; item < ppc->cache_line_size / 8; item++)
3205         for (item = 0; item < m_cache_line_size / 8; item++)
36873206         {
3688            UML_ADD(block, I0, mem(&ppc->impstate->tempaddr), 8 * item);        // add     i0,[tempaddr],8*item
3207            UML_ADD(block, I0, mem(&m_core->tempaddr), 8 * item);        // add     i0,[tempaddr],8*item
36893208            UML_DMOV(block, I1, 0);                                         // dmov    i1,0
3690            UML_CALLH(block, *ppc->impstate->write64[ppc->impstate->mode]);             // callh   write64
3209            UML_CALLH(block, *m_write64[m_core->mode]);             // callh   write64
36913210         }
36923211         return TRUE;
36933212
36943213      case 0x132: /* TLBIE */
3695         UML_MOV(block, mem(&ppc->param0), R32(G_RB(op)));                               // mov     [param0],rb
3696         UML_CALLC(block, (c_function)ppccom_execute_tlbie, ppc);                                    // callc   ppccom_execute_tlbie,ppc
3214         UML_MOV(block, mem(&m_core->param0), R32(G_RB(op)));                               // mov     [param0],rb
3215         UML_CALLC(block, (c_function)cfunc_ppccom_execute_tlbie, this);                                    // callc   ppccom_execute_tlbie,ppc
36973216         return TRUE;
36983217
36993218      case 0x172: /* TLBIA */
3700         UML_CALLC(block, (c_function)ppccom_execute_tlbia, ppc);                                    // callc   ppccom_execute_tlbia,ppc
3219         UML_CALLC(block, (c_function)cfunc_ppccom_execute_tlbia, this);                                    // callc   ppccom_execute_tlbia,ppc
37013220         return TRUE;
37023221
37033222      case 0x3d2: /* TLBLD */
3704         assert(ppc->cap & PPCCAP_603_MMU);
3705         UML_MOV(block, mem(&ppc->param0), R32(G_RB(op)));                               // mov     [param0],rb
3706         UML_MOV(block, mem(&ppc->param1), 0);                                       // mov     [param1],0
3707         UML_CALLC(block, (c_function)ppccom_execute_tlbl, ppc);                                     // callc   ppccom_execute_tlbl,ppc
3223         assert(m_cap & PPCCAP_603_MMU);
3224         UML_MOV(block, mem(&m_core->param0), R32(G_RB(op)));                               // mov     [param0],rb
3225         UML_MOV(block, mem(&m_core->param1), 0);                                       // mov     [param1],0
3226         UML_CALLC(block, (c_function)cfunc_ppccom_execute_tlbl, this);                                     // callc   ppccom_execute_tlbl,ppc
37083227         return TRUE;
37093228
37103229      case 0x3f2: /* TLBLI */
3711         assert(ppc->cap & PPCCAP_603_MMU);
3712         UML_MOV(block, mem(&ppc->param0), R32(G_RB(op)));                               // mov     [param0],rb
3713         UML_MOV(block, mem(&ppc->param1), 1);                                       // mov     [param1],1
3714         UML_CALLC(block, (c_function)ppccom_execute_tlbl, ppc);                                     // callc   ppccom_execute_tlbl,ppc
3230         assert(m_cap & PPCCAP_603_MMU);
3231         UML_MOV(block, mem(&m_core->param0), R32(G_RB(op)));                               // mov     [param0],rb
3232         UML_MOV(block, mem(&m_core->param1), 1);                                       // mov     [param1],1
3233         UML_CALLC(block, (c_function)cfunc_ppccom_execute_tlbl, this);                                     // callc   ppccom_execute_tlbl,ppc
37153234         return TRUE;
37163235
37173236      case 0x013: /* MFCR */
r31142r31143
37473266            UML_OR(block, R32(G_RD(op)), SPR32(spr), I0);                           // or      [rd],[xer],i0
37483267         }
37493268         else if (spr == SPROEA_PVR)
3750            UML_MOV(block, R32(G_RD(op)), ppc->flavor);                         // mov     rd,flavor
3269            UML_MOV(block, R32(G_RD(op)), m_flavor);                         // mov     rd,flavor
37513270         else
37523271         {
3753            generate_update_cycles(ppc, block, compiler, desc->pc, TRUE);           // <update cycles>
3754            UML_MOV(block, mem(&ppc->param0), spr);                             // mov     [param0],spr
3755            UML_CALLC(block, (c_function)ppccom_execute_mfspr, ppc);                                // callc   ppccom_execute_mfspr,ppc
3756            UML_MOV(block, R32(G_RD(op)), mem(&ppc->param1));                           // mov     rd,[param1]
3272            generate_update_cycles(block, compiler, desc->pc, TRUE);           // <update cycles>
3273            UML_MOV(block, mem(&m_core->param0), spr);                             // mov     [param0],spr
3274            UML_CALLC(block, (c_function)cfunc_ppccom_execute_mfspr, this);                                // callc   ppccom_execute_mfspr,ppc
3275            UML_MOV(block, R32(G_RD(op)), mem(&m_core->param1));                           // mov     rd,[param1]
37573276         }
37583277         return TRUE;
37593278      }
r31142r31143
37643283
37653284      case 0x293: /* MFSRIN */
37663285         UML_SHR(block, I0, R32(G_RB(op)), 28);                              // shr     i0,G_RB,28
3767         UML_LOAD(block, R32(G_RD(op)), &ppc->sr[0], I0, SIZE_DWORD, SCALE_x4);      // load    rd,sr,i0,dword
3286         UML_LOAD(block, R32(G_RD(op)), &m_core->sr[0], I0, SIZE_DWORD, SCALE_x4);      // load    rd,sr,i0,dword
37683287         return TRUE;
37693288
37703289      case 0x173: /* MFTB */
r31142r31143
37723291         UINT32 tbr = compute_spr(G_SPR(op));
37733292         if (tbr != SPRVEA_TBL_R && tbr != SPRVEA_TBU_R)
37743293            return FALSE;
3775         generate_update_cycles(ppc, block, compiler, desc->pc, TRUE);               // <update cycles>
3776         UML_MOV(block, mem(&ppc->param0), tbr);                                 // mov     [param0],tbr
3777         UML_CALLC(block, (c_function)ppccom_execute_mftb, ppc);                                     // callc   ppccom_execute_mftb,ppc
3778         UML_MOV(block, R32(G_RD(op)), mem(&ppc->param1));                               // mov     rd,[param1]
3294         generate_update_cycles(block, compiler, desc->pc, TRUE);               // <update cycles>
3295         UML_MOV(block, mem(&m_core->param0), tbr);                                 // mov     [param0],tbr
3296         UML_CALLC(block, (c_function)cfunc_ppccom_execute_mftb, this);                                     // callc   ppccom_execute_mftb,ppc
3297         UML_MOV(block, R32(G_RD(op)), mem(&m_core->param1));                               // mov     rd,[param1]
37793298         return TRUE;
37803299      }
37813300
r31142r31143
37923311         return TRUE;
37933312
37943313      case 0x092: /* MTMSR */
3795         if (ppc->cap & PPCCAP_603_MMU)
3314         if (m_cap & PPCCAP_603_MMU)
37963315            UML_XOR(block, I0, MSR32, R32(G_RS(op)));                               // xor     i0,msr32,rs
37973316         UML_MOV(block, MSR32, R32(G_RS(op)));                                           // mov     msr,rs
3798         if (ppc->cap & PPCCAP_603_MMU)
3317         if (m_cap & PPCCAP_603_MMU)
37993318         {
38003319            UML_TEST(block, I0, MSR603_TGPR);                                   // test    i0,tgpr
3801            UML_CALLHc(block, COND_NZ, *ppc->impstate->swap_tgpr);                          // callh   swap_tgpr,nz
3320            UML_CALLHc(block, COND_NZ, *m_swap_tgpr);                          // callh   swap_tgpr,nz
38023321         }
3803         generate_update_mode(ppc, block);                                               // <update mode>
3322         generate_update_mode(block);                                               // <update mode>
38043323         return TRUE;
38053324
38063325      case 0x1d3: /* MTSPR */
r31142r31143
38173336            ;                                                                           // read only
38183337         else
38193338         {
3820            generate_update_cycles(ppc, block, compiler, desc->pc, TRUE);           // <update cycles>
3821            UML_MOV(block, mem(&ppc->param0), spr);                             // mov     [param0],spr
3822            UML_MOV(block, mem(&ppc->param1), R32(G_RS(op)));                           // mov     [param1],rs
3823            UML_CALLC(block, (c_function)ppccom_execute_mtspr, ppc);                                // callc   ppccom_execute_mtspr,ppc
3339            generate_update_cycles(block, compiler, desc->pc, TRUE);           // <update cycles>
3340            UML_MOV(block, mem(&m_core->param0), spr);                             // mov     [param0],spr
3341            UML_MOV(block, mem(&m_core->param1), R32(G_RS(op)));                           // mov     [param1],rs
3342            UML_CALLC(block, (c_function)cfunc_ppccom_execute_mtspr, this);                                // callc   ppccom_execute_mtspr,ppc
38243343            compiler->checkints = TRUE;
3825            generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);       // <update cycles>
3344            generate_update_cycles(block, compiler, desc->pc + 4, TRUE);       // <update cycles>
38263345         }
38273346         return TRUE;
38283347      }
38293348
38303349      case 0x0d2: /* MTSR */
38313350         UML_MOV(block, SR32(G_SR(op)), R32(G_RS(op)));                                  // mov     sr[G_SR],rs
3832         UML_CALLC(block, (c_function)ppccom_tlb_flush, ppc);                                        // callc   ppccom_tlb_flush,ppc
3351         UML_CALLC(block, (c_function)cfunc_ppccom_tlb_flush, this);                                        // callc   ppccom_tlb_flush,ppc
38333352         return TRUE;
38343353
38353354      case 0x0f2: /* MTSRIN */
38363355         UML_SHR(block, I0, R32(G_RB(op)), 28);                              // shr     i0,G_RB,28
3837         UML_STORE(block, &ppc->sr[0], I0, R32(G_RS(op)), SIZE_DWORD, SCALE_x4); // store   sr,i0,rs,dword
3838         UML_CALLC(block, (c_function)ppccom_tlb_flush, ppc);                            // callc   ppccom_tlb_flush,ppc
3356         UML_STORE(block, &m_core->sr[0], I0, R32(G_RS(op)), SIZE_DWORD, SCALE_x4); // store   sr,i0,rs,dword
3357         UML_CALLC(block, (c_function)cfunc_ppccom_tlb_flush, this);                            // callc   ppccom_tlb_flush,ppc
38393358         return TRUE;
38403359
38413360      case 0x200: /* MCRXR */
r31142r31143
38493368      case 0x106: /* ICBT */
38503369      case 0x1c6: /* DCCCI */
38513370      case 0x3c6: /* ICCCI */
3852         assert(ppc->cap & PPCCAP_4XX);
3371         assert(m_cap & PPCCAP_4XX);
38533372         /* effective no-nop */
38543373         return TRUE;
38553374
38563375      case 0x1e6: /* DCREAD */
38573376      case 0x3e6: /* ICREAD */
3858         assert(ppc->cap & PPCCAP_4XX);
3377         assert(m_cap & PPCCAP_4XX);
38593378         UML_MOV(block, R32(G_RT(op)), 0);                                           // mov     rt,0
38603379         return TRUE;
38613380
38623381      case 0x143: /* MFDCR */
38633382      {
38643383         UINT32 spr = compute_spr(G_SPR(op));
3865         assert(ppc->cap & PPCCAP_4XX);
3866         generate_update_cycles(ppc, block, compiler, desc->pc, TRUE);               // <update cycles>
3867         UML_MOV(block, mem(&ppc->param0), spr);                                 // mov     [param0],spr
3868         UML_CALLC(block, (c_function)ppccom_execute_mfdcr, ppc);                                    // callc   ppccom_execute_mfdcr,ppc
3869         UML_MOV(block, R32(G_RD(op)), mem(&ppc->param1));                               // mov     rd,[param1]
3384         assert(m_cap & PPCCAP_4XX);
3385         generate_update_cycles(block, compiler, desc->pc, TRUE);               // <update cycles>
3386         UML_MOV(block, mem(&m_core->param0), spr);                                 // mov     [param0],spr
3387         UML_CALLC(block, (c_function)cfunc_ppccom_execute_mfdcr, this);                                    // callc   ppccom_execute_mfdcr,ppc
3388         UML_MOV(block, R32(G_RD(op)), mem(&m_core->param1));                               // mov     rd,[param1]
38703389         return TRUE;
38713390      }
38723391
38733392      case 0x1c3: /* MTDCR */
38743393      {
38753394         UINT32 spr = compute_spr(G_SPR(op));
3876         assert(ppc->cap & PPCCAP_4XX);
3877         generate_update_cycles(ppc, block, compiler, desc->pc, TRUE);               // <update cycles>
3878         UML_MOV(block, mem(&ppc->param0), spr);                                 // mov     [param0],spr
3879         UML_MOV(block, mem(&ppc->param1), R32(G_RS(op)));                               // mov     [param1],rs
3880         UML_CALLC(block, (c_function)ppccom_execute_mtdcr, ppc);                                    // callc   ppccom_execute_mtdcr,ppc
3395         assert(m_cap & PPCCAP_4XX);
3396         generate_update_cycles(block, compiler, desc->pc, TRUE);               // <update cycles>
3397         UML_MOV(block, mem(&m_core->param0), spr);                                 // mov     [param0],spr
3398         UML_MOV(block, mem(&m_core->param1), R32(G_RS(op)));                               // mov     [param1],rs
3399         UML_CALLC(block, (c_function)cfunc_ppccom_execute_mtdcr, this);                                    // callc   ppccom_execute_mtdcr,ppc
38813400         compiler->checkints = TRUE;
3882         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3401         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
38833402         return TRUE;
38843403      }
38853404
38863405      case 0x083: /* WRTEE */
3887         assert(ppc->cap & PPCCAP_4XX);
3406         assert(m_cap & PPCCAP_4XX);
38883407         UML_ROLINS(block, MSR32, R32(G_RS(op)), 0, MSR_EE);                 // rolins  msr,rs,0,MSR_EE
38893408         compiler->checkints = TRUE;
3890         generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);           // <update cycles>
3409         generate_update_cycles(block, compiler, desc->pc + 4, TRUE);           // <update cycles>
38913410         return TRUE;
38923411
38933412      case 0x0a3: /* WRTEEI */
3894         assert(ppc->cap & PPCCAP_4XX);
3413         assert(m_cap & PPCCAP_4XX);
38953414         if (op & MSR_EE)
38963415         {
38973416            UML_OR(block, MSR32, MSR32, MSR_EE);                                    // or      msr,msr,MSR_EE
38983417            compiler->checkints = TRUE;
3899            generate_update_cycles(ppc, block, compiler, desc->pc + 4, TRUE);       // <update cycles>
3418            generate_update_cycles(block, compiler, desc->pc + 4, TRUE);       // <update cycles>
39003419         }
39013420         else
39023421            UML_AND(block, MSR32, MSR32, ~MSR_EE);                                  // and     msr,msr,~MSR_EE
r31142r31143
39173436    the 0x3b group
39183437-------------------------------------------------*/
39193438
3920static int generate_instruction_3b(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
3439int ppc_device::generate_instruction_3b(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
39213440{
39223441   UINT32 op = desc->opptr.l[0];
39233442   UINT32 opswitch = (op >> 1) & 0x1f;
r31142r31143
39253444   switch (opswitch)
39263445   {
39273446      case 0x15:  /* FADDSx */
3928         if (!(ppc->impstate->drcoptions & PPCDRC_ACCURATE_SINGLES))
3929            return generate_instruction_3f(ppc, block, compiler, desc);
3447         if (!(m_drcoptions & PPCDRC_ACCURATE_SINGLES))
3448            return generate_instruction_3f(block, compiler, desc);
39303449         UML_FDADD(block, F0, F64(G_RA(op)), F64(G_RB(op)));                     // fdadd   f0,ra,rb
39313450         UML_FDRNDS(block, F64(G_RD(op)), F0);                                       // fdrnds  rd,f0
3932         generate_fp_flags(ppc, block, desc, TRUE);
3451         generate_fp_flags(block, desc, TRUE);
39333452         return TRUE;
39343453
39353454      case 0x14:  /* FSUBSx */
3936         if (!(ppc->impstate->drcoptions & PPCDRC_ACCURATE_SINGLES))
3937            return generate_instruction_3f(ppc, block, compiler, desc);
3455         if (!(m_drcoptions & PPCDRC_ACCURATE_SINGLES))
3456            return generate_instruction_3f(block, compiler, desc);
39383457         UML_FDSUB(block, F0, F64(G_RA(op)), F64(G_RB(op)));                     // fdsub   f0,ra,rb
39393458         UML_FDRNDS(block, F64(G_RD(op)), F0);                                       // fdrnds  rd,f0
3940         generate_fp_flags(ppc, block, desc, TRUE);
3459         generate_fp_flags(block, desc, TRUE);
39413460         return TRUE;
39423461
39433462      case 0x19:  /* FMULSx */
3944         if (!(ppc->impstate->drcoptions & PPCDRC_ACCURATE_SINGLES))
3945            return generate_instruction_3f(ppc, block, compiler, desc);
3463         if (!(m_drcoptions & PPCDRC_ACCURATE_SINGLES))
3464            return generate_instruction_3f(block, compiler, desc);
39463465         UML_FDMUL(block, F0, F64(G_RA(op)), F64(G_REGC(op)));                       // fdmul   f0,ra,rc
39473466         UML_FDRNDS(block, F64(G_RD(op)), F0);                                       // fdrnds  rd,f0
3948         generate_fp_flags(ppc, block, desc, TRUE);
3467         generate_fp_flags(block, desc, TRUE);
39493468         return TRUE;
39503469
39513470      case 0x12:  /* FDIVSx */
3952         if (!(ppc->impstate->drcoptions & PPCDRC_ACCURATE_SINGLES))
3953            return generate_instruction_3f(ppc, block, compiler, desc);
3471         if (!(m_drcoptions & PPCDRC_ACCURATE_SINGLES))
3472            return generate_instruction_3f(block, compiler, desc);
39543473         UML_FDDIV(block, F0, F64(G_RA(op)), F64(G_RB(op)));                     // fddiv   f0,ra,rb
39553474         UML_FDRNDS(block, F64(G_RD(op)), F0);                                       // fdrnds  rd,f0
3956         generate_fp_flags(ppc, block, desc, TRUE);
3475         generate_fp_flags(block, desc, TRUE);
39573476         return TRUE;
39583477
39593478      case 0x16:  /* FSQRTSx */
3960         if (!(ppc->impstate->drcoptions & PPCDRC_ACCURATE_SINGLES))
3961            return generate_instruction_3f(ppc, block, compiler, desc);
3479         if (!(m_drcoptions & PPCDRC_ACCURATE_SINGLES))
3480            return generate_instruction_3f(block, compiler, desc);
39623481         UML_FDSQRT(block, F0, F64(G_RB(op)));                                       // fdsqrt  f0,rb
39633482         UML_FDRNDS(block, F64(G_RD(op)), F0);                                       // fdrnds  rd,f0
3964         generate_fp_flags(ppc, block, desc, TRUE);
3483         generate_fp_flags(block, desc, TRUE);
39653484         return TRUE;
39663485
39673486      case 0x18:  /* FRESx */
39683487         UML_FSFRFLT(block, F0, F64(G_RB(op)), SIZE_QWORD);                              // fsfrlt  f0,rb,qword
39693488         UML_FSRECIP(block, F0, F0);                                         // fsrecip f0,f0
39703489         UML_FDFRFLT(block, F64(G_RD(op)), F0, SIZE_DWORD);                              // fdfrflt rd,f0,dword
3971         generate_fp_flags(ppc, block, desc, TRUE);
3490         generate_fp_flags(block, desc, TRUE);
39723491         return TRUE;
39733492
39743493      case 0x1d:  /* FMADDSx */
3975         if (!(ppc->impstate->drcoptions & PPCDRC_ACCURATE_SINGLES))
3976            return generate_instruction_3f(ppc, block, compiler, desc);
3494         if (!(m_drcoptions & PPCDRC_ACCURATE_SINGLES))
3495            return generate_instruction_3f(block, compiler, desc);
39773496         UML_FDMUL(block, F0, F64(G_RA(op)), F64(G_REGC(op)));                       // fdmul   f0,ra,rc
39783497         UML_FDADD(block, F0, F0, F64(G_RB(op)));                                // fdadd   f0,f0,rb
39793498         UML_FDRNDS(block, F64(G_RD(op)), F0);                                       // fdrnds  rd,f0
3980         generate_fp_flags(ppc, block, desc, TRUE);
3499         generate_fp_flags(block, desc, TRUE);
39813500         return TRUE;
39823501
39833502      case 0x1c:  /* FMSUBSx */
3984         if (!(ppc->impstate->drcoptions & PPCDRC_ACCURATE_SINGLES))
3985            return generate_instruction_3f(ppc, block, compiler, desc);
3503         if (!(m_drcoptions & PPCDRC_ACCURATE_SINGLES))
3504            return generate_instruction_3f(block, compiler, desc);
39863505         UML_FDMUL(block, F0, F64(G_RA(op)), F64(G_REGC(op)));                       // fdmul   f0,ra,rc
39873506         UML_FDSUB(block, F0, F0, F64(G_RB(op)));                                // fdsub   f0,f0,rb
39883507         UML_FDRNDS(block, F64(G_RD(op)), F0);                                       // fdrnds  rd,f0
3989         generate_fp_flags(ppc, block, desc, TRUE);
3508         generate_fp_flags(block, desc, TRUE);
39903509         return TRUE;
39913510
39923511      case 0x1f:  /* FNMADDSx */
3993         if (!(ppc->impstate->drcoptions & PPCDRC_ACCURATE_SINGLES))
3994            return generate_instruction_3f(ppc, block, compiler, desc);
3512         if (!(m_drcoptions & PPCDRC_ACCURATE_SINGLES))
3513            return generate_instruction_3f(block, compiler, desc);
39953514         UML_FDMUL(block, F0, F64(G_RA(op)), F64(G_REGC(op)));                       // fdmul   f0,ra,rc
39963515         UML_FDADD(block, F0, F0, F64(G_RB(op)));                                // fdadd   f0,f0,rb
39973516         UML_FDNEG(block, F0, F0);                                               // fdneg   f0,f0
39983517         UML_FDRNDS(block, F64(G_RD(op)), F0);                                       // fdrnds  rd,f0
3999         generate_fp_flags(ppc, block, desc, TRUE);
3518         generate_fp_flags(block, desc, TRUE);
40003519         return TRUE;
40013520
40023521      case 0x1e:  /* FNMSUBSx */
4003         if (!(ppc->impstate->drcoptions & PPCDRC_ACCURATE_SINGLES))
4004            return generate_instruction_3f(ppc, block, compiler, desc);
3522         if (!(m_drcoptions & PPCDRC_ACCURATE_SINGLES))
3523            return generate_instruction_3f(block, compiler, desc);
40053524         UML_FDMUL(block, F0, F64(G_RA(op)), F64(G_REGC(op)));                       // fdmul   f0,ra,rc
40063525         UML_FDSUB(block, F0, F64(G_RB(op)), F0);                                // fdsub   f0,rb,f0
40073526         UML_FDRNDS(block, F64(G_RD(op)), F0);                                       // fdrnds  rd,f0
4008         generate_fp_flags(ppc, block, desc, TRUE);
3527         generate_fp_flags(block, desc, TRUE);
40093528         return TRUE;
40103529   }
40113530
r31142r31143
40193538    the 0x3f group
40203539-------------------------------------------------*/
40213540
4022static int generate_instruction_3f(powerpc_state *ppc, drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
3541int ppc_device::generate_instruction_3f(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc)
40233542{
40243543   UINT32 op = desc->opptr.l[0];
40253544   UINT32 opswitch = (op >> 1) & 0x3ff;
r31142r31143
40313550      {
40323551         case 0x15:  /* FADDx */
40333552            UML_FDADD(block, F64(G_RD(op)), F64(G_RA(op)), F64(G_RB(op)));              // fdadd   rd,ra,rb
4034            generate_fp_flags(ppc, block, desc, TRUE);
3553            generate_fp_flags(block, desc, TRUE);
40353554            return TRUE;
40363555
40373556         case 0x14:  /* FSUBx */
40383557            UML_FDSUB(block, F64(G_RD(op)), F64(G_RA(op)), F64(G_RB(op)));              // fdsub   rd,ra,rb
4039            generate_fp_flags(ppc, block, desc, TRUE);
3558            generate_fp_flags(block, desc, TRUE);
40403559            return TRUE;
40413560
40423561         case 0x19:  /* FMULx */
40433562            UML_FDMUL(block, F64(G_RD(op)), F64(G_RA(op)), F64(G_REGC(op)));            // fdmul   rd,ra,rc
4044            generate_fp_flags(ppc, block, desc, TRUE);
3563            generate_fp_flags(block, desc, TRUE);
40453564            return TRUE;
40463565
40473566         case 0x12:  /* FDIVx */
40483567            UML_FDDIV(block, F64(G_RD(op)), F64(G_RA(op)), F64(G_RB(op)));              // fddiv   rd,ra,rb
4049            generate_fp_flags(ppc, block, desc, TRUE);
3568            generate_fp_flags(block, desc, TRUE);
40503569            return TRUE;
40513570
40523571         case 0x16:  /* FSQRTx */
40533572            UML_FDSQRT(block, F64(G_RD(op)), F64(G_RB(op)));                            // fdsqrt  rd,rb
4054            generate_fp_flags(ppc, block, desc, TRUE);
3573            generate_fp_flags(block, desc, TRUE);
40553574            return TRUE;
40563575
40573576         case 0x1a:  /* FRSQRTEx */
40583577            UML_FDRSQRT(block, F64(G_RD(op)), F64(G_RB(op)));                           // fdrsqrt rd,rb
4059            generate_fp_flags(ppc, block, desc, TRUE);
3578            generate_fp_flags(block, desc, TRUE);
40603579            return TRUE;
40613580
40623581         case 0x17:  /* FSELx */
4063            UML_FDCMP(block, F64(G_RA(op)), mem(&ppc->impstate->fp0));                  // fdcmp   f0,ra,[fp0]
3582            UML_FDCMP(block, F64(G_RA(op)), mem(&m_core->fp0));                  // fdcmp   f0,ra,[fp0]
40643583            UML_FDMOVc(block, COND_AE, F64(G_RD(op)), F64(G_REGC(op)));                 // fdmov   rd,rc,AE
40653584            UML_FDMOVc(block, COND_B, F64(G_RD(op)), F64(G_RB(op)));                        // fdmov   rd,rb,B
40663585            return TRUE;
r31142r31143
40683587         case 0x1d:  /* FMADDx */
40693588            UML_FDMUL(block, F0, F64(G_RA(op)), F64(G_REGC(op)));                   // fdmul   f0,ra,rc
40703589            UML_FDADD(block, F64(G_RD(op)), F0, F64(G_RB(op)));                 // fdadd   rd,f0,rb
4071            generate_fp_flags(ppc, block, desc, TRUE);
3590            generate_fp_flags(block, desc, TRUE);
40723591            return TRUE;
40733592
40743593         case 0x1f:  /* FNMADDx */
40753594            UML_FDMUL(block, F0, F64(G_RA(op)), F64(G_REGC(op)));                   // fdmul   f0,ra,rc
40763595            UML_FDADD(block, F0, F0, F64(G_RB(op)));                            // fdadd   f0,f0,rb
40773596            UML_FDNEG(block, F64(G_RD(op)), F0);                                    // fdneg   rd,f0
4078            generate_fp_flags(ppc, block, desc, TRUE);
3597            generate_fp_flags(block, desc, TRUE);
40793598            return TRUE;
40803599
40813600         case 0x1c:  /* FMSUBx */
40823601            UML_FDMUL(block, F0, F64(G_RA(op)), F64(G_REGC(op)));                   // fdmul   f0,ra,rc
40833602            UML_FDSUB(block, F64(G_RD(op)), F0, F64(G_RB(op)));                 // fdsub   rd,f0,rb
4084            generate_fp_flags(ppc, block, desc, TRUE);
3603            generate_fp_flags(block, desc, TRUE);
40853604            return TRUE;
40863605
40873606         case 0x1e:  /* FNMSUBx */
40883607            UML_FDMUL(block, F0, F64(G_RA(op)), F64(G_REGC(op)));                   // fdmul   f0,ra,rc
40893608            UML_FDSUB(block, F64(G_RD(op)), F64(G_RB(op)), F0);                 // fdsub   rd,rb,f0
4090            generate_fp_flags(ppc, block, desc, TRUE);
3609            generate_fp_flags(block, desc, TRUE);
40913610            return TRUE;
40923611      }
40933612   }
r31142r31143
41043623         case 0x020: /* FCMPO */
41053624            UML_FDCMP(block, F64(G_RA(op)), F64(G_RB(op)));                             // fdcmp   ra,rb
41063625            UML_GETFLGS(block, I0, FLAG_C | FLAG_Z | FLAG_U);                       // getflgs i0,czu
4107            UML_LOAD(block, I0, ppc->impstate->fcmp_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,fcmp_cr_table,i0,byte
3626            UML_LOAD(block, I0, m_fcmp_cr_table, I0, SIZE_BYTE, SCALE_x1);// load    i0,fcmp_cr_table,i0,byte
41083627            UML_OR(block, CR32(G_CRFD(op)), I0, XERSO32);                           // or      [crn],i0,[xerso]
41093628            return TRUE;
41103629
41113630         case 0x00c: /* FRSPx */
41123631            UML_FDRNDS(block, F64(G_RD(op)), F64(G_RB(op)));                            // fdrnds  rd,rb
4113            generate_fp_flags(ppc, block, desc, TRUE);
3632            generate_fp_flags(block, desc, TRUE);
41143633            return TRUE;
41153634
41163635         case 0x00e: /* FCTIWx */
41173636            UML_FDTOINT(block, I0, F64(G_RB(op)), SIZE_DWORD, ROUND_DEFAULT);                   // fdtoint i0,rb,dword,default
4118            UML_DAND(block, mem(&ppc->impstate->tempdata.w.l), I0, 0xffffffff);// dand    i0,i0,0xffffffff
4119            UML_FDMOV(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.w.l));         // fdmovr  rd,i0
3637            UML_DAND(block, mem(&m_core->tempdata.w.l), I0, 0xffffffff);// dand    i0,i0,0xffffffff
3638            UML_FDMOV(block, F64(G_RD(op)), mem(&m_core->tempdata.w.l));         // fdmovr  rd,i0
41203639            return TRUE;
41213640
41223641         case 0x00f: /* FCTIWZx */
41233642            UML_FDTOINT(block, I0, F64(G_RB(op)), SIZE_DWORD, ROUND_TRUNC);                 // fdtoint i0,rb,dword,default
4124            UML_DAND(block, mem(&ppc->impstate->tempdata.w.l), I0, 0xffffffff);// dand    i0,i0,0xffffffff
4125            UML_FDMOV(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.w.l));         // fdmovr  rd,i0
3643            UML_DAND(block, mem(&m_core->tempdata.w.l), I0, 0xffffffff);// dand    i0,i0,0xffffffff
3644            UML_FDMOV(block, F64(G_RD(op)), mem(&m_core->tempdata.w.l));         // fdmovr  rd,i0
41263645            return TRUE;
41273646
41283647         case 0x028: /* FNEGx */
r31142r31143
41573676            return TRUE;
41583677
41593678         case 0x247: /* MFFSx */
4160            UML_MOV(block, mem(&ppc->impstate->tempdata.w.l), FPSCR32);                 // mov     [tempdata],fpscr
4161            UML_FSMOV(block, F64(G_RD(op)), mem(&ppc->impstate->tempdata.d));           // fsmov   rd,fpscr
3679            UML_MOV(block, mem(&m_core->tempdata.w.l), FPSCR32);                 // mov     [tempdata],fpscr
3680            UML_FSMOV(block, F64(G_RD(op)), mem(&m_core->tempdata.d));           // fsmov   rd,fpscr
41623681            return TRUE;
41633682
41643683         case 0x2c7: /* MTFSFx */
4165            UML_FDMOV(block, mem(&ppc->impstate->tempdata.d), F64(G_RB(op)));           // fdmov   [tempdata],fb
4166            UML_ROLINS(block, FPSCR32, mem(&ppc->impstate->tempdata.w.l), 0, compute_crf_mask(G_FM(op)));
3684            UML_FDMOV(block, mem(&m_core->tempdata.d), F64(G_RB(op)));           // fdmov   [tempdata],fb
3685            UML_ROLINS(block, FPSCR32, mem(&m_core->tempdata.w.l), 0, compute_crf_mask(G_FM(op)));
41673686                                                                     // rolins  fpscr,rb,0,crf_mask
41683687            return TRUE;
41693688
r31142r31143
41883707    including disassembly of a PowerPC instruction
41893708-------------------------------------------------*/
41903709
4191static void log_add_disasm_comment(drcuml_block *block, UINT32 pc, UINT32 op)
3710void ppc_device::log_add_disasm_comment(drcuml_block *block, UINT32 pc, UINT32 op)
41923711{
41933712   char buffer[100];
41943713   if (LOG_UML)
r31142r31143
42053724    flags
42063725-------------------------------------------------*/
42073726
4208static const char *log_desc_flags_to_string(UINT32 flags)
3727const char *ppc_device::log_desc_flags_to_string(UINT32 flags)
42093728{
42103729   static char tempbuf[30];
42113730   char *dest = tempbuf;
r31142r31143
42593778    log_register_list - log a list of GPR registers
42603779-------------------------------------------------*/
42613780
4262static void log_register_list(drcuml_state *drcuml, const char *string, const UINT32 *reglist, const UINT32 *regnostarlist)
3781void ppc_device::log_register_list(drcuml_state *drcuml, const char *string, const UINT32 *reglist, const UINT32 *regnostarlist)
42633782{
42643783   static const char *const crtext[4] = { "lt", "gt", "eq", "so" };
42653784   int count = 0;
r31142r31143
43623881    log_opcode_desc - log a list of descriptions
43633882-------------------------------------------------*/
43643883
4365static void log_opcode_desc(drcuml_state *drcuml, const opcode_desc *desclist, int indent)
3884void ppc_device::log_opcode_desc(drcuml_state *drcuml, const opcode_desc *desclist, int indent)
43663885{
43673886   /* open the file, creating it if necessary */
43683887   if (indent == 0)
r31142r31143
44013920   }
44023921}
44033922
4404
4405
4406/***************************************************************************
4407    PPC 4XX VARIANTS
4408***************************************************************************/
4409
4410/*-------------------------------------------------
4411    ppcdrc4xx_get_info - PowerPC 4XX-specific
4412    information getter
4413-------------------------------------------------*/
4414
4415static CPU_GET_INFO( ppcdrc4xx )
4416{
4417   powerpc_state *ppc = (device != NULL && device->token() != NULL) ? get_safe_token(device) : NULL;
4418   CPU_GET_INFO_CALL(ppcdrc);
4419   ppc4xx_get_info(ppc, state, info);
4420}
4421
4422
4423/*-------------------------------------------------
4424    ppcdrc4xx_set_info - PowerPC 4XX-specific
4425    information setter
4426-------------------------------------------------*/
4427
4428static CPU_SET_INFO( ppcdrc4xx )
4429{
4430   powerpc_state *ppc = get_safe_token(device);
4431   CPU_SET_INFO_CALL(ppcdrc);
4432   ppc4xx_set_info(ppc, state, info);
4433}
4434
4435
4436/*-------------------------------------------------
4437    ppc403ga_init - PowerPC 403GA-specific
4438    initialization
4439-------------------------------------------------*/
4440
4441static CPU_INIT( ppc403ga )
4442{
4443   ppcdrc_init(PPC_MODEL_403GA, PPCCAP_4XX, 1, device, irqcallback);
4444}
4445
4446
4447/*-------------------------------------------------
4448    ppc403ga_get_info - PowerPC 403GA-specific
4449    information getter
4450-------------------------------------------------*/
4451
4452CPU_GET_INFO( ppc403ga )
4453{
4454   switch (state)
4455   {
4456      /* --- the following bits of info are returned as 64-bit signed integers --- */
4457
4458      /* --- the following bits of info are returned as pointers to data or functions --- */
4459      case CPUINFO_FCT_INIT:                          info->init = CPU_INIT_NAME(ppc403ga);               break;
4460      case CPUINFO_FCT_SET_INFO:                      info->setinfo = CPU_SET_INFO_NAME(ppcdrc4xx);       break;
4461
4462      /* --- the following bits of info are returned as NULL-terminated strings --- */
4463      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC 403GA");       break;
4464      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "ppc403ga");       break;
4465
4466      /* --- everything else is handled generically --- */
4467      default:                                        CPU_GET_INFO_CALL(ppcdrc4xx);       break;
4468   }
4469}
4470
4471
4472/*-------------------------------------------------
4473    ppc403gcx_init - PowerPC 403GCX-specific
4474    initialization
4475-------------------------------------------------*/
4476
4477static CPU_INIT( ppc403gcx )
4478{
4479   ppcdrc_init(PPC_MODEL_403GCX, PPCCAP_4XX, 1, device, irqcallback);
4480}
4481
4482
4483/*-------------------------------------------------
4484    ppc403gcx_get_info - PowerPC 403GCX-specific
4485    information getter
4486-------------------------------------------------*/
4487
4488CPU_GET_INFO( ppc403gcx )
4489{
4490   switch (state)
4491   {
4492      /* --- the following bits of info are returned as 64-bit signed integers --- */
4493
4494      /* --- the following bits of info are returned as pointers to data or functions --- */
4495      case CPUINFO_FCT_INIT:                          info->init = CPU_INIT_NAME(ppc403gcx);          break;
4496      case CPUINFO_FCT_SET_INFO:                      info->setinfo = CPU_SET_INFO_NAME(ppcdrc4xx);       break;
4497
4498      /* --- the following bits of info are returned as NULL-terminated strings --- */
4499      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC 403GCX");      break;
4500      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "ppc403gcx");       break;
4501
4502      /* --- everything else is handled generically --- */
4503      default:                                        CPU_GET_INFO_CALL(ppcdrc4xx);       break;
4504   }
4505}
4506
4507
4508
4509/*-------------------------------------------------
4510    ppc405gp_init - PowerPC 405GP-specific
4511    initialization
4512-------------------------------------------------*/
4513
4514static CPU_INIT( ppc405gp )
4515{
4516   ppcdrc_init(PPC_MODEL_405GP, PPCCAP_4XX | PPCCAP_VEA, 1, device, irqcallback);
4517}
4518
4519
4520/*-------------------------------------------------
4521    ppc405gp_get_info - PowerPC 405GP-specific
4522    information getter
4523-------------------------------------------------*/
4524
4525CPU_GET_INFO( ppc405gp )
4526{
4527   switch (state)
4528   {
4529      /* --- the following bits of info are returned as 64-bit signed integers --- */
4530
4531      /* --- the following bits of info are returned as pointers to data or functions --- */
4532      case CPUINFO_FCT_INIT:                          info->init = CPU_INIT_NAME(ppc405gp);           break;
4533      case CPUINFO_FCT_SET_INFO:                      info->setinfo = CPU_SET_INFO_NAME(ppcdrc4xx);       break;
4534
4535      /* --- the following bits of info are returned as NULL-terminated strings --- */
4536      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC 405GP");       break;
4537      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "ppc405gp");       break;
4538
4539      /* --- everything else is handled generically --- */
4540      default:                                        CPU_GET_INFO_CALL(ppcdrc4xx);       break;
4541   }
4542}
4543
4544
4545/***************************************************************************
4546    PPC 6XX VARIANTS
4547***************************************************************************/
4548
4549/*-------------------------------------------------
4550    ppc601_init - PowerPC 601-specific
4551    initialization
4552-------------------------------------------------*/
4553
4554static CPU_INIT( ppc601 )
4555{
4556   ppcdrc_init(PPC_MODEL_601, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_MFIOC | PPCCAP_601BAT, 0/* no TB */, device, irqcallback);
4557}
4558
4559
4560/*-------------------------------------------------
4561    ppc601_get_info - PowerPC 601-specific
4562    information getter
4563-------------------------------------------------*/
4564
4565CPU_GET_INFO( ppc601 )
4566{
4567   switch (state)
4568   {
4569      /* --- the following bits of info are returned as 64-bit signed integers --- */
4570
4571      /* --- the following bits of info are returned as pointers to data or functions --- */
4572      case CPUINFO_FCT_INIT:                          info->init = CPU_INIT_NAME(ppc601);             break;
4573
4574      /* --- the following bits of info are returned as NULL-terminated strings --- */
4575      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC 601");         break;
4576      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "ppc601");       break;
4577
4578      /* --- everything else is handled generically --- */
4579      default:                                        CPU_GET_INFO_CALL(ppcdrc);          break;
4580   }
4581}
4582
4583
4584/*-------------------------------------------------
4585    ppc602_init - PowerPC 602-specific
4586    initialization
4587-------------------------------------------------*/
4588
4589static CPU_INIT( ppc602 )
4590{
4591   ppcdrc_init(PPC_MODEL_602, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4, device, irqcallback);
4592}
4593
4594
4595/*-------------------------------------------------
4596    ppc602_get_info - PowerPC 602-specific
4597    information getter
4598-------------------------------------------------*/
4599
4600CPU_GET_INFO( ppc602 )
4601{
4602   switch (state)
4603   {
4604      /* --- the following bits of info are returned as 64-bit signed integers --- */
4605
4606      /* --- the following bits of info are returned as pointers to data or functions --- */
4607      case CPUINFO_FCT_INIT:                          info->init = CPU_INIT_NAME(ppc602);             break;
4608
4609      /* --- the following bits of info are returned as NULL-terminated strings --- */
4610      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC 602");         break;
4611      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "ppc602");       break;
4612
4613      /* --- everything else is handled generically --- */
4614      default:                                        CPU_GET_INFO_CALL(ppcdrc);          break;
4615   }
4616}
4617
4618
4619/*-------------------------------------------------
4620    ppc603_init - PowerPC 603-specific
4621    initialization
4622-------------------------------------------------*/
4623
4624static CPU_INIT( ppc603 )
4625{
4626   ppcdrc_init(PPC_MODEL_603, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4, device, irqcallback);
4627}
4628
4629
4630/*-------------------------------------------------
4631    ppc603_get_info - PowerPC 603-specific
4632    information getter
4633-------------------------------------------------*/
4634
4635CPU_GET_INFO( ppc603 )
4636{
4637   switch (state)
4638   {
4639      /* --- the following bits of info are returned as 64-bit signed integers --- */
4640
4641      /* --- the following bits of info are returned as pointers to data or functions --- */
4642      case CPUINFO_FCT_INIT:                          info->init = CPU_INIT_NAME(ppc603);             break;
4643
4644      /* --- the following bits of info are returned as NULL-terminated strings --- */
4645      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC 603");         break;
4646      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "ppc603");       break;
4647
4648      /* --- everything else is handled generically --- */
4649      default:                                        CPU_GET_INFO_CALL(ppcdrc);          break;
4650   }
4651}
4652
4653
4654/*-------------------------------------------------
4655    ppc603e_init - PowerPC 603e-specific
4656    initialization
4657-------------------------------------------------*/
4658
4659static CPU_INIT( ppc603e )
4660{
4661   ppcdrc_init(PPC_MODEL_603E, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4, device, irqcallback);
4662}
4663
4664
4665/*-------------------------------------------------
4666    ppc603e_get_info - PowerPC 603e-specific
4667    information getter
4668-------------------------------------------------*/
4669
4670CPU_GET_INFO( ppc603e )
4671{
4672   switch (state)
4673   {
4674      /* --- the following bits of info are returned as 64-bit signed integers --- */
4675
4676      /* --- the following bits of info are returned as pointers to data or functions --- */
4677      case CPUINFO_FCT_INIT:                          info->init = CPU_INIT_NAME(ppc603e);                break;
4678
4679      /* --- the following bits of info are returned as NULL-terminated strings --- */
4680      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC 603e");        break;
4681      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "ppc603e");       break;
4682
4683      /* --- everything else is handled generically --- */
4684      default:                                        CPU_GET_INFO_CALL(ppcdrc);          break;
4685   }
4686}
4687
4688
4689/*-------------------------------------------------
4690    ppc603r_init - PowerPC 603r-specific
4691    initialization
4692-------------------------------------------------*/
4693
4694static CPU_INIT( ppc603r )
4695{
4696   ppcdrc_init(PPC_MODEL_603R, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4, device, irqcallback);
4697}
4698
4699
4700/*-------------------------------------------------
4701    ppc603r_get_info - PowerPC 603r-specific
4702    information getter
4703-------------------------------------------------*/
4704
4705CPU_GET_INFO( ppc603r )
4706{
4707   switch (state)
4708   {
4709      /* --- the following bits of info are returned as 64-bit signed integers --- */
4710
4711      /* --- the following bits of info are returned as pointers to data or functions --- */
4712      case CPUINFO_FCT_INIT:                          info->init = CPU_INIT_NAME(ppc603r);                break;
4713
4714      /* --- the following bits of info are returned as NULL-terminated strings --- */
4715      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC 603R");        break;
4716      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "ppc603r");       break;
4717
4718      /* --- everything else is handled generically --- */
4719      default:                                        CPU_GET_INFO_CALL(ppcdrc);          break;
4720   }
4721}
4722
4723
4724/*-------------------------------------------------
4725    ppc604_init - PowerPC 604-specific
4726    initialization
4727-------------------------------------------------*/
4728
4729static CPU_INIT( ppc604 )
4730{
4731   ppcdrc_init(PPC_MODEL_604, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_604_MMU, 4, device, irqcallback);
4732}
4733
4734
4735/*-------------------------------------------------
4736    ppc604_get_info - PowerPC 604-specific
4737    information getter
4738-------------------------------------------------*/
4739
4740CPU_GET_INFO( ppc604 )
4741{
4742   switch (state)
4743   {
4744      /* --- the following bits of info are returned as 64-bit signed integers --- */
4745
4746      /* --- the following bits of info are returned as pointers to data or functions --- */
4747      case CPUINFO_FCT_INIT:                          info->init = CPU_INIT_NAME(ppc604);             break;
4748
4749      /* --- the following bits of info are returned as NULL-terminated strings --- */
4750      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC 604");         break;
4751      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "ppc604");       break;
4752
4753      /* --- everything else is handled generically --- */
4754      default:                                        CPU_GET_INFO_CALL(ppcdrc);          break;
4755   }
4756}
4757
4758
4759
4760/***************************************************************************
4761    MPC VARIANTS
4762***************************************************************************/
4763
4764/*-------------------------------------------------
4765    mpc8240_init - PowerPC MPC8240-specific
4766    initialization
4767-------------------------------------------------*/
4768
4769static CPU_INIT( mpc8240 )
4770{
4771   ppcdrc_init(PPC_MODEL_MPC8240, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4/* unknown */, device, irqcallback);
4772}
4773
4774
4775/*-------------------------------------------------
4776    mpc8240_get_info - PowerPC MPC8240-specific
4777    information getter
4778-------------------------------------------------*/
4779
4780CPU_GET_INFO( mpc8240 )
4781{
4782   switch (state)
4783   {
4784      /* --- the following bits of info are returned as 64-bit signed integers --- */
4785
4786      /* --- the following bits of info are returned as pointers to data or functions --- */
4787      case CPUINFO_FCT_INIT:                          info->init = CPU_INIT_NAME(mpc8240);                break;
4788
4789      /* --- the following bits of info are returned as NULL-terminated strings --- */
4790      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC MPC8240");     break;
4791      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "mpc8240");       break;
4792
4793      /* --- everything else is handled generically --- */
4794      default:                                        CPU_GET_INFO_CALL(ppcdrc);          break;
4795   }
4796}
4797
4798
4799ppc403ga_device::ppc403ga_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, UINT32 clock)
4800   : ppc4xx_device(mconfig, type, tag, owner, clock, CPU_GET_INFO_NAME(ppc403ga))
4801{
4802}
4803
4804const device_type PPC403GA = &legacy_device_creator<ppc403ga_device>;
4805
4806ppc403gcx_device::ppc403gcx_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, UINT32 clock)
4807   : ppc4xx_device(mconfig, type, tag, owner, clock, CPU_GET_INFO_NAME(ppc403gcx))
4808{
4809}
4810
4811const device_type PPC403GCX = &legacy_device_creator<ppc403gcx_device>;
4812
4813ppc405gp_device::ppc405gp_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, UINT32 clock)
4814   : ppc4xx_device(mconfig, type, tag, owner, clock, CPU_GET_INFO_NAME(ppc405gp))
4815{
4816}
4817
4818const device_type PPC405GP = &legacy_device_creator<ppc405gp_device>;
4819
4820ppc4xx_device::ppc4xx_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, UINT32 clock, cpu_get_info_func info)
4821   : legacy_cpu_device(mconfig, type, tag, owner, clock, info)
4822{
4823}
4824
4825DEFINE_LEGACY_CPU_DEVICE(PPC601, ppc601);
4826DEFINE_LEGACY_CPU_DEVICE(PPC602, ppc602);
4827DEFINE_LEGACY_CPU_DEVICE(PPC603, ppc603);
4828DEFINE_LEGACY_CPU_DEVICE(PPC603E, ppc603e);
4829DEFINE_LEGACY_CPU_DEVICE(PPC603R, ppc603r);
4830DEFINE_LEGACY_CPU_DEVICE(PPC604, ppc604);
4831DEFINE_LEGACY_CPU_DEVICE(MPC8240, mpc8240);
trunk/src/emu/cpu/powerpc/ppccom.c
r31142r31143
1010
1111#include "emu.h"
1212#include "ppccom.h"
13#include "ppcfe.h"
1314
1415
1516/***************************************************************************
r31142r31143
3334
3435
3536/***************************************************************************
36    FUNCTION PROTOTYPES
37    PRIVATE GLOBAL VARIABLES
3738***************************************************************************/
3839
39static TIMER_CALLBACK( ppc4xx_fit_callback );
40static TIMER_CALLBACK( ppc4xx_pit_callback );
41static TIMER_CALLBACK( ppc4xx_spu_callback );
42static TIMER_CALLBACK( decrementer_int_callback );
40/* lookup table for FP modes */
41static const UINT8 fpmode_source[4] =
42{
43   uml::ROUND_ROUND,
44   uml::ROUND_TRUNC,
45   uml::ROUND_CEIL,
46   uml::ROUND_FLOOR
47};
4348
44static TIMER_CALLBACK( ppc4xx_buffered_dma_callback );
49/* flag lookup table for SZ */
50static const UINT8 sz_cr_table_source[32] =
51{
52   /* ..... */ 0x4,
53   /* ....C */ 0x4,
54   /* ...V. */ 0x4,
55   /* ...VC */ 0x4,
56   /* ..Z.. */ 0x2,
57   /* ..Z.C */ 0x2,
58   /* ..ZV. */ 0x2,
59   /* ..ZVC */ 0x2,
60   /* .S... */ 0x8,
61   /* .S..C */ 0x8,
62   /* .S.V. */ 0x8,
63   /* .S.VC */ 0x8,
64   /* .SZ.. */ 0x2,
65   /* .SZ.C */ 0x2,
66   /* .SZV. */ 0x2,
67   /* .SZVC */ 0x2,
68   /* U.... */ 0x4,
69   /* U...C */ 0x4,
70   /* U..V. */ 0x4,
71   /* U..VC */ 0x4,
72   /* U.Z.. */ 0x2,
73   /* U.Z.C */ 0x2,
74   /* U.ZV. */ 0x2,
75   /* U.ZVC */ 0x2,
76   /* US... */ 0x8,
77   /* US..C */ 0x8,
78   /* US.V. */ 0x8,
79   /* US.VC */ 0x8,
80   /* USZ.. */ 0x2,
81   /* USZ.C */ 0x2,
82   /* USZV. */ 0x2,
83   /* USZVC */ 0x2
84};
4585
46static void ppc4xx_set_irq_line(powerpc_state *ppc, UINT32 bitmask, int state);
86/* flag lookup table for CMP */
87static const UINT8 cmp_cr_table_source[32] =
88{
89   /* ..... */ 0x4,
90   /* ....C */ 0x4,
91   /* ...V. */ 0x8,
92   /* ...VC */ 0x8,
93   /* ..Z.. */ 0x2,
94   /* ..Z.C */ 0x2,
95   /* ..ZV. */ 0x2,
96   /* ..ZVC */ 0x2,
97   /* .S... */ 0x8,
98   /* .S..C */ 0x8,
99   /* .S.V. */ 0x4,
100   /* .S.VC */ 0x4,
101   /* .SZ.. */ 0x2,
102   /* .SZ.C */ 0x2,
103   /* .SZV. */ 0x2,
104   /* .SZVC */ 0x2,
105   /* U.... */ 0x4,
106   /* U...C */ 0x4,
107   /* U..V. */ 0x8,
108   /* U..VC */ 0x8,
109   /* U.Z.. */ 0x2,
110   /* U.Z.C */ 0x2,
111   /* U.ZV. */ 0x2,
112   /* U.ZVC */ 0x2,
113   /* US... */ 0x8,
114   /* US..C */ 0x8,
115   /* US.V. */ 0x4,
116   /* US.VC */ 0x4,
117   /* USZ.. */ 0x2,
118   /* USZ.C */ 0x2,
119   /* USZV. */ 0x2,
120   /* USZVC */ 0x2
121};
47122
48static void ppc4xx_dma_update_irq_states(powerpc_state *ppc);
49static int ppc4xx_dma_fetch_transmit_byte(powerpc_state *ppc, int dmachan, UINT8 *byte);
50static int ppc4xx_dma_handle_receive_byte(powerpc_state *ppc, int dmachan, UINT8 byte);
51static void ppc4xx_dma_exec(powerpc_state *ppc, int dmachan);
123/* flag lookup table for CMPL */
124static const UINT8 cmpl_cr_table_source[32] =
125{
126   /* ..... */ 0x4,
127   /* ....C */ 0x8,
128   /* ...V. */ 0x4,
129   /* ...VC */ 0x8,
130   /* ..Z.. */ 0x2,
131   /* ..Z.C */ 0x2,
132   /* ..ZV. */ 0x2,
133   /* ..ZVC */ 0x2,
134   /* .S... */ 0x4,
135   /* .S..C */ 0x8,
136   /* .S.V. */ 0x4,
137   /* .S.VC */ 0x8,
138   /* .SZ.. */ 0x2,
139   /* .SZ.C */ 0x2,
140   /* .SZV. */ 0x2,
141   /* .SZVC */ 0x2,
142   /* U.... */ 0x4,
143   /* U...C */ 0x8,
144   /* U..V. */ 0x4,
145   /* U..VC */ 0x8,
146   /* U.Z.. */ 0x2,
147   /* U.Z.C */ 0x2,
148   /* U.ZV. */ 0x2,
149   /* U.ZVC */ 0x2,
150   /* US... */ 0x4,
151   /* US..C */ 0x8,
152   /* US.V. */ 0x4,
153   /* US.VC */ 0x8,
154   /* USZ.. */ 0x2,
155   /* USZ.C */ 0x2,
156   /* USZV. */ 0x2,
157   /* USZVC */ 0x2
158};
52159
53static void ppc4xx_spu_update_irq_states(powerpc_state *ppc);
54static void ppc4xx_spu_timer_reset(powerpc_state *ppc);
160/* flag lookup table for FCMP */
161static const UINT8 fcmp_cr_table_source[32] =
162{
163   /* ..... */ 0x4,
164   /* ....C */ 0x8,
165   /* ...V. */ 0x4,
166   /* ...VC */ 0x8,
167   /* ..Z.. */ 0x2,
168   /* ..Z.C */ 0xa,
169   /* ..ZV. */ 0x2,
170   /* ..ZVC */ 0xa,
171   /* .S... */ 0x4,
172   /* .S..C */ 0x8,
173   /* .S.V. */ 0x4,
174   /* .S.VC */ 0x8,
175   /* .SZ.. */ 0x2,
176   /* .SZ.C */ 0xa,
177   /* .SZV. */ 0x2,
178   /* .SZVC */ 0xa,
179   /* U.... */ 0x5,
180   /* U...C */ 0x9,
181   /* U..V. */ 0x5,
182   /* U..VC */ 0x9,
183   /* U.Z.. */ 0x3,
184   /* U.Z.C */ 0xb,
185   /* U.ZV. */ 0x3,
186   /* U.ZVC */ 0xb,
187   /* US... */ 0x5,
188   /* US..C */ 0x9,
189   /* US.V. */ 0x5,
190   /* US.VC */ 0x9,
191   /* USZ.. */ 0x3,
192   /* USZ.C */ 0xb,
193   /* USZV. */ 0x3,
194   /* USZVC */ 0xb
195};
55196
56197
198const device_type PPC601 = &device_creator<ppc601_device>;
199const device_type PPC602 = &device_creator<ppc602_device>;
200const device_type PPC603 = &device_creator<ppc603_device>;
201const device_type PPC603E = &device_creator<ppc603e_device>;
202const device_type PPC603R = &device_creator<ppc603r_device>;
203const device_type PPC604 = &device_creator<ppc604_device>;
204const device_type MPC8240 = &device_creator<mpc8240_device>;
205const device_type PPC403GA = &device_creator<ppc403ga_device>;
206const device_type PPC403GCX = &device_creator<ppc403gcx_device>;
207const device_type PPC405GP = &device_creator<ppc405gp_device>;
57208
209
210ppc_device::ppc_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, const char *shortname, int address_bits, int data_bits, powerpc_flavor flavor, UINT32 cap, UINT32 tb_divisor, address_map_constructor internal_map)
211   : cpu_device(mconfig, type, name, tag, owner, clock, shortname, __FILE__)
212   , m_program_config("program", ENDIANNESS_BIG, data_bits, address_bits, 0, internal_map)
213   , c_bus_frequency(0)
214   , m_core(NULL)
215   , m_bus_freq_multiplier(1)
216   , m_vtlb(NULL)
217   , m_flavor(flavor)
218   , m_cap(cap)
219   , m_tb_divisor(tb_divisor)
220   , m_dcstore_handler(NULL)
221   , m_cache(CACHE_SIZE + sizeof(internal_ppc_state))
222   , m_drcuml(NULL)
223   , m_drcfe(NULL)
224   , m_drcoptions(0)
225{
226   m_program_config.m_logaddr_width = 32;
227   m_program_config.m_page_shift = POWERPC_MIN_PAGE_SHIFT;
228   memset(m_ext_dma_read_handler, 0, sizeof(m_ext_dma_read_handler));
229   memset(m_ext_dma_write_handler, 0, sizeof(m_ext_dma_write_handler));
230}
231
232//ppc403_device::ppc403_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
233//   : ppc_device(mconfig, PPC403, "PPC403", tag, owner, clock, "ppc403", 32?, 64?)
234//{
235//}
236//
237//ppc405_device::ppc405_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
238//   : ppc_device(mconfig, PPC405, "PPC405", tag, owner, clock, "ppc405", 32?, 64?)
239//{
240//}
241
242ppc603_device::ppc603_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
243   : ppc_device(mconfig, PPC603, "PowerPC 603", tag, owner, clock, "ppc603", 32, 64, PPC_MODEL_603, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4, NULL)
244{
245}
246
247ppc603e_device::ppc603e_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
248   : ppc_device(mconfig, PPC603E, "PowerPC 603e", tag, owner, clock, "ppc603e", 32, 64, PPC_MODEL_603E, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4, NULL)
249{
250}
251
252ppc603r_device::ppc603r_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
253   : ppc_device(mconfig, PPC603R, "PowerPC 603R", tag, owner, clock, "ppc603r", 32, 64, PPC_MODEL_603R, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4, NULL)
254{
255}
256
257ppc602_device::ppc602_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
258   : ppc_device(mconfig, PPC602, "PowerPC 602", tag, owner, clock, "ppc602", 32, 64, PPC_MODEL_602, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4, NULL)
259{
260}
261
262mpc8240_device::mpc8240_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
263   : ppc_device(mconfig, MPC8240, "PowerPC MPC8240", tag, owner, clock, "mpc8240", 32, 64, PPC_MODEL_MPC8240, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4/* unknown */, NULL)
264{
265}
266
267ppc601_device::ppc601_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
268   : ppc_device(mconfig, PPC601, "PowerPC 601", tag, owner, clock, "ppc601", 32, 64, PPC_MODEL_601, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_MFIOC | PPCCAP_601BAT, 0/* no TB */, NULL)
269{
270}
271
272ppc604_device::ppc604_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
273   : ppc_device(mconfig, PPC604, "PowerPC 604", tag, owner, clock, "ppc604", 32, 64, PPC_MODEL_604, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_604_MMU, 4, NULL)
274{
275}
276
277static ADDRESS_MAP_START( internal_ppc4xx, AS_PROGRAM, 32, ppc4xx_device )
278   AM_RANGE(0x40000000, 0x4000000f) AM_READWRITE8(ppc4xx_spu_r, ppc4xx_spu_w, 0xffffffff)
279ADDRESS_MAP_END
280
281ppc4xx_device::ppc4xx_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, const char *shortname, powerpc_flavor flavor, UINT32 cap, UINT32 tb_divisor)
282   : ppc_device(mconfig, type, name, tag, owner, clock, shortname, 31, 32, flavor, cap, tb_divisor, ADDRESS_MAP_NAME(internal_ppc4xx))
283{
284}
285
286ppc403ga_device::ppc403ga_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
287   : ppc4xx_device(mconfig, PPC403GA, "PowerPC 403GA", tag, owner, clock, "ppc403ga", PPC_MODEL_403GA, PPCCAP_4XX, 1)
288{
289}
290
291ppc403gcx_device::ppc403gcx_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
292   : ppc4xx_device(mconfig, PPC403GCX, "PowerPC 403GCX", tag, owner, clock, "ppc403gcx", PPC_MODEL_403GCX, PPCCAP_4XX, 1)
293{
294}
295
296ppc405gp_device::ppc405gp_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
297   : ppc4xx_device(mconfig, PPC405GP, "PowerPC 405GP", tag, owner, clock, "ppc405gp", PPC_MODEL_405GP, PPCCAP_4XX | PPCCAP_VEA, 1)
298{
299}
300
301
58302/***************************************************************************
59303    INLINE FUNCTIONS
60304***************************************************************************/
r31142r31143
78322    get_cr - return the current CR value
79323-------------------------------------------------*/
80324
81INLINE UINT32 get_cr(powerpc_state *ppc)
325inline UINT32 ppc_device::get_cr()
82326{
83   return  ((ppc->cr[0] & 0x0f) << 28) |
84         ((ppc->cr[1] & 0x0f) << 24) |
85         ((ppc->cr[2] & 0x0f) << 20) |
86         ((ppc->cr[3] & 0x0f) << 16) |
87         ((ppc->cr[4] & 0x0f) << 12) |
88         ((ppc->cr[5] & 0x0f) << 8) |
89         ((ppc->cr[6] & 0x0f) << 4) |
90         ((ppc->cr[7] & 0x0f) << 0);
327   return  ((m_core->cr[0] & 0x0f) << 28) |
328         ((m_core->cr[1] & 0x0f) << 24) |
329         ((m_core->cr[2] & 0x0f) << 20) |
330         ((m_core->cr[3] & 0x0f) << 16) |
331         ((m_core->cr[4] & 0x0f) << 12) |
332         ((m_core->cr[5] & 0x0f) << 8) |
333         ((m_core->cr[6] & 0x0f) << 4) |
334         ((m_core->cr[7] & 0x0f) << 0);
91335}
92336
93337
r31142r31143
95339    set_cr - set the current CR value
96340-------------------------------------------------*/
97341
98INLINE void set_cr(powerpc_state *ppc, UINT32 value)
342inline void ppc_device::set_cr(UINT32 value)
99343{
100   ppc->cr[0] = value >> 28;
101   ppc->cr[1] = value >> 24;
102   ppc->cr[2] = value >> 20;
103   ppc->cr[3] = value >> 16;
104   ppc->cr[4] = value >> 12;
105   ppc->cr[5] = value >> 8;
106   ppc->cr[6] = value >> 4;
107   ppc->cr[7] = value >> 0;
344   m_core->cr[0] = value >> 28;
345   m_core->cr[1] = value >> 24;
346   m_core->cr[2] = value >> 20;
347   m_core->cr[3] = value >> 16;
348   m_core->cr[4] = value >> 12;
349   m_core->cr[5] = value >> 8;
350   m_core->cr[6] = value >> 4;
351   m_core->cr[7] = value >> 0;
108352}
109353
110354
r31142r31143
112356    get_xer - return the current XER value
113357-------------------------------------------------*/
114358
115INLINE UINT32 get_xer(powerpc_state *ppc)
359inline UINT32 ppc_device::get_xer()
116360{
117   return ppc->spr[SPR_XER] | (ppc->xerso << 31);
361   return m_core->spr[SPR_XER] | (m_core->xerso << 31);
118362}
119363
120364
r31142r31143
122366    set_xer - set the current XER value
123367-------------------------------------------------*/
124368
125INLINE void set_xer(powerpc_state *ppc, UINT32 value)
369inline void ppc_device::set_xer(UINT32 value)
126370{
127   ppc->spr[SPR_XER] = value & ~XER_SO;
128   ppc->xerso = value >> 31;
371   m_core->spr[SPR_XER] = value & ~XER_SO;
372   m_core->xerso = value >> 31;
129373}
130374
131375
r31142r31143
134378    value
135379-------------------------------------------------*/
136380
137INLINE UINT64 get_timebase(powerpc_state *ppc)
381inline UINT64 ppc_device::get_timebase()
138382{
139   if (!ppc->tb_divisor)
383   if (!m_tb_divisor)
140384   {
141      return (ppc->device->total_cycles() - ppc->tb_zero_cycles);
385      return (total_cycles() - m_tb_zero_cycles);
142386   }
143387
144   return (ppc->device->total_cycles() - ppc->tb_zero_cycles) / ppc->tb_divisor;
388   return (total_cycles() - m_tb_zero_cycles) / m_tb_divisor;
145389}
146390
147391
r31142r31143
149393    set_timebase - set the timebase
150394-------------------------------------------------*/
151395
152INLINE void set_timebase(powerpc_state *ppc, UINT64 newtb)
396inline void ppc_device::set_timebase(UINT64 newtb)
153397{
154   ppc->tb_zero_cycles = ppc->device->total_cycles() - newtb * ppc->tb_divisor;
398   m_tb_zero_cycles = total_cycles() - newtb * m_tb_divisor;
155399}
156400
157401
r31142r31143
160404    decrementer value
161405-------------------------------------------------*/
162406
163INLINE UINT32 get_decrementer(powerpc_state *ppc)
407inline UINT32 ppc_device::get_decrementer()
164408{
165   INT64 cycles_until_zero = ppc->dec_zero_cycles - ppc->device->total_cycles();
409   INT64 cycles_until_zero = m_dec_zero_cycles - total_cycles();
166410   cycles_until_zero = MAX(cycles_until_zero, 0);
167411
168   if (!ppc->tb_divisor)
412   if (!m_tb_divisor)
169413   {
170414      return 0;
171415   }
172416
173   return cycles_until_zero / ppc->tb_divisor;
417   return cycles_until_zero / m_tb_divisor;
174418}
175419
176420
r31142r31143
178422    set_decrementer - set the decremeter
179423-------------------------------------------------*/
180424
181INLINE void set_decrementer(powerpc_state *ppc, UINT32 newdec)
425inline void ppc_device::set_decrementer(UINT32 newdec)
182426{
183   UINT64 cycles_until_done = ((UINT64)newdec + 1) * ppc->tb_divisor;
184   UINT32 curdec = get_decrementer(ppc);
427   UINT64 cycles_until_done = ((UINT64)newdec + 1) * m_tb_divisor;
428   UINT32 curdec = get_decrementer();
185429
186   if (!ppc->tb_divisor)
430   if (!m_tb_divisor)
187431   {
188432      return;
189433   }
190434
191435   if (PRINTF_DECREMENTER)
192436   {
193      UINT64 total = ppc->device->total_cycles();
437      UINT64 total = total_cycles();
194438      osd_printf_debug("set_decrementer: olddec=%08X newdec=%08X divisor=%d totalcyc=%08X%08X timer=%08X%08X\n",
195            curdec, newdec, ppc->tb_divisor,
439            curdec, newdec, m_tb_divisor,
196440            (UINT32)(total >> 32), (UINT32)total, (UINT32)(cycles_until_done >> 32), (UINT32)cycles_until_done);
197441   }
198442
199   ppc->dec_zero_cycles = ppc->device->total_cycles() + cycles_until_done;
200   ppc->decrementer_int_timer->adjust(ppc->device->cycles_to_attotime(cycles_until_done));
443   m_dec_zero_cycles = total_cycles() + cycles_until_done;
444   m_decrementer_int_timer->adjust(cycles_to_attotime(cycles_until_done));
201445
202446   if ((INT32)curdec >= 0 && (INT32)newdec < 0)
203      ppc->irq_pending |= 0x02;
447      m_core->irq_pending |= 0x02;
204448}
205449
206450
r31142r31143
306550***************************************************************************/
307551
308552/*-------------------------------------------------
309    ppccom_init - initialize the powerpc_state
553    device_start - initialize the powerpc_state
310554    structure based on the configured type
311555-------------------------------------------------*/
312556
313void ppccom_init(powerpc_state *ppc, powerpc_flavor flavor, UINT32 cap, int tb_divisor, legacy_cpu_device *device, device_irq_acknowledge_delegate irqcallback)
557void ppc_device::device_start()
314558{
315   const powerpc_config *config = (const powerpc_config *)device->static_config();
559   /* allocate the core from the near cache */
560   m_core = (internal_ppc_state *)m_cache.alloc_near(sizeof(internal_ppc_state));
561   memset(m_core, 0, sizeof(internal_ppc_state));
316562
563   m_entry = NULL;
564   m_nocode = NULL;
565   m_out_of_cycles = NULL;
566   m_tlb_mismatch = NULL;
567   m_swap_tgpr = NULL;
568   memset(m_lsw, 0, sizeof(m_lsw));
569   memset(m_stsw, 0, sizeof(m_stsw));
570   memset(m_read8, 0, sizeof(m_read8));
571   memset(m_write8, 0, sizeof(m_write8));
572   memset(m_read16, 0, sizeof(m_read16));
573   memset(m_read16mask, 0, sizeof(m_read16mask));
574   memset(m_write16, 0, sizeof(m_write16));
575   memset(m_write16mask, 0, sizeof(m_write16mask));
576   memset(m_read32, 0, sizeof(m_read32));
577   memset(m_read32align, 0, sizeof(m_read32align));
578   memset(m_read32mask, 0, sizeof(m_read32mask));
579   memset(m_write32, 0, sizeof(m_write32));
580   memset(m_write32align, 0, sizeof(m_write32align));
581   memset(m_write32mask, 0, sizeof(m_write32mask));
582   memset(m_read64, 0, sizeof(m_read64));
583   memset(m_read64mask, 0, sizeof(m_read64mask));
584   memset(m_write64, 0, sizeof(m_write64));
585   memset(m_write64mask, 0, sizeof(m_write64mask));
586   memset(m_exception, 0, sizeof(m_exception));
587   memset(m_exception_norecover, 0, sizeof(m_exception_norecover));
588
589   /* initialize the implementation state tables */
590   memcpy(m_fpmode, fpmode_source, sizeof(fpmode_source));
591   memcpy(m_sz_cr_table, sz_cr_table_source, sizeof(sz_cr_table_source));
592   memcpy(m_cmp_cr_table, cmp_cr_table_source, sizeof(cmp_cr_table_source));
593   memcpy(m_cmpl_cr_table, cmpl_cr_table_source, sizeof(cmpl_cr_table_source));
594   memcpy(m_fcmp_cr_table, fcmp_cr_table_source, sizeof(fcmp_cr_table_source));
595
317596   /* initialize based on the config */
318   memset(ppc, 0, sizeof(*ppc));
319   ppc->flavor = flavor;
320   ppc->cap = cap;
321   ppc->cache_line_size = 32;
322   ppc->tb_divisor = tb_divisor;
323   ppc->cpu_clock = device->clock();
324   ppc->irq_callback = irqcallback;
325   ppc->device = device;
326   ppc->program = &device->space(AS_PROGRAM);
327   ppc->direct = &ppc->program->direct();
328   ppc->system_clock = (config != NULL) ? config->bus_frequency : device->clock();
329   ppc->dcr_read_func = read32_delegate();
330   ppc->dcr_write_func = write32_delegate();
597   m_ppc_tb_base_icount = 0;
598   m_ppc_dec_base_icount = 0;
599   m_ppc_dec_trigger_cycle = 0;
600   m_bus_freq_multiplier = 0;
331601
332   ppc->tb_divisor = (ppc->tb_divisor * device->clock() + ppc->system_clock / 2 - 1) / ppc->system_clock;
333   ppc->codexor = 0;
334   if (!(cap & PPCCAP_4XX) && device->space_config()->m_endianness != ENDIANNESS_NATIVE)
335      ppc->codexor = 4;
602   m_npc = 0;
603   memset(m_dcr, 0, sizeof(m_dcr));
336604
605   m_lr = 0;
606   m_ctr = 0;
607   m_xer = 0;
608   m_pvr = 0;
609   m_srr0 = 0;
610   m_srr1 = 0;
611   m_srr2 = 0;
612   m_srr3 = 0;
613   m_hid0 = 0;
614   m_hid1 = 0;
615   m_hid2 = 0;
616   m_sdr1 = 0;
617   memset(m_sprg, 0, sizeof(m_sprg));
618
619   m_dsisr = 0;
620   m_dar = 0;
621   m_ear = 0;
622   m_dmiss = 0;
623   m_dcmp = 0;
624   m_hash1 = 0;
625   m_hash2 = 0;
626   m_imiss = 0;
627   m_icmp = 0;
628   m_rpa = 0;
629
630   memset(m_ibat, 0, sizeof(m_ibat));
631   memset(m_dbat, 0, sizeof(m_dbat));
632
633   m_evpr = 0;
634   m_exier = 0;
635   m_exisr = 0;
636   m_bear = 0;
637   m_besr = 0;
638   m_iocr = 0;
639   memset(m_br, 0, sizeof(m_br));
640   m_iabr = 0;
641   m_esr = 0;
642   m_iccr = 0;
643   m_dccr = 0;
644   m_pit = 0;
645   m_pit_counter = 0;
646   m_pit_int_enable = 0;
647   m_tsr = 0;
648   m_dbsr = 0;
649   m_sgr = 0;
650   m_pid = 0;
651   m_pbl1 = 0;
652   m_pbl2 = 0;
653   m_pbu1 = 0;
654   m_pbu2 = 0;
655   m_fit_bit = 0;
656   m_fit_int_enable = 0;
657   m_wdt_bit = 0;
658   m_wdt_int_enable = 0;
659   m_dac1 = 0;
660   m_dac2 = 0;
661   m_iac1 = 0;
662   m_iac2 = 0;
663
664   memset(&m_spu_old, 0, sizeof(m_spu_old));
665   memset(m_dma, 0, sizeof(m_dma));
666   m_dmasr = 0;
667
668   m_reserved = 0;
669   m_reserved_address = 0;
670   m_interrupt_pending = 0;
671   m_tb = 0;
672   m_dec = 0;
673   m_dec_frac = 0;
674   memset(m_fpr, 0, sizeof(m_fpr));
675   m_lt = 0;
676   m_sp = 0;
677   m_tcr = 0;
678   m_ibr = 0;
679   m_esasrr = 0;
680   m_sebr = 0;
681   m_ser = 0;
682
683   memset(&m_spu, 0, sizeof(m_spu));
684   m_pit_reload = 0;
685   m_irqstate = 0;
686   memset(m_buffered_dma_rate, 0, sizeof(m_buffered_dma_rate));
687   m_codexor = 0;
688   m_system_clock = 0;
689   m_cpu_clock = 0;
690   m_tb_zero_cycles = 0;
691   m_dec_zero_cycles = 0;
692
693   m_arg1 = 0;
694   m_fastram_select = 0;
695   memset(m_fastram, 0, sizeof(m_fastram));
696   m_hotspot_select = 0;
697   memset(m_hotspot, 0, sizeof(m_hotspot));
698
699   m_cache_line_size = 32;
700   m_cpu_clock = clock();
701   m_program = &space(AS_PROGRAM);
702   m_direct = &m_program->direct();
703   m_system_clock = c_bus_frequency != 0 ? c_bus_frequency : clock();
704   m_dcr_read_func = read32_delegate();
705   m_dcr_write_func = write32_delegate();
706
707   m_tb_divisor = (m_tb_divisor * clock() + m_system_clock / 2 - 1) / m_system_clock;
708   m_codexor = 0;
709   if (!(m_cap & PPCCAP_4XX) && space_config()->m_endianness != ENDIANNESS_NATIVE)
710      m_codexor = 4;
711
337712   /* allocate the virtual TLB */
338   ppc->vtlb = vtlb_alloc(device, AS_PROGRAM, (cap & PPCCAP_603_MMU) ? PPC603_FIXED_TLB_ENTRIES : 0, POWERPC_TLB_ENTRIES);
713   m_vtlb = vtlb_alloc(this, AS_PROGRAM, (m_cap & PPCCAP_603_MMU) ? PPC603_FIXED_TLB_ENTRIES : 0, POWERPC_TLB_ENTRIES);
339714
340715   /* allocate a timer for the compare interrupt */
341   if ((cap & PPCCAP_OEA) && (ppc->tb_divisor))
342      ppc->decrementer_int_timer = device->machine().scheduler().timer_alloc(FUNC(decrementer_int_callback), ppc);
716   if ((m_cap & PPCCAP_OEA) && (m_tb_divisor))
717      m_decrementer_int_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(ppc_device::decrementer_int_callback), this));
343718
344719   /* and for the 4XX interrupts if needed */
345   if (cap & PPCCAP_4XX)
720   if (m_cap & PPCCAP_4XX)
346721   {
347      ppc->fit_timer = device->machine().scheduler().timer_alloc(FUNC(ppc4xx_fit_callback), ppc);
348      ppc->pit_timer = device->machine().scheduler().timer_alloc(FUNC(ppc4xx_pit_callback), ppc);
349      ppc->spu.timer = device->machine().scheduler().timer_alloc(FUNC(ppc4xx_spu_callback), ppc);
722      m_fit_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(ppc_device::ppc4xx_fit_callback), this));
723      m_pit_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(ppc_device::ppc4xx_pit_callback), this));
724      m_spu.timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(ppc_device::ppc4xx_spu_callback), this));
350725   }
351726
352   if (cap & PPCCAP_4XX)
727   if (m_cap & PPCCAP_4XX)
353728   {
354      ppc->buffered_dma_timer[0] = device->machine().scheduler().timer_alloc(FUNC(ppc4xx_buffered_dma_callback), ppc);
355      ppc->buffered_dma_timer[1] = device->machine().scheduler().timer_alloc(FUNC(ppc4xx_buffered_dma_callback), ppc);
356      ppc->buffered_dma_timer[2] = device->machine().scheduler().timer_alloc(FUNC(ppc4xx_buffered_dma_callback), ppc);
357      ppc->buffered_dma_timer[3] = device->machine().scheduler().timer_alloc(FUNC(ppc4xx_buffered_dma_callback), ppc);
729      m_buffered_dma_timer[0] = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(ppc_device::ppc4xx_buffered_dma_callback), this));
730      m_buffered_dma_timer[1] = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(ppc_device::ppc4xx_buffered_dma_callback), this));
731      m_buffered_dma_timer[2] = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(ppc_device::ppc4xx_buffered_dma_callback), this));
732      m_buffered_dma_timer[3] = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(ppc_device::ppc4xx_buffered_dma_callback), this));
358733
359      ppc->buffered_dma_rate[0] = 10000;
360      ppc->buffered_dma_rate[1] = 10000;
361      ppc->buffered_dma_rate[2] = 10000;
362      ppc->buffered_dma_rate[3] = 10000;
734      m_buffered_dma_rate[0] = 10000;
735      m_buffered_dma_rate[1] = 10000;
736      m_buffered_dma_rate[2] = 10000;
737      m_buffered_dma_rate[3] = 10000;
363738   }
364739
365740   /* register for save states */
366   device->save_item(NAME(ppc->pc));
367   device->save_item(NAME(ppc->r));
368   device->save_item(NAME(ppc->f));
369   device->save_item(NAME(ppc->cr));
370   device->save_item(NAME(ppc->xerso));
371   device->save_item(NAME(ppc->fpscr));
372   device->save_item(NAME(ppc->msr));
373   device->save_item(NAME(ppc->sr));
374   device->save_item(NAME(ppc->spr));
375   device->save_item(NAME(ppc->dcr));
376   if (cap & PPCCAP_4XX)
741   save_item(NAME(m_core->pc));
742   save_item(NAME(m_core->r));
743   save_item(NAME(m_core->f));
744   save_item(NAME(m_core->cr));
745   save_item(NAME(m_core->xerso));
746   save_item(NAME(m_core->fpscr));
747   save_item(NAME(m_core->msr));
748   save_item(NAME(m_core->sr));
749   save_item(NAME(m_core->spr));
750   save_item(NAME(m_dcr));
751   if (m_cap & PPCCAP_4XX)
377752   {
378      device->save_item(NAME(ppc->spu.regs));
379      device->save_item(NAME(ppc->spu.txbuf));
380      device->save_item(NAME(ppc->spu.rxbuf));
381      device->save_item(NAME(ppc->spu.rxbuffer));
382      device->save_item(NAME(ppc->spu.rxin));
383      device->save_item(NAME(ppc->spu.rxout));
384      device->save_item(NAME(ppc->pit_reload));
385      device->save_item(NAME(ppc->irqstate));
753      save_item(NAME(m_spu.regs));
754      save_item(NAME(m_spu.txbuf));
755      save_item(NAME(m_spu.rxbuf));
756      save_item(NAME(m_spu.rxbuffer));
757      save_item(NAME(m_spu.rxin));
758      save_item(NAME(m_spu.rxout));
759      save_item(NAME(m_pit_reload));
760      save_item(NAME(m_irqstate));
386761   }
387   if (cap & PPCCAP_603_MMU)
762   if (m_cap & PPCCAP_603_MMU)
388763   {
389      device->save_item(NAME(ppc->mmu603_cmp));
390      device->save_item(NAME(ppc->mmu603_hash));
391      device->save_item(NAME(ppc->mmu603_r));
764      save_item(NAME(m_core->mmu603_cmp));
765      save_item(NAME(m_core->mmu603_hash));
766      save_item(NAME(m_core->mmu603_r));
392767   }
393   device->save_item(NAME(ppc->irq_pending));
394   device->save_item(NAME(ppc->tb_zero_cycles));
395   device->save_item(NAME(ppc->dec_zero_cycles));
768   save_item(NAME(m_core->irq_pending));
769   save_item(NAME(m_tb_zero_cycles));
770   save_item(NAME(m_dec_zero_cycles));
771
772   // Register debugger state
773   state_add(PPC_PC,    "PC", m_core->pc).formatstr("%08X");
774   state_add(PPC_MSR,   "MSR", m_core->msr).formatstr("%08X");
775   state_add(PPC_CR,    "CR", m_debugger_temp).callimport().callexport().formatstr("%08X");
776   state_add(PPC_LR,    "LR", m_core->spr[SPR_LR]).formatstr("%08X");
777   state_add(PPC_CTR,   "CTR", m_core->spr[SPR_CTR]).formatstr("%08X");
778   state_add(PPC_XER,   "XER", m_debugger_temp).callimport().callexport().formatstr("%08X");
779   state_add(PPC_SRR0,  "SRR0", m_core->spr[SPROEA_SRR0]).formatstr("%08X");
780   state_add(PPC_SRR1,  "SRR1", m_core->spr[SPROEA_SRR1]).formatstr("%08X");
781   state_add(PPC_SPRG0, "SPRG0", m_core->spr[SPROEA_SPRG0]).formatstr("%08X");
782   state_add(PPC_SPRG1, "SPRG1", m_core->spr[SPROEA_SPRG1]).formatstr("%08X");
783   state_add(PPC_SPRG2, "SPRG2", m_core->spr[SPROEA_SPRG2]).formatstr("%08X");
784   state_add(PPC_SPRG3, "SPRG3", m_core->spr[SPROEA_SPRG3]).formatstr("%08X");
785   state_add(PPC_SDR1,  "SDR1", m_core->spr[SPROEA_SDR1]).formatstr("%08X");
786   state_add(PPC_EXIER, "EXIER", m_dcr[DCR4XX_EXIER]).formatstr("%08X");
787   state_add(PPC_EXISR, "EXISR", m_dcr[DCR4XX_EXISR]).formatstr("%08X");
788   state_add(PPC_EVPR,  "EVPR", m_core->spr[SPR4XX_EVPR]).formatstr("%08X");
789   state_add(PPC_IOCR,  "IOCR", m_dcr[DCR4XX_EXISR]).formatstr("%08X");
790   state_add(PPC_TBH,   "TBH", m_debugger_temp).callimport().callexport().formatstr("%08X");
791   state_add(PPC_TBL,   "TBL", m_debugger_temp).callimport().callexport().formatstr("%08X");
792   state_add(PPC_DEC,   "DEC", m_debugger_temp).callimport().callexport().formatstr("%08X");
793
794   state_add(PPC_SR0,   "SR0", m_core->sr[0]).formatstr("%08X");
795   state_add(PPC_SR1,   "SR1", m_core->sr[1]).formatstr("%08X");
796   state_add(PPC_SR2,   "SR2", m_core->sr[2]).formatstr("%08X");
797   state_add(PPC_SR3,   "SR3", m_core->sr[3]).formatstr("%08X");
798   state_add(PPC_SR4,   "SR4", m_core->sr[4]).formatstr("%08X");
799   state_add(PPC_SR5,   "SR5", m_core->sr[5]).formatstr("%08X");
800   state_add(PPC_SR6,   "SR6", m_core->sr[6]).formatstr("%08X");
801   state_add(PPC_SR7,   "SR7", m_core->sr[7]).formatstr("%08X");
802   state_add(PPC_SR8,   "SR8", m_core->sr[8]).formatstr("%08X");
803   state_add(PPC_SR9,   "SR9", m_core->sr[9]).formatstr("%08X");
804   state_add(PPC_SR10,  "SR10", m_core->sr[10]).formatstr("%08X");
805   state_add(PPC_SR11,  "SR11", m_core->sr[11]).formatstr("%08X");
806   state_add(PPC_SR12,  "SR12", m_core->sr[12]).formatstr("%08X");
807   state_add(PPC_SR13,  "SR13", m_core->sr[13]).formatstr("%08X");
808   state_add(PPC_SR14,  "SR14", m_core->sr[14]).formatstr("%08X");
809   state_add(PPC_SR15,  "SR15", m_core->sr[15]).formatstr("%08X");
810
811   state_add(PPC_R0,    "R0", m_core->r[0]).formatstr("%08X");
812   state_add(PPC_R1,    "R1", m_core->r[1]).formatstr("%08X");
813   state_add(PPC_R2,    "R2", m_core->r[2]).formatstr("%08X");
814   state_add(PPC_R3,    "R3", m_core->r[3]).formatstr("%08X");
815   state_add(PPC_R4,    "R4", m_core->r[4]).formatstr("%08X");
816   state_add(PPC_R5,    "R5", m_core->r[5]).formatstr("%08X");
817   state_add(PPC_R6,    "R6", m_core->r[6]).formatstr("%08X");
818   state_add(PPC_R7,    "R7", m_core->r[7]).formatstr("%08X");
819   state_add(PPC_R8,    "R8", m_core->r[8]).formatstr("%08X");
820   state_add(PPC_R9,    "R9", m_core->r[9]).formatstr("%08X");
821   state_add(PPC_R10,   "R10", m_core->r[10]).formatstr("%08X");
822   state_add(PPC_R11,   "R11", m_core->r[11]).formatstr("%08X");
823   state_add(PPC_R12,   "R12", m_core->r[12]).formatstr("%08X");
824   state_add(PPC_R13,   "R13", m_core->r[13]).formatstr("%08X");
825   state_add(PPC_R14,   "R14", m_core->r[14]).formatstr("%08X");
826   state_add(PPC_R15,   "R15", m_core->r[15]).formatstr("%08X");
827   state_add(PPC_R16,   "R16", m_core->r[16]).formatstr("%08X");
828   state_add(PPC_R17,   "R17", m_core->r[17]).formatstr("%08X");
829   state_add(PPC_R18,   "R18", m_core->r[18]).formatstr("%08X");
830   state_add(PPC_R19,   "R19", m_core->r[19]).formatstr("%08X");
831   state_add(PPC_R20,   "R20", m_core->r[20]).formatstr("%08X");
832   state_add(PPC_R21,   "R21", m_core->r[21]).formatstr("%08X");
833   state_add(PPC_R22,   "R22", m_core->r[22]).formatstr("%08X");
834   state_add(PPC_R23,   "R23", m_core->r[23]).formatstr("%08X");
835   state_add(PPC_R24,   "R24", m_core->r[24]).formatstr("%08X");
836   state_add(PPC_R25,   "R25", m_core->r[25]).formatstr("%08X");
837   state_add(PPC_R26,   "R26", m_core->r[26]).formatstr("%08X");
838   state_add(PPC_R27,   "R27", m_core->r[27]).formatstr("%08X");
839   state_add(PPC_R28,   "R28", m_core->r[28]).formatstr("%08X");
840   state_add(PPC_R29,   "R29", m_core->r[29]).formatstr("%08X");
841   state_add(PPC_R30,   "R30", m_core->r[30]).formatstr("%08X");
842   state_add(PPC_R31,   "R31", m_core->r[31]).formatstr("%08X");
843
844   state_add(PPC_F0,    "F0", m_core->f[0]).formatstr("%12s");
845   state_add(PPC_F1,    "F1", m_core->f[1]).formatstr("%12s");
846   state_add(PPC_F2,    "F2", m_core->f[2]).formatstr("%12s");
847   state_add(PPC_F3,    "F3", m_core->f[3]).formatstr("%12s");
848   state_add(PPC_F4,    "F4", m_core->f[4]).formatstr("%12s");
849   state_add(PPC_F5,    "F5", m_core->f[5]).formatstr("%12s");
850   state_add(PPC_F6,    "F6", m_core->f[6]).formatstr("%12s");
851   state_add(PPC_F7,    "F7", m_core->f[7]).formatstr("%12s");
852   state_add(PPC_F8,    "F8", m_core->f[8]).formatstr("%12s");
853   state_add(PPC_F9,    "F9", m_core->f[9]).formatstr("%12s");
854   state_add(PPC_F10,   "F10", m_core->f[10]).formatstr("%12s");
855   state_add(PPC_F11,   "F11", m_core->f[11]).formatstr("%12s");
856   state_add(PPC_F12,   "F12", m_core->f[12]).formatstr("%12s");
857   state_add(PPC_F13,   "F13", m_core->f[13]).formatstr("%12s");
858   state_add(PPC_F14,   "F14", m_core->f[14]).formatstr("%12s");
859   state_add(PPC_F15,   "F15", m_core->f[15]).formatstr("%12s");
860   state_add(PPC_F16,   "F16", m_core->f[16]).formatstr("%12s");
861   state_add(PPC_F17,   "F17", m_core->f[17]).formatstr("%12s");
862   state_add(PPC_F18,   "F18", m_core->f[18]).formatstr("%12s");
863   state_add(PPC_F19,   "F19", m_core->f[19]).formatstr("%12s");
864   state_add(PPC_F20,   "F20", m_core->f[20]).formatstr("%12s");
865   state_add(PPC_F21,   "F21", m_core->f[21]).formatstr("%12s");
866   state_add(PPC_F22,   "F22", m_core->f[22]).formatstr("%12s");
867   state_add(PPC_F23,   "F23", m_core->f[23]).formatstr("%12s");
868   state_add(PPC_F24,   "F24", m_core->f[24]).formatstr("%12s");
869   state_add(PPC_F25,   "F25", m_core->f[25]).formatstr("%12s");
870   state_add(PPC_F26,   "F26", m_core->f[26]).formatstr("%12s");
871   state_add(PPC_F27,   "F27", m_core->f[27]).formatstr("%12s");
872   state_add(PPC_F28,   "F28", m_core->f[28]).formatstr("%12s");
873   state_add(PPC_F29,   "F29", m_core->f[29]).formatstr("%12s");
874   state_add(PPC_F30,   "F30", m_core->f[30]).formatstr("%12s");
875   state_add(PPC_F31,   "F31", m_core->f[31]).formatstr("%12s");
876   state_add(PPC_FPSCR, "FPSCR", m_core->fpscr).formatstr("%08X");
877
878   state_add(STATE_GENPC, "GENPC", m_core->pc).noshow();
879   state_add(STATE_GENSP, "GENSP", m_core->r[31]).noshow();
880   state_add(STATE_GENFLAGS, "GENFLAGS", m_debugger_temp).noshow().formatstr("%1s");
881
882   m_icountptr = &m_core->icount;
883
884   UINT32 flags = 0;
885   /* initialize the UML generator */
886   if (LOG_UML)
887      flags |= DRCUML_OPTION_LOG_UML;
888   if (LOG_NATIVE)
889      flags |= DRCUML_OPTION_LOG_NATIVE;
890   m_drcuml = auto_alloc(machine(), drcuml_state(*this, m_cache, flags, 8, 32, 2));
891
892   /* add symbols for our stuff */
893   m_drcuml->symbol_add(&m_core->pc, sizeof(m_core->pc), "pc");
894   m_drcuml->symbol_add(&m_core->icount, sizeof(m_core->icount), "icount");
895   for (int regnum = 0; regnum < 32; regnum++)
896   {
897      char buf[10];
898      sprintf(buf, "r%d", regnum);
899      m_drcuml->symbol_add(&m_core->r[regnum], sizeof(m_core->r[regnum]), buf);
900      sprintf(buf, "fpr%d", regnum);
901      m_drcuml->symbol_add(&m_core->f[regnum], sizeof(m_core->f[regnum]), buf);
902   }
903   for (int regnum = 0; regnum < 8; regnum++)
904   {
905      char buf[10];
906      sprintf(buf, "cr%d", regnum);
907      m_drcuml->symbol_add(&m_core->cr[regnum], sizeof(m_core->cr[regnum]), buf);
908   }
909   m_drcuml->symbol_add(&m_core->xerso, sizeof(m_core->xerso), "xerso");
910   m_drcuml->symbol_add(&m_core->fpscr, sizeof(m_core->fpscr), "fpscr");
911   m_drcuml->symbol_add(&m_core->msr, sizeof(m_core->msr), "msr");
912   m_drcuml->symbol_add(&m_core->sr, sizeof(m_core->sr), "sr");
913   m_drcuml->symbol_add(&m_core->spr[SPR_XER], sizeof(m_core->spr[SPR_XER]), "xer");
914   m_drcuml->symbol_add(&m_core->spr[SPR_LR], sizeof(m_core->spr[SPR_LR]), "lr");
915   m_drcuml->symbol_add(&m_core->spr[SPR_CTR], sizeof(m_core->spr[SPR_CTR]), "ctr");
916   m_drcuml->symbol_add(&m_core->spr, sizeof(m_core->spr), "spr");
917   m_drcuml->symbol_add(&m_dcr, sizeof(m_dcr), "dcr");
918   m_drcuml->symbol_add(&m_core->param0, sizeof(m_core->param0), "param0");
919   m_drcuml->symbol_add(&m_core->param1, sizeof(m_core->param1), "param1");
920   m_drcuml->symbol_add(&m_core->irq_pending, sizeof(m_core->irq_pending), "irq_pending");
921   m_drcuml->symbol_add(&m_core->mode, sizeof(m_core->mode), "mode");
922   m_drcuml->symbol_add(&m_core->arg0, sizeof(m_core->arg0), "arg0");
923   m_drcuml->symbol_add(&m_arg1, sizeof(m_arg1), "arg1");
924   m_drcuml->symbol_add(&m_core->updateaddr, sizeof(m_core->updateaddr), "updateaddr");
925   m_drcuml->symbol_add(&m_core->swcount, sizeof(m_core->swcount), "swcount");
926   m_drcuml->symbol_add(&m_core->tempaddr, sizeof(m_core->tempaddr), "tempaddr");
927   m_drcuml->symbol_add(&m_core->tempdata, sizeof(m_core->tempdata), "tempdata");
928   m_drcuml->symbol_add(&m_core->fp0, sizeof(m_core->fp0), "fp0");
929   m_drcuml->symbol_add(&m_fpmode, sizeof(m_fpmode), "fpmode");
930   m_drcuml->symbol_add(&m_sz_cr_table, sizeof(m_sz_cr_table), "sz_cr_table");
931   m_drcuml->symbol_add(&m_cmp_cr_table, sizeof(m_cmp_cr_table), "cmp_cr_table");
932   m_drcuml->symbol_add(&m_cmpl_cr_table, sizeof(m_cmpl_cr_table), "cmpl_cr_table");
933   m_drcuml->symbol_add(&m_fcmp_cr_table, sizeof(m_fcmp_cr_table), "fcmp_cr_table");
934
935   /* initialize the front-end helper */
936   m_drcfe = auto_alloc(machine(), ppc_frontend(this, COMPILE_BACKWARDS_BYTES, COMPILE_FORWARDS_BYTES, SINGLE_INSTRUCTION_MODE ? 1 : COMPILE_MAX_SEQUENCE));
937
938   /* compute the register parameters */
939   for (int regnum = 0; regnum < 32; regnum++)
940   {
941      m_regmap[regnum] = uml::mem(&m_core->r[regnum]);
942      m_fdregmap[regnum] = uml::mem(&m_core->f[regnum]);
943   }
944
945   /* if we have registers to spare, assign r0, r1, r2 to leftovers */
946   if (!DISABLE_FAST_REGISTERS)
947   {
948      drcbe_info beinfo;
949      m_drcuml->get_backend_info(beinfo);
950      if (beinfo.direct_iregs > 5)
951         m_regmap[0] = uml::I5;
952      if (beinfo.direct_iregs > 6)
953         m_regmap[1] = uml::I6;
954      if (beinfo.direct_iregs > 7)
955         m_regmap[2] = uml::I7;
956   }
957
958   /* mark the cache dirty so it is updated on next execute */
959   m_cache_dirty = TRUE;
396960}
397961
962void ppc_device::state_export(const device_state_entry &entry)
963{
964   switch (entry.index())
965   {
966      case PPC_CR:
967         m_debugger_temp = get_cr();
968         break;
398969
970      case PPC_XER:
971         m_debugger_temp = get_xer();
972         break;
973
974      case PPC_TBH:
975         m_debugger_temp = get_timebase() >> 32;
976         break;
977
978      case PPC_TBL:
979         m_debugger_temp = (UINT32)get_timebase();
980         break;
981
982      case PPC_DEC:
983         m_debugger_temp = get_decrementer();
984         break;
985   }
986}
987
988void ppc_device::state_import(const device_state_entry &entry)
989{
990   switch (entry.index())
991   {
992      case PPC_CR:
993         set_cr(m_debugger_temp);
994         break;
995
996      case PPC_XER:
997         set_xer(m_debugger_temp);
998         break;
999
1000      case PPC_TBL:
1001         set_timebase((get_timebase() & ~U64(0x00ffffff00000000)) | m_debugger_temp);
1002         break;
1003
1004      case PPC_TBH:
1005         set_timebase((get_timebase() & ~U64(0x00000000ffffffff)) | ((UINT64)(m_debugger_temp & 0x00ffffff) << 32));
1006         break;
1007
1008      case PPC_DEC:
1009         set_decrementer(m_debugger_temp);
1010         break;
1011   }
1012}
1013
1014
1015void ppc_device::state_string_export(const device_state_entry &entry, astring &string)
1016{
1017   switch (entry.index())
1018   {
1019      case PPC_F0:
1020         string.printf("%12f", m_core->f[0]);
1021         break;
1022
1023      case PPC_F1:
1024         string.printf("%12f", m_core->f[1]);
1025         break;
1026
1027      case PPC_F2:
1028         string.printf("%12f", m_core->f[2]);
1029         break;
1030
1031      case PPC_F3:
1032         string.printf("%12f", m_core->f[3]);
1033         break;
1034
1035      case PPC_F4:
1036         string.printf("%12f", m_core->f[4]);
1037         break;
1038
1039      case PPC_F5:
1040         string.printf("%12f", m_core->f[5]);
1041         break;
1042
1043      case PPC_F6:
1044         string.printf("%12f", m_core->f[6]);
1045         break;
1046
1047      case PPC_F7:
1048         string.printf("%12f", m_core->f[7]);
1049         break;
1050
1051      case PPC_F8:
1052         string.printf("%12f", m_core->f[8]);
1053         break;
1054
1055      case PPC_F9:
1056         string.printf("%12f", m_core->f[9]);
1057         break;
1058
1059      case PPC_F10:
1060         string.printf("%12f", m_core->f[10]);
1061         break;
1062
1063      case PPC_F11:
1064         string.printf("%12f", m_core->f[11]);
1065         break;
1066
1067      case PPC_F12:
1068         string.printf("%12f", m_core->f[12]);
1069         break;
1070
1071      case PPC_F13:
1072         string.printf("%12f", m_core->f[13]);
1073         break;
1074
1075      case PPC_F14:
1076         string.printf("%12f", m_core->f[14]);
1077         break;
1078
1079      case PPC_F15:
1080         string.printf("%12f", m_core->f[15]);
1081         break;
1082
1083      case PPC_F16:
1084         string.printf("%12f", m_core->f[16]);
1085         break;
1086
1087      case PPC_F17:
1088         string.printf("%12f", m_core->f[17]);
1089         break;
1090
1091      case PPC_F18:
1092         string.printf("%12f", m_core->f[18]);
1093         break;
1094
1095      case PPC_F19:
1096         string.printf("%12f", m_core->f[19]);
1097         break;
1098
1099      case PPC_F20:
1100         string.printf("%12f", m_core->f[20]);
1101         break;
1102
1103      case PPC_F21:
1104         string.printf("%12f", m_core->f[21]);
1105         break;
1106
1107      case PPC_F22:
1108         string.printf("%12f", m_core->f[22]);
1109         break;
1110
1111      case PPC_F23:
1112         string.printf("%12f", m_core->f[23]);
1113         break;
1114
1115      case PPC_F24:
1116         string.printf("%12f", m_core->f[24]);
1117         break;
1118
1119      case PPC_F25:
1120         string.printf("%12f", m_core->f[25]);
1121         break;
1122
1123      case PPC_F26:
1124         string.printf("%12f", m_core->f[26]);
1125         break;
1126
1127      case PPC_F27:
1128         string.printf("%12f", m_core->f[27]);
1129         break;
1130
1131      case PPC_F28:
1132         string.printf("%12f", m_core->f[28]);
1133         break;
1134
1135      case PPC_F29:
1136         string.printf("%12f", m_core->f[29]);
1137         break;
1138
1139      case PPC_F30:
1140         string.printf("%12f", m_core->f[30]);
1141         break;
1142
1143      case PPC_F31:
1144         string.printf("%12f", m_core->f[31]);
1145         break;
1146   }
1147}
1148
1149
3991150/*-------------------------------------------------
4001151    ppccom_exit - common cleanup/exit
4011152-------------------------------------------------*/
4021153
403void ppccom_exit(powerpc_state *ppc)
1154void ppc_device::device_stop()
4041155{
405   if (ppc->vtlb != NULL)
406      vtlb_free(ppc->vtlb);
1156   if (m_vtlb != NULL)
1157      vtlb_free(m_vtlb);
1158   m_vtlb = NULL;
1159
1160   /* clean up the DRC */
1161   auto_free(machine(), m_drcfe);
1162   auto_free(machine(), m_drcuml);
4071163}
4081164
4091165
r31142r31143
4121168    registers
4131169-------------------------------------------------*/
4141170
415void ppccom_reset(powerpc_state *ppc)
1171void ppc_device::device_reset()
4161172{
417   int tlbindex;
418
4191173   /* initialize the OEA state */
420   if (ppc->cap & PPCCAP_OEA)
1174   if (m_cap & PPCCAP_OEA)
4211175   {
4221176      /* PC to the reset vector; MSR has IP set to start */
423      ppc->pc = 0xfff00100;
424      ppc->msr = MSROEA_IP;
1177      m_core->pc = 0xfff00100;
1178      m_core->msr = MSROEA_IP;
4251179
4261180      /* reset the decrementer */
427      ppc->dec_zero_cycles = ppc->device->total_cycles();
428      if (ppc->tb_divisor)
1181      m_dec_zero_cycles = total_cycles();
1182      if (m_tb_divisor)
4291183      {
430         decrementer_int_callback(ppc->device->machine(), ppc, 0);
1184         decrementer_int_callback(NULL, 0);
4311185      }
4321186   }
4331187
4341188   /* initialize the 4XX state */
435   if (ppc->cap & PPCCAP_4XX)
1189   if (m_cap & PPCCAP_4XX)
4361190   {
4371191      /* PC to the last word; MSR to 0 */
438      ppc->pc = 0xfffffffc;
439      ppc->msr = 0;
1192      m_core->pc = 0xfffffffc;
1193      m_core->msr = 0;
4401194
4411195      /* reset the SPU status */
442      ppc->spr[SPR4XX_TCR] &= ~PPC4XX_TCR_WRC_MASK;
443      ppc->spu.regs[SPU4XX_LINE_STATUS] = 0x06;
1196      m_core->spr[SPR4XX_TCR] &= ~PPC4XX_TCR_WRC_MASK;
1197      m_spu.regs[SPU4XX_LINE_STATUS] = 0x06;
4441198   }
4451199
4461200   /* initialize the 602 HID0 register */
447   if (ppc->flavor == PPC_MODEL_602)
448      ppc->spr[SPR603_HID0] = 1;
1201   if (m_flavor == PPC_MODEL_602)
1202      m_core->spr[SPR603_HID0] = 1;
4491203
4501204   /* time base starts here */
451   ppc->tb_zero_cycles = ppc->device->total_cycles();
1205   m_tb_zero_cycles = total_cycles();
4521206
4531207   /* clear interrupts */
454   ppc->irq_pending = 0;
1208   m_core->irq_pending = 0;
4551209
4561210   /* flush the TLB */
457   vtlb_flush_dynamic(ppc->vtlb);
458   if (ppc->cap & PPCCAP_603_MMU)
459      for (tlbindex = 0; tlbindex < PPC603_FIXED_TLB_ENTRIES; tlbindex++)
460         vtlb_load(ppc->vtlb, tlbindex, 0, 0, 0);
1211   vtlb_flush_dynamic(m_vtlb);
1212   if (m_cap & PPCCAP_603_MMU)
1213   {
1214      for (int tlbindex = 0; tlbindex < PPC603_FIXED_TLB_ENTRIES; tlbindex++)
1215      {
1216         vtlb_load(m_vtlb, tlbindex, 0, 0, 0);
1217      }
1218   }
1219
1220   /* Mark the cache dirty */
1221   m_core->mode = 0;
1222   m_cache_dirty = TRUE;
4611223}
4621224
4631225
r31142r31143
4661228    CPU
4671229-------------------------------------------------*/
4681230
469offs_t ppccom_dasm(powerpc_state *ppc, char *buffer, offs_t pc, const UINT8 *oprom, const UINT8 *opram)
1231offs_t ppc_device::disasm_disassemble(char *buffer, offs_t pc, const UINT8 *oprom, const UINT8 *opram, UINT32 options)
4701232{
4711233   extern offs_t ppc_dasm_one(char *buffer, UINT32 pc, UINT32 op);
4721234   UINT32 op = *(UINT32 *)oprom;
r31142r31143
4801242    callback if installed
4811243-------------------------------------------------*/
4821244
483void ppccom_dcstore_callback(powerpc_state *ppc)
1245void ppc_device::ppccom_dcstore_callback()
4841246{
485   if (ppc->dcstore_handler != NULL)
1247   if (m_dcstore_handler != NULL)
4861248   {
487      ppc->dcstore_handler(ppc->device, ppc->param0);
1249      m_dcstore_handler(this, m_core->param0);
4881250   }
4891251}
4901252
r31142r31143
5001262    filling
5011263-------------------------------------------------*/
5021264
503static UINT32 ppccom_translate_address_internal(powerpc_state *ppc, int intention, offs_t *address)
1265UINT32 ppc_device::ppccom_translate_address_internal(int intention, offs_t &address)
5041266{
5051267   int transpriv = ((intention & TRANSLATE_USER_MASK) == 0);   // 1 for supervisor, 0 for user
5061268   int transtype = intention & TRANSLATE_TYPE_MASK;
r31142r31143
5091271   UINT32 segreg;
5101272
5111273   /* 4xx case: "TLB" really just caches writes and checks compare registers */
512   if (ppc->cap & PPCCAP_4XX)
1274   if (m_cap & PPCCAP_4XX)
5131275   {
5141276      /* we don't support the MMU of the 403GCX */
515      if (ppc->flavor == PPC_MODEL_403GCX && (ppc->msr & MSROEA_DR))
1277      if (m_flavor == PPC_MODEL_403GCX && (m_core->msr & MSROEA_DR))
5161278         fatalerror("MMU enabled but not supported!\n");
5171279
5181280      /* only check if PE is enabled */
519      if (transtype == TRANSLATE_WRITE && (ppc->msr & MSR4XX_PE))
1281      if (transtype == TRANSLATE_WRITE && (m_core->msr & MSR4XX_PE))
5201282      {
5211283         /* are we within one of the protection ranges? */
522         int inrange1 = ((*address >> 12) >= (ppc->spr[SPR4XX_PBL1] >> 12) && (*address >> 12) < (ppc->spr[SPR4XX_PBU1] >> 12));
523         int inrange2 = ((*address >> 12) >= (ppc->spr[SPR4XX_PBL2] >> 12) && (*address >> 12) < (ppc->spr[SPR4XX_PBU2] >> 12));
1284         int inrange1 = ((address >> 12) >= (m_core->spr[SPR4XX_PBL1] >> 12) && (address >> 12) < (m_core->spr[SPR4XX_PBU1] >> 12));
1285         int inrange2 = ((address >> 12) >= (m_core->spr[SPR4XX_PBL2] >> 12) && (address >> 12) < (m_core->spr[SPR4XX_PBU2] >> 12));
5241286
5251287         /* if PX == 1, writes are only allowed OUTSIDE of the bounds */
526         if (((ppc->msr & MSR4XX_PX) && (inrange1 || inrange2)) || (!(ppc->msr & MSR4XX_PX) && (!inrange1 && !inrange2)))
1288         if (((m_core->msr & MSR4XX_PX) && (inrange1 || inrange2)) || (!(m_core->msr & MSR4XX_PX) && (!inrange1 && !inrange2)))
5271289            return 0x002;
5281290      }
529      *address &= 0x7fffffff;
1291      address &= 0x7fffffff;
5301292      return 0x001;
5311293   }
5321294
5331295   /* only applies if we support the OEA */
534   if (!(ppc->cap & PPCCAP_OEA))
1296   if (!(m_cap & PPCCAP_OEA))
5351297      return 0x001;
5361298
5371299   /* also no translation necessary if translation is disabled */
538   if ((transtype == TRANSLATE_FETCH && (ppc->msr & MSROEA_IR) == 0) || (transtype != TRANSLATE_FETCH && (ppc->msr & MSROEA_DR) == 0))
1300   if ((transtype == TRANSLATE_FETCH && (m_core->msr & MSROEA_IR) == 0) || (transtype != TRANSLATE_FETCH && (m_core->msr & MSROEA_DR) == 0))
5391301      return 0x001;
5401302
5411303   /* first scan the appropriate BAT */
542   if (ppc->cap & PPCCAP_601BAT)
1304   if (m_cap & PPCCAP_601BAT)
5431305   {
5441306      for (batnum = 0; batnum < 4; batnum++)
5451307      {
546         UINT32 upper = ppc->spr[SPROEA_IBAT0U + 2*batnum + 0];
547         UINT32 lower = ppc->spr[SPROEA_IBAT0U + 2*batnum + 1];
1308         UINT32 upper = m_core->spr[SPROEA_IBAT0U + 2*batnum + 0];
1309         UINT32 lower = m_core->spr[SPROEA_IBAT0U + 2*batnum + 1];
5481310         int privbit = ((intention & TRANSLATE_USER_MASK) == 0) ? 3 : 2;
5491311
5501312//            printf("bat %d upper = %08x privbit %d\n", batnum, upper, privbit);
r31142r31143
5571319            UINT32 key = (upper >> privbit) & 1;
5581320
5591321            /* check for a hit against this bucket */
560            if ((*address & mask) == (upper & mask))
1322            if ((address & mask) == (upper & mask))
5611323            {
5621324               /* verify protection; if we fail, return false and indicate a protection violation */
5631325               if (!page_access_allowed(transtype, key, upper & 3))
r31142r31143
5661328               }
5671329
5681330               /* otherwise we're good */
569               addrout = (lower & mask) | (*address & ~mask);
570               *address = addrout; // top 9 bits from top 9 of PBN
1331               addrout = (lower & mask) | (address & ~mask);
1332               address = addrout; // top 9 bits from top 9 of PBN
5711333               return 0x001;
5721334            }
5731335         }
r31142r31143
5791341
5801342      for (batnum = 0; batnum < 4; batnum++)
5811343      {
582         UINT32 upper = ppc->spr[batbase + 2*batnum + 0];
1344         UINT32 upper = m_core->spr[batbase + 2*batnum + 0];
5831345
5841346         /* check user/supervisor valid bit */
5851347         if ((upper >> transpriv) & 0x01)
r31142r31143
5871349            UINT32 mask = (~upper << 15) & 0xfffe0000;
5881350
5891351            /* check for a hit against this bucket */
590            if ((*address & mask) == (upper & mask))
1352            if ((address & mask) == (upper & mask))
5911353            {
592               UINT32 lower = ppc->spr[batbase + 2*batnum + 1];
1354               UINT32 lower = m_core->spr[batbase + 2*batnum + 1];
5931355
5941356               /* verify protection; if we fail, return false and indicate a protection violation */
5951357               if (!page_access_allowed(transtype, 1, lower & 3))
r31142r31143
5981360               }
5991361
6001362               /* otherwise we're good */
601               *address = (lower & mask) | (*address & ~mask);
1363               address = (lower & mask) | (address & ~mask);
6021364               return 0x001;
6031365            }
6041366         }
r31142r31143
6061368   }
6071369
6081370   /* look up the segment register */
609   segreg = ppc->sr[*address >> 28];
1371   segreg = m_core->sr[address >> 28];
6101372   if (transtype == TRANSLATE_FETCH && (segreg & 0x10000000))
6111373      return DSISR_PROTECTED | ((transtype == TRANSLATE_WRITE) ? DSISR_STORE : 0);
6121374
6131375   /* check for memory-forced I/O */
614   if (ppc->cap & PPCCAP_MFIOC)
1376   if (m_cap & PPCCAP_MFIOC)
6151377   {
6161378      if ((transtype != TRANSLATE_FETCH) && ((segreg & 0x87f00000) == 0x87f00000))
6171379      {
618         *address = ((segreg & 0xf)<<28) | (*address & 0x0fffffff);
1380         address = ((segreg & 0xf)<<28) | (address & 0x0fffffff);
6191381         return 1;
6201382      }
6211383      else if (segreg & 0x80000000)
r31142r31143
6251387   }
6261388
6271389   /* get hash table information from SD1 */
628   hashbase = ppc->spr[SPROEA_SDR1] & 0xffff0000;
629   hashmask = ((ppc->spr[SPROEA_SDR1] & 0x1ff) << 16) | 0xffff;
630   hash = (segreg & 0x7ffff) ^ ((*address >> 12) & 0xffff);
1390   hashbase = m_core->spr[SPROEA_SDR1] & 0xffff0000;
1391   hashmask = ((m_core->spr[SPROEA_SDR1] & 0x1ff) << 16) | 0xffff;
1392   hash = (segreg & 0x7ffff) ^ ((address >> 12) & 0xffff);
6311393
6321394   /* if we're simulating the 603 MMU, fill in the data and stop here */
633   if (ppc->cap & PPCCAP_603_MMU)
1395   if (m_cap & PPCCAP_603_MMU)
6341396   {
635      UINT32 entry = vtlb_table(ppc->vtlb)[*address >> 12];
636      ppc->mmu603_cmp = 0x80000000 | ((segreg & 0xffffff) << 7) | (0 << 6) | ((*address >> 22) & 0x3f);
637      ppc->mmu603_hash[0] = hashbase | ((hash << 6) & hashmask);
638      ppc->mmu603_hash[1] = hashbase | ((~hash << 6) & hashmask);
1397      UINT32 entry = vtlb_table(m_vtlb)[address >> 12];
1398      m_core->mmu603_cmp = 0x80000000 | ((segreg & 0xffffff) << 7) | (0 << 6) | ((address >> 22) & 0x3f);
1399      m_core->mmu603_hash[0] = hashbase | ((hash << 6) & hashmask);
1400      m_core->mmu603_hash[1] = hashbase | ((~hash << 6) & hashmask);
6391401      if ((entry & (VTLB_FLAG_FIXED | VTLB_FLAG_VALID)) == (VTLB_FLAG_FIXED | VTLB_FLAG_VALID))
6401402      {
641         *address = (entry & 0xfffff000) | (*address & 0x00000fff);
1403         address = (entry & 0xfffff000) | (address & 0x00000fff);
6421404         return 0x001;
6431405      }
6441406      return DSISR_NOT_FOUND | ((transtype == TRANSLATE_WRITE) ? DSISR_STORE : 0);
r31142r31143
6481410   for (hashnum = 0; hashnum < 2; hashnum++)
6491411   {
6501412      offs_t ptegaddr = hashbase | ((hash << 6) & hashmask);
651      UINT32 *ptegptr = (UINT32 *)ppc->program->get_read_ptr(ptegaddr);
1413      UINT32 *ptegptr = (UINT32 *)m_program->get_read_ptr(ptegaddr);
6521414
6531415      /* should only have valid memory here, but make sure */
6541416      if (ptegptr != NULL)
6551417      {
656         UINT32 targetupper = 0x80000000 | ((segreg & 0xffffff) << 7) | (hashnum << 6) | ((*address >> 22) & 0x3f);
1418         UINT32 targetupper = 0x80000000 | ((segreg & 0xffffff) << 7) | (hashnum << 6) | ((address >> 22) & 0x3f);
6571419         int ptenum;
6581420
6591421         /* scan PTEs */
r31142r31143
6761438               }
6771439
6781440               /* otherwise we're good */
679               *address = (pteglower & 0xfffff000) | (*address & 0x00000fff);
1441               address = (pteglower & 0xfffff000) | (address & 0x00000fff);
6801442               return (pteglower >> 7) & 1;
6811443            }
6821444      }
r31142r31143
6951457    from logical to physical
6961458-------------------------------------------------*/
6971459
698int ppccom_translate_address(powerpc_state *ppc, address_spacenum space, int intention, offs_t *address)
1460bool ppc_device::memory_translate(address_spacenum spacenum, int intention, offs_t &address)
6991461{
7001462   /* only applies to the program address space */
701   if (space != AS_PROGRAM)
1463   if (spacenum != AS_PROGRAM)
7021464      return TRUE;
7031465
7041466   /* translation is successful if the internal routine returns 0 or 1 */
705   return (ppccom_translate_address_internal(ppc, intention, address) <= 1);
1467   return (ppccom_translate_address_internal(intention, address) <= 1);
7061468}
7071469
7081470
r31142r31143
7101472    ppccom_tlb_fill - handle a missing TLB entry
7111473-------------------------------------------------*/
7121474
713void ppccom_tlb_fill(powerpc_state *ppc)
1475void ppc_device::ppccom_tlb_fill()
7141476{
715   vtlb_fill(ppc->vtlb, ppc->param0, ppc->param1);
1477   vtlb_fill(m_vtlb, m_core->param0, m_core->param1);
7161478}
7171479
7181480
r31142r31143
7211483    including fixed entries
7221484-------------------------------------------------*/
7231485
724void ppccom_tlb_flush(powerpc_state *ppc)
1486void ppc_device::ppccom_tlb_flush()
7251487{
726   vtlb_flush_dynamic(ppc->vtlb);
1488   vtlb_flush_dynamic(m_vtlb);
7271489}
7281490
7291491
r31142r31143
7371499    instruction
7381500-------------------------------------------------*/
7391501
740void ppccom_execute_tlbie(powerpc_state *ppc)
1502void ppc_device::ppccom_execute_tlbie()
7411503{
742   vtlb_flush_address(ppc->vtlb, ppc->param0);
1504   vtlb_flush_address(m_vtlb, m_core->param0);
7431505}
7441506
7451507
r31142r31143
7481510    instruction
7491511-------------------------------------------------*/
7501512
751void ppccom_execute_tlbia(powerpc_state *ppc)
1513void ppc_device::ppccom_execute_tlbia()
7521514{
753   vtlb_flush_dynamic(ppc->vtlb);
1515   vtlb_flush_dynamic(m_vtlb);
7541516}
7551517
7561518
r31142r31143
7591521    instruction
7601522-------------------------------------------------*/
7611523
762void ppccom_execute_tlbl(powerpc_state *ppc)
1524void ppc_device::ppccom_execute_tlbl()
7631525{
764   UINT32 address = ppc->param0;
765   int isitlb = ppc->param1;
1526   UINT32 address = m_core->param0;
1527   int isitlb = m_core->param1;
7661528   vtlb_entry flags = 0;
7671529   int entrynum;
7681530
7691531   /* determine entry number; we use rand() for associativity */
770   entrynum = ((address >> 12) & 0x1f) | (ppc->device->machine().rand() & 0x20) | (isitlb ? 0x40 : 0);
1532   entrynum = ((address >> 12) & 0x1f) | (machine().rand() & 0x20) | (isitlb ? 0x40 : 0);
7711533
7721534   /* determine the flags */
7731535   flags = VTLB_FLAG_VALID | VTLB_READ_ALLOWED | VTLB_FETCH_ALLOWED;
774   if (ppc->spr[SPR603_RPA] & 0x80)
1536   if (m_core->spr[SPR603_RPA] & 0x80)
7751537      flags |= VTLB_WRITE_ALLOWED;
7761538   if (isitlb)
7771539      flags |= VTLB_FETCH_ALLOWED;
7781540
7791541   /* load the entry */
780   vtlb_load(ppc->vtlb, entrynum, 1, address, (ppc->spr[SPR603_RPA] & 0xfffff000) | flags);
1542   vtlb_load(m_vtlb, entrynum, 1, address, (m_core->spr[SPR603_RPA] & 0xfffff000) | flags);
7811543}
7821544
7831545
r31142r31143
7861548    instruction
7871549-------------------------------------------------*/
7881550
789void ppccom_execute_mftb(powerpc_state *ppc)
1551void ppc_device::ppccom_execute_mftb()
7901552{
791   switch (ppc->param0)
1553   switch (m_core->param0)
7921554   {
7931555      /* user mode timebase read */
7941556      case SPRVEA_TBL_R:
795         ppc->param1 = get_timebase(ppc);
1557         m_core->param1 = get_timebase();
7961558         break;
7971559      case SPRVEA_TBU_R:
798         ppc->param1 = get_timebase(ppc) >> 32;
1560         m_core->param1 = get_timebase() >> 32;
7991561         break;
8001562   }
8011563}
r31142r31143
8061568    instruction
8071569-------------------------------------------------*/
8081570
809void ppccom_execute_mfspr(powerpc_state *ppc)
1571void ppc_device::ppccom_execute_mfspr()
8101572{
8111573   /* handle OEA SPRs */
812   if (ppc->cap & PPCCAP_OEA)
1574   if (m_cap & PPCCAP_OEA)
8131575   {
814      switch (ppc->param0)
1576      switch (m_core->param0)
8151577      {
8161578         /* read-through no-ops */
8171579         case SPROEA_DSISR:
r31142r31143
8371599         case SPROEA_DBAT3L:
8381600         case SPROEA_DBAT3U:
8391601         case SPROEA_DABR:
840            ppc->param1 = ppc->spr[ppc->param0];
1602            m_core->param1 = m_core->spr[m_core->param0];
8411603            return;
8421604
8431605         /* decrementer */
8441606         case SPROEA_DEC:
845            ppc->param1 = get_decrementer(ppc);
1607            m_core->param1 = get_decrementer();
8461608            return;
8471609      }
8481610   }
8491611
8501612   /* handle 603 SPRs */
851   if (ppc->cap & PPCCAP_603_MMU)
1613   if (m_cap & PPCCAP_603_MMU)
8521614   {
853      switch (ppc->param0)
1615      switch (m_core->param0)
8541616      {
8551617         /* read-through no-ops */
8561618         case SPR603_DMISS:
r31142r31143
8641626         case SPR603_HID1:
8651627         case SPR603_IABR:
8661628         case SPR603_HID2:
867            ppc->param1 = ppc->spr[ppc->param0];
1629            m_core->param1 = m_core->spr[m_core->param0];
8681630            return;
8691631
8701632         /* timebase */
8711633         case SPR603_TBL_R:
872            ppc->param1 = get_timebase(ppc);
1634            m_core->param1 = get_timebase();
8731635            return;
8741636         case SPR603_TBU_R:
875            ppc->param1 = (get_timebase(ppc) >> 32) & 0xffffff;
1637            m_core->param1 = (get_timebase() >> 32) & 0xffffff;
8761638            return;
8771639      }
8781640   }
8791641
8801642   /* handle 4XX SPRs */
881   if (ppc->cap & PPCCAP_4XX)
1643   if (m_cap & PPCCAP_4XX)
8821644   {
883      switch (ppc->param0)
1645      switch (m_core->param0)
8841646      {
8851647         /* read-through no-ops */
8861648         case SPR4XX_EVPR:
r31142r31143
9011663         case SPR4XX_PBU1:
9021664         case SPR4XX_PBL2:
9031665         case SPR4XX_PBU2:
904            ppc->param1 = ppc->spr[ppc->param0];
1666            m_core->param1 = m_core->spr[m_core->param0];
9051667            return;
9061668
9071669         /* timebase */
9081670         case SPR4XX_TBLO:
9091671         case SPR4XX_TBLU:
910            ppc->param1 = get_timebase(ppc);
1672            m_core->param1 = get_timebase();
9111673            return;
9121674         case SPR4XX_TBHI:
9131675         case SPR4XX_TBHU:
914            ppc->param1 = (get_timebase(ppc) >> 32) & 0xffffff;
1676            m_core->param1 = (get_timebase() >> 32) & 0xffffff;
9151677            return;
9161678      }
9171679   }
9181680
9191681   /* default handling */
920   osd_printf_debug("SPR %03X read\n", ppc->param0);
921   ppc->param1 = ppc->spr[ppc->param0];
1682   osd_printf_debug("SPR %03X read\n", m_core->param0);
1683   m_core->param1 = m_core->spr[m_core->param0];
9221684}
9231685
9241686
r31142r31143
9271689    instruction
9281690-------------------------------------------------*/
9291691
930void ppccom_execute_mtspr(powerpc_state *ppc)
1692void ppc_device::ppccom_execute_mtspr()
9311693{
9321694   /* handle OEA SPRs */
933   if (ppc->cap & PPCCAP_OEA)
1695   if (m_cap & PPCCAP_OEA)
9341696   {
935      switch (ppc->param0)
1697      switch (m_core->param0)
9361698      {
9371699         /* write-through no-ops */
9381700         case SPROEA_DSISR:
r31142r31143
9411703         case SPROEA_SRR1:
9421704         case SPROEA_EAR:
9431705         case SPROEA_DABR:
944            ppc->spr[ppc->param0] = ppc->param1;
1706            m_core->spr[m_core->param0] = m_core->param1;
9451707            return;
9461708
9471709         /* registers that affect the memory map */
r31142r31143
9621724         case SPROEA_DBAT2U:
9631725         case SPROEA_DBAT3L:
9641726         case SPROEA_DBAT3U:
965            ppc->spr[ppc->param0] = ppc->param1;
966            ppccom_tlb_flush(ppc);
1727            m_core->spr[m_core->param0] = m_core->param1;
1728            ppccom_tlb_flush();
9671729            return;
9681730
9691731         /* decrementer */
9701732         case SPROEA_DEC:
971            set_decrementer(ppc, ppc->param1);
1733            set_decrementer(m_core->param1);
9721734            return;
9731735      }
9741736   }
9751737
9761738   /* handle 603 SPRs */
977   if (ppc->cap & PPCCAP_603_MMU)
1739   if (m_cap & PPCCAP_603_MMU)
9781740   {
979      switch (ppc->param0)
1741      switch (m_core->param0)
9801742      {
9811743         /* read-only */
9821744         case SPR603_DMISS:
r31142r31143
9931755         case SPR603_HID1:
9941756         case SPR603_IABR:
9951757         case SPR603_HID2:
996            ppc->spr[ppc->param0] = ppc->param1;
1758            m_core->spr[m_core->param0] = m_core->param1;
9971759            return;
9981760
9991761         /* timebase */
10001762         case SPR603_TBL_W:
1001            set_timebase(ppc, (get_timebase(ppc) & ~U64(0xffffffff00000000)) | ppc->param1);
1763            set_timebase((get_timebase() & ~U64(0xffffffff00000000)) | m_core->param1);
10021764            return;
10031765         case SPR603_TBU_W:
1004            set_timebase(ppc, (get_timebase(ppc) & ~U64(0x00000000ffffffff)) | ((UINT64)ppc->param1 << 32));
1766            set_timebase((get_timebase() & ~U64(0x00000000ffffffff)) | ((UINT64)m_core->param1 << 32));
10051767            return;
10061768      }
10071769   }
10081770
10091771   /* handle 4XX SPRs */
1010   if (ppc->cap & PPCCAP_4XX)
1772   if (m_cap & PPCCAP_4XX)
10111773   {
1012      UINT32 oldval = ppc->spr[ppc->param0];
1013      switch (ppc->param0)
1774      UINT32 oldval = m_core->spr[m_core->param0];
1775      switch (m_core->param0)
10141776      {
10151777         /* write-through no-ops */
10161778         case SPR4XX_EVPR:
r31142r31143
10211783         case SPR4XX_SRR1:
10221784         case SPR4XX_SRR2:
10231785         case SPR4XX_SRR3:
1024            ppc->spr[ppc->param0] = ppc->param1;
1786            m_core->spr[m_core->param0] = m_core->param1;
10251787            return;
10261788
10271789         /* registers that affect the memory map */
r31142r31143
10291791         case SPR4XX_PBU1:
10301792         case SPR4XX_PBL2:
10311793         case SPR4XX_PBU2:
1032            ppc->spr[ppc->param0] = ppc->param1;
1033            ppccom_tlb_flush(ppc);
1794            m_core->spr[m_core->param0] = m_core->param1;
1795            ppccom_tlb_flush();
10341796            return;
10351797
10361798         /* timer control register */
10371799         case SPR4XX_TCR:
1038            ppc->spr[SPR4XX_TCR] = ppc->param1 | (oldval & PPC4XX_TCR_WRC_MASK);
1039            if ((oldval ^ ppc->spr[SPR4XX_TCR]) & PPC4XX_TCR_FIE)
1040               ppc4xx_fit_callback(ppc->device->machine(), ppc, FALSE);
1041            if ((oldval ^ ppc->spr[SPR4XX_TCR]) & PPC4XX_TCR_PIE)
1042               ppc4xx_pit_callback(ppc->device->machine(), ppc, FALSE);
1800            m_core->spr[SPR4XX_TCR] = m_core->param1 | (oldval & PPC4XX_TCR_WRC_MASK);
1801            if ((oldval ^ m_core->spr[SPR4XX_TCR]) & PPC4XX_TCR_FIE)
1802               ppc4xx_fit_callback(NULL, FALSE);
1803            if ((oldval ^ m_core->spr[SPR4XX_TCR]) & PPC4XX_TCR_PIE)
1804               ppc4xx_pit_callback(NULL, FALSE);
10431805            return;
10441806
10451807         /* timer status register */
10461808         case SPR4XX_TSR:
1047            ppc->spr[SPR4XX_TSR] &= ~ppc->param1;
1048            ppc4xx_set_irq_line(ppc, 0, 0);
1809            m_core->spr[SPR4XX_TSR] &= ~m_core->param1;
1810            ppc4xx_set_irq_line(0, 0);
10491811            return;
10501812
10511813         /* PIT */
10521814         case SPR4XX_PIT:
1053            ppc->spr[SPR4XX_PIT] = ppc->param1;
1054            ppc->pit_reload = ppc->param1;
1055            ppc4xx_pit_callback(ppc->device->machine(), ppc, FALSE);
1815            m_core->spr[SPR4XX_PIT] = m_core->param1;
1816            m_pit_reload = m_core->param1;
1817            ppc4xx_pit_callback(NULL, FALSE);
10561818            return;
10571819
10581820         /* timebase */
10591821         case SPR4XX_TBLO:
1060            set_timebase(ppc, (get_timebase(ppc) & ~U64(0x00ffffff00000000)) | ppc->param1);
1822            set_timebase((get_timebase() & ~U64(0x00ffffff00000000)) | m_core->param1);
10611823            return;
10621824         case SPR4XX_TBHI:
1063            set_timebase(ppc, (get_timebase(ppc) & ~U64(0x00000000ffffffff)) | ((UINT64)(ppc->param1 & 0x00ffffff) << 32));
1825            set_timebase((get_timebase() & ~U64(0x00000000ffffffff)) | ((UINT64)(m_core->param1 & 0x00ffffff) << 32));
10641826            return;
10651827      }
10661828   }
10671829
10681830   /* default handling */
1069   osd_printf_debug("SPR %03X write = %08X\n", ppc->param0, ppc->param1);
1070   ppc->spr[ppc->param0] = ppc->param1;
1831   osd_printf_debug("SPR %03X write = %08X\n", m_core->param0, m_core->param1);
1832   m_core->spr[m_core->param0] = m_core->param1;
10711833}
10721834
10731835
r31142r31143
10761838    instruction
10771839-------------------------------------------------*/
10781840
1079void ppccom_execute_mfdcr(powerpc_state *ppc)
1841void ppc_device::ppccom_execute_mfdcr()
10801842{
10811843   /* handle various DCRs */
1082   switch (ppc->param0)
1844   switch (m_core->param0)
10831845   {
10841846      /* read-through no-ops */
10851847      case DCR4XX_BR0:
r31142r31143
11151877      case DCR4XX_EXIER:
11161878      case DCR4XX_EXISR:
11171879      case DCR4XX_IOCR:
1118         ppc->param1 = ppc->dcr[ppc->param0];
1880         m_core->param1 = m_dcr[m_core->param0];
11191881         return;
11201882   }
11211883
11221884   /* default handling */
1123   if (ppc->dcr_read_func.isnull()) {
1124      osd_printf_debug("DCR %03X read\n", ppc->param0);
1125      if (ppc->param0 < ARRAY_LENGTH(ppc->dcr))
1126         ppc->param1 = ppc->dcr[ppc->param0];
1885   if (m_dcr_read_func.isnull()) {
1886      osd_printf_debug("DCR %03X read\n", m_core->param0);
1887      if (m_core->param0 < ARRAY_LENGTH(m_dcr))
1888         m_core->param1 = m_dcr[m_core->param0];
11271889      else
1128         ppc->param1 = 0;
1890         m_core->param1 = 0;
11291891   } else {
1130      ppc->param1 = ppc->dcr_read_func(*ppc->program,ppc->param0,0xffffffff);
1892      m_core->param1 = m_dcr_read_func(*m_program,m_core->param0,0xffffffff);
11311893   }
11321894}
11331895
r31142r31143
11371899    instruction
11381900-------------------------------------------------*/
11391901
1140void ppccom_execute_mtdcr(powerpc_state *ppc)
1902void ppc_device::ppccom_execute_mtdcr()
11411903{
11421904   UINT8 oldval;
11431905
11441906   /* handle various DCRs */
1145   switch (ppc->param0)
1907   switch (m_core->param0)
11461908   {
11471909      /* write-through no-ops */
11481910      case DCR4XX_BR0:
r31142r31143
11701932      case DCR4XX_DMADA3:
11711933      case DCR4XX_DMASA3:
11721934      case DCR4XX_DMACC3:
1173         ppc->dcr[ppc->param0] = ppc->param1;
1935         m_dcr[m_core->param0] = m_core->param1;
11741936         return;
11751937
11761938      /* DMA status */
11771939      case DCR4XX_DMASR:
1178         ppc->dcr[DCR4XX_DMASR] &= ~(ppc->param1 & 0xfff80070);
1179         ppc4xx_dma_update_irq_states(ppc);
1940         m_dcr[DCR4XX_DMASR] &= ~(m_core->param1 & 0xfff80070);
1941         ppc4xx_dma_update_irq_states();
11801942         return;
11811943
11821944      /* interrupt enables */
11831945      case DCR4XX_EXIER:
1184         ppc->dcr[DCR4XX_EXIER] = ppc->param1;
1185         ppc4xx_set_irq_line(ppc, 0, 0);
1946         m_dcr[DCR4XX_EXIER] = m_core->param1;
1947         ppc4xx_set_irq_line(0, 0);
11861948         return;
11871949
11881950      /* interrupt clear */
11891951      case DCR4XX_EXISR:
1190         ppc->dcr[ppc->param0] &= ~ppc->param1;
1191         ppc4xx_set_irq_line(ppc, 0, 0);
1952         m_dcr[m_core->param0] &= ~m_core->param1;
1953         ppc4xx_set_irq_line(0, 0);
11921954         return;
11931955
11941956      /* DMA controls */
r31142r31143
11961958      case DCR4XX_DMACR1:
11971959      case DCR4XX_DMACR2:
11981960      case DCR4XX_DMACR3:
1199         ppc->dcr[ppc->param0] = ppc->param1;
1200         if (ppc->param1 & PPC4XX_DMACR_CE)
1201            ppc4xx_dma_exec(ppc, (ppc->param0 - DCR4XX_DMACR0) / 8);
1202         ppc4xx_dma_update_irq_states(ppc);
1961         m_dcr[m_core->param0] = m_core->param1;
1962         if (m_core->param1 & PPC4XX_DMACR_CE)
1963            ppc4xx_dma_exec((m_core->param0 - DCR4XX_DMACR0) / 8);
1964         ppc4xx_dma_update_irq_states();
12031965         return;
12041966
12051967      /* I/O control */
12061968      case DCR4XX_IOCR:
1207         oldval = ppc->dcr[ppc->param0];
1208         ppc->dcr[ppc->param0] = ppc->param1;
1209         if ((oldval ^ ppc->param1) & 0x02)
1210            ppc4xx_spu_timer_reset(ppc);
1969         oldval = m_dcr[m_core->param0];
1970         m_dcr[m_core->param0] = m_core->param1;
1971         if ((oldval ^ m_core->param1) & 0x02)
1972            ppc4xx_spu_timer_reset();
12111973         return;
12121974   }
12131975
12141976   /* default handling */
1215   if (ppc->dcr_write_func.isnull()) {
1216      osd_printf_debug("DCR %03X write = %08X\n", ppc->param0, ppc->param1);
1217      if (ppc->param0 < ARRAY_LENGTH(ppc->dcr))
1218         ppc->dcr[ppc->param0] = ppc->param1;
1977   if (m_dcr_write_func.isnull()) {
1978      osd_printf_debug("DCR %03X write = %08X\n", m_core->param0, m_core->param1);
1979      if (m_core->param0 < ARRAY_LENGTH(m_dcr))
1980         m_dcr[m_core->param0] = m_core->param1;
12191981   } else {
1220      ppc->dcr_write_func(*ppc->program,ppc->param0,ppc->param1,0xffffffff);
1982      m_dcr_write_func(*m_program,m_core->param0,m_core->param1,0xffffffff);
12211983   }
12221984}
12231985
r31142r31143
12321994    of the FPSCR register
12331995-------------------------------------------------*/
12341996
1235void ppccom_update_fprf(powerpc_state *ppc)
1997void ppc_device::ppccom_update_fprf()
12361998{
12371999   UINT32 fprf;
1238   double f = ppc->f[ppc->param0];
2000   double f = m_core->f[m_core->param0];
12392001
12402002   if (is_qnan_double(f))
12412003   {
r31142r31143
12702032         fprf = 0x02;
12712033   }
12722034
1273   ppc->fpscr &= ~0x0001f000;
1274   ppc->fpscr |= fprf << 12;
2035   m_core->fpscr &= ~0x0001f000;
2036   m_core->fpscr |= fprf << 12;
12752037}
12762038
12772039
1278
12792040/***************************************************************************
1280    COMMON GET/SET INFO
2041    OEA HELPERS
12812042***************************************************************************/
12822043
12832044/*-------------------------------------------------
1284    ppccom_set_info - set information about
1285    a PowerPC CPU
2045    decrementer_int_callback - callback that fires
2046    whenever a decrementer interrupt is generated
12862047-------------------------------------------------*/
12872048
1288void ppccom_set_info(powerpc_state *ppc, UINT32 state, cpuinfo *info)
2049TIMER_CALLBACK_MEMBER( ppc_device::decrementer_int_callback )
12892050{
1290   switch (state)
1291   {
1292      /* --- the following bits of info are set as 64-bit signed integers --- */
1293      case CPUINFO_INT_INPUT_STATE + PPC_IRQ:         ppc->irq_pending = (ppc->irq_pending & ~1) | (info->i  != CLEAR_LINE); break;
2051   UINT64 cycles_until_next;
12942052
1295      case CPUINFO_INT_PC:
1296      case CPUINFO_INT_REGISTER + PPC_PC:             ppc->pc = info->i;                      break;
1297      case CPUINFO_INT_REGISTER + PPC_MSR:            ppc->msr = info->i;                     break;
1298      case CPUINFO_INT_REGISTER + PPC_CR:             set_cr(ppc, info->i);                   break;
1299      case CPUINFO_INT_REGISTER + PPC_LR:             ppc->spr[SPR_LR] = info->i;             break;
1300      case CPUINFO_INT_REGISTER + PPC_CTR:            ppc->spr[SPR_CTR] = info->i;            break;
1301      case CPUINFO_INT_REGISTER + PPC_XER:            set_xer(ppc, info->i);                  break;
1302      case CPUINFO_INT_REGISTER + PPC_SRR0:           ppc->spr[SPROEA_SRR0] = info->i;        break;
1303      case CPUINFO_INT_REGISTER + PPC_SRR1:           ppc->spr[SPROEA_SRR1] = info->i;        break;
1304      case CPUINFO_INT_REGISTER + PPC_SPRG0:          ppc->spr[SPROEA_SPRG0] = info->i;       break;
1305      case CPUINFO_INT_REGISTER + PPC_SPRG1:          ppc->spr[SPROEA_SPRG1] = info->i;       break;
1306      case CPUINFO_INT_REGISTER + PPC_SPRG2:          ppc->spr[SPROEA_SPRG2] = info->i;       break;
1307      case CPUINFO_INT_REGISTER + PPC_SPRG3:          ppc->spr[SPROEA_SPRG3] = info->i;       break;
1308      case CPUINFO_INT_REGISTER + PPC_SDR1:           ppc->spr[SPROEA_SDR1] = info->i;        break;
1309      case CPUINFO_INT_REGISTER + PPC_EXIER:          ppc->dcr[DCR4XX_EXIER] = info->i;       break;
1310      case CPUINFO_INT_REGISTER + PPC_EXISR:          ppc->dcr[DCR4XX_EXISR] = info->i;       break;
1311      case CPUINFO_INT_REGISTER + PPC_EVPR:           ppc->spr[SPR4XX_EVPR] = info->i;        break;
1312      case CPUINFO_INT_REGISTER + PPC_IOCR:           ppc->dcr[DCR4XX_IOCR] = info->i;        break;
1313      case CPUINFO_INT_REGISTER + PPC_TBL:            set_timebase(ppc, (get_timebase(ppc) & ~U64(0x00ffffff00000000)) | info->i); break;
1314      case CPUINFO_INT_REGISTER + PPC_TBH:            set_timebase(ppc, (get_timebase(ppc) & ~U64(0x00000000ffffffff)) | ((UINT64)(ppc->param1 & 0x00ffffff) << 32)); break;
1315      case CPUINFO_INT_REGISTER + PPC_DEC:            set_decrementer(ppc, info->i);          break;
2053   /* set the decrementer IRQ state */
2054   m_core->irq_pending |= 0x02;
13162055
1317      case CPUINFO_INT_REGISTER + PPC_SR0:            ppc->sr[0] = info->i;                   break;
1318      case CPUINFO_INT_REGISTER + PPC_SR1:            ppc->sr[1] = info->i;                   break;
1319      case CPUINFO_INT_REGISTER + PPC_SR2:            ppc->sr[2] = info->i;                   break;
1320      case CPUINFO_INT_REGISTER + PPC_SR3:            ppc->sr[3] = info->i;                   break;
1321      case CPUINFO_INT_REGISTER + PPC_SR4:            ppc->sr[4] = info->i;                   break;
1322      case CPUINFO_INT_REGISTER + PPC_SR5:            ppc->sr[5] = info->i;                   break;
1323      case CPUINFO_INT_REGISTER + PPC_SR6:            ppc->sr[6] = info->i;                   break;
1324      case CPUINFO_INT_REGISTER + PPC_SR7:            ppc->sr[7] = info->i;                   break;
1325      case CPUINFO_INT_REGISTER + PPC_SR8:            ppc->sr[8] = info->i;                   break;
1326      case CPUINFO_INT_REGISTER + PPC_SR9:            ppc->sr[9] = info->i;                   break;
1327      case CPUINFO_INT_REGISTER + PPC_SR10:           ppc->sr[10] = info->i;                  break;
1328      case CPUINFO_INT_REGISTER + PPC_SR11:           ppc->sr[11] = info->i;                  break;
1329      case CPUINFO_INT_REGISTER + PPC_SR12:           ppc->sr[12] = info->i;                  break;
1330      case CPUINFO_INT_REGISTER + PPC_SR13:           ppc->sr[13] = info->i;                  break;
1331      case CPUINFO_INT_REGISTER + PPC_SR14:           ppc->sr[14] = info->i;                  break;
1332      case CPUINFO_INT_REGISTER + PPC_SR15:           ppc->sr[15] = info->i;                  break;
1333
1334      case CPUINFO_INT_REGISTER + PPC_R0:             ppc->r[0] = info->i;                    break;
1335      case CPUINFO_INT_REGISTER + PPC_R1:             ppc->r[1] = info->i;                    break;
1336      case CPUINFO_INT_REGISTER + PPC_R2:             ppc->r[2] = info->i;                    break;
1337      case CPUINFO_INT_REGISTER + PPC_R3:             ppc->r[3] = info->i;                    break;
1338      case CPUINFO_INT_REGISTER + PPC_R4:             ppc->r[4] = info->i;                    break;
1339      case CPUINFO_INT_REGISTER + PPC_R5:             ppc->r[5] = info->i;                    break;
1340      case CPUINFO_INT_REGISTER + PPC_R6:             ppc->r[6] = info->i;                    break;
1341      case CPUINFO_INT_REGISTER + PPC_R7:             ppc->r[7] = info->i;                    break;
1342      case CPUINFO_INT_REGISTER + PPC_R8:             ppc->r[8] = info->i;                    break;
1343      case CPUINFO_INT_REGISTER + PPC_R9:             ppc->r[9] = info->i;                    break;
1344      case CPUINFO_INT_REGISTER + PPC_R10:            ppc->r[10] = info->i;                   break;
1345      case CPUINFO_INT_REGISTER + PPC_R11:            ppc->r[11] = info->i;                   break;
1346      case CPUINFO_INT_REGISTER + PPC_R12:            ppc->r[12] = info->i;                   break;
1347      case CPUINFO_INT_REGISTER + PPC_R13:            ppc->r[13] = info->i;                   break;
1348      case CPUINFO_INT_REGISTER + PPC_R14:            ppc->r[14] = info->i;                   break;
1349      case CPUINFO_INT_REGISTER + PPC_R15:            ppc->r[15] = info->i;                   break;
1350      case CPUINFO_INT_REGISTER + PPC_R16:            ppc->r[16] = info->i;                   break;
1351      case CPUINFO_INT_REGISTER + PPC_R17:            ppc->r[17] = info->i;                   break;
1352      case CPUINFO_INT_REGISTER + PPC_R18:            ppc->r[18] = info->i;                   break;
1353      case CPUINFO_INT_REGISTER + PPC_R19:            ppc->r[19] = info->i;                   break;
1354      case CPUINFO_INT_REGISTER + PPC_R20:            ppc->r[20] = info->i;                   break;
1355      case CPUINFO_INT_REGISTER + PPC_R21:            ppc->r[21] = info->i;                   break;
1356      case CPUINFO_INT_REGISTER + PPC_R22:            ppc->r[22] = info->i;                   break;
1357      case CPUINFO_INT_REGISTER + PPC_R23:            ppc->r[23] = info->i;                   break;
1358      case CPUINFO_INT_REGISTER + PPC_R24:            ppc->r[24] = info->i;                   break;
1359      case CPUINFO_INT_REGISTER + PPC_R25:            ppc->r[25] = info->i;                   break;
1360      case CPUINFO_INT_REGISTER + PPC_R26:            ppc->r[26] = info->i;                   break;
1361      case CPUINFO_INT_REGISTER + PPC_R27:            ppc->r[27] = info->i;                   break;
1362      case CPUINFO_INT_REGISTER + PPC_R28:            ppc->r[28] = info->i;                   break;
1363      case CPUINFO_INT_REGISTER + PPC_R29:            ppc->r[29] = info->i;                   break;
1364      case CPUINFO_INT_REGISTER + PPC_R30:            ppc->r[30] = info->i;                   break;
1365      case CPUINFO_INT_SP:
1366      case CPUINFO_INT_REGISTER + PPC_R31:            ppc->r[31] = info->i;                   break;
1367
1368      case CPUINFO_INT_REGISTER + PPC_F0:             ppc->f[0] = *(double *)&info->i;        break;
1369      case CPUINFO_INT_REGISTER + PPC_F1:             ppc->f[1] = *(double *)&info->i;        break;
1370      case CPUINFO_INT_REGISTER + PPC_F2:             ppc->f[2] = *(double *)&info->i;        break;
1371      case CPUINFO_INT_REGISTER + PPC_F3:             ppc->f[3] = *(double *)&info->i;        break;
1372      case CPUINFO_INT_REGISTER + PPC_F4:             ppc->f[4] = *(double *)&info->i;        break;
1373      case CPUINFO_INT_REGISTER + PPC_F5:             ppc->f[5] = *(double *)&info->i;        break;
1374      case CPUINFO_INT_REGISTER + PPC_F6:             ppc->f[6] = *(double *)&info->i;        break;
1375      case CPUINFO_INT_REGISTER + PPC_F7:             ppc->f[7] = *(double *)&info->i;        break;
1376      case CPUINFO_INT_REGISTER + PPC_F8:             ppc->f[8] = *(double *)&info->i;        break;
1377      case CPUINFO_INT_REGISTER + PPC_F9:             ppc->f[9] = *(double *)&info->i;        break;
1378      case CPUINFO_INT_REGISTER + PPC_F10:            ppc->f[10] = *(double *)&info->i;       break;
1379      case CPUINFO_INT_REGISTER + PPC_F11:            ppc->f[11] = *(double *)&info->i;       break;
1380      case CPUINFO_INT_REGISTER + PPC_F12:            ppc->f[12] = *(double *)&info->i;       break;
1381      case CPUINFO_INT_REGISTER + PPC_F13:            ppc->f[13] = *(double *)&info->i;       break;
1382      case CPUINFO_INT_REGISTER + PPC_F14:            ppc->f[14] = *(double *)&info->i;       break;
1383      case CPUINFO_INT_REGISTER + PPC_F15:            ppc->f[15] = *(double *)&info->i;       break;
1384      case CPUINFO_INT_REGISTER + PPC_F16:            ppc->f[16] = *(double *)&info->i;       break;
1385      case CPUINFO_INT_REGISTER + PPC_F17:            ppc->f[17] = *(double *)&info->i;       break;
1386      case CPUINFO_INT_REGISTER + PPC_F18:            ppc->f[18] = *(double *)&info->i;       break;
1387      case CPUINFO_INT_REGISTER + PPC_F19:            ppc->f[19] = *(double *)&info->i;       break;
1388      case CPUINFO_INT_REGISTER + PPC_F20:            ppc->f[20] = *(double *)&info->i;       break;
1389      case CPUINFO_INT_REGISTER + PPC_F21:            ppc->f[21] = *(double *)&info->i;       break;
1390      case CPUINFO_INT_REGISTER + PPC_F22:            ppc->f[22] = *(double *)&info->i;       break;
1391      case CPUINFO_INT_REGISTER + PPC_F23:            ppc->f[23] = *(double *)&info->i;       break;
1392      case CPUINFO_INT_REGISTER + PPC_F24:            ppc->f[24] = *(double *)&info->i;       break;
1393      case CPUINFO_INT_REGISTER + PPC_F25:            ppc->f[25] = *(double *)&info->i;       break;
1394      case CPUINFO_INT_REGISTER + PPC_F26:            ppc->f[26] = *(double *)&info->i;       break;
1395      case CPUINFO_INT_REGISTER + PPC_F27:            ppc->f[27] = *(double *)&info->i;       break;
1396      case CPUINFO_INT_REGISTER + PPC_F28:            ppc->f[28] = *(double *)&info->i;       break;
1397      case CPUINFO_INT_REGISTER + PPC_F29:            ppc->f[29] = *(double *)&info->i;       break;
1398      case CPUINFO_INT_REGISTER + PPC_F30:            ppc->f[30] = *(double *)&info->i;       break;
1399      case CPUINFO_INT_REGISTER + PPC_F31:            ppc->f[31] = *(double *)&info->i;       break;
1400      case CPUINFO_INT_REGISTER + PPC_FPSCR:          ppc->fpscr = info->i;                   break;
1401   }
2056   /* advance by another full rev */
2057   m_dec_zero_cycles += (UINT64)m_tb_divisor << 32;
2058   cycles_until_next = m_dec_zero_cycles - total_cycles();
2059   m_decrementer_int_timer->adjust(cycles_to_attotime(cycles_until_next));
14022060}
14032061
1404
14052062/*-------------------------------------------------
1406    ppccom_get_info - get information about
1407    a PowerPC CPU
2063    ppc_set_dcstore_callback - installs a callback
2064    for detecting datacache stores with dcbst
14082065-------------------------------------------------*/
14092066
1410void ppccom_get_info(powerpc_state *ppc, UINT32 state, cpuinfo *info)
2067void ppc_device::ppc_set_dcstore_callback(ppc_dcstore_handler handler)
14112068{
1412   switch (state)
1413   {
1414      /* --- the following bits of info are returned as 64-bit signed integers --- */
1415      case CPUINFO_INT_CONTEXT_SIZE:                  /* provided by core */                  break;
1416      case CPUINFO_INT_INPUT_LINES:                   info->i = 1;                            break;
1417      case CPUINFO_INT_DEFAULT_IRQ_VECTOR:            info->i = 0;                            break;
1418      case CPUINFO_INT_ENDIANNESS:                    info->i = ENDIANNESS_BIG;                   break;
1419      case CPUINFO_INT_CLOCK_MULTIPLIER:              info->i = 1;                            break;
1420      case CPUINFO_INT_CLOCK_DIVIDER:                 info->i = 1;                            break;
1421      case CPUINFO_INT_MIN_INSTRUCTION_BYTES:         info->i = 4;                            break;
1422      case CPUINFO_INT_MAX_INSTRUCTION_BYTES:         info->i = 4;                            break;
1423      case CPUINFO_INT_MIN_CYCLES:                    info->i = 1;                            break;
1424      case CPUINFO_INT_MAX_CYCLES:                    info->i = 40;                           break;
2069   m_dcstore_handler = handler;
2070}
14252071
1426      case CPUINFO_INT_DATABUS_WIDTH + AS_PROGRAM:    info->i = 64;                   break;
1427      case CPUINFO_INT_ADDRBUS_WIDTH + AS_PROGRAM: info->i = 32;                  break;
1428      case CPUINFO_INT_ADDRBUS_SHIFT + AS_PROGRAM: info->i = 0;                   break;
1429      case CPUINFO_INT_LOGADDR_WIDTH_PROGRAM: info->i = 32;                   break;
1430      case CPUINFO_INT_PAGE_SHIFT_PROGRAM:    info->i = POWERPC_MIN_PAGE_SHIFT;break;
14312072
1432      case CPUINFO_INT_INPUT_STATE + PPC_IRQ:         info->i = ppc->irq_pending ? ASSERT_LINE : CLEAR_LINE; break;
1433
1434      case CPUINFO_INT_PREVIOUSPC:                    /* optionally implemented */            break;
1435
1436      case CPUINFO_INT_PC:
1437      case CPUINFO_INT_REGISTER + PPC_PC:             info->i = ppc->pc;                      break;
1438      case CPUINFO_INT_REGISTER + PPC_MSR:            info->i = ppc->msr;                     break;
1439      case CPUINFO_INT_REGISTER + PPC_CR:             info->i = get_cr(ppc);                  break;
1440      case CPUINFO_INT_REGISTER + PPC_LR:             info->i = ppc->spr[SPR_LR];             break;
1441      case CPUINFO_INT_REGISTER + PPC_CTR:            info->i = ppc->spr[SPR_CTR];            break;
1442      case CPUINFO_INT_REGISTER + PPC_XER:            info->i = get_xer(ppc);                 break;
1443      case CPUINFO_INT_REGISTER + PPC_SRR0:           info->i = ppc->spr[SPROEA_SRR0];        break;
1444      case CPUINFO_INT_REGISTER + PPC_SRR1:           info->i = ppc->spr[SPROEA_SRR1];        break;
1445      case CPUINFO_INT_REGISTER + PPC_SPRG0:          info->i = ppc->spr[SPROEA_SPRG0];       break;
1446      case CPUINFO_INT_REGISTER + PPC_SPRG1:          info->i = ppc->spr[SPROEA_SPRG1];       break;
1447      case CPUINFO_INT_REGISTER + PPC_SPRG2:          info->i = ppc->spr[SPROEA_SPRG2];       break;
1448      case CPUINFO_INT_REGISTER + PPC_SPRG3:          info->i = ppc->spr[SPROEA_SPRG3];       break;
1449      case CPUINFO_INT_REGISTER + PPC_SDR1:           info->i = ppc->spr[SPROEA_SDR1];        break;
1450      case CPUINFO_INT_REGISTER + PPC_EXIER:          info->i = ppc->dcr[DCR4XX_EXIER];       break;
1451      case CPUINFO_INT_REGISTER + PPC_EXISR:          info->i = ppc->dcr[DCR4XX_EXISR];       break;
1452      case CPUINFO_INT_REGISTER + PPC_EVPR:           info->i = ppc->spr[SPR4XX_EVPR];        break;
1453      case CPUINFO_INT_REGISTER + PPC_IOCR:           info->i = ppc->dcr[DCR4XX_IOCR];        break;
1454      case CPUINFO_INT_REGISTER + PPC_TBH:            info->i = get_timebase(ppc) >> 32;      break;
1455      case CPUINFO_INT_REGISTER + PPC_TBL:            info->i = (UINT32)get_timebase(ppc);    break;
1456      case CPUINFO_INT_REGISTER + PPC_DEC:            info->i = get_decrementer(ppc);         break;
1457
1458      case CPUINFO_INT_REGISTER + PPC_SR0:            info->i = ppc->sr[0];                   break;
1459      case CPUINFO_INT_REGISTER + PPC_SR1:            info->i = ppc->sr[1];                   break;
1460      case CPUINFO_INT_REGISTER + PPC_SR2:            info->i = ppc->sr[2];                   break;
1461      case CPUINFO_INT_REGISTER + PPC_SR3:            info->i = ppc->sr[3];                   break;
1462      case CPUINFO_INT_REGISTER + PPC_SR4:            info->i = ppc->sr[4];                   break;
1463      case CPUINFO_INT_REGISTER + PPC_SR5:            info->i = ppc->sr[5];                   break;
1464      case CPUINFO_INT_REGISTER + PPC_SR6:            info->i = ppc->sr[6];                   break;
1465      case CPUINFO_INT_REGISTER + PPC_SR7:            info->i = ppc->sr[7];                   break;
1466      case CPUINFO_INT_REGISTER + PPC_SR8:            info->i = ppc->sr[8];                   break;
1467      case CPUINFO_INT_REGISTER + PPC_SR9:            info->i = ppc->sr[9];                   break;
1468      case CPUINFO_INT_REGISTER + PPC_SR10:           info->i = ppc->sr[10];                  break;
1469      case CPUINFO_INT_REGISTER + PPC_SR11:           info->i = ppc->sr[11];                  break;
1470      case CPUINFO_INT_REGISTER + PPC_SR12:           info->i = ppc->sr[12];                  break;
1471      case CPUINFO_INT_REGISTER + PPC_SR13:           info->i = ppc->sr[13];                  break;
1472      case CPUINFO_INT_REGISTER + PPC_SR14:           info->i = ppc->sr[14];                  break;
1473      case CPUINFO_INT_REGISTER + PPC_SR15:           info->i = ppc->sr[15];                  break;
1474
1475      case CPUINFO_INT_REGISTER + PPC_R0:             info->i = ppc->r[0];                    break;
1476      case CPUINFO_INT_REGISTER + PPC_R1:             info->i = ppc->r[1];                    break;
1477      case CPUINFO_INT_REGISTER + PPC_R2:             info->i = ppc->r[2];                    break;
1478      case CPUINFO_INT_REGISTER + PPC_R3:             info->i = ppc->r[3];                    break;
1479      case CPUINFO_INT_REGISTER + PPC_R4:             info->i = ppc->r[4];                    break;
1480      case CPUINFO_INT_REGISTER + PPC_R5:             info->i = ppc->r[5];                    break;
1481      case CPUINFO_INT_REGISTER + PPC_R6:             info->i = ppc->r[6];                    break;
1482      case CPUINFO_INT_REGISTER + PPC_R7:             info->i = ppc->r[7];                    break;
1483      case CPUINFO_INT_REGISTER + PPC_R8:             info->i = ppc->r[8];                    break;
1484      case CPUINFO_INT_REGISTER + PPC_R9:             info->i = ppc->r[9];                    break;
1485      case CPUINFO_INT_REGISTER + PPC_R10:            info->i = ppc->r[10];                   break;
1486      case CPUINFO_INT_REGISTER + PPC_R11:            info->i = ppc->r[11];                   break;
1487      case CPUINFO_INT_REGISTER + PPC_R12:            info->i = ppc->r[12];                   break;
1488      case CPUINFO_INT_REGISTER + PPC_R13:            info->i = ppc->r[13];                   break;
1489      case CPUINFO_INT_REGISTER + PPC_R14:            info->i = ppc->r[14];                   break;
1490      case CPUINFO_INT_REGISTER + PPC_R15:            info->i = ppc->r[15];                   break;
1491      case CPUINFO_INT_REGISTER + PPC_R16:            info->i = ppc->r[16];                   break;
1492      case CPUINFO_INT_REGISTER + PPC_R17:            info->i = ppc->r[17];                   break;
1493      case CPUINFO_INT_REGISTER + PPC_R18:            info->i = ppc->r[18];                   break;
1494      case CPUINFO_INT_REGISTER + PPC_R19:            info->i = ppc->r[19];                   break;
1495      case CPUINFO_INT_REGISTER + PPC_R20:            info->i = ppc->r[20];                   break;
1496      case CPUINFO_INT_REGISTER + PPC_R21:            info->i = ppc->r[21];                   break;
1497      case CPUINFO_INT_REGISTER + PPC_R22:            info->i = ppc->r[22];                   break;
1498      case CPUINFO_INT_REGISTER + PPC_R23:            info->i = ppc->r[23];                   break;
1499      case CPUINFO_INT_REGISTER + PPC_R24:            info->i = ppc->r[24];                   break;
1500      case CPUINFO_INT_REGISTER + PPC_R25:            info->i = ppc->r[25];                   break;
1501      case CPUINFO_INT_REGISTER + PPC_R26:            info->i = ppc->r[26];                   break;
1502      case CPUINFO_INT_REGISTER + PPC_R27:            info->i = ppc->r[27];                   break;
1503      case CPUINFO_INT_REGISTER + PPC_R28:            info->i = ppc->r[28];                   break;
1504      case CPUINFO_INT_REGISTER + PPC_R29:            info->i = ppc->r[29];                   break;
1505      case CPUINFO_INT_REGISTER + PPC_R30:            info->i = ppc->r[30];                   break;
1506      case CPUINFO_INT_SP:
1507      case CPUINFO_INT_REGISTER + PPC_R31:            info->i = ppc->r[31];                   break;
1508
1509      case CPUINFO_INT_REGISTER + PPC_F0:             info->i = *(UINT64 *)&ppc->f[0];        break;
1510      case CPUINFO_INT_REGISTER + PPC_F1:             info->i = *(UINT64 *)&ppc->f[1];        break;
1511      case CPUINFO_INT_REGISTER + PPC_F2:             info->i = *(UINT64 *)&ppc->f[2];        break;
1512      case CPUINFO_INT_REGISTER + PPC_F3:             info->i = *(UINT64 *)&ppc->f[3];        break;
1513      case CPUINFO_INT_REGISTER + PPC_F4:             info->i = *(UINT64 *)&ppc->f[4];        break;
1514      case CPUINFO_INT_REGISTER + PPC_F5:             info->i = *(UINT64 *)&ppc->f[5];        break;
1515      case CPUINFO_INT_REGISTER + PPC_F6:             info->i = *(UINT64 *)&ppc->f[6];        break;
1516      case CPUINFO_INT_REGISTER + PPC_F7:             info->i = *(UINT64 *)&ppc->f[7];        break;
1517      case CPUINFO_INT_REGISTER + PPC_F8:             info->i = *(UINT64 *)&ppc->f[8];        break;
1518      case CPUINFO_INT_REGISTER + PPC_F9:             info->i = *(UINT64 *)&ppc->f[9];        break;
1519      case CPUINFO_INT_REGISTER + PPC_F10:            info->i = *(UINT64 *)&ppc->f[10];       break;
1520      case CPUINFO_INT_REGISTER + PPC_F11:            info->i = *(UINT64 *)&ppc->f[11];       break;
1521      case CPUINFO_INT_REGISTER + PPC_F12:            info->i = *(UINT64 *)&ppc->f[12];       break;
1522      case CPUINFO_INT_REGISTER + PPC_F13:            info->i = *(UINT64 *)&ppc->f[13];       break;
1523      case CPUINFO_INT_REGISTER + PPC_F14:            info->i = *(UINT64 *)&ppc->f[14];       break;
1524      case CPUINFO_INT_REGISTER + PPC_F15:            info->i = *(UINT64 *)&ppc->f[15];       break;
1525      case CPUINFO_INT_REGISTER + PPC_F16:            info->i = *(UINT64 *)&ppc->f[16];       break;
1526      case CPUINFO_INT_REGISTER + PPC_F17:            info->i = *(UINT64 *)&ppc->f[17];       break;
1527      case CPUINFO_INT_REGISTER + PPC_F18:            info->i = *(UINT64 *)&ppc->f[18];       break;
1528      case CPUINFO_INT_REGISTER + PPC_F19:            info->i = *(UINT64 *)&ppc->f[19];       break;
1529      case CPUINFO_INT_REGISTER + PPC_F20:            info->i = *(UINT64 *)&ppc->f[20];       break;
1530      case CPUINFO_INT_REGISTER + PPC_F21:            info->i = *(UINT64 *)&ppc->f[21];       break;
1531      case CPUINFO_INT_REGISTER + PPC_F22:            info->i = *(UINT64 *)&ppc->f[22];       break;
1532      case CPUINFO_INT_REGISTER + PPC_F23:            info->i = *(UINT64 *)&ppc->f[23];       break;
1533      case CPUINFO_INT_REGISTER + PPC_F24:            info->i = *(UINT64 *)&ppc->f[24];       break;
1534      case CPUINFO_INT_REGISTER + PPC_F25:            info->i = *(UINT64 *)&ppc->f[25];       break;
1535      case CPUINFO_INT_REGISTER + PPC_F26:            info->i = *(UINT64 *)&ppc->f[26];       break;
1536      case CPUINFO_INT_REGISTER + PPC_F27:            info->i = *(UINT64 *)&ppc->f[27];       break;
1537      case CPUINFO_INT_REGISTER + PPC_F28:            info->i = *(UINT64 *)&ppc->f[28];       break;
1538      case CPUINFO_INT_REGISTER + PPC_F29:            info->i = *(UINT64 *)&ppc->f[29];       break;
1539      case CPUINFO_INT_REGISTER + PPC_F30:            info->i = *(UINT64 *)&ppc->f[30];       break;
1540      case CPUINFO_INT_REGISTER + PPC_F31:            info->i = *(UINT64 *)&ppc->f[31];       break;
1541      case CPUINFO_INT_REGISTER + PPC_FPSCR:          info->i = ppc->fpscr;                   break;
1542
1543      /* --- the following bits of info are returned as pointers to data or functions --- */
1544      case CPUINFO_FCT_SET_INFO:                      /* provided by core */                  break;
1545      case CPUINFO_FCT_INIT:                          /* provided by core */                  break;
1546      case CPUINFO_FCT_RESET:                         /* provided by core */                  break;
1547      case CPUINFO_FCT_EXIT:                          /* provided by core */                  break;
1548      case CPUINFO_FCT_EXECUTE:                       /* provided by core */                  break;
1549      case CPUINFO_FCT_TRANSLATE:                     /* provided by core */                  break;
1550      case CPUINFO_FCT_DISASSEMBLE:                   /* provided by core */                  break;
1551      case CPUINFO_PTR_INSTRUCTION_COUNTER:           info->icount = &ppc->icount;            break;
1552
1553      /* --- the following bits of info are returned as NULL-terminated strings --- */
1554      case CPUINFO_STR_NAME:                          strcpy(info->s, "PowerPC");             break;
1555      case CPUINFO_STR_SHORTNAME:                     strcpy(info->s, "ppc");             break;
1556      case CPUINFO_STR_FAMILY:                    strcpy(info->s, "PowerPC");             break;
1557      case CPUINFO_STR_VERSION:                   strcpy(info->s, "2.0");                 break;
1558      case CPUINFO_STR_SOURCE_FILE:                       /* provided by core */                  break;
1559      case CPUINFO_STR_CREDITS:                   strcpy(info->s, "Copyright Aaron Giles"); break;
1560
1561      case CPUINFO_STR_FLAGS:                         strcpy(info->s, " ");                   break;
1562
1563      case CPUINFO_STR_REGISTER + PPC_PC:             sprintf(info->s, "PC: %08X", ppc->pc);              break;
1564      case CPUINFO_STR_REGISTER + PPC_MSR:            sprintf(info->s, "MSR:%08X", ppc->msr);             break;
1565      case CPUINFO_STR_REGISTER + PPC_CR:             sprintf(info->s, "CR: %08X", get_cr(ppc));          break;
1566      case CPUINFO_STR_REGISTER + PPC_LR:             sprintf(info->s, "LR: %08X", ppc->spr[SPR_LR]);     break;
1567      case CPUINFO_STR_REGISTER + PPC_CTR:            sprintf(info->s, "CTR:%08X", ppc->spr[SPR_CTR]);    break;
1568      case CPUINFO_STR_REGISTER + PPC_XER:            sprintf(info->s, "XER:%08X", get_xer(ppc));         break;
1569      case CPUINFO_STR_REGISTER + PPC_SRR0:           sprintf(info->s, "SRR0: %08X", ppc->spr[SPROEA_SRR0]);  break;
1570      case CPUINFO_STR_REGISTER + PPC_SRR1:           sprintf(info->s, "SRR1: %08X", ppc->spr[SPROEA_SRR1]);  break;
1571      case CPUINFO_STR_REGISTER + PPC_SPRG0:          sprintf(info->s, "SPRG0: %08X", ppc->spr[SPROEA_SPRG0]); break;
1572      case CPUINFO_STR_REGISTER + PPC_SPRG1:          sprintf(info->s, "SPRG1: %08X", ppc->spr[SPROEA_SPRG1]); break;
1573      case CPUINFO_STR_REGISTER + PPC_SPRG2:          sprintf(info->s, "SPRG2: %08X", ppc->spr[SPROEA_SPRG2]); break;
1574      case CPUINFO_STR_REGISTER + PPC_SPRG3:          sprintf(info->s, "SPRG3: %08X", ppc->spr[SPROEA_SPRG3]); break;
1575      case CPUINFO_STR_REGISTER + PPC_SDR1:           sprintf(info->s, "SDR1: %08X", ppc->spr[SPROEA_SDR1]); break;
1576      case CPUINFO_STR_REGISTER + PPC_EXIER:          sprintf(info->s, "EXIER: %08X", ppc->dcr[DCR4XX_EXIER]); break;
1577      case CPUINFO_STR_REGISTER + PPC_EXISR:          sprintf(info->s, "EXISR: %08X", ppc->dcr[DCR4XX_EXISR]); break;
1578      case CPUINFO_STR_REGISTER + PPC_EVPR:           sprintf(info->s, "EVPR: %08X", ppc->spr[SPR4XX_EVPR]); break;
1579      case CPUINFO_STR_REGISTER + PPC_IOCR:           sprintf(info->s, "IOCR: %08X", ppc->dcr[DCR4XX_EXISR]); break;
1580      case CPUINFO_STR_REGISTER + PPC_TBH:            sprintf(info->s, "TBH: %08X", (UINT32)(get_timebase(ppc) >> 32)); break;
1581      case CPUINFO_STR_REGISTER + PPC_TBL:            sprintf(info->s, "TBL: %08X", (UINT32)get_timebase(ppc)); break;
1582      case CPUINFO_STR_REGISTER + PPC_DEC:            sprintf(info->s, "DEC: %08X", get_decrementer(ppc)); break;
1583
1584      case CPUINFO_STR_REGISTER + PPC_SR0:            sprintf(info->s, "SR0: %08X", ppc->sr[0]); break;
1585      case CPUINFO_STR_REGISTER + PPC_SR1:            sprintf(info->s, "SR1: %08X", ppc->sr[1]); break;
1586      case CPUINFO_STR_REGISTER + PPC_SR2:            sprintf(info->s, "SR2: %08X", ppc->sr[2]); break;
1587      case CPUINFO_STR_REGISTER + PPC_SR3:            sprintf(info->s, "SR3: %08X", ppc->sr[3]); break;
1588      case CPUINFO_STR_REGISTER + PPC_SR4:            sprintf(info->s, "SR4: %08X", ppc->sr[4]); break;
1589      case CPUINFO_STR_REGISTER + PPC_SR5:            sprintf(info->s, "SR5: %08X", ppc->sr[5]); break;
1590      case CPUINFO_STR_REGISTER + PPC_SR6:            sprintf(info->s, "SR6: %08X", ppc->sr[6]); break;
1591      case CPUINFO_STR_REGISTER + PPC_SR7:            sprintf(info->s, "SR7: %08X", ppc->sr[7]); break;
1592      case CPUINFO_STR_REGISTER + PPC_SR8:            sprintf(info->s, "SR8: %08X", ppc->sr[8]); break;
1593      case CPUINFO_STR_REGISTER + PPC_SR9:            sprintf(info->s, "SR9: %08X", ppc->sr[9]); break;
1594      case CPUINFO_STR_REGISTER + PPC_SR10:           sprintf(info->s, "SR10: %08X", ppc->sr[10]); break;
1595      case CPUINFO_STR_REGISTER + PPC_SR11:           sprintf(info->s, "SR11: %08X", ppc->sr[11]); break;
1596      case CPUINFO_STR_REGISTER + PPC_SR12:           sprintf(info->s, "SR12: %08X", ppc->sr[12]); break;
1597      case CPUINFO_STR_REGISTER + PPC_SR13:           sprintf(info->s, "SR13: %08X", ppc->sr[13]); break;
1598      case CPUINFO_STR_REGISTER + PPC_SR14:           sprintf(info->s, "SR14: %08X", ppc->sr[14]); break;
1599      case CPUINFO_STR_REGISTER + PPC_SR15:           sprintf(info->s, "SR15: %08X", ppc->sr[15]); break;
1600
1601      case CPUINFO_STR_REGISTER + PPC_R0:             sprintf(info->s, "R0: %08X", ppc->r[0]); break;
1602      case CPUINFO_STR_REGISTER + PPC_R1:             sprintf(info->s, "R1: %08X", ppc->r[1]); break;
1603      case CPUINFO_STR_REGISTER + PPC_R2:             sprintf(info->s, "R2: %08X", ppc->r[2]); break;
1604      case CPUINFO_STR_REGISTER + PPC_R3:             sprintf(info->s, "R3: %08X", ppc->r[3]); break;
1605      case CPUINFO_STR_REGISTER + PPC_R4:             sprintf(info->s, "R4: %08X", ppc->r[4]); break;
1606      case CPUINFO_STR_REGISTER + PPC_R5:             sprintf(info->s, "R5: %08X", ppc->r[5]); break;
1607      case CPUINFO_STR_REGISTER + PPC_R6:             sprintf(info->s, "R6: %08X", ppc->r[6]); break;
1608      case CPUINFO_STR_REGISTER + PPC_R7:             sprintf(info->s, "R7: %08X", ppc->r[7]); break;
1609      case CPUINFO_STR_REGISTER + PPC_R8:             sprintf(info->s, "R8: %08X", ppc->r[8]); break;
1610      case CPUINFO_STR_REGISTER + PPC_R9:             sprintf(info->s, "R9: %08X", ppc->r[9]); break;
1611      case CPUINFO_STR_REGISTER + PPC_R10:            sprintf(info->s, "R10:%08X", ppc->r[10]); break;
1612      case CPUINFO_STR_REGISTER + PPC_R11:            sprintf(info->s, "R11:%08X", ppc->r[11]); break;
1613      case CPUINFO_STR_REGISTER + PPC_R12:            sprintf(info->s, "R12:%08X", ppc->r[12]); break;
1614      case CPUINFO_STR_REGISTER + PPC_R13:            sprintf(info->s, "R13:%08X", ppc->r[13]); break;
1615      case CPUINFO_STR_REGISTER + PPC_R14:            sprintf(info->s, "R14:%08X", ppc->r[14]); break;
1616      case CPUINFO_STR_REGISTER + PPC_R15:            sprintf(info->s, "R15:%08X", ppc->r[15]); break;
1617      case CPUINFO_STR_REGISTER + PPC_R16:            sprintf(info->s, "R16:%08X", ppc->r[16]); break;
1618      case CPUINFO_STR_REGISTER + PPC_R17:            sprintf(info->s, "R17:%08X", ppc->r[17]); break;
1619      case CPUINFO_STR_REGISTER + PPC_R18:            sprintf(info->s, "R18:%08X", ppc->r[18]); break;
1620      case CPUINFO_STR_REGISTER + PPC_R19:            sprintf(info->s, "R19:%08X", ppc->r[19]); break;
1621      case CPUINFO_STR_REGISTER + PPC_R20:            sprintf(info->s, "R20:%08X", ppc->r[20]); break;
1622      case CPUINFO_STR_REGISTER + PPC_R21:            sprintf(info->s, "R21:%08X", ppc->r[21]); break;
1623      case CPUINFO_STR_REGISTER + PPC_R22:            sprintf(info->s, "R22:%08X", ppc->r[22]); break;
1624      case CPUINFO_STR_REGISTER + PPC_R23:            sprintf(info->s, "R23:%08X", ppc->r[23]); break;
1625      case CPUINFO_STR_REGISTER + PPC_R24:            sprintf(info->s, "R24:%08X", ppc->r[24]); break;
1626      case CPUINFO_STR_REGISTER + PPC_R25:            sprintf(info->s, "R25:%08X", ppc->r[25]); break;
1627      case CPUINFO_STR_REGISTER + PPC_R26:            sprintf(info->s, "R26:%08X", ppc->r[26]); break;
1628      case CPUINFO_STR_REGISTER + PPC_R27:            sprintf(info->s, "R27:%08X", ppc->r[27]); break;
1629      case CPUINFO_STR_REGISTER + PPC_R28:            sprintf(info->s, "R28:%08X", ppc->r[28]); break;
1630      case CPUINFO_STR_REGISTER + PPC_R29:            sprintf(info->s, "R29:%08X", ppc->r[29]); break;
1631      case CPUINFO_STR_REGISTER + PPC_R30:            sprintf(info->s, "R30:%08X", ppc->r[30]); break;
1632      case CPUINFO_STR_REGISTER + PPC_R31:            sprintf(info->s, "R31:%08X", ppc->r[31]); break;
1633
1634      case CPUINFO_STR_REGISTER + PPC_F0:             sprintf(info->s, "F0: %12f", ppc->f[0]); break;
1635      case CPUINFO_STR_REGISTER + PPC_F1:             sprintf(info->s, "F1: %12f", ppc->f[1]); break;
1636      case CPUINFO_STR_REGISTER + PPC_F2:             sprintf(info->s, "F2: %12f", ppc->f[2]); break;
1637      case CPUINFO_STR_REGISTER + PPC_F3:             sprintf(info->s, "F3: %12f", ppc->f[3]); break;
1638      case CPUINFO_STR_REGISTER + PPC_F4:             sprintf(info->s, "F4: %12f", ppc->f[4]); break;
1639      case CPUINFO_STR_REGISTER + PPC_F5:             sprintf(info->s, "F5: %12f", ppc->f[5]); break;
1640      case CPUINFO_STR_REGISTER + PPC_F6:             sprintf(info->s, "F6: %12f", ppc->f[6]); break;
1641      case CPUINFO_STR_REGISTER + PPC_F7:             sprintf(info->s, "F7: %12f", ppc->f[7]); break;
1642      case CPUINFO_STR_REGISTER + PPC_F8:             sprintf(info->s, "F8: %12f", ppc->f[8]); break;
1643      case CPUINFO_STR_REGISTER + PPC_F9:             sprintf(info->s, "F9: %12f", ppc->f[9]); break;
1644      case CPUINFO_STR_REGISTER + PPC_F10:            sprintf(info->s, "F10:%12f", ppc->f[10]); break;
1645      case CPUINFO_STR_REGISTER + PPC_F11:            sprintf(info->s, "F11:%12f", ppc->f[11]); break;
1646      case CPUINFO_STR_REGISTER + PPC_F12:            sprintf(info->s, "F12:%12f", ppc->f[12]); break;
1647      case CPUINFO_STR_REGISTER + PPC_F13:            sprintf(info->s, "F13:%12f", ppc->f[13]); break;
1648      case CPUINFO_STR_REGISTER + PPC_F14:            sprintf(info->s, "F14:%12f", ppc->f[14]); break;
1649      case CPUINFO_STR_REGISTER + PPC_F15:            sprintf(info->s, "F15:%12f", ppc->f[15]); break;
1650      case CPUINFO_STR_REGISTER + PPC_F16:            sprintf(info->s, "F16:%12f", ppc->f[16]); break;
1651      case CPUINFO_STR_REGISTER + PPC_F17:            sprintf(info->s, "F17:%12f", ppc->f[17]); break;
1652      case CPUINFO_STR_REGISTER + PPC_F18:            sprintf(info->s, "F18:%12f", ppc->f[18]); break;
1653      case CPUINFO_STR_REGISTER + PPC_F19:            sprintf(info->s, "F19:%12f", ppc->f[19]); break;
1654      case CPUINFO_STR_REGISTER + PPC_F20:            sprintf(info->s, "F20:%12f", ppc->f[20]); break;
1655      case CPUINFO_STR_REGISTER + PPC_F21:            sprintf(info->s, "F21:%12f", ppc->f[21]); break;
1656      case CPUINFO_STR_REGISTER + PPC_F22:            sprintf(info->s, "F22:%12f", ppc->f[22]); break;
1657      case CPUINFO_STR_REGISTER + PPC_F23:            sprintf(info->s, "F23:%12f", ppc->f[23]); break;
1658      case CPUINFO_STR_REGISTER + PPC_F24:            sprintf(info->s, "F24:%12f", ppc->f[24]); break;
1659      case CPUINFO_STR_REGISTER + PPC_F25:            sprintf(info->s, "F25:%12f", ppc->f[25]); break;
1660      case CPUINFO_STR_REGISTER + PPC_F26:            sprintf(info->s, "F26:%12f", ppc->f[26]); break;
1661      case CPUINFO_STR_REGISTER + PPC_F27:            sprintf(info->s, "F27:%12f", ppc->f[27]); break;
1662      case CPUINFO_STR_REGISTER + PPC_F28:            sprintf(info->s, "F28:%12f", ppc->f[28]); break;
1663      case CPUINFO_STR_REGISTER + PPC_F29:            sprintf(info->s, "F29:%12f", ppc->f[29]); break;
1664      case CPUINFO_STR_REGISTER + PPC_F30:            sprintf(info->s, "F30:%12f", ppc->f[30]); break;
1665      case CPUINFO_STR_REGISTER + PPC_F31:            sprintf(info->s, "F31:%12f", ppc->f[31]); break;
1666      case CPUINFO_STR_REGISTER + PPC_FPSCR:          sprintf(info->s, "FPSCR:%08X", ppc->fpscr); break;
2073void ppc_device::execute_set_input(int inputnum, int state)
2074{
2075   switch (inputnum)
2076   {
2077      case PPC_IRQ:
2078         m_core->irq_pending = (m_core->irq_pending & ~1) | ((state != CLEAR_LINE) ? 1 : 0);
2079         break;
16672080   }
16682081}
16692082
16702083
1671
1672/***************************************************************************
1673    OEA HELPERS
1674***************************************************************************/
1675
1676/*-------------------------------------------------
1677    decrementer_int_callback - callback that fires
1678    whenever a decrementer interrupt is generated
1679-------------------------------------------------*/
1680
1681static TIMER_CALLBACK( decrementer_int_callback )
2084void ppc4xx_device::execute_set_input(int inputnum, int state)
16822085{
1683   powerpc_state *ppc = (powerpc_state *)ptr;
1684   UINT64 cycles_until_next;
2086   switch (inputnum)
2087   {
2088      case PPC_IRQ_LINE_0:
2089         ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_EXT0, state);
2090         break;
16852091
1686   /* set the decrementer IRQ state */
1687   ppc->irq_pending |= 0x02;
2092      case PPC_IRQ_LINE_1:
2093         ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_EXT1, state);
2094         break;
16882095
1689   /* advance by another full rev */
1690   ppc->dec_zero_cycles += (UINT64)ppc->tb_divisor << 32;
1691   cycles_until_next = ppc->dec_zero_cycles - ppc->device->total_cycles();
1692   ppc->decrementer_int_timer->adjust(ppc->device->cycles_to_attotime(cycles_until_next));
1693}
2096      case PPC_IRQ_LINE_2:
2097         ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_EXT2, state);
2098         break;
16942099
1695/*-------------------------------------------------
1696    ppc_set_dcstore_callback - installs a callback
1697    for detecting datacache stores with dcbst
1698-------------------------------------------------*/
2100      case PPC_IRQ_LINE_3:
2101         ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_EXT3, state);
2102         break;
16992103
1700void ppc_set_dcstore_callback(device_t *device, ppc_dcstore_handler handler)
1701{
1702   powerpc_state *ppc = *(powerpc_state **)downcast<legacy_cpu_device *>(device)->token();
1703   ppc->dcstore_handler = handler;
2104      case PPC_IRQ_LINE_4:
2105         ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_EXT4, state);
2106         break;
2107   }
17042108}
17052109
17062110
r31142r31143
17132117    IRQ line management
17142118-------------------------------------------------*/
17152119
1716static void ppc4xx_set_irq_line(powerpc_state *ppc, UINT32 bitmask, int state)
2120void ppc_device::ppc4xx_set_irq_line(UINT32 bitmask, int state)
17172121{
1718   UINT32 oldstate = ppc->irqstate;
2122   UINT32 oldstate = m_irqstate;
17192123   UINT32 levelmask;
17202124
17212125   /* set or clear the appropriate bit */
17222126   if (state != CLEAR_LINE)
1723      ppc->irqstate |= bitmask;
2127      m_irqstate |= bitmask;
17242128   else
1725      ppc->irqstate &= ~bitmask;
2129      m_irqstate &= ~bitmask;
17262130
17272131   /* if the state changed to on, edge trigger the interrupt */
1728   if (((ppc->irqstate ^ oldstate) & bitmask) && (ppc->irqstate & bitmask))
1729      ppc->dcr[DCR4XX_EXISR] |= bitmask;
2132   if (((m_irqstate ^ oldstate) & bitmask) && (m_irqstate & bitmask))
2133      m_dcr[DCR4XX_EXISR] |= bitmask;
17302134
17312135   /* pass through all level-triggered interrupts */
17322136   levelmask = PPC4XX_IRQ_BIT_CRITICAL | PPC4XX_IRQ_BIT_SPUR | PPC4XX_IRQ_BIT_SPUT;
17332137   levelmask |= PPC4XX_IRQ_BIT_JTAGR | PPC4XX_IRQ_BIT_JTAGT;
17342138   levelmask |= PPC4XX_IRQ_BIT_DMA0 | PPC4XX_IRQ_BIT_DMA1 | PPC4XX_IRQ_BIT_DMA2 | PPC4XX_IRQ_BIT_DMA3;
1735   if (!(ppc->dcr[DCR4XX_IOCR] & 0x80000000)) levelmask |= PPC4XX_IRQ_BIT_EXT0;
1736   if (!(ppc->dcr[DCR4XX_IOCR] & 0x20000000)) levelmask |= PPC4XX_IRQ_BIT_EXT1;
1737   if (!(ppc->dcr[DCR4XX_IOCR] & 0x08000000)) levelmask |= PPC4XX_IRQ_BIT_EXT2;
1738   if (!(ppc->dcr[DCR4XX_IOCR] & 0x02000000)) levelmask |= PPC4XX_IRQ_BIT_EXT3;
1739   if (!(ppc->dcr[DCR4XX_IOCR] & 0x00800000)) levelmask |= PPC4XX_IRQ_BIT_EXT4;
1740   ppc->dcr[DCR4XX_EXISR] = (ppc->dcr[DCR4XX_EXISR] & ~levelmask) | (ppc->irqstate & levelmask);
2139   if (!(m_dcr[DCR4XX_IOCR] & 0x80000000)) levelmask |= PPC4XX_IRQ_BIT_EXT0;
2140   if (!(m_dcr[DCR4XX_IOCR] & 0x20000000)) levelmask |= PPC4XX_IRQ_BIT_EXT1;
2141   if (!(m_dcr[DCR4XX_IOCR] & 0x08000000)) levelmask |= PPC4XX_IRQ_BIT_EXT2;
2142   if (!(m_dcr[DCR4XX_IOCR] & 0x02000000)) levelmask |= PPC4XX_IRQ_BIT_EXT3;
2143   if (!(m_dcr[DCR4XX_IOCR] & 0x00800000)) levelmask |= PPC4XX_IRQ_BIT_EXT4;
2144   m_dcr[DCR4XX_EXISR] = (m_dcr[DCR4XX_EXISR] & ~levelmask) | (m_irqstate & levelmask);
17412145
17422146   /* update the IRQ status */
1743   ppc->irq_pending = ((ppc->dcr[DCR4XX_EXISR] & ppc->dcr[DCR4XX_EXIER]) != 0);
1744   if ((ppc->spr[SPR4XX_TCR] & PPC4XX_TCR_FIE) && (ppc->spr[SPR4XX_TSR] & PPC4XX_TSR_FIS))
1745      ppc->irq_pending = TRUE;
1746   if ((ppc->spr[SPR4XX_TCR] & PPC4XX_TCR_PIE) && (ppc->spr[SPR4XX_TSR] & PPC4XX_TSR_PIS))
1747      ppc->irq_pending = TRUE;
2147   m_core->irq_pending = ((m_dcr[DCR4XX_EXISR] & m_dcr[DCR4XX_EXIER]) != 0);
2148   if ((m_core->spr[SPR4XX_TCR] & PPC4XX_TCR_FIE) && (m_core->spr[SPR4XX_TSR] & PPC4XX_TSR_FIS))
2149      m_core->irq_pending = TRUE;
2150   if ((m_core->spr[SPR4XX_TCR] & PPC4XX_TCR_PIE) && (m_core->spr[SPR4XX_TSR] & PPC4XX_TSR_PIS))
2151      m_core->irq_pending = TRUE;
17482152}
17492153
17502154
r31142r31143
17532157    IRQ line state getter
17542158-------------------------------------------------*/
17552159
1756static int ppc4xx_get_irq_line(powerpc_state *ppc, UINT32 bitmask)
2160int ppc_device::ppc4xx_get_irq_line(UINT32 bitmask)
17572161{
1758   return (ppc->irqstate & bitmask) ? ASSERT_LINE : CLEAR_LINE;
2162   return (m_irqstate & bitmask) ? ASSERT_LINE : CLEAR_LINE;
17592163}
17602164
17612165
r31142r31143
17642168    state for each DMA channel
17652169-------------------------------------------------*/
17662170
1767static void ppc4xx_dma_update_irq_states(powerpc_state *ppc)
2171void ppc_device::ppc4xx_dma_update_irq_states()
17682172{
17692173   /* update the IRQ state for each DMA channel */
17702174   for (int dmachan = 0; dmachan < 4; dmachan++)
r31142r31143
17722176      bool irq_pending = false;
17732177
17742178      // Channel interrupt enabled?
1775      if ((ppc->dcr[DCR4XX_DMACR0 + 8 * dmachan] & PPC4XX_DMACR_CIE))
2179      if ((m_dcr[DCR4XX_DMACR0 + 8 * dmachan] & PPC4XX_DMACR_CIE))
17762180      {
17772181         // Terminal count and end-of-transfer status bits
17782182         int bitmask = 0x11 << (27 - dmachan);
r31142r31143
17912195               break;
17922196         }
17932197
1794         irq_pending = (ppc->dcr[DCR4XX_DMASR] & bitmask) != 0;
2198         irq_pending = (m_dcr[DCR4XX_DMASR] & bitmask) != 0;
17952199      }
17962200
1797      ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_DMA(dmachan), irq_pending ? ASSERT_LINE : CLEAR_LINE);
2201      ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_DMA(dmachan), irq_pending ? ASSERT_LINE : CLEAR_LINE);
17982202   }
17992203}
18002204
r31142r31143
18052209    to do so
18062210-------------------------------------------------*/
18072211
1808static int ppc4xx_dma_decrement_count(powerpc_state *ppc, int dmachan)
2212int ppc_device::ppc4xx_dma_decrement_count(int dmachan)
18092213{
1810   UINT32 *dmaregs = &ppc->dcr[8 * dmachan];
2214   UINT32 *dmaregs = &m_dcr[8 * dmachan];
18112215
18122216   /* decrement the counter */
18132217   dmaregs[DCR4XX_DMACT0]--;
r31142r31143
18262230      switch (dmachan)
18272231      {
18282232         case 0:
1829            ppc->dcr[DCR4XX_DMASR] |= 0x00080000;
2233            m_dcr[DCR4XX_DMASR] |= 0x00080000;
18302234            break;
18312235
18322236         case 1:
18332237         case 2:
18342238         case 3:
1835            ppc->dcr[DCR4XX_DMASR] |= 1 << (7 - dmachan);
2239            m_dcr[DCR4XX_DMASR] |= 1 << (7 - dmachan);
18362240            break;
18372241      }
18382242
1839      ppc4xx_dma_update_irq_states(ppc);
2243      ppc4xx_dma_update_irq_states();
18402244
18412245      INT64 numdata = dmaregs[DCR4XX_DMACT0];
18422246      if (numdata == 0)
18432247         numdata = 65536;
18442248
1845      INT64 time = (numdata * 1000000) / ppc->buffered_dma_rate[dmachan];
2249      INT64 time = (numdata * 1000000) / m_buffered_dma_rate[dmachan];
18462250
1847      ppc->buffered_dma_timer[dmachan]->adjust(attotime::from_usec(time), dmachan);
2251      m_buffered_dma_timer[dmachan]->adjust(attotime::from_usec(time), dmachan);
18482252   }
18492253   else
18502254   {
18512255      /* set the complete bit and handle interrupts */
1852      ppc->dcr[DCR4XX_DMASR] |= 1 << (31 - dmachan);
1853   //  ppc->dcr[DCR4XX_DMASR] |= 1 << (27 - dmachan);
1854      ppc4xx_dma_update_irq_states(ppc);
2256      m_dcr[DCR4XX_DMASR] |= 1 << (31 - dmachan);
2257   //  m_dcr[DCR4XX_DMASR] |= 1 << (27 - dmachan);
2258      ppc4xx_dma_update_irq_states();
18552259
1856      ppc->buffered_dma_timer[dmachan]->adjust(attotime::never, FALSE);
2260      m_buffered_dma_timer[dmachan]->adjust(attotime::never, FALSE);
18572261   }
18582262   return TRUE;
18592263}
r31142r31143
18642268    when buffered DMA transfer is ready
18652269-------------------------------------------------*/
18662270
1867static TIMER_CALLBACK( ppc4xx_buffered_dma_callback )
2271TIMER_CALLBACK_MEMBER( ppc_device::ppc4xx_buffered_dma_callback )
18682272{
1869   powerpc_state *ppc = (powerpc_state *)ptr;
18702273   int dmachan = param;
18712274
18722275   static const UINT8 dma_transfer_width[4] = { 1, 2, 4, 16 };
1873   UINT32 *dmaregs = &ppc->dcr[8 * dmachan];
2276   UINT32 *dmaregs = &m_dcr[8 * dmachan];
18742277   INT32 destinc;
18752278   UINT8 width;
18762279
r31142r31143
18882291         do
18892292         {
18902293            UINT8 data = 0;
1891            if (ppc->ext_dma_read_handler[dmachan] != NULL)
1892               data = (*ppc->ext_dma_read_handler[dmachan])(ppc->device, 1);
1893            ppc->program->write_byte(dmaregs[DCR4XX_DMADA0], data);
2294            if (m_ext_dma_read_handler[dmachan] != NULL)
2295               data = (*m_ext_dma_read_handler[dmachan])(this, 1);
2296            m_program->write_byte(dmaregs[DCR4XX_DMADA0], data);
18942297            dmaregs[DCR4XX_DMADA0] += destinc;
1895         } while (!ppc4xx_dma_decrement_count(ppc, dmachan));
2298         } while (!ppc4xx_dma_decrement_count(dmachan));
18962299         break;
18972300
18982301         /* word transfer */
r31142r31143
19002303         do
19012304         {
19022305            UINT16 data = 0;
1903            if (ppc->ext_dma_read_handler[dmachan] != NULL)
1904               data = (*ppc->ext_dma_read_handler[dmachan])(ppc->device, 2);
1905            ppc->program->write_word(dmaregs[DCR4XX_DMADA0], data);
2306            if (m_ext_dma_read_handler[dmachan] != NULL)
2307               data = (*m_ext_dma_read_handler[dmachan])(this, 2);
2308            m_program->write_word(dmaregs[DCR4XX_DMADA0], data);
19062309            dmaregs[DCR4XX_DMADA0] += destinc;
1907         } while (!ppc4xx_dma_decrement_count(ppc, dmachan));
2310         } while (!ppc4xx_dma_decrement_count(dmachan));
19082311         break;
19092312
19102313         /* dword transfer */
r31142r31143
19122315         do
19132316         {
19142317            UINT32 data = 0;
1915            if (ppc->ext_dma_read_handler[dmachan] != NULL)
1916               data = (*ppc->ext_dma_read_handler[dmachan])(ppc->device, 4);
1917            ppc->program->write_dword(dmaregs[DCR4XX_DMADA0], data);
2318            if (m_ext_dma_read_handler[dmachan] != NULL)
2319               data = (*m_ext_dma_read_handler[dmachan])(this, 4);
2320            m_program->write_dword(dmaregs[DCR4XX_DMADA0], data);
19182321            dmaregs[DCR4XX_DMADA0] += destinc;
1919         } while (!ppc4xx_dma_decrement_count(ppc, dmachan));
2322         } while (!ppc4xx_dma_decrement_count(dmachan));
19202323         break;
19212324      }
19222325   }
r31142r31143
19312334         case 1:
19322335         do
19332336         {
1934            UINT8 data = ppc->program->read_byte(dmaregs[DCR4XX_DMADA0]);
1935            if (ppc->ext_dma_write_handler[dmachan] != NULL)
1936               (*ppc->ext_dma_write_handler[dmachan])(ppc->device, 1, data);
2337            UINT8 data = m_program->read_byte(dmaregs[DCR4XX_DMADA0]);
2338            if (m_ext_dma_write_handler[dmachan] != NULL)
2339               (*m_ext_dma_write_handler[dmachan])(this, 1, data);
19372340            dmaregs[DCR4XX_DMADA0] += destinc;
1938         } while (!ppc4xx_dma_decrement_count(ppc, dmachan));
2341         } while (!ppc4xx_dma_decrement_count(dmachan));
19392342         break;
19402343
19412344         /* word transfer */
19422345         case 2:
19432346         do
19442347         {
1945            UINT16 data = ppc->program->read_word(dmaregs[DCR4XX_DMADA0]);
1946            if (ppc->ext_dma_write_handler[dmachan] != NULL)
1947               (*ppc->ext_dma_write_handler[dmachan])(ppc->device, 2, data);
2348            UINT16 data = m_program->read_word(dmaregs[DCR4XX_DMADA0]);
2349            if (m_ext_dma_write_handler[dmachan] != NULL)
2350               (*m_ext_dma_write_handler[dmachan])(this, 2, data);
19482351            dmaregs[DCR4XX_DMADA0] += destinc;
1949         } while (!ppc4xx_dma_decrement_count(ppc, dmachan));
2352         } while (!ppc4xx_dma_decrement_count(dmachan));
19502353         break;
19512354
19522355         /* dword transfer */
19532356         case 4:
19542357         do
19552358         {
1956            UINT32 data = ppc->program->read_dword(dmaregs[DCR4XX_DMADA0]);
1957            if (ppc->ext_dma_write_handler[dmachan] != NULL)
1958               (*ppc->ext_dma_write_handler[dmachan])(ppc->device, 4, data);
2359            UINT32 data = m_program->read_dword(dmaregs[DCR4XX_DMADA0]);
2360            if (m_ext_dma_write_handler[dmachan] != NULL)
2361               (*m_ext_dma_write_handler[dmachan])(this, 4, data);
19592362            dmaregs[DCR4XX_DMADA0] += destinc;
1960         } while (!ppc4xx_dma_decrement_count(ppc, dmachan));
2363         } while (!ppc4xx_dma_decrement_count(dmachan));
19612364         break;
19622365      }
19632366   }
r31142r31143
19692372    to send to a peripheral
19702373-------------------------------------------------*/
19712374
1972static int ppc4xx_dma_fetch_transmit_byte(powerpc_state *ppc, int dmachan, UINT8 *byte)
2375int ppc_device::ppc4xx_dma_fetch_transmit_byte(int dmachan, UINT8 *byte)
19732376{
1974   UINT32 *dmaregs = &ppc->dcr[8 * dmachan];
2377   UINT32 *dmaregs = &m_dcr[8 * dmachan];
19752378
19762379   /* if the channel is not enabled, fail */
19772380   if (!(dmaregs[DCR4XX_DMACR0] & PPC4XX_DMACR_CE))
r31142r31143
19822385      return FALSE;
19832386
19842387   /* fetch the data */
1985   *byte = ppc->program->read_byte(dmaregs[DCR4XX_DMADA0]++);
1986   ppc4xx_dma_decrement_count(ppc, dmachan);
2388   *byte = m_program->read_byte(dmaregs[DCR4XX_DMADA0]++);
2389   ppc4xx_dma_decrement_count(dmachan);
19872390   return TRUE;
19882391}
19892392
r31142r31143
19932396    transmitted by a peripheral
19942397-------------------------------------------------*/
19952398
1996static int ppc4xx_dma_handle_receive_byte(powerpc_state *ppc, int dmachan, UINT8 byte)
2399int ppc_device::ppc4xx_dma_handle_receive_byte(int dmachan, UINT8 byte)
19972400{
1998   UINT32 *dmaregs = &ppc->dcr[8 * dmachan];
2401   UINT32 *dmaregs = &m_dcr[8 * dmachan];
19992402
20002403   /* if the channel is not enabled, fail */
20012404   if (!(dmaregs[DCR4XX_DMACR0] & PPC4XX_DMACR_CE))
r31142r31143
20062409      return FALSE;
20072410
20082411   /* store the data */
2009   ppc->program->write_byte(dmaregs[DCR4XX_DMADA0]++, byte);
2010   ppc4xx_dma_decrement_count(ppc, dmachan);
2412   m_program->write_byte(dmaregs[DCR4XX_DMADA0]++, byte);
2413   ppc4xx_dma_decrement_count(dmachan);
20112414   return TRUE;
20122415}
20132416
r31142r31143
20172420    if one is pending
20182421-------------------------------------------------*/
20192422
2020static void ppc4xx_dma_exec(powerpc_state *ppc, int dmachan)
2423void ppc_device::ppc4xx_dma_exec(int dmachan)
20212424{
20222425   static const UINT8 dma_transfer_width[4] = { 1, 2, 4, 16 };
2023   UINT32 *dmaregs = &ppc->dcr[8 * dmachan];
2426   UINT32 *dmaregs = &m_dcr[8 * dmachan];
20242427   INT32 destinc, srcinc;
20252428   UINT8 width;
20262429
r31142r31143
20482451            INT64 time;
20492452            if (numdata > 100)
20502453            {
2051               time = (numdata * 1000000) / ppc->buffered_dma_rate[dmachan];
2454               time = (numdata * 1000000) / m_buffered_dma_rate[dmachan];
20522455            }
20532456            else
20542457            {
20552458               time = 0;       // let very short transfers occur instantly
20562459            }
20572460
2058            ppc->buffered_dma_timer[dmachan]->adjust(attotime::from_usec(time), dmachan);
2461            m_buffered_dma_timer[dmachan]->adjust(attotime::from_usec(time), dmachan);
20592462         }
20602463         else        /* buffered DMA with internal peripheral (SPU) */
20612464         {
r31142r31143
20802483            case 1:
20812484               do
20822485               {
2083                  ppc->program->write_byte(dmaregs[DCR4XX_DMADA0], ppc->program->read_byte(dmaregs[DCR4XX_DMASA0]));
2486                  m_program->write_byte(dmaregs[DCR4XX_DMADA0], m_program->read_byte(dmaregs[DCR4XX_DMASA0]));
20842487                  dmaregs[DCR4XX_DMASA0] += srcinc;
20852488                  dmaregs[DCR4XX_DMADA0] += destinc;
2086               } while (!ppc4xx_dma_decrement_count(ppc, dmachan));
2489               } while (!ppc4xx_dma_decrement_count(dmachan));
20872490               break;
20882491
20892492            /* word transfer */
20902493            case 2:
20912494               do
20922495               {
2093                  ppc->program->write_word(dmaregs[DCR4XX_DMADA0], ppc->program->read_word(dmaregs[DCR4XX_DMASA0]));
2496                  m_program->write_word(dmaregs[DCR4XX_DMADA0], m_program->read_word(dmaregs[DCR4XX_DMASA0]));
20942497                  dmaregs[DCR4XX_DMASA0] += srcinc;
20952498                  dmaregs[DCR4XX_DMADA0] += destinc;
2096               } while (!ppc4xx_dma_decrement_count(ppc, dmachan));
2499               } while (!ppc4xx_dma_decrement_count(dmachan));
20972500               break;
20982501
20992502            /* dword transfer */
21002503            case 4:
21012504               do
21022505               {
2103                  ppc->program->write_dword(dmaregs[DCR4XX_DMADA0], ppc->program->read_dword(dmaregs[DCR4XX_DMASA0]));
2506                  m_program->write_dword(dmaregs[DCR4XX_DMADA0], m_program->read_dword(dmaregs[DCR4XX_DMASA0]));
21042507                  dmaregs[DCR4XX_DMASA0] += srcinc;
21052508                  dmaregs[DCR4XX_DMADA0] += destinc;
2106               } while (!ppc4xx_dma_decrement_count(ppc, dmachan));
2509               } while (!ppc4xx_dma_decrement_count(dmachan));
21072510               break;
21082511
21092512            /* 16-byte transfer */
21102513            case 16:
21112514               do
21122515               {
2113                  ppc->program->write_qword(dmaregs[DCR4XX_DMADA0], ppc->program->read_qword(dmaregs[DCR4XX_DMASA0]));
2114                  ppc->program->write_qword(dmaregs[DCR4XX_DMADA0] + 8, ppc->program->read_qword(dmaregs[DCR4XX_DMASA0] + 8));
2516                  m_program->write_qword(dmaregs[DCR4XX_DMADA0], m_program->read_qword(dmaregs[DCR4XX_DMASA0]));
2517                  m_program->write_qword(dmaregs[DCR4XX_DMADA0] + 8, m_program->read_qword(dmaregs[DCR4XX_DMASA0] + 8));
21152518                  dmaregs[DCR4XX_DMASA0] += srcinc;
21162519                  dmaregs[DCR4XX_DMADA0] += destinc;
2117               } while (!ppc4xx_dma_decrement_count(ppc, dmachan));
2520               } while (!ppc4xx_dma_decrement_count(dmachan));
21182521               break;
21192522         }
21202523         break;
r31142r31143
21312534    ppc4xx_fit_callback - FIT timer callback
21322535-------------------------------------------------*/
21332536
2134static TIMER_CALLBACK( ppc4xx_fit_callback )
2537TIMER_CALLBACK_MEMBER( ppc_device::ppc4xx_fit_callback )
21352538{
2136   powerpc_state *ppc = (powerpc_state *)ptr;
2137
21382539   /* if this is a real callback and we are enabled, signal an interrupt */
21392540   if (param)
21402541   {
2141      ppc->spr[SPR4XX_TSR] |= PPC4XX_TSR_FIS;
2142      ppc4xx_set_irq_line(ppc, 0, 0);
2542      m_core->spr[SPR4XX_TSR] |= PPC4XX_TSR_FIS;
2543      ppc4xx_set_irq_line(0, 0);
21432544   }
21442545
21452546   /* update ourself for the next interval if we are enabled */
2146   if (ppc->spr[SPR4XX_TCR] & PPC4XX_TCR_FIE)
2547   if (m_core->spr[SPR4XX_TCR] & PPC4XX_TCR_FIE)
21472548   {
2148      UINT32 timebase = get_timebase(ppc);
2149      UINT32 interval = 0x200 << (4 * ((ppc->spr[SPR4XX_TCR] & PPC4XX_TCR_FP_MASK) >> 24));
2549      UINT32 timebase = get_timebase();
2550      UINT32 interval = 0x200 << (4 * ((m_core->spr[SPR4XX_TCR] & PPC4XX_TCR_FP_MASK) >> 24));
21502551      UINT32 target = (timebase + interval) & ~(interval - 1);
2151      ppc->fit_timer->adjust(ppc->device->cycles_to_attotime((target + 1 - timebase) / ppc->tb_divisor), TRUE);
2552      m_fit_timer->adjust(cycles_to_attotime((target + 1 - timebase) / m_tb_divisor), TRUE);
21522553   }
21532554
21542555   /* otherwise, turn ourself off */
21552556   else
2156      ppc->fit_timer->adjust(attotime::never, FALSE);
2557      m_fit_timer->adjust(attotime::never, FALSE);
21572558}
21582559
21592560
r31142r31143
21612562    ppc4xx_pit_callback - PIT timer callback
21622563-------------------------------------------------*/
21632564
2164static TIMER_CALLBACK( ppc4xx_pit_callback )
2565TIMER_CALLBACK_MEMBER( ppc_device::ppc4xx_pit_callback )
21652566{
2166   powerpc_state *ppc = (powerpc_state *)ptr;
2167
21682567   /* if this is a real callback and we are enabled, signal an interrupt */
21692568   if (param)
21702569   {
2171      ppc->spr[SPR4XX_TSR] |= PPC4XX_TSR_PIS;
2172      ppc4xx_set_irq_line(ppc, 0, 0);
2570      m_core->spr[SPR4XX_TSR] |= PPC4XX_TSR_PIS;
2571      ppc4xx_set_irq_line(0, 0);
21732572   }
21742573
21752574   /* update ourself for the next interval if we are enabled and we are either being
21762575      forced to update, or we are in auto-reload mode */
2177   if ((ppc->spr[SPR4XX_TCR] & PPC4XX_TCR_PIE) && ppc->pit_reload != 0 && (!param || (ppc->spr[SPR4XX_TCR] & PPC4XX_TCR_ARE)))
2576   if ((m_core->spr[SPR4XX_TCR] & PPC4XX_TCR_PIE) && m_pit_reload != 0 && (!param || (m_core->spr[SPR4XX_TCR] & PPC4XX_TCR_ARE)))
21782577   {
2179      UINT32 timebase = get_timebase(ppc);
2180      UINT32 interval = ppc->pit_reload;
2578      UINT32 timebase = get_timebase();
2579      UINT32 interval = m_pit_reload;
21812580      UINT32 target = timebase + interval;
2182      ppc->pit_timer->adjust(ppc->device->cycles_to_attotime((target + 1 - timebase) / ppc->tb_divisor), TRUE);
2581      m_pit_timer->adjust(cycles_to_attotime((target + 1 - timebase) / m_tb_divisor), TRUE);
21832582   }
21842583
21852584   /* otherwise, turn ourself off */
21862585   else
2187      ppc->pit_timer->adjust(attotime::never, FALSE);
2586      m_pit_timer->adjust(attotime::never, FALSE);
21882587}
21892588
21902589
r31142r31143
21932592    state for the SPU
21942593-------------------------------------------------*/
21952594
2196static void ppc4xx_spu_update_irq_states(powerpc_state *ppc)
2595void ppc_device::ppc4xx_spu_update_irq_states()
21972596{
21982597   /* check for receive buffer full interrupt */
2199   if ((ppc->spu.regs[SPU4XX_RX_COMMAND] & 0x60) == 0x20 && (ppc->spu.regs[SPU4XX_LINE_STATUS] & 0x80))
2200      ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_SPUR, ASSERT_LINE);
2598   if ((m_spu.regs[SPU4XX_RX_COMMAND] & 0x60) == 0x20 && (m_spu.regs[SPU4XX_LINE_STATUS] & 0x80))
2599      ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_SPUR, ASSERT_LINE);
22012600
22022601   /* check for receive error interrupt */
2203   else if ((ppc->spu.regs[SPU4XX_RX_COMMAND] & 0x10) && (ppc->spu.regs[SPU4XX_LINE_STATUS] & 0x78))
2204      ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_SPUR, ASSERT_LINE);
2602   else if ((m_spu.regs[SPU4XX_RX_COMMAND] & 0x10) && (m_spu.regs[SPU4XX_LINE_STATUS] & 0x78))
2603      ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_SPUR, ASSERT_LINE);
22052604
22062605   /* clear otherwise */
22072606   else
2208      ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_SPUR, CLEAR_LINE);
2607      ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_SPUR, CLEAR_LINE);
22092608
22102609   /* check for transmit buffer empty interrupt */
2211   if ((ppc->spu.regs[SPU4XX_TX_COMMAND] & 0x60) == 0x20 && (ppc->spu.regs[SPU4XX_LINE_STATUS] & 0x04))
2212      ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_SPUT, ASSERT_LINE);
2610   if ((m_spu.regs[SPU4XX_TX_COMMAND] & 0x60) == 0x20 && (m_spu.regs[SPU4XX_LINE_STATUS] & 0x04))
2611      ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_SPUT, ASSERT_LINE);
22132612
22142613   /* check for shift register empty interrupt */
2215   else if ((ppc->spu.regs[SPU4XX_TX_COMMAND] & 0x10) && (ppc->spu.regs[SPU4XX_LINE_STATUS] & 0x02))
2216      ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_SPUT, ASSERT_LINE);
2614   else if ((m_spu.regs[SPU4XX_TX_COMMAND] & 0x10) && (m_spu.regs[SPU4XX_LINE_STATUS] & 0x02))
2615      ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_SPUT, ASSERT_LINE);
22172616
22182617   /* clear otherwise */
22192618   else
2220      ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_SPUT, CLEAR_LINE);
2619      ppc4xx_set_irq_line(PPC4XX_IRQ_BIT_SPUT, CLEAR_LINE);
22212620}
22222621
22232622
r31142r31143
22252624    ppc4xx_spu_rx_data - serial port data receive
22262625-------------------------------------------------*/
22272626
2228static void ppc4xx_spu_rx_data(powerpc_state *ppc, UINT8 data)
2627void ppc_device::ppc4xx_spu_rx_data(UINT8 data)
22292628{
22302629   UINT32 new_rxin;
22312630
22322631   /* fail if we are going to overflow */
2233   new_rxin = (ppc->spu.rxin + 1) % ARRAY_LENGTH(ppc->spu.rxbuffer);
2234   if (new_rxin == ppc->spu.rxout)
2632   new_rxin = (m_spu.rxin + 1) % ARRAY_LENGTH(m_spu.rxbuffer);
2633   if (new_rxin == m_spu.rxout)
22352634      fatalerror("ppc4xx_spu_rx_data: buffer overrun!\n");
22362635
22372636   /* store the data and accept the new in index */
2238   ppc->spu.rxbuffer[ppc->spu.rxin] = data;
2239   ppc->spu.rxin = new_rxin;
2637   m_spu.rxbuffer[m_spu.rxin] = data;
2638   m_spu.rxin = new_rxin;
22402639}
22412640
22422641
r31142r31143
22452644    the transmit/receive timer
22462645-------------------------------------------------*/
22472646
2248static void ppc4xx_spu_timer_reset(powerpc_state *ppc)
2647void ppc_device::ppc4xx_spu_timer_reset()
22492648{
2250   UINT8 enabled = (ppc->spu.regs[SPU4XX_RX_COMMAND] | ppc->spu.regs[SPU4XX_TX_COMMAND]) & 0x80;
2649   UINT8 enabled = (m_spu.regs[SPU4XX_RX_COMMAND] | m_spu.regs[SPU4XX_TX_COMMAND]) & 0x80;
22512650
22522651   /* if we're enabled, reset at the current baud rate */
22532652   if (enabled)
22542653   {
2255      attotime clockperiod = attotime::from_hz((ppc->dcr[DCR4XX_IOCR] & 0x02) ? 3686400 : 33333333);
2256      int divisor = ((ppc->spu.regs[SPU4XX_BAUD_DIVISOR_H] * 256 + ppc->spu.regs[SPU4XX_BAUD_DIVISOR_L]) & 0xfff) + 1;
2257      int bpc = 7 + ((ppc->spu.regs[SPU4XX_CONTROL] & 8) >> 3) + 1 + (ppc->spu.regs[SPU4XX_CONTROL] & 1);
2654      attotime clockperiod = attotime::from_hz((m_dcr[DCR4XX_IOCR] & 0x02) ? 3686400 : 33333333);
2655      int divisor = ((m_spu.regs[SPU4XX_BAUD_DIVISOR_H] * 256 + m_spu.regs[SPU4XX_BAUD_DIVISOR_L]) & 0xfff) + 1;
2656      int bpc = 7 + ((m_spu.regs[SPU4XX_CONTROL] & 8) >> 3) + 1 + (m_spu.regs[SPU4XX_CONTROL] & 1);
22582657      attotime charperiod = clockperiod * (divisor * 16 * bpc);
2259      ppc->spu.timer->adjust(charperiod, 0, charperiod);
2658      m_spu.timer->adjust(charperiod, 0, charperiod);
22602659      if (PRINTF_SPU)
22612660         printf("ppc4xx_spu_timer_reset: baud rate = %.0f\n", ATTOSECONDS_TO_HZ(charperiod.attoseconds) * bpc);
22622661   }
22632662
22642663   /* otherwise, disable the timer */
22652664   else
2266      ppc->spu.timer->adjust(attotime::never);
2665      m_spu.timer->adjust(attotime::never);
22672666}
22682667
22692668
r31142r31143
22722671    timer
22732672-------------------------------------------------*/
22742673
2275static TIMER_CALLBACK( ppc4xx_spu_callback )
2674TIMER_CALLBACK_MEMBER( ppc_device::ppc4xx_spu_callback )
22762675{
2277   powerpc_state *ppc = (powerpc_state *)ptr;
2278
22792676   /* transmit enabled? */
2280   if (ppc->spu.regs[SPU4XX_TX_COMMAND] & 0x80)
2677   if (m_spu.regs[SPU4XX_TX_COMMAND] & 0x80)
22812678   {
2282      int operation = (ppc->spu.regs[SPU4XX_TX_COMMAND] >> 5) & 3;
2679      int operation = (m_spu.regs[SPU4XX_TX_COMMAND] >> 5) & 3;
22832680
22842681      /* if we have data to transmit, do it now */
2285      if (!(ppc->spu.regs[SPU4XX_LINE_STATUS] & 0x04))
2682      if (!(m_spu.regs[SPU4XX_LINE_STATUS] & 0x04))
22862683      {
22872684         /* if we have a transmit handler, send it that way */
2288         if (ppc->spu.tx_handler != NULL)
2289            (*ppc->spu.tx_handler)(ppc->device, ppc->spu.txbuf);
2685         if (m_spu.tx_handler != NULL)
2686            (*m_spu.tx_handler)(this, m_spu.txbuf);
22902687
22912688         /* indicate that we have moved it to the shift register */
2292         ppc->spu.regs[SPU4XX_LINE_STATUS] |= 0x04;
2293         ppc->spu.regs[SPU4XX_LINE_STATUS] &= ~0x02;
2689         m_spu.regs[SPU4XX_LINE_STATUS] |= 0x04;
2690         m_spu.regs[SPU4XX_LINE_STATUS] &= ~0x02;
22942691      }
22952692
22962693      /* otherwise, clear the shift register */
2297      else if (!(ppc->spu.regs[SPU4XX_LINE_STATUS] & 0x02))
2298         ppc->spu.regs[SPU4XX_LINE_STATUS] |= 0x02;
2694      else if (!(m_spu.regs[SPU4XX_LINE_STATUS] & 0x02))
2695         m_spu.regs[SPU4XX_LINE_STATUS] |= 0x02;
22992696
23002697      /* handle DMA */
2301      if (operation >= 2 && ppc4xx_dma_fetch_transmit_byte(ppc, operation, &ppc->spu.txbuf))
2302         ppc->spu.regs[SPU4XX_LINE_STATUS] &= ~0x04;
2698      if (operation >= 2 && ppc4xx_dma_fetch_transmit_byte(operation, &m_spu.txbuf))
2699         m_spu.regs[SPU4XX_LINE_STATUS] &= ~0x04;
23032700   }
23042701
23052702   /* receive enabled? */
2306   if (ppc->spu.regs[SPU4XX_RX_COMMAND] & 0x80)
2307      if (ppc->spu.rxout != ppc->spu.rxin)
2703   if (m_spu.regs[SPU4XX_RX_COMMAND] & 0x80)
2704      if (m_spu.rxout != m_spu.rxin)
23082705      {
2309         int operation = (ppc->spu.regs[SPU4XX_RX_COMMAND] >> 5) & 3;
2706         int operation = (m_spu.regs[SPU4XX_RX_COMMAND] >> 5) & 3;
23102707         UINT8 rxbyte;
23112708
23122709         /* consume the byte and advance the out pointer */
2313         rxbyte = ppc->spu.rxbuffer[ppc->spu.rxout];
2314         ppc->spu.rxout = (ppc->spu.rxout + 1) % ARRAY_LENGTH(ppc->spu.rxbuffer);
2710         rxbyte = m_spu.rxbuffer[m_spu.rxout];
2711         m_spu.rxout = (m_spu.rxout + 1) % ARRAY_LENGTH(m_spu.rxbuffer);
23152712
23162713         /* if we're not full, copy data to the buffer and update the line status */
2317         if (!(ppc->spu.regs[SPU4XX_LINE_STATUS] & 0x80))
2714         if (!(m_spu.regs[SPU4XX_LINE_STATUS] & 0x80))
23182715         {
2319            ppc->spu.rxbuf = rxbyte;
2320            ppc->spu.regs[SPU4XX_LINE_STATUS] |= 0x80;
2716            m_spu.rxbuf = rxbyte;
2717            m_spu.regs[SPU4XX_LINE_STATUS] |= 0x80;
23212718         }
23222719
23232720         /* otherwise signal an overrun */
23242721         else
23252722         {
2326            ppc->spu.regs[SPU4XX_LINE_STATUS] |= 0x20;
2723            m_spu.regs[SPU4XX_LINE_STATUS] |= 0x20;
23272724            goto updateirq;
23282725         }
23292726
23302727         /* handle DMA */
2331         if (operation >= 2 && ppc4xx_dma_handle_receive_byte(ppc, operation, ppc->spu.rxbuf))
2332            ppc->spu.regs[SPU4XX_LINE_STATUS] &= ~0x80;
2728         if (operation >= 2 && ppc4xx_dma_handle_receive_byte(operation, m_spu.rxbuf))
2729            m_spu.regs[SPU4XX_LINE_STATUS] &= ~0x80;
23332730      }
23342731
23352732   /* update the final IRQ states */
23362733updateirq:
2337   ppc4xx_spu_update_irq_states(ppc);
2734   ppc4xx_spu_update_irq_states();
23382735}
23392736
23402737
r31142r31143
23442741
23452742READ8_MEMBER( ppc4xx_device::ppc4xx_spu_r )
23462743{
2347   powerpc_state *ppc = *(powerpc_state **)downcast<legacy_cpu_device *>(this)->token();
23482744   UINT8 result = 0xff;
23492745
23502746   switch (offset)
23512747   {
23522748      case SPU4XX_BUFFER:
2353         result = ppc->spu.rxbuf;
2354         ppc->spu.regs[SPU4XX_LINE_STATUS] &= ~0x80;
2749         result = m_spu.rxbuf;
2750         m_spu.regs[SPU4XX_LINE_STATUS] &= ~0x80;
23552751         break;
23562752
23572753      default:
2358         if (offset < ARRAY_LENGTH(ppc->spu.regs))
2359            result = ppc->spu.regs[offset];
2754         if (offset < ARRAY_LENGTH(m_spu.regs))
2755            result = m_spu.regs[offset];
23602756         break;
23612757   }
23622758   if (PRINTF_SPU)
r31142r31143
23712767
23722768WRITE8_MEMBER( ppc4xx_device::ppc4xx_spu_w )
23732769{
2374   powerpc_state *ppc = *(powerpc_state **)downcast<legacy_cpu_device *>(this)->token();
23752770   UINT8 oldstate, newstate;
23762771
23772772   if (PRINTF_SPU)
r31142r31143
23802775   {
23812776      /* clear error bits */
23822777      case SPU4XX_LINE_STATUS:
2383         ppc->spu.regs[SPU4XX_LINE_STATUS] &= ~(data & 0xf8);
2384         ppc4xx_spu_update_irq_states(ppc);
2778         m_spu.regs[SPU4XX_LINE_STATUS] &= ~(data & 0xf8);
2779         ppc4xx_spu_update_irq_states();
23852780         break;
23862781
23872782      /* enable/disable the timer if one of these is enabled */
23882783      case SPU4XX_RX_COMMAND:
23892784      case SPU4XX_TX_COMMAND:
2390         oldstate = ppc->spu.regs[SPU4XX_RX_COMMAND] | ppc->spu.regs[SPU4XX_TX_COMMAND];
2391         ppc->spu.regs[offset] = data;
2392         newstate = ppc->spu.regs[SPU4XX_RX_COMMAND] | ppc->spu.regs[SPU4XX_TX_COMMAND];
2785         oldstate = m_spu.regs[SPU4XX_RX_COMMAND] | m_spu.regs[SPU4XX_TX_COMMAND];
2786         m_spu.regs[offset] = data;
2787         newstate = m_spu.regs[SPU4XX_RX_COMMAND] | m_spu.regs[SPU4XX_TX_COMMAND];
23932788         if ((oldstate ^ newstate) & 0x80)
2394            ppc4xx_spu_timer_reset(ppc);
2395         ppc4xx_spu_update_irq_states(ppc);
2789            ppc4xx_spu_timer_reset();
2790         ppc4xx_spu_update_irq_states();
23962791         break;
23972792
23982793      /* if the divisor changes, we need to update the timer */
23992794      case SPU4XX_BAUD_DIVISOR_H:
24002795      case SPU4XX_BAUD_DIVISOR_L:
2401         if (data != ppc->spu.regs[offset])
2796         if (data != m_spu.regs[offset])
24022797         {
2403            ppc->spu.regs[offset] = data;
2404            ppc4xx_spu_timer_reset(ppc);
2798            m_spu.regs[offset] = data;
2799            ppc4xx_spu_timer_reset();
24052800         }
24062801         break;
24072802
24082803      /* if the number of data bits or stop bits changes, we need to update the timer */
24092804      case SPU4XX_CONTROL:
2410         oldstate = ppc->spu.regs[offset];
2411         ppc->spu.regs[offset] = data;
2805         oldstate = m_spu.regs[offset];
2806         m_spu.regs[offset] = data;
24122807         if ((oldstate ^ data) & 0x09)
2413            ppc4xx_spu_timer_reset(ppc);
2808            ppc4xx_spu_timer_reset();
24142809         break;
24152810
24162811         break;
24172812
24182813      case SPU4XX_BUFFER:
24192814         /* write to the transmit buffer and mark it full */
2420         ppc->spu.txbuf = data;
2421         ppc->spu.regs[SPU4XX_LINE_STATUS] &= ~0x04;
2815         m_spu.txbuf = data;
2816         m_spu.regs[SPU4XX_LINE_STATUS] &= ~0x04;
24222817         break;
24232818
24242819      default:
2425         if (offset < ARRAY_LENGTH(ppc->spu.regs))
2426            ppc->spu.regs[offset] = data;
2820         if (offset < ARRAY_LENGTH(m_spu.regs))
2821            m_spu.regs[offset] = data;
24272822         break;
24282823   }
24292824}
r31142r31143
24312826
24322827
24332828/*-------------------------------------------------
2434    internal_ppc4xx - internal address map for
2435    the 4XX
2436-------------------------------------------------*/
2437
2438static ADDRESS_MAP_START( internal_ppc4xx, AS_PROGRAM, 32, ppc4xx_device )
2439   AM_RANGE(0x40000000, 0x4000000f) AM_READWRITE8(ppc4xx_spu_r, ppc4xx_spu_w, 0xffffffff)
2440ADDRESS_MAP_END
2441
2442
2443
2444/*-------------------------------------------------
24452829    ppc4xx_spu_set_tx_handler - PowerPC 4XX-
24462830    specific TX handler configuration
24472831-------------------------------------------------*/
24482832
2449void ppc4xx_spu_set_tx_handler(device_t *device, ppc4xx_spu_tx_handler handler)
2833void ppc4xx_device::ppc4xx_spu_set_tx_handler(ppc4xx_spu_tx_handler handler)
24502834{
2451   powerpc_state *ppc = *(powerpc_state **)downcast<legacy_cpu_device *>(device)->token();
2452   ppc->spu.tx_handler = handler;
2835   m_spu.tx_handler = handler;
24532836}
24542837
24552838
r31142r31143
24582841    specific serial byte receive
24592842-------------------------------------------------*/
24602843
2461void ppc4xx_spu_receive_byte(device_t *device, UINT8 byteval)
2844void ppc4xx_device::ppc4xx_spu_receive_byte(UINT8 byteval)
24622845{
2463   powerpc_state *ppc = *(powerpc_state **)downcast<legacy_cpu_device *>(device)->token();
2464   ppc4xx_spu_rx_data(ppc, byteval);
2846   ppc4xx_spu_rx_data(byteval);
24652847}
24662848
24672849/*-------------------------------------------------
r31142r31143
24692851    specific external DMA read handler configuration
24702852-------------------------------------------------*/
24712853
2472void ppc4xx_set_dma_read_handler(device_t *device, int channel, ppc4xx_dma_read_handler handler, int rate)
2854void ppc4xx_device::ppc4xx_set_dma_read_handler(int channel, ppc4xx_dma_read_handler handler, int rate)
24732855{
2474   powerpc_state *ppc = *(powerpc_state **)downcast<legacy_cpu_device *>(device)->token();
2475   ppc->ext_dma_read_handler[channel] = handler;
2476   ppc->buffered_dma_rate[channel] = rate;
2856   m_ext_dma_read_handler[channel] = handler;
2857   m_buffered_dma_rate[channel] = rate;
24772858}
24782859
24792860/*-------------------------------------------------
r31142r31143
24812862    specific external DMA write handler configuration
24822863-------------------------------------------------*/
24832864
2484void ppc4xx_set_dma_write_handler(device_t *device, int channel, ppc4xx_dma_write_handler handler, int rate)
2865void ppc4xx_device::ppc4xx_set_dma_write_handler(int channel, ppc4xx_dma_write_handler handler, int rate)
24852866{
2486   powerpc_state *ppc = *(powerpc_state **)downcast<legacy_cpu_device *>(device)->token();
2487   ppc->ext_dma_write_handler[channel] = handler;
2488   ppc->buffered_dma_rate[channel] = rate;
2867   m_ext_dma_write_handler[channel] = handler;
2868   m_buffered_dma_rate[channel] = rate;
24892869}
24902870
24912871/*-------------------------------------------------
24922872    ppc4xx_set_dcr_read_handler
24932873-------------------------------------------------*/
24942874
2495void ppc4xx_set_dcr_read_handler(device_t *device, read32_delegate dcr_read_func)
2875void ppc4xx_device::ppc4xx_set_dcr_read_handler(read32_delegate dcr_read_func)
24962876{
2497   powerpc_state *ppc = *(powerpc_state **)downcast<legacy_cpu_device *>(device)->token();
2498   ppc->dcr_read_func = dcr_read_func;
2877   m_dcr_read_func = dcr_read_func;
24992878
25002879}
25012880
r31142r31143
25032882    ppc4xx_set_dcr_write_handler
25042883-------------------------------------------------*/
25052884
2506void ppc4xx_set_dcr_write_handler(device_t *device, write32_delegate dcr_write_func)
2885void ppc4xx_device::ppc4xx_set_dcr_write_handler(write32_delegate dcr_write_func)
25072886{
2508   powerpc_state *ppc = *(powerpc_state **)downcast<legacy_cpu_device *>(device)->token();
2509   ppc->dcr_write_func = dcr_write_func;
2887   m_dcr_write_func = dcr_write_func;
25102888}
25112889
2512/*-------------------------------------------------
2513    ppc4xx_set_info - PowerPC 4XX-specific
2514    information setter
2515-------------------------------------------------*/
2516
2517void ppc4xx_set_info(powerpc_state *ppc, UINT32 state, cpuinfo *info)
2518{
2519   switch (state)
2520   {
2521      /* --- the following bits of info are returned as 64-bit signed integers --- */
2522      case CPUINFO_INT_INPUT_STATE + PPC_IRQ_LINE_0:  ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_EXT0, info->i);     break;
2523      case CPUINFO_INT_INPUT_STATE + PPC_IRQ_LINE_1:  ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_EXT1, info->i);     break;
2524      case CPUINFO_INT_INPUT_STATE + PPC_IRQ_LINE_2:  ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_EXT2, info->i);     break;
2525      case CPUINFO_INT_INPUT_STATE + PPC_IRQ_LINE_3:  ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_EXT3, info->i);     break;
2526      case CPUINFO_INT_INPUT_STATE + PPC_IRQ_LINE_4:  ppc4xx_set_irq_line(ppc, PPC4XX_IRQ_BIT_EXT4, info->i);     break;
2527
2528      /* --- everything else is handled generically --- */
2529      default:                                        ppccom_set_info(ppc, state, info);      break;
2530   }
2531}
2532
2533
2534/*-------------------------------------------------
2535    ppc4xx_get_info - PowerPC 4XX-specific
2536    information getter
2537-------------------------------------------------*/
2538
2539void ppc4xx_get_info(powerpc_state *ppc, UINT32 state, cpuinfo *info)
2540{
2541   switch (state)
2542   {
2543      /* --- the following bits of info are returned as 64-bit signed integers --- */
2544      case CPUINFO_INT_INPUT_LINES:                   info->i = 5;                            break;
2545      case CPUINFO_INT_INPUT_STATE + PPC_IRQ_LINE_0:  info->i = ppc4xx_get_irq_line(ppc, PPC4XX_IRQ_BIT_EXT0);        break;
2546      case CPUINFO_INT_INPUT_STATE + PPC_IRQ_LINE_1:  info->i = ppc4xx_get_irq_line(ppc, PPC4XX_IRQ_BIT_EXT1);        break;
2547      case CPUINFO_INT_INPUT_STATE + PPC_IRQ_LINE_2:  info->i = ppc4xx_get_irq_line(ppc, PPC4XX_IRQ_BIT_EXT2);        break;
2548      case CPUINFO_INT_INPUT_STATE + PPC_IRQ_LINE_3:  info->i = ppc4xx_get_irq_line(ppc, PPC4XX_IRQ_BIT_EXT3);        break;
2549      case CPUINFO_INT_INPUT_STATE + PPC_IRQ_LINE_4:  info->i = ppc4xx_get_irq_line(ppc, PPC4XX_IRQ_BIT_EXT4);        break;
2550
2551      case CPUINFO_INT_DATABUS_WIDTH + AS_PROGRAM:    info->i = 32;                   break;
2552      case CPUINFO_INT_ADDRBUS_WIDTH + AS_PROGRAM: info->i = 31;                  break;
2553      case CPUINFO_INT_LOGADDR_WIDTH_PROGRAM: info->i = 32;                   break;
2554      case CPUINFO_INT_PAGE_SHIFT_PROGRAM:    info->i = POWERPC_MIN_PAGE_SHIFT;break;
2555
2556      /* --- the following bits of info are returned as pointers to data or functions --- */
2557      case CPUINFO_FCT_INIT:                          /* provided per-CPU */                  break;
2558      case CPUINFO_PTR_INTERNAL_MEMORY_MAP + AS_PROGRAM: info->internal_map32 = ADDRESS_MAP_NAME(internal_ppc4xx); break;
2559
2560      /* --- everything else is handled generically --- */
2561      default:                                        ppccom_get_info(ppc, state, info);      break;
2562   }
2563}
trunk/src/emu/cpu/powerpc/ppc.c
r31142r31143
109109#define AABIT           (op & 0x2)
110110#define LKBIT           (op & 0x1)
111111
112#define REG(x)          (ppc.r[x])
113#define LR              (ppc.lr)
114#define CTR             (ppc.ctr)
115#define XER             (ppc.xer)
116#define CR(x)           (ppc.cr[x])
117#define MSR             (ppc.msr)
118#define SRR0            (ppc.srr0)
119#define SRR1            (ppc.srr1)
120#define SRR2            (ppc.srr2)
121#define SRR3            (ppc.srr3)
122#define EVPR            (ppc.evpr)
123#define EXIER           (ppc.exier)
124#define EXISR           (ppc.exisr)
125#define DEC             (ppc.dec)
112#define REG(x)          (m_r[x])
113#define LR              (m_lr)
114#define CTR             (m_ctr)
115#define XER             (m_xer)
116#define CR(x)           (m_cr[x])
117#define MSR             (m_msr)
118#define SRR0            (m_srr0)
119#define SRR1            (m_srr1)
120#define SRR2            (m_srr2)
121#define SRR3            (m_srr3)
122#define EVPR            (m_evpr)
123#define EXIER           (m_exier)
124#define EXISR           (m_exisr)
125#define DEC             (m_dec)
126126
127127
128128// Stuff added for the 6xx
129#define FPR(x)          (ppc.fpr[x])
129#define FPR(x)          (m_fpr[x])
130130#define FM              ((op >> 17) & 0xFF)
131131#define SPRF            (((op >> 6) & 0x3E0) | ((op >> 16) & 0x1F))
132132
133133
134134#define CHECK_SUPERVISOR()          \
135   if((ppc.msr & 0x4000) != 0){    \
135   if((m_msr & 0x4000) != 0){    \
136136   }
137137
138138#define CHECK_FPU_AVAILABLE()       \
139   if((ppc.msr & 0x2000) == 0){    \
139   if((m_msr & 0x2000) == 0){    \
140140   }
141141
142142static UINT32       ppc_field_xlat[256];
r31142r31143
154154
155155
156156#define BITMASK_0(n)    (UINT32)(((UINT64)1 << n) - 1)
157#define CRBIT(x)        ((ppc.cr[x / 4] & (1 << (3 - (x % 4)))) ? 1 : 0)
157#define CRBIT(x)        ((m_cr[x / 4] & (1 << (3 - (x % 4)))) ? 1 : 0)
158158#define _BIT(n)         (1 << (n))
159159#define GET_ROTATE_MASK(mb,me)      (ppc_rotate_mask[mb][me])
160160#define ADD_CA(r,a,b)       ((UINT32)r < (UINT32)a)
r31142r31143
195195#define BYTE_REVERSE16(x)   ((((x) >> 8) & 0xff) | (((x) << 8) & 0xff00))
196196#define BYTE_REVERSE32(x)   ((((x) >> 24) & 0xff) | (((x) >> 8) & 0xff00) | (((x) << 8) & 0xff0000) | (((x) << 24) & 0xff000000))
197197
198struct DMA_REGS {
199   UINT32 cr;
200   UINT32 da;
201   UINT32 sa;
202   UINT32 ct;
203   UINT32 cc;
204};
205198
206struct SPU_REGS {
207   UINT8 spls;
208   UINT8 sphs;
209   UINT16 brd;
210   UINT8 spctl;
211   UINT8 sprc;
212   UINT8 sptc;
213   UINT8 sprb;
214   UINT8 sptb;
215   emu_timer *rx_timer;
216   emu_timer *tx_timer;
217};
199const device_type PPC403 = &device_creator<ppc403_device>;
200const device_type PPC405 = &device_creator<ppc405_device>;
201const device_type PPC601 = &device_creator<ppc601_device>;
202const device_type PPC602 = &device_creator<ppc602_device>;
203const device_type PPC603 = &device_creator<ppc603_device>;
204const device_type PPC603E = &device_creator<ppc603e_device>;
205const device_type PPC603R = &device_creator<ppc603r_device>;
206const device_type PPC604 = &device_creator<ppc604_device>;
207const device_type MPC8240 = &device_creator<mpc8240_device>;
208const device_type PPC403GA = &device_creator<ppc403ga_device>;
209const device_type PPC403GCX = &device_creator<ppc403gcx_device>;
210const device_type PPC405GP = &device_creator<ppc405gp_device>;
218211
219union FPR {
220   UINT64  id;
221   double  fd;
222};
223212
224union FPR32 {
225   UINT32 i;
226   float f;
213struct PPC_OPCODE {
214   int code;
215   int subcode;
216   void (* handler)(UINT32);
227217};
228218
229struct BATENT {
230   UINT32 u;
231   UINT32 l;
232};
233219
234220
235struct PPC_REGS {
236   UINT32 r[32];
237   UINT32 pc;
238   UINT32 npc;
221static UINT32 ppc_rotate_mask[32][32];
239222
240   UINT32 lr;
241   UINT32 ctr;
242   UINT32 xer;
243   UINT32 msr;
244   UINT8 cr[8];
245   UINT32 pvr;
246   UINT32 srr0;
247   UINT32 srr1;
248   UINT32 srr2;
249   UINT32 srr3;
250   UINT32 hid0;
251   UINT32 hid1;
252   UINT32 hid2;
253   UINT32 sdr1;
254   UINT32 sprg[4];
223#define ROPCODE(pc)         memory_decrypted_read_dword(m_program, pc)
224#define ROPCODE64(pc)       memory_decrypted_read_qword(m_program, DWORD_XOR_BE(pc))
255225
256   UINT32 dsisr;
257   UINT32 dar;
258   UINT32 ear;
259   UINT32 dmiss;
260   UINT32 dcmp;
261   UINT32 hash1;
262   UINT32 hash2;
263   UINT32 imiss;
264   UINT32 icmp;
265   UINT32 rpa;
266226
227ppc_device::ppc_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, const char *shortname, int address_bits, powerpc_flavor flavor, UINT32 cap, UINT32 tb_divisor)
228   : cpu_device(mconfig, type, name, tag, owner, clock, shortname, __FILE__)
229   , m_program_config("program", ENDIANNESS_BIG, address_bits, 32)
230   , m_core(NULL)
231   , c_bus_frequency(0)
232   , m_bus_freq_multiplier(1)
233   , m_flavor(flavor)
234   , m_cap(cap)
235   , m_tb_divisor(tb_divisor)
236   , m_vtlb(NULL)
237   , m_cache(CACHE_SIZE + sizeof(internal_ppc_state))
238{
239}
267240
268   BATENT ibat[4];
269   BATENT dbat[4];
241//ppc403_device::ppc403_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
242//   : ppc_device(mconfig, PPC403, "PPC403", tag, owner, clock, "ppc403", 32)
243//{
244//}
245//
246//ppc405_device::ppc405_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
247//   : ppc_device(mconfig, PPC405, "PPC405", tag, owner, clock, "ppc405", 32)
248//{
249//}
270250
271   UINT32 evpr;
272   UINT32 exier;
273   UINT32 exisr;
274   UINT32 bear;
275   UINT32 besr;
276   UINT32 iocr;
277   UINT32 br[8];
278   UINT32 iabr;
279   UINT32 esr;
280   UINT32 iccr;
281   UINT32 dccr;
282   UINT32 pit;
283   UINT32 pit_counter;
284   UINT32 pit_int_enable;
285   UINT32 tsr;
286   UINT32 dbsr;
287   UINT32 sgr;
288   UINT32 pid;
289   UINT32 pbl1, pbl2, pbu1, pbu2;
290   UINT32 fit_bit;
291   UINT32 fit_int_enable;
292   UINT32 wdt_bit;
293   UINT32 wdt_int_enable;
294   UINT32 dac1, dac2;
295   UINT32 iac1, iac2;
251ppc603_device::ppc603_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
252   : ppc_device(mconfig, PPC603", "PowerPC 603", tag, owner, clock, "ppc603", 64, PPC_MODEL_603, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4)
253{
254}
296255
297   SPU_REGS spu;
298   DMA_REGS dma[4];
299   UINT32 dmasr;
256ppc603e_device::ppc603e_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
257   : ppc_device(mconfig, PPC603E, "PowerPC 603e", tag, owner, clock, "ppc603e", 64, PPC_MODEL_603E, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4)
258{
259}
300260
301   int reserved;
302   UINT32 reserved_address;
261ppc603r_device::ppc603r_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
262   : ppc_device(mconfig, PPC603R, "PowerPC 603R", tag, owner, clock, "ppc603r", 64, PPC_MODEL_603R, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4)
263{
264}
303265
304   int interrupt_pending;
266ppc602_device::ppc602_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
267   : ppc_device(mconfig, PPC602, "PowerPC 602", tag, owner, clock, "ppc602", 64, PPC_MODEL_602, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4)
268{
269}
305270
306   UINT64 tb;          /* 56-bit timebase register */
271mpc8240_device::mpc8240_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
272   : ppc_device(mconfig, MPC8240, "PowerPC MPC8240", tag, owner, clock, "mpc8240", 64, PPC_MODEL_MPC8240, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_603_MMU, 4/* unknown */)
273{
274}
307275
308   device_irq_acknowledge_delegate irq_callback;
309   legacy_cpu_device *device;
310   address_space *program;
276ppc601_device::ppc601_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
277   : ppc_device(mconfig, PPC601, "PowerPC 601", tag, owner, clock, "ppc601", 64, PPC_MODEL_601, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_MFIOC | PPCCAP_601BAT, 0/* no TB */)
278{
279}
311280
312   // STUFF added for the 6xx series
313   UINT32 dec, dec_frac;
314   UINT32 fpscr;
281ppc604_device::ppc604_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
282   : ppc_device(mconfig, PPC604, "PowerPC 604", tag, owner, clock, "ppc604", 64, PPC_MODEL_604, PPCCAP_OEA | PPCCAP_VEA | PPCCAP_FPU | PPCCAP_MISALIGNED | PPCCAP_604_MMU, 4)
283{
284}
315285
316   FPR fpr[32];
317   UINT32 sr[16];
286ppc4xx_device::ppc4xx_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, const char *shortname, powerpc_flavor flavor, UINT32 cap, UINT32 tb_divisor)
287   : ppc_device(mconfig, type, name, tag, owner, clock, shortname, 64, flavor, cap, tb_divisor) // TODO address bits, ppccom has 31 address bits??
288{
289}
318290
319   int is603;
320   int is602;
291ppc403ga_device::ppc403ga_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
292   : ppc4xx_device(mconfig, PPC403GA, "PowerPC 403GA", tag, owner, clock, "ppc403ga", PPC_MODEL_403GA, PPCCAP_4XX, 1)
293{
294}
321295
322   /* PowerPC 602 specific registers */
323   UINT32 lt;
324   UINT32 sp;
325   UINT32 tcr;
326   UINT32 ibr;
327   UINT32 esasrr;
328   UINT32 sebr;
329   UINT32 ser;
296ppc403gcx_device::ppc403gcx_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
297   : ppc4xx_device(mconfig, PPC403GCX, "PowerPC 403GCX", tag, owner, clock, "ppc403gcx", PPC_MODEL_403GCX, PPCCAP_4XX, 1)
298{
299}
330300
331   /* PowerPC function pointers for memory accesses/exceptions */
332   jmp_buf exception_jmpbuf;
333   UINT8 (*read8)(address_space &space, offs_t address);
334   UINT16 (*read16)(address_space &space, offs_t address);
335   UINT32 (*read32)(address_space &space, offs_t address);
336   UINT64 (*read64)(address_space &space, offs_t address);
337   void (*write8)(address_space &space, offs_t address, UINT8 data);
338   void (*write16)(address_space &space, offs_t address, UINT16 data);
339   void (*write32)(address_space &space, offs_t address, UINT32 data);
340   void (*write64)(address_space &space, offs_t address, UINT64 data);
341   UINT16 (*read16_unaligned)(address_space &space, offs_t address);
342   UINT32 (*read32_unaligned)(address_space &space, offs_t address);
343   UINT64 (*read64_unaligned)(address_space &space, offs_t address);
344   void (*write16_unaligned)(address_space &space, offs_t address, UINT16 data);
345   void (*write32_unaligned)(address_space &space, offs_t address, UINT32 data);
346   void (*write64_unaligned)(address_space &space, offs_t address, UINT64 data);
301ppc405gp_device::ppc405gp_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
302   : ppc4xx_device(mconfig, PPC405GP, "PowerPC 405GP", tag, owner, clock, "ppc405gp", PPC_MODEL_405GP, PPCCAP_4XX | PPCCAP_VEA, 1)
303{
304}
347305
348   void (* optable19[1024])(UINT32);
349   void (* optable31[1024])(UINT32);
350   void (* optable59[1024])(UINT32);
351   void (* optable63[1024])(UINT32);
352   void (* optable[64])(UINT32);
353};
354
355
356
357struct PPC_OPCODE {
358   int code;
359   int subcode;
360   void (* handler)(UINT32);
361};
362
363
364
365static int ppc_icount;
366static int ppc_tb_base_icount;
367static int ppc_dec_base_icount;
368static int ppc_dec_trigger_cycle;
369static int bus_freq_multiplier = 1;
370static PPC_REGS ppc;
371static UINT32 ppc_rotate_mask[32][32];
372
373#define ROPCODE(pc)         memory_decrypted_read_dword(ppc.program, pc)
374#define ROPCODE64(pc)       memory_decrypted_read_qword(ppc.program, DWORD_XOR_BE(pc))
375
376306/*********************************************************************/
377307
378INLINE int IS_PPC602(void)
308inline int ppc_device::IS_PPC602(void)
379309{
380   return ppc.is602;
310   return m_is602;
381311}
382312
383INLINE int IS_PPC603(void)
313inline int ppc_device::IS_PPC603(void)
384314{
385   return ppc.is603;
315   return m_is603;
386316}
387317
388INLINE int IS_PPC403(void)
318inline int ppc_device::IS_PPC403(void)
389319{
390320   return !IS_PPC602() && !IS_PPC603();
391321}
trunk/src/emu/cpu/powerpc/ppccom.h
r31142r31143
1212#define __PPCCOM_H__
1313
1414#include "ppc.h"
15#include "cpu/vtlb.h"
1615
1716
1817/***************************************************************************
18    DEBUGGING
19***************************************************************************/
20
21#define LOG_UML                         (0)
22#define LOG_NATIVE                      (0)
23
24#define DISABLE_FLAG_OPTIMIZATIONS      (0)
25#define DISABLE_FAST_REGISTERS          (0)
26#define SINGLE_INSTRUCTION_MODE         (0)
27
28#define PRINTF_EXCEPTIONS               (0)
29#define PRINTF_MMU                      (0)
30
31#define PROBE_ADDRESS                   ~0
32
33
34/***************************************************************************
1935    CONSTANTS
2036***************************************************************************/
2137
38/* size of the execution code cache */
39#define CACHE_SIZE                      (32 * 1024 * 1024)
40
41/* compilation boundaries -- how far back/forward does the analysis extend? */
42#define COMPILE_BACKWARDS_BYTES         128
43#define COMPILE_FORWARDS_BYTES          512
44#define COMPILE_MAX_INSTRUCTIONS        ((COMPILE_BACKWARDS_BYTES/4) + (COMPILE_FORWARDS_BYTES/4))
45#define COMPILE_MAX_SEQUENCE            64
46
47
2248/* core parameters */
2349#define POWERPC_MIN_PAGE_SHIFT      12
2450#define POWERPC_MIN_PAGE_SIZE       (1 << POWERPC_MIN_PAGE_SHIFT)
r31142r31143
4369#define PPCCAP_601BAT               0x80        /* TRUE if we're doing 601-style BATs (unified I/D, different bit layout) */
4470#define PPCCAP_604_MMU              0x100       /* TRUE if we have 604-class MMU features */
4571
46/* PowerPC flavors */
47enum powerpc_flavor
48{
49   PPC_MODEL_403GA             = 0x00200000,
50   PPC_MODEL_403GB             = 0x00200100,
51   PPC_MODEL_403GC             = 0x00200200,
52   PPC_MODEL_403GCX            = 0x00201400,
53   PPC_MODEL_405GP             = 0x40110000,
54   PPC_MODEL_601               = 0x00010000,
55   PPC_MODEL_603               = 0x00030000,   /* "Wart" */
56   PPC_MODEL_604               = 0x00040000,   /* "Zephyr" */
57   PPC_MODEL_602               = 0x00050200,   /* "Galahad" */
58   PPC_MODEL_603E              = 0x00060103,   /* "Stretch", version 1.3 */
59   PPC_MODEL_603EV             = 0x00070000,   /* "Valiant" */
60   PPC_MODEL_603R              = 0x00071202,   /* "Goldeneye", version 2.1 */
61   PPC_MODEL_740               = 0x00080301,   /* "Arthur", version 3.1 */
62   PPC_MODEL_750               = PPC_MODEL_740,
63   PPC_MODEL_740P              = 0x00080202,   /* "Conan Doyle", version 1.2 */
64   PPC_MODEL_750P              = PPC_MODEL_740P,
65   PPC_MODEL_755               = 0x00083203,   /* "Goldfinger", version 2.3 */
66   PPC_MODEL_7400              = 0x000c0209,   /* "Max", version 2.9 */
67   PPC_MODEL_7410              = 0x800c1104,   /* "Nitro", version 3.4 */
68   PPC_MODEL_7450              = 0x80000201,   /* "Vger", version 2.1 */
69   PPC_MODEL_7451              = 0x80000203,   /* "Vger", version 2.3 */
70   PPC_MODEL_7441              = PPC_MODEL_7451,
71   PPC_MODEL_7455              = 0x80010303,   /* "Apollo 6", version 3.3 */
72   PPC_MODEL_7445              = PPC_MODEL_7455,
73   PPC_MODEL_7457              = 0x80020101,   /* "Apollo 7", version 1.1 */
74   PPC_MODEL_MPC8240           = 0x00810101,   /* "Kahlua" */
75   PPC_MODEL_MPC8241           = 0x80811014,   /* "Kahlua Lt" */
76   PPC_MODEL_MPC8245           = 0x80811014,   /* "Kahlua II" */
77};
7872
79
8073/* exception types */
8174enum
8275{
r31142r31143
485478
486479
487480
488/***************************************************************************
489    STRUCTURES & TYPEDEFS
490***************************************************************************/
491
492/* PowerPC 4XX-specific serial port state */
493struct ppc4xx_spu_state
494{
495   UINT8           regs[9];
496   UINT8           txbuf;
497   UINT8           rxbuf;
498   emu_timer *     timer;
499   UINT8           rxbuffer[256];
500   UINT32          rxin, rxout;
501   ppc4xx_spu_tx_handler tx_handler;
502};
503
504
505/* forward declaration of implementation-specific state */
506struct ppcimp_state;
507
508
509/* PowerPC state */
510struct powerpc_state
511{
512   /* core registers */
513   UINT32          pc;
514   int             icount;
515   UINT32          r[32];
516   double          f[32];
517   UINT32          cr[8];
518   UINT32          xerso;
519   UINT32          fpscr;
520   UINT32          msr;
521   UINT32          sr[16];
522   UINT32          spr[1024];
523   UINT32          dcr[256];
524
525   /* parameters for calls */
526   UINT32          param0;
527   UINT32          param1;
528
529   /* MMU */
530   vtlb_state *    vtlb;
531
532   /* architectural distinctions */
533   powerpc_flavor  flavor;
534   UINT32          cap;
535   UINT8           cache_line_size;
536   UINT32          tb_divisor;
537
538   /* PowerPC 4xx-specific state */
539   ppc4xx_spu_state spu;
540   emu_timer *     fit_timer;
541   emu_timer *     pit_timer;
542   emu_timer *     wdog_timer;
543   UINT32          pit_reload;
544   UINT32          irqstate;
545   emu_timer *     buffered_dma_timer[4];
546   int             buffered_dma_rate[4];
547
548   /* PowerPC 603-specific state */
549   UINT32          mmu603_cmp;
550   UINT32          mmu603_hash[2];
551   UINT32          mmu603_r[4];
552
553   /* internal stuff */
554   device_irq_acknowledge_delegate irq_callback;
555   legacy_cpu_device * device;
556   address_space *program;
557   direct_read_data *direct;
558   offs_t          codexor;
559   UINT32          irq_pending;
560   UINT32          system_clock;
561   UINT32          cpu_clock;
562   UINT64          tb_zero_cycles;
563   UINT64          dec_zero_cycles;
564   emu_timer *     decrementer_int_timer;
565
566   /* for use by specific implementations */
567   ppcimp_state *  impstate;
568
569   read32_delegate  dcr_read_func;
570   write32_delegate dcr_write_func;
571
572   ppc_dcstore_handler dcstore_handler;
573
574   ppc4xx_dma_read_handler ext_dma_read_handler[4];
575   ppc4xx_dma_write_handler ext_dma_write_handler[4];
576};
577
578
579
580/***************************************************************************
581    FUNCTION PROTOTYPES
582***************************************************************************/
583
584void ppccom_init(powerpc_state *ppc, powerpc_flavor flavor, UINT32 cap, int tb_divisor, legacy_cpu_device *device, device_irq_acknowledge_delegate irqcallback);
585void ppccom_exit(powerpc_state *ppc);
586
587void ppccom_reset(powerpc_state *ppc);
588offs_t ppccom_dasm(powerpc_state *ppc, char *buffer, offs_t pc, const UINT8 *oprom, const UINT8 *opram);
589
590int ppccom_translate_address(powerpc_state *ppc, address_spacenum space, int intention, offs_t *address);
591
592void ppccom_set_info(powerpc_state *ppc, UINT32 state, cpuinfo *info);
593void ppccom_get_info(powerpc_state *ppc, UINT32 state, cpuinfo *info);
594
595void ppccom_tlb_fill(powerpc_state *ppc);
596void ppccom_tlb_flush(powerpc_state *ppc);
597
598void ppccom_execute_tlbie(powerpc_state *ppc);
599void ppccom_execute_tlbia(powerpc_state *ppc);
600void ppccom_execute_tlbl(powerpc_state *ppc);
601void ppccom_execute_mftb(powerpc_state *ppc);
602void ppccom_execute_mfspr(powerpc_state *ppc);
603void ppccom_execute_mtspr(powerpc_state *ppc);
604void ppccom_execute_mfdcr(powerpc_state *ppc);
605void ppccom_execute_mtdcr(powerpc_state *ppc);
606
607void ppccom_update_fprf(powerpc_state *ppc);
608
609void ppccom_dcstore_callback(powerpc_state *ppc);
610
611void ppc4xx_set_info(powerpc_state *ppc, UINT32 state, cpuinfo *info);
612void ppc4xx_get_info(powerpc_state *ppc, UINT32 state, cpuinfo *info);
613
614481#endif /* __PPCCOM_H__ */
trunk/src/emu/cpu/powerpc/ppc.h
r31142r31143
1414#ifndef __PPC_H__
1515#define __PPC_H__
1616
17#include <setjmp.h>
18#include "cpu/vtlb.h"
19#include "cpu/drcfe.h"
20#include "cpu/drcuml.h"
21#include "cpu/drcumlsh.h"
1722
1823
1924/***************************************************************************
r31142r31143
162167
163168typedef void (*ppc4xx_spu_tx_handler)(device_t *device, UINT8 data);
164169
165struct powerpc_config
166{
167   UINT32      bus_frequency;
168};
169170
170171typedef void (*ppc_dcstore_handler)(device_t *device, UINT32 address);
171172typedef UINT32 (*ppc4xx_dma_read_handler)(device_t *device, int width);
r31142r31143
176177    PUBLIC FUNCTIONS
177178***************************************************************************/
178179
179void ppcdrc_set_options(device_t *device, UINT32 options);
180void ppcdrc_add_fastram(device_t *device, offs_t start, offs_t end, UINT8 readonly, void *base);
181void ppcdrc_add_hotspot(device_t *device, offs_t pc, UINT32 opcode, UINT32 cycles);
180#define MCFG_PPC_BUS_FREQUENCY(_frequency) \
181   ppc_device::set_bus_frequency(*device, _frequency);
182182
183void ppc4xx_spu_set_tx_handler(device_t *device, ppc4xx_spu_tx_handler handler);
184void ppc4xx_spu_receive_byte(device_t *device, UINT8 byteval);
185183
186void ppc_set_dcstore_callback(device_t *device, ppc_dcstore_handler handler);
187void ppc4xx_set_dma_read_handler(device_t *device, int channel, ppc4xx_dma_read_handler handler, int rate);
188void ppc4xx_set_dma_write_handler(device_t *device, int channel, ppc4xx_dma_write_handler handler, int rate);
189void ppc4xx_set_dcr_read_handler(device_t *device, read32_delegate dcr_read_func);
190void ppc4xx_set_dcr_write_handler(device_t *device, write32_delegate dcr_write_func);
184class ppc_frontend;
191185
192class ppc4xx_device : public legacy_cpu_device
186
187class ppc_device : public cpu_device
193188{
189   friend class ppc_frontend;
190
191protected:
192   /* PowerPC flavors */
193   enum powerpc_flavor
194   {
195      PPC_MODEL_403GA             = 0x00200000,
196      PPC_MODEL_403GB             = 0x00200100,
197      PPC_MODEL_403GC             = 0x00200200,
198      PPC_MODEL_403GCX            = 0x00201400,
199      PPC_MODEL_405GP             = 0x40110000,
200      PPC_MODEL_601               = 0x00010000,
201      PPC_MODEL_603               = 0x00030000,   /* "Wart" */
202      PPC_MODEL_604               = 0x00040000,   /* "Zephyr" */
203      PPC_MODEL_602               = 0x00050200,   /* "Galahad" */
204      PPC_MODEL_603E              = 0x00060103,   /* "Stretch", version 1.3 */
205      PPC_MODEL_603EV             = 0x00070000,   /* "Valiant" */
206      PPC_MODEL_603R              = 0x00071202,   /* "Goldeneye", version 2.1 */
207      PPC_MODEL_740               = 0x00080301,   /* "Arthur", version 3.1 */
208      PPC_MODEL_750               = PPC_MODEL_740,
209      PPC_MODEL_740P              = 0x00080202,   /* "Conan Doyle", version 1.2 */
210      PPC_MODEL_750P              = PPC_MODEL_740P,
211      PPC_MODEL_755               = 0x00083203,   /* "Goldfinger", version 2.3 */
212      PPC_MODEL_7400              = 0x000c0209,   /* "Max", version 2.9 */
213      PPC_MODEL_7410              = 0x800c1104,   /* "Nitro", version 3.4 */
214      PPC_MODEL_7450              = 0x80000201,   /* "Vger", version 2.1 */
215      PPC_MODEL_7451              = 0x80000203,   /* "Vger", version 2.3 */
216      PPC_MODEL_7441              = PPC_MODEL_7451,
217      PPC_MODEL_7455              = 0x80010303,   /* "Apollo 6", version 3.3 */
218      PPC_MODEL_7445              = PPC_MODEL_7455,
219      PPC_MODEL_7457              = 0x80020101,   /* "Apollo 7", version 1.1 */
220      PPC_MODEL_MPC8240           = 0x00810101,   /* "Kahlua" */
221      PPC_MODEL_MPC8241           = 0x80811014,   /* "Kahlua Lt" */
222      PPC_MODEL_MPC8245           = 0x80811014,   /* "Kahlua II" */
223   };
224
194225public:
195   ppc4xx_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, UINT32 clock, cpu_get_info_func info);
226   // construction/destruction
227   ppc_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, const char *shortname, int address_bits, int data_bits, powerpc_flavor flavor, UINT32 cap, UINT32 tb_divisor, address_map_constructor internal_map);
228
229   static void set_bus_frequency(device_t &device, UINT32 bus_frequency) { downcast<ppc_device &>(device).c_bus_frequency = bus_frequency; }
230
231   void ppc_set_dcstore_callback(ppc_dcstore_handler handler);
232
233   void ppcdrc_set_options(UINT32 options);
234   void ppcdrc_add_fastram(offs_t start, offs_t end, UINT8 readonly, void *base);
235   void ppcdrc_add_hotspot(offs_t pc, UINT32 opcode, UINT32 cycles);
236
237   TIMER_CALLBACK_MEMBER(decrementer_int_callback);
238   TIMER_CALLBACK_MEMBER(ppc4xx_buffered_dma_callback);
239   TIMER_CALLBACK_MEMBER(ppc4xx_fit_callback);
240   TIMER_CALLBACK_MEMBER(ppc4xx_pit_callback);
241   TIMER_CALLBACK_MEMBER(ppc4xx_spu_callback);
242
243   void ppc_cfunc_printf_exception();
244   void ppc_cfunc_printf_debug();
245   void ppc_cfunc_printf_probe();
246   void ppc_cfunc_unimplemented();
247   void ppccom_tlb_fill();
248   void ppccom_update_fprf();
249   void ppccom_dcstore_callback();
250   void ppccom_execute_tlbie();
251   void ppccom_execute_tlbia();
252   void ppccom_execute_tlbl();
253   void ppccom_execute_mfspr();
254   void ppccom_execute_mftb();
255   void ppccom_execute_mtspr();
256   void ppccom_tlb_flush();
257   void ppccom_execute_mfdcr();
258   void ppccom_execute_mtdcr();
259
260protected:
261   // device-level overrides
262   virtual void device_start();
263   virtual void device_reset();
264   virtual void device_stop();
265
266   // device_execute_interface overrides
267   virtual UINT32 execute_min_cycles() const { return 1; }
268   virtual UINT32 execute_max_cycles() const { return 40; }
269   virtual UINT32 execute_input_lines() const { return 1; }
270   virtual void execute_run();
271   virtual void execute_set_input(int inputnum, int state);
272
273   // device_memory_interface overrides
274   virtual const address_space_config *memory_space_config(address_spacenum spacenum = AS_0) const { return (spacenum == AS_PROGRAM) ? &m_program_config : NULL; }
275   virtual bool memory_translate(address_spacenum spacenum, int intention, offs_t &address);
276
277   // device_state_interface overrides
278   virtual void state_export(const device_state_entry &entry);
279   virtual void state_import(const device_state_entry &entry);
280   virtual void state_string_export(const device_state_entry &entry, astring &string);
281
282   // device_disasm_interface overrides
283   virtual UINT32 disasm_min_opcode_bytes() const { return 4; }
284   virtual UINT32 disasm_max_opcode_bytes() const { return 4; }
285   virtual offs_t disasm_disassemble(char *buffer, offs_t pc, const UINT8 *oprom, const UINT8 *opram, UINT32 options);
286
287   /* exception types */
288   enum
289   {
290      EXCEPTION_RESET         = 1,
291      EXCEPTION_MACHCHECK     = 2,
292      EXCEPTION_DSI           = 3,        /* PPCCAP_OEA */
293      EXCEPTION_PROTECTION    = 3,        /* PPCCAP_4XX */
294      EXCEPTION_ISI           = 4,
295      EXCEPTION_EI            = 5,
296      EXCEPTION_ALIGN         = 6,
297      EXCEPTION_PROGRAM       = 7,
298      EXCEPTION_NOFPU         = 8,
299      EXCEPTION_DECREMENT     = 9,
300      EXCEPTION_SYSCALL       = 12,
301      EXCEPTION_TRACE         = 13,
302      EXCEPTION_FPASSIST      = 14,
303      EXCEPTION_ITLBMISS      = 16,       /* PPCCAP_603_MMU */
304      EXCEPTION_DTLBMISSL     = 17,       /* PPCCAP_603_MMU */
305      EXCEPTION_DTLBMISSS     = 18,       /* PPCCAP_603_MMU */
306      EXCEPTION_COUNT
307   };
308
309   address_space_config m_program_config;
310   address_space *m_program;
311   UINT32 c_bus_frequency;
312
313   struct internal_ppc_state
314   {
315      UINT32 pc;
316      UINT32 r[32];
317      double f[32];
318      UINT32 cr[8];
319      UINT32 fpscr;
320      UINT32 msr;
321      UINT32 xerso;
322      UINT32 sr[16];
323      UINT32 spr[1024];
324      int icount;
325      UINT32 mode;                       /* current global mode */
326      UINT32 irq_pending;
327      /* parameters for calls */
328      UINT32 param0;
329      UINT32 param1;
330      /* PowerPC 603-specific state */
331      UINT32 mmu603_cmp;
332      UINT32 mmu603_hash[2];
333      UINT32 mmu603_r[4];
334      /* parameters for subroutines */
335      UINT32       tempaddr;                   /* temporary address storage */
336      drcuml_ireg  tempdata;                   /* temporary data storage */
337      UINT32       updateaddr;                 /* update address storage */
338      UINT32       swcount;                    /* counter for sw instructions */
339      const char * format;                     /* format string for printing */
340      UINT32       arg0;                       /* print_debug argument 1 */
341      double       fp0;                        /* floating point 0 */
342   };
343
344   internal_ppc_state *m_core;
345
346   int m_ppc_tb_base_icount;
347   int m_ppc_dec_base_icount;
348   int m_ppc_dec_trigger_cycle;
349   int m_bus_freq_multiplier;
350
351   UINT32 m_npc;
352   UINT32 m_dcr[256];
353
354   UINT32 m_lr;
355   UINT32 m_ctr;
356   UINT32 m_xer;
357   UINT32 m_pvr;
358   UINT32 m_srr0;
359   UINT32 m_srr1;
360   UINT32 m_srr2;
361   UINT32 m_srr3;
362   UINT32 m_hid0;
363   UINT32 m_hid1;
364   UINT32 m_hid2;
365   UINT32 m_sdr1;
366   UINT32 m_sprg[4];
367
368   UINT32 m_dsisr;
369   UINT32 m_dar;
370   UINT32 m_ear;
371   UINT32 m_dmiss;
372   UINT32 m_dcmp;
373   UINT32 m_hash1;
374   UINT32 m_hash2;
375   UINT32 m_imiss;
376   UINT32 m_icmp;
377   UINT32 m_rpa;
378
379   struct BATENT {
380      UINT32 u;
381      UINT32 l;
382   };
383
384   BATENT m_ibat[4];
385   BATENT m_dbat[4];
386
387   UINT32 m_evpr;
388   UINT32 m_exier;
389   UINT32 m_exisr;
390   UINT32 m_bear;
391   UINT32 m_besr;
392   UINT32 m_iocr;
393   UINT32 m_br[8];
394   UINT32 m_iabr;
395   UINT32 m_esr;
396   UINT32 m_iccr;
397   UINT32 m_dccr;
398   UINT32 m_pit;
399   UINT32 m_pit_counter;
400   UINT32 m_pit_int_enable;
401   UINT32 m_tsr;
402   UINT32 m_dbsr;
403   UINT32 m_sgr;
404   UINT32 m_pid;
405   UINT32 m_pbl1;
406   UINT32 m_pbl2;
407   UINT32 m_pbu1;
408   UINT32 m_pbu2;
409   UINT32 m_fit_bit;
410   UINT32 m_fit_int_enable;
411   UINT32 m_wdt_bit;
412   UINT32 m_wdt_int_enable;
413   UINT32 m_dac1;
414   UINT32 m_dac2;
415   UINT32 m_iac1;
416   UINT32 m_iac2;
417
418   struct SPU_REGS {
419      UINT8 spls;
420      UINT8 sphs;
421      UINT16 brd;
422      UINT8 spctl;
423      UINT8 sprc;
424      UINT8 sptc;
425      UINT8 sprb;
426      UINT8 sptb;
427      emu_timer *rx_timer;
428      emu_timer *tx_timer;
429   };
430
431   SPU_REGS m_spu_old;
432
433   struct DMA_REGS {
434      UINT32 cr;
435      UINT32 da;
436      UINT32 sa;
437      UINT32 ct;
438      UINT32 cc;
439   };
440
441   DMA_REGS m_dma[4];
442   UINT32 m_dmasr;
443
444   int m_reserved;
445   UINT32 m_reserved_address;
446
447   int m_interrupt_pending;
448
449   UINT64 m_tb;          /* 56-bit timebase register */
450
451   // STUFF added for the 6xx series
452   UINT32 m_dec, m_dec_frac;
453
454   union FPR {
455      UINT64  id;
456      double  fd;
457   };
458
459   union FPR32 {
460      UINT32 i;
461      float f;
462   };
463
464   FPR m_fpr[32];
465
466   int m_is603;
467   int m_is602;
468
469   /* PowerPC 602 specific registers */
470   UINT32 m_lt;
471   UINT32 m_sp;
472   UINT32 m_tcr;
473   UINT32 m_ibr;
474   UINT32 m_esasrr;
475   UINT32 m_sebr;
476   UINT32 m_ser;
477
478   /* MMU */
479   vtlb_state *m_vtlb;
480
481   /* architectural distinctions */
482   powerpc_flavor  m_flavor;
483   UINT32          m_cap;
484   UINT8           m_cache_line_size;
485   UINT32          m_tb_divisor;
486
487   /* PowerPC 4xx-specific state */
488   /* PowerPC 4XX-specific serial port state */
489   struct ppc4xx_spu_state
490   {
491      UINT8           regs[9];
492      UINT8           txbuf;
493      UINT8           rxbuf;
494      emu_timer *     timer;
495      UINT8           rxbuffer[256];
496      UINT32          rxin, rxout;
497      ppc4xx_spu_tx_handler tx_handler;
498   };
499
500   ppc4xx_spu_state m_spu;
501   emu_timer *     m_fit_timer;
502   emu_timer *     m_pit_timer;
503   emu_timer *     m_wdog_timer;
504   UINT32          m_pit_reload;
505   UINT32          m_irqstate;
506   emu_timer *     m_buffered_dma_timer[4];
507   int             m_buffered_dma_rate[4];
508
509   /* internal stuff */
510   direct_read_data *m_direct;
511   offs_t          m_codexor;
512   UINT32          m_system_clock;
513   UINT32          m_cpu_clock;
514   UINT64          m_tb_zero_cycles;
515   UINT64          m_dec_zero_cycles;
516   emu_timer *     m_decrementer_int_timer;
517
518   read32_delegate  m_dcr_read_func;
519   write32_delegate m_dcr_write_func;
520
521   ppc_dcstore_handler m_dcstore_handler;
522
523   ppc4xx_dma_read_handler m_ext_dma_read_handler[4];
524   ppc4xx_dma_write_handler m_ext_dma_write_handler[4];
525
526   /* PowerPC function pointers for memory accesses/exceptions */
527   jmp_buf m_exception_jmpbuf;
528   UINT8 (*m_ppcread8)(address_space &space, offs_t address);
529   UINT16 (*m_ppcread16)(address_space &space, offs_t address);
530   UINT32 (*m_ppcread32)(address_space &space, offs_t address);
531   UINT64 (*m_ppcread64)(address_space &space, offs_t address);
532   void (*m_ppcwrite8)(address_space &space, offs_t address, UINT8 data);
533   void (*m_ppcwrite16)(address_space &space, offs_t address, UINT16 data);
534   void (*m_ppcwrite32)(address_space &space, offs_t address, UINT32 data);
535   void (*m_ppcwrite64)(address_space &space, offs_t address, UINT64 data);
536   UINT16 (*m_ppcread16_unaligned)(address_space &space, offs_t address);
537   UINT32 (*m_ppcread32_unaligned)(address_space &space, offs_t address);
538   UINT64 (*m_ppcread64_unaligned)(address_space &space, offs_t address);
539   void (*m_ppcwrite16_unaligned)(address_space &space, offs_t address, UINT16 data);
540   void (*m_ppcwrite32_unaligned)(address_space &space, offs_t address, UINT32 data);
541   void (*m_ppcwrite64_unaligned)(address_space &space, offs_t address, UINT64 data);
542
543   void (*m_optable19[1024])(UINT32);
544   void (*m_optable31[1024])(UINT32);
545   void (*m_optable59[1024])(UINT32);
546   void (*m_optable63[1024])(UINT32);
547   void (*m_optable[64])(UINT32);
548
549   /* core state */
550   drc_cache           m_cache;                      /* pointer to the DRC code cache */
551   drcuml_state *      m_drcuml;                     /* DRC UML generator state */
552   ppc_frontend *      m_drcfe;                      /* pointer to the DRC front-end state */
553   UINT32              m_drcoptions;                 /* configurable DRC options */
554
555   /* parameters for subroutines */
556   UINT32              m_arg1;                       /* print_debug argument 2 */
557
558   /* tables */
559   UINT8               m_fpmode[4];                  /* FPU mode table */
560   UINT8               m_sz_cr_table[32];            /* SZ CR table */
561   UINT8               m_cmp_cr_table[32];           /* CMP CR table */
562   UINT8               m_cmpl_cr_table[32];          /* CMPL CR table */
563   UINT8               m_fcmp_cr_table[32];          /* FCMP CR table */
564
565   /* internal stuff */
566   UINT8               m_cache_dirty;                /* true if we need to flush the cache */
567
568   /* register mappings */
569   uml::parameter   m_regmap[32];                 /* parameter to register mappings for all 32 integer registers */
570   uml::parameter   m_fdregmap[32];               /* parameter to register mappings for all 32 floating point registers */
571
572   /* subroutines */
573   uml::code_handle *   m_entry;                      /* entry point */
574   uml::code_handle *   m_nocode;                     /* nocode exception handler */
575   uml::code_handle *   m_out_of_cycles;              /* out of cycles exception handler */
576   uml::code_handle *   m_tlb_mismatch;               /* tlb mismatch handler */
577   uml::code_handle *   m_swap_tgpr;                  /* swap TGPR handler */
578   uml::code_handle *   m_lsw[8][32];                 /* lsw entries */
579   uml::code_handle *   m_stsw[8][32];                /* stsw entries */
580   uml::code_handle *   m_read8[8];                   /* read byte */
581   uml::code_handle *   m_write8[8];                  /* write byte */
582   uml::code_handle *   m_read16[8];                  /* read half */
583   uml::code_handle *   m_read16mask[8];              /* read half */
584   uml::code_handle *   m_write16[8];                 /* write half */
585   uml::code_handle *   m_write16mask[8];             /* write half */
586   uml::code_handle *   m_read32[8];                  /* read word */
587   uml::code_handle *   m_read32align[8];             /* read word aligned */
588   uml::code_handle *   m_read32mask[8];              /* read word */
589   uml::code_handle *   m_write32[8];                 /* write word */
590   uml::code_handle *   m_write32align[8];            /* write word aligned */
591   uml::code_handle *   m_write32mask[8];             /* write word */
592   uml::code_handle *   m_read64[8];                  /* read double */
593   uml::code_handle *   m_read64mask[8];              /* read double */
594   uml::code_handle *   m_write64[8];                 /* write double */
595   uml::code_handle *   m_write64mask[8];             /* write double */
596   uml::code_handle *   m_exception[EXCEPTION_COUNT]; /* array of exception handlers */
597   uml::code_handle *   m_exception_norecover[EXCEPTION_COUNT];   /* array of exception handlers */
598
599   /* fast RAM */
600   /* fast RAM info */
601   struct fast_ram_info
602   {
603      offs_t              start;                      /* start of the RAM block */
604      offs_t              end;                        /* end of the RAM block */
605      UINT8               readonly;                   /* TRUE if read-only */
606      void *              base;                       /* base in memory where the RAM lives */
607   };
608
609   UINT32              m_fastram_select;
610   fast_ram_info       m_fastram[PPC_MAX_FASTRAM];
611
612   /* hotspots */
613   /* hotspot info */
614   struct hotspot_info
615   {
616      offs_t              pc;                         /* PC to consider */
617      UINT32              opcode;                     /* required opcode at that PC */
618      UINT32              cycles;                     /* number of cycles to eat when hit */
619   };
620   UINT32              m_hotspot_select;
621   hotspot_info        m_hotspot[PPC_MAX_HOTSPOTS];
622
623   UINT64 m_debugger_temp;
624
625   /* internal compiler state */
626   struct compiler_state
627   {
628      UINT32              cycles;                     /* accumulated cycles */
629      UINT8               checkints;                  /* need to check interrupts before next instruction */
630      UINT8               checksoftints;              /* need to check software interrupts before next instruction */
631      uml::code_label  labelnum;                   /* index for local labels */
632   };
633
634   int IS_PPC602(void);
635   int IS_PPC603(void);
636   int IS_PPC403(void);
637   UINT32 get_cr();
638   void set_cr(UINT32 value);
639   UINT32 get_xer();
640   void set_xer(UINT32 value);
641   UINT64 get_timebase();
642   void set_timebase(UINT64 newtb);
643   UINT32 get_decrementer();
644   void set_decrementer(UINT32 newdec);
645   UINT32 ppccom_translate_address_internal(int intention, offs_t &address);
646   void ppc4xx_set_irq_line(UINT32 bitmask, int state);
647   int ppc4xx_get_irq_line(UINT32 bitmask);
648   void ppc4xx_dma_update_irq_states();
649   int ppc4xx_dma_decrement_count(int dmachan);
650   int ppc4xx_dma_fetch_transmit_byte(int dmachan, UINT8 *byte);
651   int ppc4xx_dma_handle_receive_byte(int dmachan, UINT8 byte);
652   void ppc4xx_dma_exec(int dmachan);
653   void ppc4xx_spu_update_irq_states();
654   void ppc4xx_spu_rx_data(UINT8 data);
655   void ppc4xx_spu_timer_reset();
656   void alloc_handle(drcuml_state *drcuml, uml::code_handle **handleptr, const char *name);
657   void load_fast_iregs(drcuml_block *block);
658   void save_fast_iregs(drcuml_block *block);
659   UINT32 compute_rlw_mask(UINT8 mb, UINT8 me);
660   UINT32 compute_crf_mask(UINT8 crm);
661   UINT32 compute_spr(UINT32 spr);
662   void code_flush_cache();
663   void code_compile_block(UINT8 mode, offs_t pc);
664   void static_generate_entry_point();
665   void static_generate_nocode_handler();
666   void static_generate_out_of_cycles();
667   void static_generate_tlb_mismatch();
668   void static_generate_exception(UINT8 exception, int recover, const char *name);
669   void static_generate_memory_accessor(int mode, int size, int iswrite, int ismasked, const char *name, uml::code_handle *&handleptr, uml::code_handle *masked);
670   void static_generate_swap_tgpr();
671   void static_generate_lsw_entries(int mode);
672   void static_generate_stsw_entries(int mode);
673   void generate_update_mode(drcuml_block *block);
674   void generate_update_cycles(drcuml_block *block, compiler_state *compiler, uml::parameter param, int allow_exception);
675   void generate_checksum_block(drcuml_block *block, compiler_state *compiler, const opcode_desc *seqhead, const opcode_desc *seqlast);
676   void generate_sequence_instruction(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
677   void generate_compute_flags(drcuml_block *block, const opcode_desc *desc, int updatecr, UINT32 xermask, int invertcarry);
678   void generate_shift_flags(drcuml_block *block, const opcode_desc *desc, UINT32 op);
679   void generate_fp_flags(drcuml_block *block, const opcode_desc *desc, int updatefprf);
680   void generate_branch(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc, int source, UINT8 link);
681   void generate_branch_bo(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc, UINT32 bo, UINT32 bi, int source, int link);
682   int generate_opcode(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
683   int generate_instruction_13(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
684   int generate_instruction_1f(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
685   int generate_instruction_3b(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
686   int generate_instruction_3f(drcuml_block *block, compiler_state *compiler, const opcode_desc *desc);
687   void log_add_disasm_comment(drcuml_block *block, UINT32 pc, UINT32 op);
688   const char *log_desc_flags_to_string(UINT32 flags);
689   void log_register_list(drcuml_state *drcuml, const char *string, const UINT32 *reglist, const UINT32 *regnostarlist);
690   void log_opcode_desc(drcuml_state *drcuml, const opcode_desc *desclist, int indent);
691
692};
693
694
695//class ppc403_device : public ppc_device
696//{
697//public:
698//   ppc403_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
699//
700//protected:
701//   virtual UINT32 execute_input_lines() const { return 8; }
702//};
703//
704//
705//class ppc405_device : public ppc_device
706//{
707//public:
708//   ppc405_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
709//
710//protected:
711//   virtual UINT32 execute_input_lines() const { return 8; }
712//};
713
714
715class ppc603_device : public ppc_device
716{
717public:
718   ppc603_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
719};
720
721
722class ppc603e_device : public ppc_device
723{
724public:
725   ppc603e_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
726};
727
728
729class ppc603r_device : public ppc_device
730{
731public:
732   ppc603r_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
733};
734
735
736class ppc602_device : public ppc_device
737{
738public:
739   ppc602_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
740};
741
742
743class mpc8240_device : public ppc_device
744{
745public:
746   mpc8240_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
747};
748
749
750class ppc601_device : public ppc_device
751{
752public:
753   ppc601_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
754};
755
756
757class ppc604_device : public ppc_device
758{
759public:
760   ppc604_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
761};
762
763
764class ppc4xx_device : public ppc_device
765{
766public:
767   ppc4xx_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, const char *shortname, powerpc_flavor flavor, UINT32 cap, UINT32 tb_divisor);
768
769   void ppc4xx_spu_set_tx_handler(ppc4xx_spu_tx_handler handler);
770   void ppc4xx_spu_receive_byte(UINT8 byteval);
771
772   void ppc4xx_set_dma_read_handler(int channel, ppc4xx_dma_read_handler handler, int rate);
773   void ppc4xx_set_dma_write_handler(int channel, ppc4xx_dma_write_handler handler, int rate);
774   void ppc4xx_set_dcr_read_handler(read32_delegate dcr_read_func);
775   void ppc4xx_set_dcr_write_handler(write32_delegate dcr_write_func);
776
196777   DECLARE_READ8_MEMBER( ppc4xx_spu_r );
197778   DECLARE_WRITE8_MEMBER( ppc4xx_spu_w );
779
780protected:
781   virtual UINT32 execute_input_lines() const { return 5; }
782   virtual void execute_set_input(int inputnum, int state);
198783};
199784
200CPU_GET_INFO( ppc403ga );
201785
202786class ppc403ga_device : public ppc4xx_device
203787{
204788public:
205   ppc403ga_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, UINT32 clock);
789   ppc403ga_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
206790};
207791
208extern const device_type PPC403GA;
209792
210CPU_GET_INFO( ppc403gcx );
211
212793class ppc403gcx_device : public ppc4xx_device
213794{
214795public:
215   ppc403gcx_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, UINT32 clock);
796   ppc403gcx_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
216797};
217798
218extern const device_type PPC403GCX;
219799
220
221CPU_GET_INFO( ppc405gp );
222
223800class ppc405gp_device : public ppc4xx_device
224801{
225802public:
226   ppc405gp_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, UINT32 clock);
803   ppc405gp_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
227804};
228805
806
807extern const device_type PPC601;
808extern const device_type PPC602;
809extern const device_type PPC603;
810extern const device_type PPC603E;
811extern const device_type PPC603R;
812extern const device_type PPC604;
813extern const device_type MPC8240;
814extern const device_type PPC403GA;
815extern const device_type PPC403GCX;
229816extern const device_type PPC405GP;
230817
231DECLARE_LEGACY_CPU_DEVICE(PPC601, ppc601);
232DECLARE_LEGACY_CPU_DEVICE(PPC602, ppc602);
233DECLARE_LEGACY_CPU_DEVICE(PPC603, ppc603);
234DECLARE_LEGACY_CPU_DEVICE(PPC603E, ppc603e);
235DECLARE_LEGACY_CPU_DEVICE(PPC603R, ppc603r);
236DECLARE_LEGACY_CPU_DEVICE(PPC604, ppc604);
237DECLARE_LEGACY_CPU_DEVICE(MPC8240, mpc8240);
238818
239
240819#endif  /* __PPC_H__ */
trunk/src/emu/drivers/testcpu.c
r31142r31143
9797      m_space = &m_cpu->space(AS_PROGRAM);
9898
9999      // configure DRC in the most compatible mode
100      ppcdrc_set_options(m_cpu, PPCDRC_COMPATIBLE_OPTIONS);
100      m_cpu->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS);
101101
102102      // set a timer to go off right away
103103      timer_set(attotime::zero);
r31142r31143
185185//  MACHINE DRIVERS
186186//**************************************************************************
187187
188static const powerpc_config ppc_config =
189{
190   // 603e, Stretch, 1.3
191   66000000        // Multiplier 1, Bus = 66MHz, Core = 66MHz
192};
193
194188static MACHINE_CONFIG_START( testcpu, testcpu_state )
195189
196190   // CPUs
197191   MCFG_CPU_ADD("maincpu", PPC603E, 66000000)
198   MCFG_CPU_CONFIG(ppc_config)
192   MCFG_PPC_BUS_FREQUENCY(66000000)  // Multiplier 1, Bus = 66MHz, Core = 66MHz
199193   MCFG_CPU_PROGRAM_MAP(ppc_mem)
200194MACHINE_CONFIG_END
201195
trunk/src/mess/includes/dm7000.h
r31142r31143
1717   {
1818   }
1919
20   required_device<cpu_device> m_maincpu;
20   required_device<ppc4xx_device> m_maincpu;
2121   required_device<generic_terminal_device> m_terminal;
2222
2323   DECLARE_WRITE8_MEMBER ( dm7000_iic0_w );
trunk/src/mess/drivers/dm7000.c
r31142r31143
257257   dcr[DCRSTB045_FRAME_BUFR_BASE] = 0x0f000000;
258258   m_scc0_lsr = UART_LSR_THRE | UART_LSR_TEMT;
259259
260   ppc4xx_set_dcr_read_handler(m_maincpu, read32_delegate(FUNC(dm7000_state::dcr_r),this));
261   ppc4xx_set_dcr_write_handler(m_maincpu, write32_delegate(FUNC(dm7000_state::dcr_w),this));
260   m_maincpu->ppc4xx_set_dcr_read_handler(read32_delegate(FUNC(dm7000_state::dcr_r),this));
261   m_maincpu->ppc4xx_set_dcr_write_handler(write32_delegate(FUNC(dm7000_state::dcr_w),this));
262262}
263263
264264void dm7000_state::video_start()
r31142r31143
297297   m_scc0_lsr = 1;
298298}
299299
300static const powerpc_config ppc405_config =
301{
302   252000000
303};
304
305300static MACHINE_CONFIG_START( dm7000, dm7000_state )
306301   /* basic machine hardware */
307302   MCFG_CPU_ADD("maincpu",PPC405GP, 252000000 / 10) // Should be PPC405D4?
308303   // Slowed down 10 times in order to get normal response for now
309   MCFG_CPU_CONFIG(ppc405_config)
304   MCFG_PPC_BUS_FREQUENCY(252000000)
310305   MCFG_CPU_PROGRAM_MAP(dm7000_mem)
311306
312307
trunk/src/mame/drivers/viper.c
r31142r31143
363363   void mpc8240_epic_reset(void);
364364   int ds2430_insert_cmd_bit(int bit);
365365   void DS2430_w(int bit);
366   required_device<cpu_device> m_maincpu;
366   required_device<ppc_device> m_maincpu;
367367   required_device<ata_interface_device> m_ata;
368368};
369369
r31142r31143
19861986/*****************************************************************************/
19871987
19881988
1989static const powerpc_config viper_ppc_cfg =
1990{
1991   100000000
1992};
1993
19941989INTERRUPT_GEN_MEMBER(viper_state::viper_vblank)
19951990{
19961991   mpc8240_interrupt(MPC8240_IRQ0);
r31142r31143
20092004   mpc8240_epic_init();
20102005
20112006   /* set conservative DRC options */
2012   ppcdrc_set_options(m_maincpu, PPCDRC_COMPATIBLE_OPTIONS);
2007   m_maincpu->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS);
20132008
20142009   /* configure fast RAM regions for DRC */
2015   ppcdrc_add_fastram(m_maincpu, 0x00000000, 0x00ffffff, FALSE, workram);
2010   m_maincpu->ppcdrc_add_fastram(0x00000000, 0x00ffffff, FALSE, workram);
20162011
20172012   ds2430_rom = (UINT8*)memregion("ds2430")->base();
20182013}
r31142r31143
20332028
20342029   /* basic machine hardware */
20352030   MCFG_CPU_ADD("maincpu", MPC8240, 200000000)
2036   MCFG_CPU_CONFIG(viper_ppc_cfg)
2031   MCFG_PPC_BUS_FREQUENCY(100000000)
20372032   MCFG_CPU_PROGRAM_MAP(viper_map)
20382033   MCFG_CPU_VBLANK_INT_DRIVER("screen", viper_state,  viper_vblank)
20392034
trunk/src/mame/drivers/taitotz.c
r31142r31143
547547   {
548548   }
549549
550   required_device<cpu_device> m_maincpu;
550   required_device<ppc_device> m_maincpu;
551551   required_device<cpu_device> m_iocpu;
552552   required_shared_ptr<UINT64> m_work_ram;
553553   required_shared_ptr<UINT16> m_mbox_ram;
r31142r31143
26412641void taitotz_state::machine_start()
26422642{
26432643   /* set conservative DRC options */
2644   ppcdrc_set_options(m_maincpu, PPCDRC_COMPATIBLE_OPTIONS);
2644   m_maincpu->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS);
26452645
26462646   /* configure fast RAM regions for DRC */
2647   ppcdrc_add_fastram(m_maincpu, 0x40000000, 0x40ffffff, FALSE, m_work_ram);
2647   m_maincpu->ppcdrc_add_fastram(0x40000000, 0x40ffffff, FALSE, m_work_ram);
26482648}
26492649
26502650
r31142r31143
26582658   m_iocpu->set_input_line(TLCS900_INT2, state);
26592659}
26602660
2661static const powerpc_config ppc603e_config =
2662{
2663   XTAL_66_6667MHz        /* Multiplier 1.5, Bus = 66MHz, Core = 100MHz */
2664};
2665
2666
26672661static MACHINE_CONFIG_START( taitotz, taitotz_state )
26682662   /* IBM EMPPC603eBG-100 */
26692663   MCFG_CPU_ADD("maincpu", PPC603E, 100000000)
2670   MCFG_CPU_CONFIG(ppc603e_config)
2664   MCFG_PPC_BUS_FREQUENCY(XTAL_66_6667MHz)    /* Multiplier 1.5, Bus = 66MHz, Core = 100MHz */
26712665   MCFG_CPU_PROGRAM_MAP(ppc603e_mem)
26722666
26732667   /* TMP95C063F I/O CPU */
trunk/src/mame/drivers/hornet.c
r31142r31143
357357   required_shared_ptr<UINT32> m_workram;
358358   required_shared_ptr<UINT32> m_sharc_dataram0;
359359   optional_shared_ptr<UINT32> m_sharc_dataram1;
360   required_device<cpu_device> m_maincpu;
360   required_device<ppc4xx_device> m_maincpu;
361361   required_device<cpu_device> m_audiocpu;
362362   required_device<k056800_device> m_k056800;
363363   optional_device<cpu_device> m_gn680;
r31142r31143
919919   m_jvs_sdata = auto_alloc_array_clear(machine(), UINT8, 1024);
920920
921921   /* set conservative DRC options */
922   ppcdrc_set_options(m_maincpu, PPCDRC_COMPATIBLE_OPTIONS);
922   m_maincpu->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS);
923923
924924   /* configure fast RAM regions for DRC */
925   ppcdrc_add_fastram(m_maincpu, 0x00000000, 0x003fffff, FALSE, m_workram);
925   m_maincpu->ppcdrc_add_fastram(0x00000000, 0x003fffff, FALSE, m_workram);
926926
927927   save_item(NAME(m_led_reg0));
928928   save_item(NAME(m_led_reg1));
r31142r31143
11611161      if (b == 0xe0)
11621162      {
11631163         sum += 0xd0 + 0xdf;
1164         ppc4xx_spu_receive_byte(m_maincpu, 0xd0);
1165         ppc4xx_spu_receive_byte(m_maincpu, 0xdf);
1164         m_maincpu->ppc4xx_spu_receive_byte(0xd0);
1165         m_maincpu->ppc4xx_spu_receive_byte(0xdf);
11661166      }
11671167      else if (b == 0xd0)
11681168      {
11691169         sum += 0xd0 + 0xcf;
1170         ppc4xx_spu_receive_byte(m_maincpu, 0xd0);
1171         ppc4xx_spu_receive_byte(m_maincpu, 0xcf);
1170         m_maincpu->ppc4xx_spu_receive_byte(0xd0);
1171         m_maincpu->ppc4xx_spu_receive_byte(0xcf);
11721172      }
11731173      else
11741174      {
11751175         sum += b;
1176         ppc4xx_spu_receive_byte(m_maincpu, b);
1176         m_maincpu->ppc4xx_spu_receive_byte(b);
11771177      }
11781178   }
11791179   return sum;
r31142r31143
12661266
12671267   // write jvs return data
12681268   sum = 0x00 + (rdata_ptr+1);
1269   ppc4xx_spu_receive_byte(m_maincpu, 0xe0);           // sync
1270   ppc4xx_spu_receive_byte(m_maincpu, 0x00);           // node
1271   ppc4xx_spu_receive_byte(m_maincpu, rdata_ptr + 1);  // num of bytes
1269   m_maincpu->ppc4xx_spu_receive_byte(0xe0);           // sync
1270   m_maincpu->ppc4xx_spu_receive_byte(0x00);           // node
1271   m_maincpu->ppc4xx_spu_receive_byte(rdata_ptr + 1);  // num of bytes
12721272   sum += jvs_encode_data(rdata, rdata_ptr);
1273   ppc4xx_spu_receive_byte(m_maincpu, sum - 1);        // checksum
1273   m_maincpu->ppc4xx_spu_receive_byte(sum - 1);        // checksum
12741274
12751275   m_jvs_sdata_ptr = 0;
12761276}
r31142r31143
12831283   m_konppc->set_cgboard_texture_bank(0, "bank5", memregion("user5")->base());
12841284   m_led_reg0 = m_led_reg1 = 0x7f;
12851285
1286   ppc4xx_spu_set_tx_handler(m_maincpu, jamma_jvs_w);
1286   m_maincpu->ppc4xx_spu_set_tx_handler(jamma_jvs_w);
12871287}
12881288
12891289DRIVER_INIT_MEMBER(hornet_state,hornet_2board)
r31142r31143
12921292   m_konppc->set_cgboard_texture_bank(1, "bank6", memregion("user5")->base());
12931293   m_led_reg0 = m_led_reg1 = 0x7f;
12941294
1295   ppc4xx_spu_set_tx_handler(m_maincpu, jamma_jvs_w);
1295   m_maincpu->ppc4xx_spu_set_tx_handler(jamma_jvs_w);
12961296}
12971297
12981298/*****************************************************************************/
trunk/src/mame/drivers/gticlub.c
r31142r31143
265265   static const int m_sound_timer_usec = 2400;
266266
267267   required_shared_ptr<UINT32> m_work_ram;
268   required_device<cpu_device> m_maincpu;
268   required_device<ppc_device> m_maincpu;
269269   required_device<cpu_device> m_audiocpu;
270270   required_device<adsp21062_device> m_dsp;
271271   optional_device<cpu_device> m_dsp2;
r31142r31143
479479MACHINE_START_MEMBER(gticlub_state,gticlub)
480480{
481481   /* set conservative DRC options */
482   ppcdrc_set_options(m_maincpu, PPCDRC_COMPATIBLE_OPTIONS);
482   m_maincpu->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS);
483483
484484   /* configure fast RAM regions for DRC */
485   ppcdrc_add_fastram(m_maincpu, 0x00000000, 0x000fffff, FALSE, m_work_ram);
485   m_maincpu->ppcdrc_add_fastram(0x00000000, 0x000fffff, FALSE, m_work_ram);
486486
487487   m_sound_irq_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(gticlub_state::sound_irq), this));
488488}
trunk/src/mame/drivers/ultrsprt.c
r31142r31143
2525   static const UINT32 VRAM_PAGES      = 2;
2626   static const UINT32 VRAM_PAGE_BYTES = 512 * 1024;
2727
28   required_device<cpu_device> m_maincpu;
28   required_device<ppc_device> m_maincpu;
2929   required_device<cpu_device> m_audiocpu;
3030   required_device<k056800_device> m_k056800;
3131   required_shared_ptr<UINT32> m_workram;
r31142r31143
184184void ultrsprt_state::machine_start()
185185{
186186   /* set conservative DRC options */
187   ppcdrc_set_options(m_maincpu, PPCDRC_COMPATIBLE_OPTIONS);
187   m_maincpu->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS);
188188
189189   /* configure fast RAM regions for DRC */
190   ppcdrc_add_fastram(m_maincpu, 0xff000000, 0xff01ffff, FALSE, m_workram);
190   m_maincpu->ppcdrc_add_fastram(0xff000000, 0xff01ffff, FALSE, m_workram);
191191
192192   m_vram = auto_alloc_array(machine(), UINT8, VRAM_PAGE_BYTES * VRAM_PAGES);
193193
trunk/src/mame/drivers/cobra.c
r31142r31143
617617   {
618618   }
619619
620   required_device<cpu_device> m_maincpu;
621   required_device<cpu_device> m_subcpu;
622   required_device<cpu_device> m_gfxcpu;
620   required_device<ppc_device> m_maincpu;
621   required_device<ppc4xx_device> m_subcpu;
622   required_device<ppc_device> m_gfxcpu;
623623   required_shared_ptr<UINT64> m_gfx_pagetable;
624624   required_device<k001604_device> m_k001604;
625625   required_device<ata_interface_device> m_ata;
r31142r31143
19231923
19241924static void sub_jvs_w(device_t *device, UINT8 data)
19251925{
1926   cobra_state *cobra = device->machine().driver_data<cobra_state>();
19261927   cobra_jvs_host *jvs = downcast<cobra_jvs_host *>(device->machine().device("cobra_jvs_host"));
19271928
19281929#if LOG_JVS
r31142r31143
19471948
19481949      for (int i=0; i < rec_size; i++)
19491950      {
1950         ppc4xx_spu_receive_byte(device, rec_data[i]);
1951         cobra->m_subcpu->ppc4xx_spu_receive_byte(rec_data[i]);
19511952      }
19521953   }
19531954}
r31142r31143
31163117   PORT_BIT( 0x0001, IP_ACTIVE_LOW, IPT_UNUSED ) PORT_PLAYER(2)
31173118INPUT_PORTS_END
31183119
3119static powerpc_config main_ppc_cfg =
3120{
3121   XTAL_66_6667MHz        /* Multiplier 1.5, Bus = 66MHz, Core = 100MHz */
3122};
3123
3124static powerpc_config gfx_ppc_cfg =
3125{
3126   XTAL_66_6667MHz        /* Multiplier 1.5, Bus = 66MHz, Core = 100MHz */
3127};
3128
3129
31303120WRITE_LINE_MEMBER(cobra_state::ide_interrupt)
31313121{
31323122   if (state == CLEAR_LINE)
r31142r31143
31763166
31773167   /* basic machine hardware */
31783168   MCFG_CPU_ADD("maincpu", PPC603, 100000000)      /* 603EV, 100? MHz */
3179   MCFG_CPU_CONFIG(main_ppc_cfg)
3169   MCFG_PPC_BUS_FREQUENCY(XTAL_66_6667MHz)  /* Multiplier 1.5, Bus = 66MHz, Core = 100MHz */
31803170   MCFG_CPU_PROGRAM_MAP(cobra_main_map)
31813171   MCFG_CPU_VBLANK_INT_DRIVER("screen", cobra_state,  cobra_vblank)
31823172
r31142r31143
31843174   MCFG_CPU_PROGRAM_MAP(cobra_sub_map)
31853175
31863176   MCFG_CPU_ADD("gfxcpu", PPC604, 100000000)       /* 604, 100? MHz */
3187   MCFG_CPU_CONFIG(gfx_ppc_cfg)
3177   MCFG_PPC_BUS_FREQUENCY(XTAL_66_6667MHz)   /* Multiplier 1.5, Bus = 66MHz, Core = 100MHz */
31883178   MCFG_CPU_PROGRAM_MAP(cobra_gfx_map)
31893179
31903180   MCFG_QUANTUM_TIME(attotime::from_hz(15005))
r31142r31143
32733263                        cobra_fifo::event_delegate(FUNC(cobra_state::s2mfifo_event_callback), this))
32743264                        );
32753265
3276   ppc_set_dcstore_callback(m_maincpu, main_cpu_dc_store);
3266   m_maincpu->ppc_set_dcstore_callback(main_cpu_dc_store);
32773267
3278   ppc_set_dcstore_callback(m_gfxcpu, gfx_cpu_dc_store);
3268   m_gfxcpu->ppc_set_dcstore_callback(gfx_cpu_dc_store);
32793269
3280   ppc4xx_set_dma_write_handler(m_subcpu, 0, sub_sound_dma_w, 44100);
3281   ppc4xx_spu_set_tx_handler(m_subcpu, sub_jvs_w);
3270   m_subcpu->ppc4xx_set_dma_write_handler(0, sub_sound_dma_w, 44100);
3271   m_subcpu->ppc4xx_spu_set_tx_handler(sub_jvs_w);
32823272
32833273
32843274   m_comram[0] = auto_alloc_array(machine(), UINT32, 0x40000/4);
trunk/src/mame/drivers/taitopjc.c
r31142r31143
504504}
505505
506506
507static const powerpc_config ppc603e_config =
508{
509   XTAL_66_6667MHz        /* Multiplier 1.5, Bus = 66MHz, Core = 100MHz */
510};
511
512
513507static MACHINE_CONFIG_START( taitopjc, taitopjc_state )
514508   MCFG_CPU_ADD("maincpu", PPC603E, 100000000)
515   MCFG_CPU_CONFIG(ppc603e_config)
509   MCFG_PPC_BUS_FREQUENCY(XTAL_66_6667MHz)    /* Multiplier 1.5, Bus = 66MHz, Core = 100MHz */
516510   MCFG_CPU_PROGRAM_MAP(ppc603e_mem)
517511
518512   /* TMP95C063F I/O CPU */
trunk/src/mame/drivers/firebeat.c
r31142r31143
181181      m_ata(*this, "ata")
182182   { }
183183
184   required_device<cpu_device> m_maincpu;
184   required_device<ppc4xx_device> m_maincpu;
185185   required_shared_ptr<UINT32> m_work_ram;
186186   required_device<fujitsu_29f016a_device> m_flash_main;
187187   required_device<fujitsu_29f016a_device> m_flash_snd1;
r31142r31143
14831483MACHINE_START_MEMBER(firebeat_state,firebeat)
14841484{
14851485   /* set conservative DRC options */
1486   ppcdrc_set_options(m_maincpu, PPCDRC_COMPATIBLE_OPTIONS);
1486   m_maincpu->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS);
14871487
14881488   /* configure fast RAM regions for DRC */
1489   ppcdrc_add_fastram(m_maincpu, 0x00000000, 0x01ffffff, FALSE, m_work_ram);
1489   m_maincpu->ppcdrc_add_fastram(0x00000000, 0x01ffffff, FALSE, m_work_ram);
14901490}
14911491
14921492static ADDRESS_MAP_START( firebeat_map, AS_PROGRAM, 32, firebeat_state )
r31142r31143
19551955   firebeat_state *state = device->machine().driver_data<firebeat_state>();
19561956   int r = state->ibutton_w(data);
19571957   if (r >= 0)
1958      ppc4xx_spu_receive_byte(state->m_maincpu, r);
1958      state->m_maincpu->ppc4xx_spu_receive_byte(r);
19591959}
19601960
19611961/*****************************************************************************/
r31142r31143
19831983
19841984   m_cur_cab_data = cab_data;
19851985
1986   ppc4xx_spu_set_tx_handler(m_maincpu, security_w);
1986   m_maincpu->ppc4xx_spu_set_tx_handler(security_w);
19871987
19881988   set_ibutton(rom);
19891989
trunk/src/mame/drivers/model3.c
r31142r31143
11841184{
11851185   model3_state *state = machine.driver_data<model3_state>();
11861186   /* set conservative DRC options */
1187   ppcdrc_set_options(machine.device("maincpu"), PPCDRC_COMPATIBLE_OPTIONS - PPCDRC_ACCURATE_SINGLES);
1187   machine.device<ppc_device>("maincpu")->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS - PPCDRC_ACCURATE_SINGLES);
11881188
11891189   /* configure fast RAM regions for DRC */
1190   ppcdrc_add_fastram(machine.device("maincpu"), 0x00000000, 0x007fffff, FALSE, state->m_work_ram);
1190   machine.device<ppc_device>("maincpu")->ppcdrc_add_fastram(0x00000000, 0x007fffff, FALSE, state->m_work_ram);
11911191}
11921192
11931193TIMER_CALLBACK_MEMBER(model3_state::model3_sound_timer_tick)
r31142r31143
53805380      set_irq_line(0x0d, ASSERT_LINE);
53815381}
53825382
5383static const powerpc_config model3_10 =
5384{
5385   /* 603e, Stretch, 1.3 */
5386   66000000       /* Multiplier 1, Bus = 66MHz, Core = 66MHz */
5387};
5388
5389static const powerpc_config model3_15 =
5390{
5391   /* 603e, Stretch, 1.3 */
5392   66000000       /* Multiplier 1.5, Bus = 66MHz, Core = 100MHz */
5393};
5394
5395static const powerpc_config model3_2x =
5396{
5397   /* 603e-PID7t, Goldeneye, 2.1 */
5398   66000000       /* Multiplier 2.5, Bus = 66MHz, Core = 166MHz */
5399};
5400
54015383static MACHINE_CONFIG_START( model3_10, model3_state )
54025384   MCFG_CPU_ADD("maincpu", PPC603E, 66000000)
5403   MCFG_CPU_CONFIG(model3_10)
5385   MCFG_PPC_BUS_FREQUENCY(66000000)   /* Multiplier 1, Bus = 66MHz, Core = 66MHz */
54045386   MCFG_CPU_PROGRAM_MAP(model3_mem)
54055387   MCFG_TIMER_DRIVER_ADD_SCANLINE("scantimer", model3_state, model3_interrupt, "screen", 0, 1)
54065388
r31142r31143
54475429
54485430static MACHINE_CONFIG_START( model3_15, model3_state )
54495431   MCFG_CPU_ADD("maincpu", PPC603E, 100000000)
5450   MCFG_CPU_CONFIG(model3_15)
5432   MCFG_PPC_BUS_FREQUENCY(66000000)       /* Multiplier 1.5, Bus = 66MHz, Core = 100MHz */
54515433   MCFG_CPU_PROGRAM_MAP(model3_mem)
54525434   MCFG_TIMER_DRIVER_ADD_SCANLINE("scantimer", model3_state, model3_interrupt, "screen", 0, 1)
54535435
r31142r31143
54985480
54995481static MACHINE_CONFIG_START( model3_20, model3_state )
55005482   MCFG_CPU_ADD("maincpu", PPC603R, 166000000)
5501   MCFG_CPU_CONFIG(model3_2x)
5483   MCFG_PPC_BUS_FREQUENCY(66000000)    /* Multiplier 2.5, Bus = 66MHz, Core = 166MHz */
55025484   MCFG_CPU_PROGRAM_MAP(model3_mem)
55035485   MCFG_TIMER_DRIVER_ADD_SCANLINE("scantimer", model3_state, model3_interrupt, "screen", 0, 1)
55045486
r31142r31143
55355517
55365518static MACHINE_CONFIG_START( model3_21, model3_state )
55375519   MCFG_CPU_ADD("maincpu", PPC603R, 166000000)
5538   MCFG_CPU_CONFIG(model3_2x)
5520   MCFG_PPC_BUS_FREQUENCY(66000000)    /* Multiplier 2.5, Bus = 66MHz, Core = 166MHz */
55395521   MCFG_CPU_PROGRAM_MAP(model3_mem)
55405522   MCFG_TIMER_DRIVER_ADD_SCANLINE("scantimer", model3_state, model3_interrupt, "screen", 0, 1)
55415523
trunk/src/mame/drivers/triforce.c
r31142r31143
439439   virtual void machine_start();
440440   virtual void video_start();
441441   UINT32 screen_update_triforce(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect);
442   required_device<cpu_device> m_maincpu;
442   required_device<ppc_device> m_maincpu;
443443};
444444
445445READ64_MEMBER(triforce_state::gc_pi_r)
r31142r31143
537537void triforce_state::machine_start()
538538{
539539   /* set conservative DRC options */
540   ppcdrc_set_options(m_maincpu, PPCDRC_COMPATIBLE_OPTIONS);
540   m_maincpu->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS);
541541
542542   UINT8 *rom = (UINT8*)memregion("maincpu")->base();
543543   descrambler(&rom[0x100], 0x1afe00);
trunk/src/mame/drivers/zr107.c
r31142r31143
210210      m_konppc(*this, "konppc") { }
211211
212212
213   required_device<cpu_device> m_maincpu;
213   required_device<ppc_device> m_maincpu;
214214   required_device<cpu_device> m_audiocpu;
215215   required_device<cpu_device> m_dsp;
216216   optional_device<k001604_device> m_k001604;
r31142r31143
457457void zr107_state::machine_start()
458458{
459459   /* set conservative DRC options */
460   ppcdrc_set_options(m_maincpu, PPCDRC_COMPATIBLE_OPTIONS);
460   m_maincpu->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS);
461461
462462   /* configure fast RAM regions for DRC */
463   ppcdrc_add_fastram(m_maincpu, 0x00000000, 0x000fffff, FALSE, m_workram);
463   m_maincpu->ppcdrc_add_fastram(0x00000000, 0x000fffff, FALSE, m_workram);
464464}
465465
466466static ADDRESS_MAP_START( zr107_map, AS_PROGRAM, 32, zr107_state )
trunk/src/mame/drivers/konamim2.c
r31142r31143
11481148INPUT_PORTS_END
11491149
11501150
1151static const powerpc_config ppc602_config =
1152{
1153   33000000           /* Multiplier 2, Bus = 33MHz, Core = 66MHz */
1154};
1155
11561151INTERRUPT_GEN_MEMBER(konamim2_state::m2)
11571152{
11581153   if (m_irq_enable & 0x800000)
r31142r31143
11721167
11731168   /* basic machine hardware */
11741169   MCFG_CPU_ADD("maincpu", PPC602, 66000000)   /* actually PPC602, 66MHz */
1175   MCFG_CPU_CONFIG(ppc602_config)
1170   MCFG_PPC_BUS_FREQUENCY(33000000)  /* Multiplier 2, Bus = 33MHz, Core = 66MHz */
11761171   MCFG_CPU_PROGRAM_MAP(m2_main)
11771172   MCFG_CPU_VBLANK_INT_DRIVER("screen", konamim2_state,  m2)
11781173
11791174   MCFG_CPU_ADD("sub", PPC602, 66000000)   /* actually PPC602, 66MHz */
1180   MCFG_CPU_CONFIG(ppc602_config)
1175   MCFG_PPC_BUS_FREQUENCY(33000000)  /* Multiplier 2, Bus = 33MHz, Core = 66MHz */
11811176   MCFG_CPU_PROGRAM_MAP(m2_main)
11821177
11831178   /* video hardware */
trunk/src/mame/drivers/nwk-tr.c
r31142r31143
256256   UINT8 m_led_reg0;
257257   UINT8 m_led_reg1;
258258   required_shared_ptr<UINT32> m_work_ram;
259   required_device<cpu_device> m_maincpu;
259   required_device<ppc_device> m_maincpu;
260260   required_device<cpu_device> m_audiocpu;
261261   required_device<cpu_device> m_dsp;
262262   required_device<k056800_device> m_k056800;
r31142r31143
573573void nwktr_state::machine_start()
574574{
575575   /* set conservative DRC options */
576   ppcdrc_set_options(m_maincpu, PPCDRC_COMPATIBLE_OPTIONS);
576   m_maincpu->ppcdrc_set_options(PPCDRC_COMPATIBLE_OPTIONS);
577577
578578   /* configure fast RAM regions for DRC */
579   ppcdrc_add_fastram(m_maincpu, 0x00000000, 0x003fffff, FALSE, m_work_ram);
579   m_maincpu->ppcdrc_add_fastram(0x00000000, 0x003fffff, FALSE, m_work_ram);
580580
581581   m_sound_irq_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(nwktr_state::sound_irq), this));
582582}

Previous 199869 Revisions Next


© 1997-2024 The MAME Team