this repo has no description
at main 8932 lines 189 kB view raw
1/* 2 MINEM68K.c 3 4 Copyright (C) 2009 Bernd Schmidt, Paul C. Pratt 5 6 You can redistribute this file and/or modify it under the terms 7 of version 2 of the GNU General Public License as published by 8 the Free Software Foundation. You should have received a copy 9 of the license along with this file; see the file COPYING. 10 11 This file is distributed in the hope that it will be useful, 12 but WITHOUT ANY WARRANTY; without even the implied warranty of 13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 license for more details. 15*/ 16 17/* 18 EMulator of 68K cpu with GENeric c code (not assembly) 19 20 This code descends from a simple 68000 emulator that I 21 (Paul C. Pratt) wrote long ago. That emulator ran on a 680x0, 22 and used the cpu it ran on to do some of the work. This 23 descendent fills in those holes with code from the 24 Un*x Amiga Emulator by Bernd Schmidt, as found being used in vMac. 25 26 This emulator is about 10 times smaller than the UAE, 27 at the cost of being 2 to 3 times slower. 28 29 FPU Emulation added 9/12/2009 by Ross Martin 30 (this code now located in "FPCPEMDV.h") 31*/ 32 33#include "PICOMMON.h" 34 35#include "M68KITAB.h" 36 37#if WantDisasm 38#include "DISAM68K.h" 39#endif 40 41#include "MINEM68K.h" 42 43/* 44 ReportAbnormalID unused 0x0123 - 0x01FF 45*/ 46 47#ifndef DisableLazyFlagAll 48#define DisableLazyFlagAll 0 49#endif 50 /* 51 useful for debugging, to tell if an observed bug is 52 being cause by lazy flag evaluation stuff. 53 Can also disable parts of it individually: 54 */ 55 56#ifndef ForceFlagsEval 57#if DisableLazyFlagAll 58#define ForceFlagsEval 1 59#else 60#define ForceFlagsEval 0 61#endif 62#endif 63 64#ifndef UseLazyZ 65#if DisableLazyFlagAll || ForceFlagsEval 66#define UseLazyZ 0 67#else 68#define UseLazyZ 1 69#endif 70#endif 71 72#ifndef UseLazyCC 73#if DisableLazyFlagAll 74#define UseLazyCC 0 75#else 76#define UseLazyCC 1 77#endif 78#endif 79 80 81typedef unsigned char flagtype; /* must be 0 or 1, not boolean */ 82 83 84/* Memory Address Translation Cache record */ 85 86struct MATCr { 87 ui5r cmpmask; 88 ui5r cmpvalu; 89 ui5r usemask; 90 ui3p usebase; 91}; 92typedef struct MATCr MATCr; 93typedef MATCr *MATCp; 94 95#ifndef USE_PCLIMIT 96#define USE_PCLIMIT 1 97#endif 98 99#define AKMemory 0 100#define AKRegister 1 101 102union ArgAddrT { 103 ui5r mem; 104 ui5r *rga; 105}; 106typedef union ArgAddrT ArgAddrT; 107 108enum { 109 kLazyFlagsDefault, 110 kLazyFlagsTstB, 111 kLazyFlagsTstW, 112 kLazyFlagsTstL, 113 kLazyFlagsCmpB, 114 kLazyFlagsCmpW, 115 kLazyFlagsCmpL, 116 kLazyFlagsSubB, 117 kLazyFlagsSubW, 118 kLazyFlagsSubL, 119 kLazyFlagsAddB, 120 kLazyFlagsAddW, 121 kLazyFlagsAddL, 122 kLazyFlagsNegB, 123 kLazyFlagsNegW, 124 kLazyFlagsNegL, 125 kLazyFlagsAsrB, 126 kLazyFlagsAsrW, 127 kLazyFlagsAsrL, 128 kLazyFlagsAslB, 129 kLazyFlagsAslW, 130 kLazyFlagsAslL, 131#if UseLazyZ 132 kLazyFlagsZSet, 133#endif 134 135 kNumLazyFlagsKinds 136}; 137 138typedef void (my_reg_call *ArgSetDstP)(ui5r f); 139 140#define FasterAlignedL 0 141 /* 142 If most long memory access is long aligned, 143 this should be faster. But on the Mac, this 144 doesn't seem to be the case, so an 145 unpredictable branch slows it down. 146 */ 147 148#ifndef HaveGlbReg 149#define HaveGlbReg 0 150#endif 151 152LOCALVAR struct regstruct 153{ 154 ui5r regs[16]; /* Data and Address registers */ 155 156 ui3p pc_p; 157 ui3p pc_pHi; 158 si5rr MaxCyclesToGo; 159 160#if WantCloserCyc 161 DecOpR *CurDecOp; 162#endif 163 DecOpYR CurDecOpY; 164 165 ui3r LazyFlagKind; 166 ui3r LazyXFlagKind; 167#if UseLazyZ 168 ui3r LazyFlagZSavedKind; 169#endif 170 ui5r LazyFlagArgSrc; 171 ui5r LazyFlagArgDst; 172 ui5r LazyXFlagArgSrc; 173 ui5r LazyXFlagArgDst; 174 175 ArgAddrT ArgAddr; 176 ArgSetDstP ArgSetDst; 177 ui5b SrcVal; 178 179 ui3p pc_pLo; 180 ui5r pc; /* Program Counter */ 181 182 MATCr MATCrdB; 183 MATCr MATCwrB; 184 MATCr MATCrdW; 185 MATCr MATCwrW; 186#if FasterAlignedL 187 MATCr MATCrdL; 188 MATCr MATCwrL; 189#endif 190 ATTep HeadATTel; 191 192 si5r MoreCyclesToGo; 193 si5r ResidualCycles; 194 ui3b fakeword[2]; 195 196 /* Status Register */ 197 ui5r intmask; /* bits 10-8 : interrupt priority mask */ 198 flagtype t1; /* bit 15: Trace mode 1 */ 199#if Use68020 200 flagtype t0; /* bit 14: Trace mode 0 */ 201#endif 202 flagtype s; /* bit 13: Supervisor or user privilege level */ 203#if Use68020 204 flagtype m; /* bit 12: Master or interrupt mode */ 205#endif 206 207 flagtype x; /* bit 4: eXtend */ 208 flagtype n; /* bit 3: Negative */ 209 flagtype z; /* bit 2: Zero */ 210 flagtype v; /* bit 1: oVerflow */ 211 flagtype c; /* bit 0: Carry */ 212 213#if EmMMU | EmFPU 214 ui5b ArgKind; 215#endif 216 217 blnr TracePending; 218 blnr ExternalInterruptPending; 219#if 0 220 blnr ResetPending; 221#endif 222 ui3b *fIPL; 223#ifdef r_regs 224 struct regstruct *save_regs; 225#endif 226 227 CPTR usp; /* User Stack Pointer */ 228 CPTR isp; /* Interrupt Stack Pointer */ 229#if Use68020 230 CPTR msp; /* Master Stack Pointer */ 231 ui5b sfc; /* Source Function Code register */ 232 ui5b dfc; /* Destination Function Code register */ 233 ui5b vbr; /* Vector Base Register */ 234 ui5b cacr; /* Cache Control Register */ 235 /* 236 bit 0 : Enable Cache 237 bit 1 : Freeze Cache 238 bit 2 : Clear Entry In Cache (write only) 239 bit 3 : Clear Cache (write only) 240 */ 241 ui5b caar; /* Cache Address Register */ 242#endif 243 244#define disp_table_sz (256 * 256) 245#if SmallGlobals 246 DecOpR *disp_table; 247#else 248 DecOpR disp_table[disp_table_sz]; 249#endif 250} regs; 251 252#define ui5r_MSBisSet(x) (((si5r)(x)) < 0) 253 254#define Bool2Bit(x) ((x) ? 1 : 0) 255 256 257#ifdef r_regs 258register struct regstruct *g_regs asm (r_regs); 259#define V_regs (*g_regs) 260#else 261#define V_regs regs 262#endif 263 264#ifdef r_pc_p 265register ui3p g_pc_p asm (r_pc_p); 266#define V_pc_p g_pc_p 267#else 268#define V_pc_p V_regs.pc_p 269#endif 270 271#ifdef r_MaxCyclesToGo 272register si5rr g_MaxCyclesToGo asm (r_MaxCyclesToGo); 273#define V_MaxCyclesToGo g_MaxCyclesToGo 274#else 275#define V_MaxCyclesToGo V_regs.MaxCyclesToGo 276#endif 277 278#ifdef r_pc_pHi 279register ui3p g_pc_pHi asm (r_pc_pHi); 280#define V_pc_pHi g_pc_pHi 281#else 282#define V_pc_pHi V_regs.pc_pHi 283#endif 284 285#define ZFLG V_regs.z 286#define NFLG V_regs.n 287#define CFLG V_regs.c 288#define VFLG V_regs.v 289#define XFLG V_regs.x 290 291#define m68k_dreg(num) (V_regs.regs[(num)]) 292#define m68k_areg(num) (V_regs.regs[(num) + 8]) 293 294 295#ifndef WantDumpTable 296#define WantDumpTable 0 297#endif 298 299#if WantDumpTable 300LOCALVAR ui5b DumpTable[kNumIKinds]; 301#endif 302 303#if USE_PCLIMIT 304FORWARDPROC Recalc_PC_Block(void); 305FORWARDFUNC ui5r my_reg_call Recalc_PC_BlockReturnUi5r(ui5r v); 306#endif 307 308LOCALINLINEFUNC ui4r nextiword(void) 309/* NOT sign extended */ 310{ 311 ui4r r = do_get_mem_word(V_pc_p); 312 V_pc_p += 2; 313 314#if USE_PCLIMIT 315 if (my_cond_rare(V_pc_p >= V_pc_pHi)) { 316 Recalc_PC_Block(); 317 } 318#endif 319 320 return r; 321} 322 323LOCALINLINEFUNC ui5r nextiSByte(void) 324{ 325 ui5r r = ui5r_FromSByte(do_get_mem_byte(V_pc_p + 1)); 326 V_pc_p += 2; 327 328#if USE_PCLIMIT 329 if (my_cond_rare(V_pc_p >= V_pc_pHi)) { 330 return Recalc_PC_BlockReturnUi5r(r); 331 } 332#endif 333 334 return r; 335} 336 337LOCALINLINEFUNC ui5r nextiSWord(void) 338/* NOT sign extended */ 339{ 340 ui5r r = ui5r_FromSWord(do_get_mem_word(V_pc_p)); 341 V_pc_p += 2; 342 343#if USE_PCLIMIT 344 if (my_cond_rare(V_pc_p >= V_pc_pHi)) { 345 return Recalc_PC_BlockReturnUi5r(r); 346 } 347#endif 348 349 return r; 350} 351 352FORWARDFUNC ui5r nextilong_ext(void); 353 354LOCALINLINEFUNC ui5r nextilong(void) 355{ 356 ui5r r = do_get_mem_long(V_pc_p); 357 V_pc_p += 4; 358 359#if USE_PCLIMIT 360 /* could be two words in different blocks */ 361 if (my_cond_rare(V_pc_p >= V_pc_pHi)) { 362 r = nextilong_ext(); 363 } 364#endif 365 366 return r; 367} 368 369LOCALINLINEPROC BackupPC(void) 370{ 371 V_pc_p -= 2; 372 373#if USE_PCLIMIT 374 if (my_cond_rare(V_pc_p < V_regs.pc_pLo)) { 375 Recalc_PC_Block(); 376 } 377#endif 378} 379 380LOCALINLINEFUNC CPTR m68k_getpc(void) 381{ 382 return V_regs.pc + (V_pc_p - V_regs.pc_pLo); 383} 384 385 386FORWARDPROC DoCodeTst(void); 387FORWARDPROC DoCodeCmpB(void); 388FORWARDPROC DoCodeCmpW(void); 389FORWARDPROC DoCodeCmpL(void); 390FORWARDPROC DoCodeBccB(void); 391FORWARDPROC DoCodeBccW(void); 392FORWARDPROC DoCodeBraB(void); 393FORWARDPROC DoCodeBraW(void); 394FORWARDPROC DoCodeDBcc(void); 395FORWARDPROC DoCodeDBF(void); 396FORWARDPROC DoCodeSwap(void); 397FORWARDPROC DoCodeMoveL(void); 398FORWARDPROC DoCodeMoveW(void); 399FORWARDPROC DoCodeMoveB(void); 400FORWARDPROC DoCodeMoveA(void); 401FORWARDPROC DoCodeMoveQ(void); 402FORWARDPROC DoCodeAddB(void); 403FORWARDPROC DoCodeAddW(void); 404FORWARDPROC DoCodeAddL(void); 405FORWARDPROC DoCodeSubB(void); 406FORWARDPROC DoCodeSubW(void); 407FORWARDPROC DoCodeSubL(void); 408FORWARDPROC DoCodeLea(void); 409FORWARDPROC DoCodePEA(void); 410FORWARDPROC DoCodeA(void); 411FORWARDPROC DoCodeBsrB(void); 412FORWARDPROC DoCodeBsrW(void); 413FORWARDPROC DoCodeJsr(void); 414FORWARDPROC DoCodeLinkA6(void); 415FORWARDPROC DoCodeMOVEMRmML(void); 416FORWARDPROC DoCodeMOVEMApRL(void); 417FORWARDPROC DoCodeUnlkA6(void); 418FORWARDPROC DoCodeRts(void); 419FORWARDPROC DoCodeJmp(void); 420FORWARDPROC DoCodeClr(void); 421FORWARDPROC DoCodeAddA(void); 422FORWARDPROC DoCodeSubA(void); 423FORWARDPROC DoCodeCmpA(void); 424FORWARDPROC DoCodeAddXB(void); 425FORWARDPROC DoCodeAddXW(void); 426FORWARDPROC DoCodeAddXL(void); 427FORWARDPROC DoCodeSubXB(void); 428FORWARDPROC DoCodeSubXW(void); 429FORWARDPROC DoCodeSubXL(void); 430FORWARDPROC DoCodeAslB(void); 431FORWARDPROC DoCodeAslW(void); 432FORWARDPROC DoCodeAslL(void); 433FORWARDPROC DoCodeAsrB(void); 434FORWARDPROC DoCodeAsrW(void); 435FORWARDPROC DoCodeAsrL(void); 436FORWARDPROC DoCodeLslB(void); 437FORWARDPROC DoCodeLslW(void); 438FORWARDPROC DoCodeLslL(void); 439FORWARDPROC DoCodeLsrB(void); 440FORWARDPROC DoCodeLsrW(void); 441FORWARDPROC DoCodeLsrL(void); 442FORWARDPROC DoCodeRxlB(void); 443FORWARDPROC DoCodeRxlW(void); 444FORWARDPROC DoCodeRxlL(void); 445FORWARDPROC DoCodeRxrB(void); 446FORWARDPROC DoCodeRxrW(void); 447FORWARDPROC DoCodeRxrL(void); 448FORWARDPROC DoCodeRolB(void); 449FORWARDPROC DoCodeRolW(void); 450FORWARDPROC DoCodeRolL(void); 451FORWARDPROC DoCodeRorB(void); 452FORWARDPROC DoCodeRorW(void); 453FORWARDPROC DoCodeRorL(void); 454FORWARDPROC DoCodeBTstB(void); 455FORWARDPROC DoCodeBChgB(void); 456FORWARDPROC DoCodeBClrB(void); 457FORWARDPROC DoCodeBSetB(void); 458FORWARDPROC DoCodeBTstL(void); 459FORWARDPROC DoCodeBChgL(void); 460FORWARDPROC DoCodeBClrL(void); 461FORWARDPROC DoCodeBSetL(void); 462FORWARDPROC DoCodeAnd(void); 463FORWARDPROC DoCodeOr(void); 464FORWARDPROC DoCodeEor(void); 465FORWARDPROC DoCodeNot(void); 466FORWARDPROC DoCodeScc(void); 467FORWARDPROC DoCodeNegXB(void); 468FORWARDPROC DoCodeNegXW(void); 469FORWARDPROC DoCodeNegXL(void); 470FORWARDPROC DoCodeNegB(void); 471FORWARDPROC DoCodeNegW(void); 472FORWARDPROC DoCodeNegL(void); 473FORWARDPROC DoCodeEXTW(void); 474FORWARDPROC DoCodeEXTL(void); 475FORWARDPROC DoCodeMulU(void); 476FORWARDPROC DoCodeMulS(void); 477FORWARDPROC DoCodeDivU(void); 478FORWARDPROC DoCodeDivS(void); 479FORWARDPROC DoCodeExg(void); 480FORWARDPROC DoCodeMoveEaCR(void); 481FORWARDPROC DoCodeMoveSREa(void); 482FORWARDPROC DoCodeMoveEaSR(void); 483FORWARDPROC DoCodeOrISR(void); 484FORWARDPROC DoCodeAndISR(void); 485FORWARDPROC DoCodeEorISR(void); 486FORWARDPROC DoCodeOrICCR(void); 487FORWARDPROC DoCodeAndICCR(void); 488FORWARDPROC DoCodeEorICCR(void); 489FORWARDPROC DoCodeMOVEMApRW(void); 490FORWARDPROC DoCodeMOVEMRmMW(void); 491FORWARDPROC DoCodeMOVEMrmW(void); 492FORWARDPROC DoCodeMOVEMrmL(void); 493FORWARDPROC DoCodeMOVEMmrW(void); 494FORWARDPROC DoCodeMOVEMmrL(void); 495FORWARDPROC DoCodeAbcd(void); 496FORWARDPROC DoCodeSbcd(void); 497FORWARDPROC DoCodeNbcd(void); 498FORWARDPROC DoCodeRte(void); 499FORWARDPROC DoCodeNop(void); 500FORWARDPROC DoCodeMoveP0(void); 501FORWARDPROC DoCodeMoveP1(void); 502FORWARDPROC DoCodeMoveP2(void); 503FORWARDPROC DoCodeMoveP3(void); 504FORWARDPROC op_illg(void); 505FORWARDPROC DoCodeChk(void); 506FORWARDPROC DoCodeTrap(void); 507FORWARDPROC DoCodeTrapV(void); 508FORWARDPROC DoCodeRtr(void); 509FORWARDPROC DoCodeLink(void); 510FORWARDPROC DoCodeUnlk(void); 511FORWARDPROC DoCodeMoveRUSP(void); 512FORWARDPROC DoCodeMoveUSPR(void); 513FORWARDPROC DoCodeTas(void); 514FORWARDPROC DoCodeFdefault(void); 515FORWARDPROC DoCodeStop(void); 516FORWARDPROC DoCodeReset(void); 517 518#if Use68020 519FORWARDPROC DoCodeCallMorRtm(void); 520FORWARDPROC DoCodeBraL(void); 521FORWARDPROC DoCodeBccL(void); 522FORWARDPROC DoCodeBsrL(void); 523FORWARDPROC DoCodeEXTBL(void); 524FORWARDPROC DoCodeTRAPcc(void); 525FORWARDPROC DoCodeBkpt(void); 526FORWARDPROC DoCodeDivL(void); 527FORWARDPROC DoCodeMulL(void); 528FORWARDPROC DoCodeRtd(void); 529FORWARDPROC DoCodeMoveCCREa(void); 530FORWARDPROC DoMoveFromControl(void); 531FORWARDPROC DoMoveToControl(void); 532FORWARDPROC DoCodeLinkL(void); 533FORWARDPROC DoCodePack(void); 534FORWARDPROC DoCodeUnpk(void); 535FORWARDPROC DoCHK2orCMP2(void); 536FORWARDPROC DoCAS2(void); 537FORWARDPROC DoCAS(void); 538FORWARDPROC DoMOVES(void); 539FORWARDPROC DoBitField(void); 540#endif 541 542#if EmMMU 543FORWARDPROC DoCodeMMU(void); 544#endif 545 546#if EmFPU 547FORWARDPROC DoCodeFPU_md60(void); 548FORWARDPROC DoCodeFPU_DBcc(void); 549FORWARDPROC DoCodeFPU_Trapcc(void); 550FORWARDPROC DoCodeFPU_Scc(void); 551FORWARDPROC DoCodeFPU_FBccW(void); 552FORWARDPROC DoCodeFPU_FBccL(void); 553FORWARDPROC DoCodeFPU_Save(void); 554FORWARDPROC DoCodeFPU_Restore(void); 555FORWARDPROC DoCodeFPU_dflt(void); 556#endif 557 558typedef void (*func_pointer_t)(void); 559 560LOCALVAR const func_pointer_t OpDispatch[kNumIKinds + 1] = { 561 DoCodeTst /* kIKindTst */, 562 DoCodeCmpB /* kIKindCmpB */, 563 DoCodeCmpW /* kIKindCmpW */, 564 DoCodeCmpL /* kIKindCmpL */, 565 DoCodeBccB /* kIKindBccB */, 566 DoCodeBccW /* kIKindBccW */, 567 DoCodeBraB /* kIKindBraB */, 568 DoCodeBraW /* kIKindBraW */, 569 DoCodeDBcc /* kIKindDBcc */, 570 DoCodeDBF /* kIKindDBF */, 571 DoCodeSwap /* kIKindSwap */, 572 DoCodeMoveL /* kIKindMoveL */, 573 DoCodeMoveW /* kIKindMoveW */, 574 DoCodeMoveB /* kIKindMoveB */, 575 DoCodeMoveA /* kIKindMoveAL */, 576 DoCodeMoveA /* kIKindMoveAW */, 577 DoCodeMoveQ /* kIKindMoveQ */, 578 DoCodeAddB /* kIKindAddB */, 579 DoCodeAddW /* kIKindAddW */, 580 DoCodeAddL /* kIKindAddL */, 581 DoCodeSubB /* kIKindSubB */, 582 DoCodeSubW /* kIKindSubW */, 583 DoCodeSubL /* kIKindSubL */, 584 DoCodeLea /* kIKindLea */, 585 DoCodePEA /* kIKindPEA */, 586 DoCodeA /* kIKindA */, 587 DoCodeBsrB /* kIKindBsrB */, 588 DoCodeBsrW /* kIKindBsrW */, 589 DoCodeJsr /* kIKindJsr */, 590 DoCodeLinkA6 /* kIKindLinkA6 */, 591 DoCodeMOVEMRmML /* kIKindMOVEMRmML */, 592 DoCodeMOVEMApRL /* kIKindMOVEMApRL */, 593 DoCodeUnlkA6 /* kIKindUnlkA6 */, 594 DoCodeRts /* kIKindRts */, 595 DoCodeJmp /* kIKindJmp */, 596 DoCodeClr /* kIKindClr */, 597 DoCodeAddA /* kIKindAddA */, 598 DoCodeAddA /* kIKindAddQA */, 599 DoCodeSubA /* kIKindSubA */, 600 DoCodeSubA /* kIKindSubQA */, 601 DoCodeCmpA /* kIKindCmpA */, 602 DoCodeAddXB /* kIKindAddXB */, 603 DoCodeAddXW /* kIKindAddXW */, 604 DoCodeAddXL /* kIKindAddXL */, 605 DoCodeSubXB /* kIKindSubXB */, 606 DoCodeSubXW /* kIKindSubXW */, 607 DoCodeSubXL /* kIKindSubXL */, 608 DoCodeAslB /* kIKindAslB */, 609 DoCodeAslW /* kIKindAslW */, 610 DoCodeAslL /* kIKindAslL */, 611 DoCodeAsrB /* kIKindAsrB */, 612 DoCodeAsrW /* kIKindAsrW */, 613 DoCodeAsrL /* kIKindAsrL */, 614 DoCodeLslB /* kIKindLslB */, 615 DoCodeLslW /* kIKindLslW */, 616 DoCodeLslL /* kIKindLslL */, 617 DoCodeLsrB /* kIKindLsrB */, 618 DoCodeLsrW /* kIKindLsrW */, 619 DoCodeLsrL /* kIKindLsrL */, 620 DoCodeRxlB /* kIKindRxlB */, 621 DoCodeRxlW /* kIKindRxlW */, 622 DoCodeRxlL /* kIKindRxlL */, 623 DoCodeRxrB /* kIKindRxrB */, 624 DoCodeRxrW /* kIKindRxrW */, 625 DoCodeRxrL /* kIKindRxrL */, 626 DoCodeRolB /* kIKindRolB */, 627 DoCodeRolW /* kIKindRolW */, 628 DoCodeRolL /* kIKindRolL */, 629 DoCodeRorB /* kIKindRorB */, 630 DoCodeRorW /* kIKindRorW */, 631 DoCodeRorL /* kIKindRorL */, 632 DoCodeBTstB /* kIKindBTstB */, 633 DoCodeBChgB /* kIKindBChgB */, 634 DoCodeBClrB /* kIKindBClrB */, 635 DoCodeBSetB /* kIKindBSetB */, 636 DoCodeBTstL /* kIKindBTstL */, 637 DoCodeBChgL /* kIKindBChgL */, 638 DoCodeBClrL /* kIKindBClrL */, 639 DoCodeBSetL /* kIKindBSetL */, 640 DoCodeAnd /* kIKindAndI */, 641 DoCodeAnd /* kIKindAndEaD */, 642 DoCodeAnd /* kIKindAndDEa */, 643 DoCodeOr /* kIKindOrI */, 644 DoCodeOr /* kIKindOrDEa */, 645 DoCodeOr /* kIKindOrEaD */, 646 DoCodeEor /* kIKindEor */, 647 DoCodeEor /* kIKindEorI */, 648 DoCodeNot /* kIKindNot */, 649 DoCodeScc /* kIKindScc */, 650 DoCodeNegXB /* kIKindNegXB */, 651 DoCodeNegXW /* kIKindNegXW */, 652 DoCodeNegXL /* kIKindNegXL */, 653 DoCodeNegB /* kIKindNegB */, 654 DoCodeNegW /* kIKindNegW */, 655 DoCodeNegL /* kIKindNegL */, 656 DoCodeEXTW /* kIKindEXTW */, 657 DoCodeEXTL /* kIKindEXTL */, 658 DoCodeMulU /* kIKindMulU */, 659 DoCodeMulS /* kIKindMulS */, 660 DoCodeDivU /* kIKindDivU */, 661 DoCodeDivS /* kIKindDivS */, 662 DoCodeExg /* kIKindExg */, 663 DoCodeMoveEaCR /* kIKindMoveEaCCR */, 664 DoCodeMoveSREa /* kIKindMoveSREa */, 665 DoCodeMoveEaSR /* kIKindMoveEaSR */, 666 DoCodeOrISR /* kIKindOrISR */, 667 DoCodeAndISR /* kIKindAndISR */, 668 DoCodeEorISR /* kIKindEorISR */, 669 DoCodeOrICCR /* kIKindOrICCR */, 670 DoCodeAndICCR /* kIKindAndICCR */, 671 DoCodeEorICCR /* kIKindEorICCR */, 672 DoCodeMOVEMApRW /* kIKindMOVEMApRW */, 673 DoCodeMOVEMRmMW /* kIKindMOVEMRmMW */, 674 DoCodeMOVEMrmW /* kIKindMOVEMrmW */, 675 DoCodeMOVEMrmL /* kIKindMOVEMrmL */, 676 DoCodeMOVEMmrW /* kIKindMOVEMmrW */, 677 DoCodeMOVEMmrL /* kIKindMOVEMmrL */, 678 DoCodeAbcd /* kIKindAbcd */, 679 DoCodeSbcd /* kIKindSbcd */, 680 DoCodeNbcd /* kIKindNbcd */, 681 DoCodeRte /* kIKindRte */, 682 DoCodeNop /* kIKindNop */, 683 DoCodeMoveP0 /* kIKindMoveP0 */, 684 DoCodeMoveP1 /* kIKindMoveP1 */, 685 DoCodeMoveP2 /* kIKindMoveP2 */, 686 DoCodeMoveP3 /* kIKindMoveP3 */, 687 op_illg /* kIKindIllegal */, 688 DoCodeChk /* kIKindChkW */, 689 DoCodeTrap /* kIKindTrap */, 690 DoCodeTrapV /* kIKindTrapV */, 691 DoCodeRtr /* kIKindRtr */, 692 DoCodeLink /* kIKindLink */, 693 DoCodeUnlk /* kIKindUnlk */, 694 DoCodeMoveRUSP /* kIKindMoveRUSP */, 695 DoCodeMoveUSPR /* kIKindMoveUSPR */, 696 DoCodeTas /* kIKindTas */, 697 DoCodeFdefault /* kIKindFdflt */, 698 DoCodeStop /* kIKindStop */, 699 DoCodeReset /* kIKindReset */, 700 701#if Use68020 702 DoCodeCallMorRtm /* kIKindCallMorRtm */, 703 DoCodeBraL /* kIKindBraL */, 704 DoCodeBccL /* kIKindBccL */, 705 DoCodeBsrL /* kIKindBsrL */, 706 DoCodeEXTBL /* kIKindEXTBL */, 707 DoCodeTRAPcc /* kIKindTRAPcc */, 708 DoCodeChk /* kIKindChkL */, 709 DoCodeBkpt /* kIKindBkpt */, 710 DoCodeDivL /* kIKindDivL */, 711 DoCodeMulL /* kIKindMulL */, 712 DoCodeRtd /* kIKindRtd */, 713 DoCodeMoveCCREa /* kIKindMoveCCREa */, 714 DoMoveFromControl /* kIKindMoveCEa */, 715 DoMoveToControl /* kIKindMoveEaC */, 716 DoCodeLinkL /* kIKindLinkL */, 717 DoCodePack /* kIKindPack */, 718 DoCodeUnpk /* kIKindUnpk */, 719 DoCHK2orCMP2 /* kIKindCHK2orCMP2 */, 720 DoCAS2 /* kIKindCAS2 */, 721 DoCAS /* kIKindCAS */, 722 DoMOVES /* kIKindMoveS */, 723 DoBitField /* kIKindBitField */, 724#endif 725#if EmMMU 726 DoCodeMMU /* kIKindMMU */, 727#endif 728#if EmFPU 729 DoCodeFPU_md60 /* kIKindFPUmd60 */, 730 DoCodeFPU_DBcc /* kIKindFPUDBcc */, 731 DoCodeFPU_Trapcc /* kIKindFPUTrapcc */, 732 DoCodeFPU_Scc /* kIKindFPUScc */, 733 DoCodeFPU_FBccW /* kIKindFPUFBccW */, 734 DoCodeFPU_FBccL /* kIKindFPUFBccL */, 735 DoCodeFPU_Save /* kIKindFPUSave */, 736 DoCodeFPU_Restore /* kIKindFPURestore */, 737 DoCodeFPU_dflt /* kIKindFPUdflt */, 738#endif 739 740 0 741}; 742 743#ifndef WantBreakPoint 744#define WantBreakPoint 0 745#endif 746 747#if WantBreakPoint 748 749#define BreakPointAddress 0xD198 750 751LOCALPROC BreakPointAction(void) 752{ 753 dbglog_StartLine(); 754 dbglog_writeCStr("breakpoint A0="); 755 dbglog_writeHex(m68k_areg(0)); 756 dbglog_writeCStr(" A1="); 757 dbglog_writeHex(m68k_areg(1)); 758 dbglog_writeReturn(); 759} 760 761#endif 762 763LOCALINLINEPROC DecodeNextInstruction(func_pointer_t *d, ui4rr *Cycles, 764 DecOpYR *y) 765{ 766 ui5r opcode; 767 DecOpR *p; 768 ui4rr MainClas; 769 770 opcode = nextiword(); 771 772 p = &V_regs.disp_table[opcode]; 773 774#if WantCloserCyc 775 V_regs.CurDecOp = p; 776#endif 777 MainClas = p->x.MainClas; 778 *Cycles = p->x.Cycles; 779 *y = p->y; 780#if WantDumpTable 781 DumpTable[MainClas] ++; 782#endif 783 *d = OpDispatch[MainClas]; 784} 785 786LOCALINLINEPROC UnDecodeNextInstruction(ui4rr Cycles) 787{ 788 V_MaxCyclesToGo += Cycles; 789 790 BackupPC(); 791 792#if WantDumpTable 793 { 794 ui5r opcode = do_get_mem_word(V_pc_p); 795 DecOpR *p = &V_regs.disp_table[opcode]; 796 ui4rr MainClas = p->x.MainClas; 797 798 DumpTable[MainClas] --; 799 } 800#endif 801} 802 803LOCALPROC m68k_go_MaxCycles(void) 804{ 805 ui4rr Cycles; 806 DecOpYR y; 807 func_pointer_t d; 808 809 /* 810 Main loop of emulator. 811 812 Always execute at least one instruction, 813 even if V_regs.MaxInstructionsToGo == 0. 814 Needed for trace flag to work. 815 */ 816 817 DecodeNextInstruction(&d, &Cycles, &y); 818 819 V_MaxCyclesToGo -= Cycles; 820 821 do { 822 V_regs.CurDecOpY = y; 823 824#if WantDisasm || WantBreakPoint 825 { 826 CPTR pc = m68k_getpc() - 2; 827#if WantDisasm 828 DisasmOneOrSave(pc); 829#endif 830#if WantBreakPoint 831 if (BreakPointAddress == pc) { 832 BreakPointAction(); 833 } 834#endif 835 } 836#endif 837 838 d(); 839 840 DecodeNextInstruction(&d, &Cycles, &y); 841 842 } while (((si5rr)(V_MaxCyclesToGo -= Cycles)) > 0); 843 844 /* abort instruction that have started to decode */ 845 846 UnDecodeNextInstruction(Cycles); 847} 848 849FORWARDFUNC ui5r my_reg_call get_byte_ext(CPTR addr); 850 851LOCALFUNC ui5r my_reg_call get_byte(CPTR addr) 852{ 853 ui3p m = (addr & V_regs.MATCrdB.usemask) + V_regs.MATCrdB.usebase; 854 855 if ((addr & V_regs.MATCrdB.cmpmask) == V_regs.MATCrdB.cmpvalu) { 856 return ui5r_FromSByte(*m); 857 } else { 858 return get_byte_ext(addr); 859 } 860} 861 862FORWARDPROC my_reg_call put_byte_ext(CPTR addr, ui5r b); 863 864LOCALPROC my_reg_call put_byte(CPTR addr, ui5r b) 865{ 866 ui3p m = (addr & V_regs.MATCwrB.usemask) + V_regs.MATCwrB.usebase; 867 if ((addr & V_regs.MATCwrB.cmpmask) == V_regs.MATCwrB.cmpvalu) { 868 *m = b; 869 } else { 870 put_byte_ext(addr, b); 871 } 872} 873 874FORWARDFUNC ui5r my_reg_call get_word_ext(CPTR addr); 875 876LOCALFUNC ui5r my_reg_call get_word(CPTR addr) 877{ 878 ui3p m = (addr & V_regs.MATCrdW.usemask) + V_regs.MATCrdW.usebase; 879 if ((addr & V_regs.MATCrdW.cmpmask) == V_regs.MATCrdW.cmpvalu) { 880 return ui5r_FromSWord(do_get_mem_word(m)); 881 } else { 882 return get_word_ext(addr); 883 } 884} 885 886FORWARDPROC my_reg_call put_word_ext(CPTR addr, ui5r w); 887 888LOCALPROC my_reg_call put_word(CPTR addr, ui5r w) 889{ 890 ui3p m = (addr & V_regs.MATCwrW.usemask) + V_regs.MATCwrW.usebase; 891 if ((addr & V_regs.MATCwrW.cmpmask) == V_regs.MATCwrW.cmpvalu) { 892 do_put_mem_word(m, w); 893 } else { 894 put_word_ext(addr, w); 895 } 896} 897 898FORWARDFUNC ui5r my_reg_call get_long_misaligned_ext(CPTR addr); 899 900LOCALFUNC ui5r my_reg_call get_long_misaligned(CPTR addr) 901{ 902 CPTR addr2 = addr + 2; 903 ui3p m = (addr & V_regs.MATCrdW.usemask) + V_regs.MATCrdW.usebase; 904 ui3p m2 = (addr2 & V_regs.MATCrdW.usemask) + V_regs.MATCrdW.usebase; 905 if (((addr & V_regs.MATCrdW.cmpmask) == V_regs.MATCrdW.cmpvalu) 906 && ((addr2 & V_regs.MATCrdW.cmpmask) == V_regs.MATCrdW.cmpvalu)) 907 { 908 ui5r hi = do_get_mem_word(m); 909 ui5r lo = do_get_mem_word(m2); 910 ui5r Data = ((hi << 16) & 0xFFFF0000) 911 | (lo & 0x0000FFFF); 912 913 return ui5r_FromSLong(Data); 914 } else { 915 return get_long_misaligned_ext(addr); 916 } 917} 918 919#if FasterAlignedL 920FORWARDFUNC ui5r my_reg_call get_long_ext(CPTR addr); 921#endif 922 923#if FasterAlignedL 924LOCALFUNC ui5r my_reg_call get_long(CPTR addr) 925{ 926 if (0 == (addr & 0x03)) { 927 ui3p m = (addr & V_regs.MATCrdL.usemask) 928 + V_regs.MATCrdL.usebase; 929 if ((addr & V_regs.MATCrdL.cmpmask) == V_regs.MATCrdL.cmpvalu) { 930 return ui5r_FromSLong(do_get_mem_long(m)); 931 } else { 932 return get_long_ext(addr); 933 } 934 } else { 935 return get_long_misaligned(addr); 936 } 937} 938#else 939#define get_long get_long_misaligned 940#endif 941 942FORWARDPROC my_reg_call put_long_misaligned_ext(CPTR addr, ui5r l); 943 944LOCALPROC my_reg_call put_long_misaligned(CPTR addr, ui5r l) 945{ 946 CPTR addr2 = addr + 2; 947 ui3p m = (addr & V_regs.MATCwrW.usemask) + V_regs.MATCwrW.usebase; 948 ui3p m2 = (addr2 & V_regs.MATCwrW.usemask) + V_regs.MATCwrW.usebase; 949 if (((addr & V_regs.MATCwrW.cmpmask) == V_regs.MATCwrW.cmpvalu) 950 && ((addr2 & V_regs.MATCwrW.cmpmask) == V_regs.MATCwrW.cmpvalu)) 951 { 952 do_put_mem_word(m, l >> 16); 953 do_put_mem_word(m2, l); 954 } else { 955 put_long_misaligned_ext(addr, l); 956 } 957} 958 959#if FasterAlignedL 960FORWARDPROC my_reg_call put_long_ext(CPTR addr, ui5r l); 961#endif 962 963#if FasterAlignedL 964LOCALPROC my_reg_call put_long(CPTR addr, ui5r l) 965{ 966 if (0 == (addr & 0x03)) { 967 ui3p m = (addr & V_regs.MATCwrL.usemask) 968 + V_regs.MATCwrL.usebase; 969 if ((addr & V_regs.MATCwrL.cmpmask) == V_regs.MATCwrL.cmpvalu) { 970 do_put_mem_long(m, l); 971 } else { 972 put_long_ext(addr, l); 973 } 974 } else { 975 put_long_misaligned(addr, l); 976 } 977} 978#else 979#define put_long put_long_misaligned 980#endif 981 982LOCALFUNC ui5b my_reg_call get_disp_ea(ui5b base) 983{ 984 ui4b dp = nextiword(); 985 int regno = (dp >> 12) & 0x0F; 986 si5b regd = V_regs.regs[regno]; 987 if ((dp & 0x0800) == 0) { 988 regd = (si5b)(si4b)regd; 989 } 990#if Use68020 991 regd <<= (dp >> 9) & 3; 992#if ExtraAbnormalReports 993 if (((dp >> 9) & 3) != 0) { 994 /* ReportAbnormal("Have scale in Extension Word"); */ 995 /* apparently can happen in Sys 7.5.5 boot on 68000 */ 996 } 997#endif 998 if (dp & 0x0100) { 999 if ((dp & 0x80) != 0) { 1000 base = 0; 1001 /* ReportAbnormal("Extension Word: suppress base"); */ 1002 /* used by Sys 7.5.5 boot */ 1003 } 1004 if ((dp & 0x40) != 0) { 1005 regd = 0; 1006 /* ReportAbnormal("Extension Word: suppress regd"); */ 1007 /* used by Mac II boot */ 1008 } 1009 1010 switch ((dp >> 4) & 0x03) { 1011 case 0: 1012 /* reserved */ 1013 ReportAbnormalID(0x0101, "Extension Word: dp reserved"); 1014 break; 1015 case 1: 1016 /* no displacement */ 1017 /* ReportAbnormal("Extension Word: no displacement"); */ 1018 /* used by Sys 7.5.5 boot */ 1019 break; 1020 case 2: 1021 base += nextiSWord(); 1022 /* 1023 ReportAbnormal("Extension Word: word displacement"); 1024 */ 1025 /* used by Sys 7.5.5 boot */ 1026 break; 1027 case 3: 1028 base += nextilong(); 1029 /* 1030 ReportAbnormal("Extension Word: long displacement"); 1031 */ 1032 /* used by Mac II boot from system 6.0.8? */ 1033 break; 1034 } 1035 1036 if ((dp & 0x03) == 0) { 1037 base += regd; 1038 if ((dp & 0x04) != 0) { 1039 ReportAbnormalID(0x0102, 1040 "Extension Word: reserved dp form"); 1041 } 1042 /* ReportAbnormal("Extension Word: noindex"); */ 1043 /* used by Sys 7.5.5 boot */ 1044 } else { 1045 if ((dp & 0x04) != 0) { 1046 base = get_long(base); 1047 base += regd; 1048 /* ReportAbnormal("Extension Word: postindex"); */ 1049 /* used by Sys 7.5.5 boot */ 1050 } else { 1051 base += regd; 1052 base = get_long(base); 1053 /* ReportAbnormal("Extension Word: preindex"); */ 1054 /* used by Sys 7.5.5 boot */ 1055 } 1056 switch (dp & 0x03) { 1057 case 1: 1058 /* null outer displacement */ 1059 /* 1060 ReportAbnormal( 1061 "Extension Word: null outer displacement"); 1062 */ 1063 /* used by Sys 7.5.5 boot */ 1064 break; 1065 case 2: 1066 base += nextiSWord(); 1067 /* 1068 ReportAbnormal( 1069 "Extension Word: word outer displacement"); 1070 */ 1071 /* used by Mac II boot from system 6.0.8? */ 1072 break; 1073 case 3: 1074 base += nextilong(); 1075 /* 1076 ReportAbnormal( 1077 "Extension Word: long outer displacement"); 1078 */ 1079 /* used by Mac II boot from system 6.0.8? */ 1080 break; 1081 } 1082 } 1083 1084 return base; 1085 } else 1086#endif 1087 { 1088 return base + (si3b)(dp) + regd; 1089 } 1090} 1091 1092LOCALFUNC ui5r my_reg_call DecodeAddr_Indirect(ui3rr ArgDat) 1093{ 1094 return V_regs.regs[ArgDat]; 1095} 1096 1097LOCALFUNC ui5r my_reg_call DecodeAddr_APosIncB(ui3rr ArgDat) 1098{ 1099 ui5r *p = &V_regs.regs[ArgDat]; 1100 ui5r a = *p; 1101 1102 *p = a + 1; 1103 1104 return a; 1105} 1106 1107LOCALFUNC ui5r my_reg_call DecodeAddr_APosIncW(ui3rr ArgDat) 1108{ 1109 ui5r *p = &V_regs.regs[ArgDat]; 1110 ui5r a = *p; 1111 1112 *p = a + 2; 1113 1114 return a; 1115} 1116 1117LOCALFUNC ui5r my_reg_call DecodeAddr_APosIncL(ui3rr ArgDat) 1118{ 1119 ui5r *p = &V_regs.regs[ArgDat]; 1120 ui5r a = *p; 1121 1122 *p = a + 4; 1123 1124 return a; 1125} 1126 1127LOCALFUNC ui5r my_reg_call DecodeAddr_APreDecB(ui3rr ArgDat) 1128{ 1129 ui5r *p = &V_regs.regs[ArgDat]; 1130 ui5r a = *p - 1; 1131 1132 *p = a; 1133 1134 return a; 1135} 1136 1137LOCALFUNC ui5r my_reg_call DecodeAddr_APreDecW(ui3rr ArgDat) 1138{ 1139 ui5r *p = &V_regs.regs[ArgDat]; 1140 ui5r a = *p - 2; 1141 1142 *p = a; 1143 1144 return a; 1145} 1146 1147LOCALFUNC ui5r my_reg_call DecodeAddr_APreDecL(ui3rr ArgDat) 1148{ 1149 ui5r *p = &V_regs.regs[ArgDat]; 1150 ui5r a = *p - 4; 1151 1152 *p = a; 1153 1154 return a; 1155} 1156 1157LOCALFUNC ui5r my_reg_call DecodeAddr_ADisp(ui3rr ArgDat) 1158{ 1159 return V_regs.regs[ArgDat] + nextiSWord(); 1160} 1161 1162LOCALFUNC ui5r my_reg_call DecodeAddr_AIndex(ui3rr ArgDat) 1163{ 1164 return get_disp_ea(V_regs.regs[ArgDat]); 1165} 1166 1167LOCALFUNC ui5r my_reg_call DecodeAddr_AbsW(ui3rr ArgDat) 1168{ 1169 UnusedParam(ArgDat); 1170 return nextiSWord(); 1171} 1172 1173LOCALFUNC ui5r my_reg_call DecodeAddr_AbsL(ui3rr ArgDat) 1174{ 1175 UnusedParam(ArgDat); 1176 return nextilong(); 1177} 1178 1179LOCALFUNC ui5r my_reg_call DecodeAddr_PCDisp(ui3rr ArgDat) 1180{ 1181 CPTR pc = m68k_getpc(); 1182 1183 UnusedParam(ArgDat); 1184 return pc + nextiSWord(); 1185} 1186 1187LOCALFUNC ui5r my_reg_call DecodeAddr_PCIndex(ui3rr ArgDat) 1188{ 1189 UnusedParam(ArgDat); 1190 return get_disp_ea(m68k_getpc()); 1191} 1192 1193typedef ui5r (my_reg_call *DecodeAddrP)(ui3rr ArgDat); 1194 1195LOCALVAR const DecodeAddrP DecodeAddrDispatch[kNumAMds] = { 1196 (DecodeAddrP)nullpr /* kAMdRegB */, 1197 (DecodeAddrP)nullpr /* kAMdRegW */, 1198 (DecodeAddrP)nullpr /* kAMdRegL */, 1199 DecodeAddr_Indirect /* kAMdIndirectB */, 1200 DecodeAddr_Indirect /* kAMdIndirectW */, 1201 DecodeAddr_Indirect /* kAMdIndirectL */, 1202 DecodeAddr_APosIncB /* kAMdAPosIncB */, 1203 DecodeAddr_APosIncW /* kAMdAPosIncW */, 1204 DecodeAddr_APosIncL /* kAMdAPosIncL */, 1205 DecodeAddr_APosIncW /* kAMdAPosInc7B */, 1206 DecodeAddr_APreDecB /* kAMdAPreDecB */, 1207 DecodeAddr_APreDecW /* kAMdAPreDecW */, 1208 DecodeAddr_APreDecL /* kAMdAPreDecL */, 1209 DecodeAddr_APreDecW /* kAMdAPreDec7B */, 1210 DecodeAddr_ADisp /* kAMdADispB */, 1211 DecodeAddr_ADisp /* kAMdADispW */, 1212 DecodeAddr_ADisp /* kAMdADispL */, 1213 DecodeAddr_AIndex /* kAMdAIndexB */, 1214 DecodeAddr_AIndex /* kAMdAIndexW */, 1215 DecodeAddr_AIndex /* kAMdAIndexL */, 1216 DecodeAddr_AbsW /* kAMdAbsWB */, 1217 DecodeAddr_AbsW /* kAMdAbsWW */, 1218 DecodeAddr_AbsW /* kAMdAbsWL */, 1219 DecodeAddr_AbsL /* kAMdAbsLB */, 1220 DecodeAddr_AbsL /* kAMdAbsLW */, 1221 DecodeAddr_AbsL /* kAMdAbsLL */, 1222 DecodeAddr_PCDisp /* kAMdPCDispB */, 1223 DecodeAddr_PCDisp /* kAMdPCDispW */, 1224 DecodeAddr_PCDisp /* kAMdPCDispL */, 1225 DecodeAddr_PCIndex /* kAMdPCIndexB */, 1226 DecodeAddr_PCIndex /* kAMdPCIndexW */, 1227 DecodeAddr_PCIndex /* kAMdPCIndexL */, 1228 (DecodeAddrP)nullpr /* kAMdImmedB */, 1229 (DecodeAddrP)nullpr /* kAMdImmedW */, 1230 (DecodeAddrP)nullpr /* kAMdImmedL */, 1231 (DecodeAddrP)nullpr /* kAMdDat4 */ 1232}; 1233 1234LOCALINLINEFUNC ui5r DecodeAddrSrcDst(DecArgR *f) 1235{ 1236 return (DecodeAddrDispatch[f->AMd])(f->ArgDat); 1237} 1238 1239LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_RegB(ui3rr ArgDat) 1240{ 1241 return ui5r_FromSByte(V_regs.regs[ArgDat]); 1242} 1243 1244LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_RegW(ui3rr ArgDat) 1245{ 1246 return ui5r_FromSWord(V_regs.regs[ArgDat]); 1247} 1248 1249LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_RegL(ui3rr ArgDat) 1250{ 1251 return ui5r_FromSLong(V_regs.regs[ArgDat]); 1252} 1253 1254LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_IndirectB(ui3rr ArgDat) 1255{ 1256 return get_byte(V_regs.regs[ArgDat]); 1257} 1258 1259LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_IndirectW(ui3rr ArgDat) 1260{ 1261 return get_word(V_regs.regs[ArgDat]); 1262} 1263 1264LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_IndirectL(ui3rr ArgDat) 1265{ 1266 return get_long(V_regs.regs[ArgDat]); 1267} 1268 1269LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_APosIncB(ui3rr ArgDat) 1270{ 1271 ui5r *p = &V_regs.regs[ArgDat]; 1272 ui5r a = *p; 1273 1274 *p = a + 1; 1275 1276 return get_byte(a); 1277} 1278 1279LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_APosIncW(ui3rr ArgDat) 1280{ 1281 ui5r *p = &V_regs.regs[ArgDat]; 1282 ui5r a = *p; 1283 1284 *p = a + 2; 1285 1286 return get_word(a); 1287} 1288 1289LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_APosIncL(ui3rr ArgDat) 1290{ 1291 ui5r *p = &V_regs.regs[ArgDat]; 1292 ui5r a = *p; 1293 1294 *p = a + 4; 1295 1296 return get_long(a); 1297} 1298 1299LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_APosInc7B(ui3rr ArgDat) 1300{ 1301 ui5r *p = &V_regs.regs[ArgDat]; 1302 ui5r a = *p; 1303 1304 *p = a + 2; 1305 1306 return get_byte(a); 1307} 1308 1309LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_APreDecB(ui3rr ArgDat) 1310{ 1311 ui5r *p = &V_regs.regs[ArgDat]; 1312 ui5r a = *p - 1; 1313 1314 *p = a; 1315 1316 return get_byte(a); 1317} 1318 1319LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_APreDecW(ui3rr ArgDat) 1320{ 1321 ui5r *p = &V_regs.regs[ArgDat]; 1322 ui5r a = *p - 2; 1323 1324 *p = a; 1325 1326 return get_word(a); 1327} 1328 1329LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_APreDecL(ui3rr ArgDat) 1330{ 1331 ui5r *p = &V_regs.regs[ArgDat]; 1332 ui5r a = *p - 4; 1333 1334 *p = a; 1335 1336 return get_long(a); 1337} 1338 1339LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_APreDec7B(ui3rr ArgDat) 1340{ 1341 ui5r *p = &V_regs.regs[ArgDat]; 1342 ui5r a = *p - 2; 1343 1344 *p = a; 1345 1346 return get_byte(a); 1347} 1348 1349LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_ADispB(ui3rr ArgDat) 1350{ 1351 return get_byte(DecodeAddr_ADisp(ArgDat)); 1352} 1353 1354LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_ADispW(ui3rr ArgDat) 1355{ 1356 return get_word(DecodeAddr_ADisp(ArgDat)); 1357} 1358 1359LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_ADispL(ui3rr ArgDat) 1360{ 1361 return get_long(DecodeAddr_ADisp(ArgDat)); 1362} 1363 1364LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_AIndexB(ui3rr ArgDat) 1365{ 1366 return get_byte(get_disp_ea(V_regs.regs[ArgDat])); 1367} 1368 1369LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_AIndexW(ui3rr ArgDat) 1370{ 1371 return get_word(get_disp_ea(V_regs.regs[ArgDat])); 1372} 1373 1374LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_AIndexL(ui3rr ArgDat) 1375{ 1376 return get_long(get_disp_ea(V_regs.regs[ArgDat])); 1377} 1378 1379LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_AbsWB(ui3rr ArgDat) 1380{ 1381 return get_byte(DecodeAddr_AbsW(ArgDat)); 1382} 1383 1384LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_AbsWW(ui3rr ArgDat) 1385{ 1386 return get_word(DecodeAddr_AbsW(ArgDat)); 1387} 1388 1389LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_AbsWL(ui3rr ArgDat) 1390{ 1391 return get_long(DecodeAddr_AbsW(ArgDat)); 1392} 1393 1394LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_AbsLB(ui3rr ArgDat) 1395{ 1396 return get_byte(DecodeAddr_AbsL(ArgDat)); 1397} 1398 1399LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_AbsLW(ui3rr ArgDat) 1400{ 1401 return get_word(DecodeAddr_AbsL(ArgDat)); 1402} 1403 1404LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_AbsLL(ui3rr ArgDat) 1405{ 1406 return get_long(DecodeAddr_AbsL(ArgDat)); 1407} 1408 1409LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_PCDispB(ui3rr ArgDat) 1410{ 1411 return get_byte(DecodeAddr_PCDisp(ArgDat)); 1412} 1413 1414LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_PCDispW(ui3rr ArgDat) 1415{ 1416 return get_word(DecodeAddr_PCDisp(ArgDat)); 1417} 1418 1419LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_PCDispL(ui3rr ArgDat) 1420{ 1421 return get_long(DecodeAddr_PCDisp(ArgDat)); 1422} 1423 1424LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_PCIndexB(ui3rr ArgDat) 1425{ 1426 return get_byte(DecodeAddr_PCIndex(ArgDat)); 1427} 1428 1429LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_PCIndexW(ui3rr ArgDat) 1430{ 1431 return get_word(DecodeAddr_PCIndex(ArgDat)); 1432} 1433 1434LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_PCIndexL(ui3rr ArgDat) 1435{ 1436 return get_long(DecodeAddr_PCIndex(ArgDat)); 1437} 1438 1439LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_ImmedB(ui3rr ArgDat) 1440{ 1441 UnusedParam(ArgDat); 1442 return nextiSByte(); 1443} 1444 1445LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_ImmedW(ui3rr ArgDat) 1446{ 1447 UnusedParam(ArgDat); 1448 return nextiSWord(); 1449} 1450 1451LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_ImmedL(ui3rr ArgDat) 1452{ 1453 UnusedParam(ArgDat); 1454 return ui5r_FromSLong(nextilong()); 1455} 1456 1457LOCALFUNC ui5r my_reg_call DecodeGetSrcDst_Dat4(ui3rr ArgDat) 1458{ 1459 return ArgDat; 1460} 1461 1462typedef ui5r (my_reg_call *DecodeGetSrcDstP)(ui3rr ArgDat); 1463 1464LOCALVAR const DecodeGetSrcDstP DecodeGetSrcDstDispatch[kNumAMds] = { 1465 DecodeGetSrcDst_RegB /* kAMdRegB */, 1466 DecodeGetSrcDst_RegW /* kAMdRegW */, 1467 DecodeGetSrcDst_RegL /* kAMdRegL */, 1468 DecodeGetSrcDst_IndirectB /* kAMdIndirectB */, 1469 DecodeGetSrcDst_IndirectW /* kAMdIndirectW */, 1470 DecodeGetSrcDst_IndirectL /* kAMdIndirectL */, 1471 DecodeGetSrcDst_APosIncB /* kAMdAPosIncB */, 1472 DecodeGetSrcDst_APosIncW /* kAMdAPosIncW */, 1473 DecodeGetSrcDst_APosIncL /* kAMdAPosIncL */, 1474 DecodeGetSrcDst_APosInc7B /* kAMdAPosInc7B */, 1475 DecodeGetSrcDst_APreDecB /* kAMdAPreDecB */, 1476 DecodeGetSrcDst_APreDecW /* kAMdAPreDecW */, 1477 DecodeGetSrcDst_APreDecL /* kAMdAPreDecL */, 1478 DecodeGetSrcDst_APreDec7B /* kAMdAPreDec7B */, 1479 DecodeGetSrcDst_ADispB /* kAMdADispB */, 1480 DecodeGetSrcDst_ADispW /* kAMdADispW */, 1481 DecodeGetSrcDst_ADispL /* kAMdADispL */, 1482 DecodeGetSrcDst_AIndexB /* kAMdAIndexB */, 1483 DecodeGetSrcDst_AIndexW /* kAMdAIndexW */, 1484 DecodeGetSrcDst_AIndexL /* kAMdAIndexL */, 1485 DecodeGetSrcDst_AbsWB /* kAMdAbsWB */, 1486 DecodeGetSrcDst_AbsWW /* kAMdAbsWW */, 1487 DecodeGetSrcDst_AbsWL /* kAMdAbsWL */, 1488 DecodeGetSrcDst_AbsLB /* kAMdAbsLB */, 1489 DecodeGetSrcDst_AbsLW /* kAMdAbsLW */, 1490 DecodeGetSrcDst_AbsLL /* kAMdAbsLL */, 1491 DecodeGetSrcDst_PCDispB /* kAMdPCDispB */, 1492 DecodeGetSrcDst_PCDispW /* kAMdPCDispW */, 1493 DecodeGetSrcDst_PCDispL /* kAMdPCDispL */, 1494 DecodeGetSrcDst_PCIndexB /* kAMdPCIndexB */, 1495 DecodeGetSrcDst_PCIndexW /* kAMdPCIndexW */, 1496 DecodeGetSrcDst_PCIndexL /* kAMdPCIndexL */, 1497 DecodeGetSrcDst_ImmedB /* kAMdImmedB */, 1498 DecodeGetSrcDst_ImmedW /* kAMdImmedW */, 1499 DecodeGetSrcDst_ImmedL /* kAMdImmedL */, 1500 DecodeGetSrcDst_Dat4 /* kAMdDat4 */ 1501}; 1502 1503LOCALINLINEFUNC ui5r DecodeGetSrcDst(DecArgR *f) 1504{ 1505 return (DecodeGetSrcDstDispatch[f->AMd])(f->ArgDat); 1506} 1507 1508LOCALPROC my_reg_call DecodeSetSrcDst_RegB(ui5r v, ui3rr ArgDat) 1509{ 1510 ui5r *p = &V_regs.regs[ArgDat]; 1511 1512#if LittleEndianUnaligned 1513 *(ui3b *)p = v; 1514#else 1515 *p = (*p & ~ 0xff) | ((v) & 0xff); 1516#endif 1517} 1518 1519LOCALPROC my_reg_call DecodeSetSrcDst_RegW(ui5r v, ui3rr ArgDat) 1520{ 1521 ui5r *p = &V_regs.regs[ArgDat]; 1522 1523#if LittleEndianUnaligned 1524 *(ui4b *)p = v; 1525#else 1526 *p = (*p & ~ 0xffff) | ((v) & 0xffff); 1527#endif 1528} 1529 1530LOCALPROC my_reg_call DecodeSetSrcDst_RegL(ui5r v, ui3rr ArgDat) 1531{ 1532 V_regs.regs[ArgDat] = v; 1533} 1534 1535LOCALPROC my_reg_call DecodeSetSrcDst_IndirectB(ui5r v, ui3rr ArgDat) 1536{ 1537 put_byte(V_regs.regs[ArgDat], v); 1538} 1539 1540LOCALPROC my_reg_call DecodeSetSrcDst_IndirectW(ui5r v, ui3rr ArgDat) 1541{ 1542 put_word(V_regs.regs[ArgDat], v); 1543} 1544 1545LOCALPROC my_reg_call DecodeSetSrcDst_IndirectL(ui5r v, ui3rr ArgDat) 1546{ 1547 put_long(V_regs.regs[ArgDat], v); 1548} 1549 1550LOCALPROC my_reg_call DecodeSetSrcDst_APosIncB(ui5r v, ui3rr ArgDat) 1551{ 1552 ui5r *p = &V_regs.regs[ArgDat]; 1553 ui5r a = *p; 1554 1555 *p = a + 1; 1556 1557 put_byte(a, v); 1558} 1559 1560LOCALPROC my_reg_call DecodeSetSrcDst_APosIncW(ui5r v, ui3rr ArgDat) 1561{ 1562 ui5r *p = &V_regs.regs[ArgDat]; 1563 ui5r a = *p; 1564 1565 *p = a + 2; 1566 1567 put_word(a, v); 1568} 1569 1570LOCALPROC my_reg_call DecodeSetSrcDst_APosIncL(ui5r v, ui3rr ArgDat) 1571{ 1572 ui5r *p = &V_regs.regs[ArgDat]; 1573 ui5r a = *p; 1574 1575 *p = a + 4; 1576 1577 put_long(a, v); 1578} 1579 1580LOCALPROC my_reg_call DecodeSetSrcDst_APosInc7B(ui5r v, ui3rr ArgDat) 1581{ 1582 ui5r *p = &V_regs.regs[ArgDat]; 1583 ui5r a = *p; 1584 1585 *p = a + 2; 1586 1587 put_byte(a, v); 1588} 1589 1590LOCALPROC my_reg_call DecodeSetSrcDst_APreDecB(ui5r v, ui3rr ArgDat) 1591{ 1592 ui5r *p = &V_regs.regs[ArgDat]; 1593 ui5r a = *p - 1; 1594 1595 *p = a; 1596 1597 put_byte(a, v); 1598} 1599 1600LOCALPROC my_reg_call DecodeSetSrcDst_APreDecW(ui5r v, ui3rr ArgDat) 1601{ 1602 ui5r *p = &V_regs.regs[ArgDat]; 1603 ui5r a = *p - 2; 1604 1605 *p = a; 1606 1607 put_word(a, v); 1608} 1609 1610LOCALPROC my_reg_call DecodeSetSrcDst_APreDecL(ui5r v, ui3rr ArgDat) 1611{ 1612 ui5r *p = &V_regs.regs[ArgDat]; 1613 ui5r a = *p - 4; 1614 1615 *p = a; 1616 1617 put_long(a, v); 1618} 1619 1620LOCALPROC my_reg_call DecodeSetSrcDst_APreDec7B(ui5r v, ui3rr ArgDat) 1621{ 1622 ui5r *p = &V_regs.regs[ArgDat]; 1623 ui5r a = *p - 2; 1624 1625 *p = a; 1626 1627 put_byte(a, v); 1628} 1629 1630LOCALPROC my_reg_call DecodeSetSrcDst_ADispB(ui5r v, ui3rr ArgDat) 1631{ 1632 put_byte(V_regs.regs[ArgDat] 1633 + nextiSWord(), v); 1634} 1635 1636LOCALPROC my_reg_call DecodeSetSrcDst_ADispW(ui5r v, ui3rr ArgDat) 1637{ 1638 put_word(V_regs.regs[ArgDat] 1639 + nextiSWord(), v); 1640} 1641 1642LOCALPROC my_reg_call DecodeSetSrcDst_ADispL(ui5r v, ui3rr ArgDat) 1643{ 1644 put_long(V_regs.regs[ArgDat] 1645 + nextiSWord(), v); 1646} 1647 1648LOCALPROC my_reg_call DecodeSetSrcDst_AIndexB(ui5r v, ui3rr ArgDat) 1649{ 1650 put_byte(get_disp_ea(V_regs.regs[ArgDat]), v); 1651} 1652 1653LOCALPROC my_reg_call DecodeSetSrcDst_AIndexW(ui5r v, ui3rr ArgDat) 1654{ 1655 put_word(get_disp_ea(V_regs.regs[ArgDat]), v); 1656} 1657 1658LOCALPROC my_reg_call DecodeSetSrcDst_AIndexL(ui5r v, ui3rr ArgDat) 1659{ 1660 put_long(get_disp_ea(V_regs.regs[ArgDat]), v); 1661} 1662 1663LOCALPROC my_reg_call DecodeSetSrcDst_AbsWB(ui5r v, ui3rr ArgDat) 1664{ 1665 put_byte(DecodeAddr_AbsW(ArgDat), v); 1666} 1667 1668LOCALPROC my_reg_call DecodeSetSrcDst_AbsWW(ui5r v, ui3rr ArgDat) 1669{ 1670 put_word(DecodeAddr_AbsW(ArgDat), v); 1671} 1672 1673LOCALPROC my_reg_call DecodeSetSrcDst_AbsWL(ui5r v, ui3rr ArgDat) 1674{ 1675 put_long(DecodeAddr_AbsW(ArgDat), v); 1676} 1677 1678LOCALPROC my_reg_call DecodeSetSrcDst_AbsLB(ui5r v, ui3rr ArgDat) 1679{ 1680 put_byte(DecodeAddr_AbsL(ArgDat), v); 1681} 1682 1683LOCALPROC my_reg_call DecodeSetSrcDst_AbsLW(ui5r v, ui3rr ArgDat) 1684{ 1685 put_word(DecodeAddr_AbsL(ArgDat), v); 1686} 1687 1688LOCALPROC my_reg_call DecodeSetSrcDst_AbsLL(ui5r v, ui3rr ArgDat) 1689{ 1690 put_long(DecodeAddr_AbsL(ArgDat), v); 1691} 1692 1693LOCALPROC my_reg_call DecodeSetSrcDst_PCDispB(ui5r v, ui3rr ArgDat) 1694{ 1695 put_byte(DecodeAddr_PCDisp(ArgDat), v); 1696} 1697 1698LOCALPROC my_reg_call DecodeSetSrcDst_PCDispW(ui5r v, ui3rr ArgDat) 1699{ 1700 put_word(DecodeAddr_PCDisp(ArgDat), v); 1701} 1702 1703LOCALPROC my_reg_call DecodeSetSrcDst_PCDispL(ui5r v, ui3rr ArgDat) 1704{ 1705 put_long(DecodeAddr_PCDisp(ArgDat), v); 1706} 1707 1708LOCALPROC my_reg_call DecodeSetSrcDst_PCIndexB(ui5r v, ui3rr ArgDat) 1709{ 1710 put_byte(DecodeAddr_PCIndex(ArgDat), v); 1711} 1712 1713LOCALPROC my_reg_call DecodeSetSrcDst_PCIndexW(ui5r v, ui3rr ArgDat) 1714{ 1715 put_word(DecodeAddr_PCIndex(ArgDat), v); 1716} 1717 1718LOCALPROC my_reg_call DecodeSetSrcDst_PCIndexL(ui5r v, ui3rr ArgDat) 1719{ 1720 put_long(DecodeAddr_PCIndex(ArgDat), v); 1721} 1722 1723typedef void (my_reg_call *DecodeSetSrcDstP)(ui5r v, ui3rr ArgDat); 1724 1725LOCALVAR const DecodeSetSrcDstP DecodeSetSrcDstDispatch[kNumAMds] = { 1726 DecodeSetSrcDst_RegB /* kAMdRegB */, 1727 DecodeSetSrcDst_RegW /* kAMdRegW */, 1728 DecodeSetSrcDst_RegL /* kAMdRegL */, 1729 DecodeSetSrcDst_IndirectB /* kAMdIndirectB */, 1730 DecodeSetSrcDst_IndirectW /* kAMdIndirectW */, 1731 DecodeSetSrcDst_IndirectL /* kAMdIndirectL*/, 1732 DecodeSetSrcDst_APosIncB /* kAMdAPosIncB */, 1733 DecodeSetSrcDst_APosIncW /* kAMdAPosIncW */, 1734 DecodeSetSrcDst_APosIncL /* kAMdAPosIncL */, 1735 DecodeSetSrcDst_APosInc7B /* kAMdAPosInc7B */, 1736 DecodeSetSrcDst_APreDecB /* kAMdAPreDecB */, 1737 DecodeSetSrcDst_APreDecW /* kAMdAPreDecW */, 1738 DecodeSetSrcDst_APreDecL /* kAMdAPreDecL */, 1739 DecodeSetSrcDst_APreDec7B /* kAMdAPreDec7B */, 1740 DecodeSetSrcDst_ADispB /* kAMdADispB */, 1741 DecodeSetSrcDst_ADispW /* kAMdADispW */, 1742 DecodeSetSrcDst_ADispL /* kAMdADispL */, 1743 DecodeSetSrcDst_AIndexB /* kAMdAIndexB */, 1744 DecodeSetSrcDst_AIndexW /* kAMdAIndexW */, 1745 DecodeSetSrcDst_AIndexL /* kAMdAIndexL */, 1746 DecodeSetSrcDst_AbsWB /* kAMdAbsWB */, 1747 DecodeSetSrcDst_AbsWW /* kAMdAbsWW */, 1748 DecodeSetSrcDst_AbsWL /* kAMdAbsWL */, 1749 DecodeSetSrcDst_AbsLB /* kAMdAbsLB */, 1750 DecodeSetSrcDst_AbsLW /* kAMdAbsLW */, 1751 DecodeSetSrcDst_AbsLL /* kAMdAbsLL */, 1752 DecodeSetSrcDst_PCDispB /* kAMdPCDispB */, 1753 DecodeSetSrcDst_PCDispW /* kAMdPCDispW */, 1754 DecodeSetSrcDst_PCDispL /* kAMdPCDispL */, 1755 DecodeSetSrcDst_PCIndexB /* kAMdPCIndexB */, 1756 DecodeSetSrcDst_PCIndexW /* kAMdPCIndexW */, 1757 DecodeSetSrcDst_PCIndexL /* kAMdPCIndexL */, 1758 (DecodeSetSrcDstP)nullpr /* kAMdImmedB */, 1759 (DecodeSetSrcDstP)nullpr /* kAMdImmedW */, 1760 (DecodeSetSrcDstP)nullpr /* kAMdImmedL */, 1761 (DecodeSetSrcDstP)nullpr /* kAMdDat4 */ 1762}; 1763 1764LOCALINLINEPROC DecodeSetSrcDst(ui5r v, DecArgR *f) 1765{ 1766 (DecodeSetSrcDstDispatch[f->AMd])(v, f->ArgDat); 1767} 1768 1769LOCALPROC my_reg_call ArgSetDstRegBValue(ui5r v) 1770{ 1771 ui5r *p = V_regs.ArgAddr.rga; 1772 1773#if LittleEndianUnaligned 1774 *(ui3b *)p = v; 1775#else 1776 *p = (*p & ~ 0xff) | ((v) & 0xff); 1777#endif 1778} 1779 1780LOCALPROC my_reg_call ArgSetDstRegWValue(ui5r v) 1781{ 1782 ui5r *p = V_regs.ArgAddr.rga; 1783 1784#if LittleEndianUnaligned 1785 *(ui4b *)p = v; 1786#else 1787 *p = (*p & ~ 0xffff) | ((v) & 0xffff); 1788#endif 1789} 1790 1791LOCALPROC my_reg_call ArgSetDstRegLValue(ui5r v) 1792{ 1793 ui5r *p = V_regs.ArgAddr.rga; 1794 1795 *p = v; 1796} 1797 1798LOCALPROC my_reg_call ArgSetDstMemBValue(ui5r v) 1799{ 1800 put_byte(V_regs.ArgAddr.mem, v); 1801} 1802 1803LOCALPROC my_reg_call ArgSetDstMemWValue(ui5r v) 1804{ 1805 put_word(V_regs.ArgAddr.mem, v); 1806} 1807 1808LOCALPROC my_reg_call ArgSetDstMemLValue(ui5r v) 1809{ 1810 put_long(V_regs.ArgAddr.mem, v); 1811} 1812 1813LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_RegB(ui3rr ArgDat) 1814{ 1815 ui5r *p = &V_regs.regs[ArgDat]; 1816 1817 V_regs.ArgAddr.rga = p; 1818 V_regs.ArgSetDst = ArgSetDstRegBValue; 1819 1820 return ui5r_FromSByte(*p); 1821} 1822 1823LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_RegW(ui3rr ArgDat) 1824{ 1825 ui5r *p = &V_regs.regs[ArgDat]; 1826 1827 V_regs.ArgAddr.rga = p; 1828 V_regs.ArgSetDst = ArgSetDstRegWValue; 1829 1830 return ui5r_FromSWord(*p); 1831} 1832 1833LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_RegL(ui3rr ArgDat) 1834{ 1835 ui5r *p = &V_regs.regs[ArgDat]; 1836 1837 V_regs.ArgAddr.rga = p; 1838 V_regs.ArgSetDst = ArgSetDstRegLValue; 1839 1840 return ui5r_FromSLong(*p); 1841} 1842 1843LOCALFUNC ui5r my_reg_call getarg_byte(ui5r a) 1844{ 1845 V_regs.ArgAddr.mem = a; 1846 V_regs.ArgSetDst = ArgSetDstMemBValue; 1847 1848 return get_byte(a); 1849} 1850 1851LOCALFUNC ui5r my_reg_call getarg_word(ui5r a) 1852{ 1853 V_regs.ArgAddr.mem = a; 1854 V_regs.ArgSetDst = ArgSetDstMemWValue; 1855 1856 return get_word(a); 1857} 1858 1859LOCALFUNC ui5r my_reg_call getarg_long(ui5r a) 1860{ 1861 V_regs.ArgAddr.mem = a; 1862 V_regs.ArgSetDst = ArgSetDstMemLValue; 1863 1864 return get_long(a); 1865} 1866 1867LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_IndirectB(ui3rr ArgDat) 1868{ 1869 return getarg_byte(V_regs.regs[ArgDat]); 1870} 1871 1872LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_IndirectW(ui3rr ArgDat) 1873{ 1874 return getarg_word(V_regs.regs[ArgDat]); 1875} 1876 1877LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_IndirectL(ui3rr ArgDat) 1878{ 1879 return getarg_long(V_regs.regs[ArgDat]); 1880} 1881 1882LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_APosIncB(ui3rr ArgDat) 1883{ 1884 ui5r *p = &V_regs.regs[ArgDat]; 1885 ui5r a = *p; 1886 1887 *p = a + 1; 1888 1889 return getarg_byte(a); 1890} 1891 1892LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_APosIncW(ui3rr ArgDat) 1893{ 1894 ui5r *p = &V_regs.regs[ArgDat]; 1895 ui5r a = *p; 1896 1897 *p = a + 2; 1898 1899 return getarg_word(a); 1900} 1901 1902LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_APosIncL(ui3rr ArgDat) 1903{ 1904 ui5r *p = &V_regs.regs[ArgDat]; 1905 ui5r a = *p; 1906 1907 *p = a + 4; 1908 1909 return getarg_long(a); 1910} 1911 1912LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_APosInc7B(ui3rr ArgDat) 1913{ 1914 ui5r *p = &V_regs.regs[ArgDat]; 1915 ui5r a = *p; 1916 1917 *p = a + 2; 1918 1919 return getarg_byte(a); 1920} 1921 1922LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_APreDecB(ui3rr ArgDat) 1923{ 1924 ui5r *p = &V_regs.regs[ArgDat]; 1925 ui5r a = *p - 1; 1926 1927 *p = a; 1928 1929 return getarg_byte(a); 1930} 1931 1932LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_APreDecW(ui3rr ArgDat) 1933{ 1934 ui5r *p = &V_regs.regs[ArgDat]; 1935 ui5r a = *p - 2; 1936 1937 *p = a; 1938 1939 return getarg_word(a); 1940} 1941 1942LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_APreDecL(ui3rr ArgDat) 1943{ 1944 ui5r *p = &V_regs.regs[ArgDat]; 1945 ui5r a = *p - 4; 1946 1947 *p = a; 1948 1949 return getarg_long(a); 1950} 1951 1952LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_APreDec7B(ui3rr ArgDat) 1953{ 1954 ui5r *p = &V_regs.regs[ArgDat]; 1955 ui5r a = *p - 2; 1956 1957 *p = a; 1958 1959 return getarg_byte(a); 1960} 1961 1962LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_ADispB(ui3rr ArgDat) 1963{ 1964 return getarg_byte(V_regs.regs[ArgDat] 1965 + nextiSWord()); 1966} 1967 1968LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_ADispW(ui3rr ArgDat) 1969{ 1970 return getarg_word(V_regs.regs[ArgDat] 1971 + nextiSWord()); 1972} 1973 1974LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_ADispL(ui3rr ArgDat) 1975{ 1976 return getarg_long(V_regs.regs[ArgDat] 1977 + nextiSWord()); 1978} 1979 1980LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_AIndexB(ui3rr ArgDat) 1981{ 1982 return getarg_byte(get_disp_ea(V_regs.regs[ArgDat])); 1983} 1984 1985LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_AIndexW(ui3rr ArgDat) 1986{ 1987 return getarg_word(get_disp_ea(V_regs.regs[ArgDat])); 1988} 1989 1990LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_AIndexL(ui3rr ArgDat) 1991{ 1992 return getarg_long(get_disp_ea(V_regs.regs[ArgDat])); 1993} 1994 1995LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_AbsWB(ui3rr ArgDat) 1996{ 1997 return getarg_byte(DecodeAddr_AbsW(ArgDat)); 1998} 1999 2000LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_AbsWW(ui3rr ArgDat) 2001{ 2002 return getarg_word(DecodeAddr_AbsW(ArgDat)); 2003} 2004 2005LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_AbsWL(ui3rr ArgDat) 2006{ 2007 return getarg_long(DecodeAddr_AbsW(ArgDat)); 2008} 2009 2010LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_AbsLB(ui3rr ArgDat) 2011{ 2012 return getarg_byte(DecodeAddr_AbsL(ArgDat)); 2013} 2014 2015LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_AbsLW(ui3rr ArgDat) 2016{ 2017 return getarg_word(DecodeAddr_AbsL(ArgDat)); 2018} 2019 2020LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_AbsLL(ui3rr ArgDat) 2021{ 2022 return getarg_long(DecodeAddr_AbsL(ArgDat)); 2023} 2024 2025LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_PCDispB(ui3rr ArgDat) 2026{ 2027 return getarg_byte(DecodeAddr_PCDisp(ArgDat)); 2028} 2029 2030LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_PCDispW(ui3rr ArgDat) 2031{ 2032 return getarg_word(DecodeAddr_PCDisp(ArgDat)); 2033} 2034 2035LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_PCDispL(ui3rr ArgDat) 2036{ 2037 return getarg_long(DecodeAddr_PCDisp(ArgDat)); 2038} 2039 2040LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_PCIndexB(ui3rr ArgDat) 2041{ 2042 return getarg_byte(DecodeAddr_PCIndex(ArgDat)); 2043} 2044 2045LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_PCIndexW(ui3rr ArgDat) 2046{ 2047 return getarg_word(DecodeAddr_PCIndex(ArgDat)); 2048} 2049 2050LOCALFUNC ui5r my_reg_call DecodeGetSetSrcDst_PCIndexL(ui3rr ArgDat) 2051{ 2052 return getarg_long(DecodeAddr_PCIndex(ArgDat)); 2053} 2054 2055typedef ui5r (my_reg_call *DecodeGetSetSrcDstP)(ui3rr ArgDat); 2056 2057LOCALVAR const DecodeGetSetSrcDstP 2058 DecodeGetSetSrcDstDispatch[kNumAMds] = 2059{ 2060 DecodeGetSetSrcDst_RegB /* kAMdRegB */, 2061 DecodeGetSetSrcDst_RegW /* kAMdRegW */, 2062 DecodeGetSetSrcDst_RegL /* kAMdRegL */, 2063 DecodeGetSetSrcDst_IndirectB /* kAMdIndirectB */, 2064 DecodeGetSetSrcDst_IndirectW /* kAMdIndirectW */, 2065 DecodeGetSetSrcDst_IndirectL /* kAMdIndirectL*/, 2066 DecodeGetSetSrcDst_APosIncB /* kAMdAPosIncB */, 2067 DecodeGetSetSrcDst_APosIncW /* kAMdAPosIncW */, 2068 DecodeGetSetSrcDst_APosIncL /* kAMdAPosIncL */, 2069 DecodeGetSetSrcDst_APosInc7B /* kAMdAPosInc7B */, 2070 DecodeGetSetSrcDst_APreDecB /* kAMdAPreDecB */, 2071 DecodeGetSetSrcDst_APreDecW /* kAMdAPreDecW */, 2072 DecodeGetSetSrcDst_APreDecL /* kAMdAPreDecL */, 2073 DecodeGetSetSrcDst_APreDec7B /* kAMdAPreDec7B */, 2074 DecodeGetSetSrcDst_ADispB /* kAMdADispB */, 2075 DecodeGetSetSrcDst_ADispW /* kAMdADispW */, 2076 DecodeGetSetSrcDst_ADispL /* kAMdADispL */, 2077 DecodeGetSetSrcDst_AIndexB /* kAMdAIndexB */, 2078 DecodeGetSetSrcDst_AIndexW /* kAMdAIndexW */, 2079 DecodeGetSetSrcDst_AIndexL /* kAMdAIndexL */, 2080 DecodeGetSetSrcDst_AbsWB /* kAMdAbsWB */, 2081 DecodeGetSetSrcDst_AbsWW /* kAMdAbsWW */, 2082 DecodeGetSetSrcDst_AbsWL /* kAMdAbsWL */, 2083 DecodeGetSetSrcDst_AbsLB /* kAMdAbsLB */, 2084 DecodeGetSetSrcDst_AbsLW /* kAMdAbsLW */, 2085 DecodeGetSetSrcDst_AbsLL /* kAMdAbsLL */, 2086 DecodeGetSetSrcDst_PCDispB /* kAMdPCDispB */, 2087 DecodeGetSetSrcDst_PCDispW /* kAMdPCDispW */, 2088 DecodeGetSetSrcDst_PCDispL /* kAMdPCDispL */, 2089 DecodeGetSetSrcDst_PCIndexB /* kAMdPCIndexB */, 2090 DecodeGetSetSrcDst_PCIndexW /* kAMdPCIndexW */, 2091 DecodeGetSetSrcDst_PCIndexL /* kAMdPCIndexL */, 2092 (DecodeGetSetSrcDstP)nullpr /* kAMdImmedB */, 2093 (DecodeGetSetSrcDstP)nullpr /* kAMdImmedW */, 2094 (DecodeGetSetSrcDstP)nullpr /* kAMdImmedL */, 2095 (DecodeGetSetSrcDstP)nullpr /* kAMdDat4 */ 2096}; 2097 2098LOCALINLINEFUNC ui5r DecodeGetSetSrcDst(DecArgR *f) 2099{ 2100 return (DecodeGetSetSrcDstDispatch[f->AMd])(f->ArgDat); 2101} 2102 2103 2104LOCALINLINEFUNC ui5r DecodeDst(void) 2105{ 2106 return DecodeAddrSrcDst(&V_regs.CurDecOpY.v[1]); 2107} 2108 2109LOCALINLINEFUNC ui5r DecodeGetSetDstValue(void) 2110{ 2111 return DecodeGetSetSrcDst(&V_regs.CurDecOpY.v[1]); 2112} 2113 2114LOCALINLINEPROC ArgSetDstValue(ui5r v) 2115{ 2116 V_regs.ArgSetDst(v); 2117} 2118 2119LOCALINLINEPROC DecodeSetDstValue(ui5r v) 2120{ 2121 DecodeSetSrcDst(v, &V_regs.CurDecOpY.v[1]); 2122} 2123 2124LOCALINLINEFUNC ui5r DecodeGetSrcValue(void) 2125{ 2126 return DecodeGetSrcDst(&V_regs.CurDecOpY.v[0]); 2127} 2128 2129LOCALINLINEFUNC ui5r DecodeGetDstValue(void) 2130{ 2131 return DecodeGetSrcDst(&V_regs.CurDecOpY.v[1]); 2132} 2133 2134LOCALINLINEFUNC ui5r DecodeGetSrcSetDstValue(void) 2135{ 2136 V_regs.SrcVal = DecodeGetSrcValue(); 2137 2138 return DecodeGetSetDstValue(); 2139} 2140 2141LOCALINLINEFUNC ui5r DecodeGetSrcGetDstValue(void) 2142{ 2143 V_regs.SrcVal = DecodeGetSrcValue(); 2144 2145 return DecodeGetDstValue(); 2146} 2147 2148 2149typedef void (*cond_actP)(void); 2150 2151LOCALPROC my_reg_call cctrue_T(cond_actP t_act, cond_actP f_act) 2152{ 2153 UnusedParam(f_act); 2154 t_act(); 2155} 2156 2157LOCALPROC my_reg_call cctrue_F(cond_actP t_act, cond_actP f_act) 2158{ 2159 UnusedParam(t_act); 2160 f_act(); 2161} 2162 2163LOCALPROC my_reg_call cctrue_HI(cond_actP t_act, cond_actP f_act) 2164{ 2165 if (0 == (CFLG | ZFLG)) { 2166 t_act(); 2167 } else { 2168 f_act(); 2169 } 2170} 2171 2172LOCALPROC my_reg_call cctrue_LS(cond_actP t_act, cond_actP f_act) 2173{ 2174 if (0 != (CFLG | ZFLG)) { 2175 t_act(); 2176 } else { 2177 f_act(); 2178 } 2179} 2180 2181LOCALPROC my_reg_call cctrue_CC(cond_actP t_act, cond_actP f_act) 2182{ 2183 if (0 == (CFLG)) { 2184 t_act(); 2185 } else { 2186 f_act(); 2187 } 2188} 2189 2190LOCALPROC my_reg_call cctrue_CS(cond_actP t_act, cond_actP f_act) 2191{ 2192 if (0 != (CFLG)) { 2193 t_act(); 2194 } else { 2195 f_act(); 2196 } 2197} 2198 2199LOCALPROC my_reg_call cctrue_NE(cond_actP t_act, cond_actP f_act) 2200{ 2201 if (0 == (ZFLG)) { 2202 t_act(); 2203 } else { 2204 f_act(); 2205 } 2206} 2207 2208LOCALPROC my_reg_call cctrue_EQ(cond_actP t_act, cond_actP f_act) 2209{ 2210 if (0 != (ZFLG)) { 2211 t_act(); 2212 } else { 2213 f_act(); 2214 } 2215} 2216 2217LOCALPROC my_reg_call cctrue_VC(cond_actP t_act, cond_actP f_act) 2218{ 2219 if (0 == (VFLG)) { 2220 t_act(); 2221 } else { 2222 f_act(); 2223 } 2224} 2225 2226LOCALPROC my_reg_call cctrue_VS(cond_actP t_act, cond_actP f_act) 2227{ 2228 if (0 != (VFLG)) { 2229 t_act(); 2230 } else { 2231 f_act(); 2232 } 2233} 2234 2235LOCALPROC my_reg_call cctrue_PL(cond_actP t_act, cond_actP f_act) 2236{ 2237 if (0 == (NFLG)) { 2238 t_act(); 2239 } else { 2240 f_act(); 2241 } 2242} 2243 2244LOCALPROC my_reg_call cctrue_MI(cond_actP t_act, cond_actP f_act) 2245{ 2246 if (0 != (NFLG)) { 2247 t_act(); 2248 } else { 2249 f_act(); 2250 } 2251} 2252 2253LOCALPROC my_reg_call cctrue_GE(cond_actP t_act, cond_actP f_act) 2254{ 2255 if (0 == (NFLG ^ VFLG)) { 2256 t_act(); 2257 } else { 2258 f_act(); 2259 } 2260} 2261 2262LOCALPROC my_reg_call cctrue_LT(cond_actP t_act, cond_actP f_act) 2263{ 2264 if (0 != (NFLG ^ VFLG)) { 2265 t_act(); 2266 } else { 2267 f_act(); 2268 } 2269} 2270 2271LOCALPROC my_reg_call cctrue_GT(cond_actP t_act, cond_actP f_act) 2272{ 2273 if (0 == (ZFLG | (NFLG ^ VFLG))) { 2274 t_act(); 2275 } else { 2276 f_act(); 2277 } 2278} 2279 2280LOCALPROC my_reg_call cctrue_LE(cond_actP t_act, cond_actP f_act) 2281{ 2282 if (0 != (ZFLG | (NFLG ^ VFLG))) { 2283 t_act(); 2284 } else { 2285 f_act(); 2286 } 2287} 2288 2289#if Have_ASR 2290#define Ui5rASR(x, s) ((ui5r)(((si5r)(x)) >> (s))) 2291#else 2292LOCALFUNC ui5r Ui5rASR(ui5r x, ui5r s) 2293{ 2294 ui5r v; 2295 2296 if (ui5r_MSBisSet(x)) { 2297 v = ~ ((~ x) >> s); 2298 } else { 2299 v = x >> s; 2300 } 2301 2302 return v; 2303} 2304#endif 2305 2306#if UseLazyCC 2307 2308LOCALPROC my_reg_call cctrue_TstL_HI(cond_actP t_act, cond_actP f_act) 2309{ 2310 if (((ui5b)V_regs.LazyFlagArgDst) > ((ui5b)0)) { 2311 t_act(); 2312 } else { 2313 f_act(); 2314 } 2315} 2316 2317LOCALPROC my_reg_call cctrue_TstL_LS(cond_actP t_act, cond_actP f_act) 2318{ 2319 if (((ui5b)V_regs.LazyFlagArgDst) <= ((ui5b)0)) { 2320 t_act(); 2321 } else { 2322 f_act(); 2323 } 2324} 2325 2326#if 0 /* always true */ 2327LOCALPROC my_reg_call cctrue_TstL_CC(cond_actP t_act, cond_actP f_act) 2328{ 2329 if (((ui5b)V_regs.LazyFlagArgDst) >= ((ui5b)0)) { 2330 t_act(); 2331 } else { 2332 f_act(); 2333 } 2334} 2335#endif 2336 2337#if 0 /* always false */ 2338LOCALPROC my_reg_call cctrue_TstL_CS(cond_actP t_act, cond_actP f_act) 2339{ 2340 if (((ui5b)V_regs.LazyFlagArgDst) < ((ui5b)0)) { 2341 t_act(); 2342 } else { 2343 f_act(); 2344 } 2345} 2346#endif 2347 2348LOCALPROC my_reg_call cctrue_TstL_NE(cond_actP t_act, cond_actP f_act) 2349{ 2350 if (V_regs.LazyFlagArgDst != 0) { 2351 t_act(); 2352 } else { 2353 f_act(); 2354 } 2355} 2356 2357LOCALPROC my_reg_call cctrue_TstL_EQ(cond_actP t_act, cond_actP f_act) 2358{ 2359 if (V_regs.LazyFlagArgDst == 0) { 2360 t_act(); 2361 } else { 2362 f_act(); 2363 } 2364} 2365 2366LOCALPROC my_reg_call cctrue_TstL_PL(cond_actP t_act, cond_actP f_act) 2367{ 2368 if (((si5b)(V_regs.LazyFlagArgDst)) >= 0) { 2369 t_act(); 2370 } else { 2371 f_act(); 2372 } 2373} 2374 2375LOCALPROC my_reg_call cctrue_TstL_MI(cond_actP t_act, cond_actP f_act) 2376{ 2377 if (((si5b)(V_regs.LazyFlagArgDst)) < 0) { 2378 t_act(); 2379 } else { 2380 f_act(); 2381 } 2382} 2383 2384LOCALPROC my_reg_call cctrue_TstL_GE(cond_actP t_act, cond_actP f_act) 2385{ 2386 if (((si5b)V_regs.LazyFlagArgDst) >= ((si5b)0)) { 2387 t_act(); 2388 } else { 2389 f_act(); 2390 } 2391} 2392 2393LOCALPROC my_reg_call cctrue_TstL_LT(cond_actP t_act, cond_actP f_act) 2394{ 2395 if (((si5b)V_regs.LazyFlagArgDst) < ((si5b)0)) { 2396 t_act(); 2397 } else { 2398 f_act(); 2399 } 2400} 2401 2402LOCALPROC my_reg_call cctrue_TstL_GT(cond_actP t_act, cond_actP f_act) 2403{ 2404 if (((si5b)V_regs.LazyFlagArgDst) > ((si5b)0)) { 2405 t_act(); 2406 } else { 2407 f_act(); 2408 } 2409} 2410 2411LOCALPROC my_reg_call cctrue_TstL_LE(cond_actP t_act, cond_actP f_act) 2412{ 2413 if (((si5b)V_regs.LazyFlagArgDst) <= ((si5b)0)) { 2414 t_act(); 2415 } else { 2416 f_act(); 2417 } 2418} 2419 2420LOCALPROC my_reg_call cctrue_CmpB_HI(cond_actP t_act, cond_actP f_act) 2421{ 2422 if (((ui3b)V_regs.LazyFlagArgDst) > ((ui3b)V_regs.LazyFlagArgSrc)) { 2423 t_act(); 2424 } else { 2425 f_act(); 2426 } 2427} 2428 2429LOCALPROC my_reg_call cctrue_CmpB_LS(cond_actP t_act, cond_actP f_act) 2430{ 2431 if (((ui3b)V_regs.LazyFlagArgDst) <= ((ui3b)V_regs.LazyFlagArgSrc)) 2432 { 2433 t_act(); 2434 } else { 2435 f_act(); 2436 } 2437} 2438 2439LOCALPROC my_reg_call cctrue_CmpB_CC(cond_actP t_act, cond_actP f_act) 2440{ 2441 if (((ui3b)V_regs.LazyFlagArgDst) >= ((ui3b)V_regs.LazyFlagArgSrc)) 2442 { 2443 t_act(); 2444 } else { 2445 f_act(); 2446 } 2447} 2448 2449LOCALPROC my_reg_call cctrue_CmpB_CS(cond_actP t_act, cond_actP f_act) 2450{ 2451 if (((ui3b)V_regs.LazyFlagArgDst) < ((ui3b)V_regs.LazyFlagArgSrc)) 2452 { 2453 t_act(); 2454 } else { 2455 f_act(); 2456 } 2457} 2458 2459LOCALPROC my_reg_call cctrue_CmpB_NE(cond_actP t_act, cond_actP f_act) 2460{ 2461 if (((ui3b)V_regs.LazyFlagArgDst) != ((ui3b)V_regs.LazyFlagArgSrc)) 2462 { 2463 t_act(); 2464 } else { 2465 f_act(); 2466 } 2467} 2468 2469LOCALPROC my_reg_call cctrue_CmpB_EQ(cond_actP t_act, cond_actP f_act) 2470{ 2471 if (((ui3b)V_regs.LazyFlagArgDst) == ((ui3b)V_regs.LazyFlagArgSrc)) 2472 { 2473 t_act(); 2474 } else { 2475 f_act(); 2476 } 2477} 2478 2479LOCALPROC my_reg_call cctrue_CmpB_PL(cond_actP t_act, cond_actP f_act) 2480{ 2481 if (((si3b)(V_regs.LazyFlagArgDst - V_regs.LazyFlagArgSrc)) >= 0) { 2482 t_act(); 2483 } else { 2484 f_act(); 2485 } 2486} 2487 2488LOCALPROC my_reg_call cctrue_CmpB_MI(cond_actP t_act, cond_actP f_act) 2489{ 2490 if (((si3b)(V_regs.LazyFlagArgDst - V_regs.LazyFlagArgSrc)) < 0) { 2491 t_act(); 2492 } else { 2493 f_act(); 2494 } 2495} 2496 2497LOCALPROC my_reg_call cctrue_CmpB_GE(cond_actP t_act, cond_actP f_act) 2498{ 2499 if (((si3b)V_regs.LazyFlagArgDst) >= ((si3b)V_regs.LazyFlagArgSrc)) 2500 { 2501 t_act(); 2502 } else { 2503 f_act(); 2504 } 2505} 2506 2507LOCALPROC my_reg_call cctrue_CmpB_LT(cond_actP t_act, cond_actP f_act) 2508{ 2509 if (((si3b)V_regs.LazyFlagArgDst) < ((si3b)V_regs.LazyFlagArgSrc)) { 2510 t_act(); 2511 } else { 2512 f_act(); 2513 } 2514} 2515 2516LOCALPROC my_reg_call cctrue_CmpB_GT(cond_actP t_act, cond_actP f_act) 2517{ 2518 if (((si3b)V_regs.LazyFlagArgDst) > ((si3b)V_regs.LazyFlagArgSrc)) { 2519 t_act(); 2520 } else { 2521 f_act(); 2522 } 2523} 2524 2525LOCALPROC my_reg_call cctrue_CmpB_LE(cond_actP t_act, cond_actP f_act) 2526{ 2527 if (((si3b)V_regs.LazyFlagArgDst) <= ((si3b)V_regs.LazyFlagArgSrc)) 2528 { 2529 t_act(); 2530 } else { 2531 f_act(); 2532 } 2533} 2534 2535LOCALPROC my_reg_call cctrue_CmpW_HI(cond_actP t_act, cond_actP f_act) 2536{ 2537 if (((ui4b)V_regs.LazyFlagArgDst) > ((ui4b)V_regs.LazyFlagArgSrc)) 2538 { 2539 t_act(); 2540 } else { 2541 f_act(); 2542 } 2543} 2544 2545LOCALPROC my_reg_call cctrue_CmpW_LS(cond_actP t_act, cond_actP f_act) 2546{ 2547 if (((ui4b)V_regs.LazyFlagArgDst) <= ((ui4b)V_regs.LazyFlagArgSrc)) 2548 { 2549 t_act(); 2550 } else { 2551 f_act(); 2552 } 2553} 2554 2555LOCALPROC my_reg_call cctrue_CmpW_CC(cond_actP t_act, cond_actP f_act) 2556{ 2557 if (((ui4b)V_regs.LazyFlagArgDst) >= ((ui4b)V_regs.LazyFlagArgSrc)) 2558 { 2559 t_act(); 2560 } else { 2561 f_act(); 2562 } 2563} 2564 2565LOCALPROC my_reg_call cctrue_CmpW_CS(cond_actP t_act, cond_actP f_act) 2566{ 2567 if (((ui4b)V_regs.LazyFlagArgDst) < ((ui4b)V_regs.LazyFlagArgSrc)) { 2568 t_act(); 2569 } else { 2570 f_act(); 2571 } 2572} 2573 2574LOCALPROC my_reg_call cctrue_CmpW_NE(cond_actP t_act, cond_actP f_act) 2575{ 2576 if (((ui4b)V_regs.LazyFlagArgDst) != ((ui4b)V_regs.LazyFlagArgSrc)) 2577 { 2578 t_act(); 2579 } else { 2580 f_act(); 2581 } 2582} 2583 2584LOCALPROC my_reg_call cctrue_CmpW_EQ(cond_actP t_act, cond_actP f_act) 2585{ 2586 if (((ui4b)V_regs.LazyFlagArgDst) == ((ui4b)V_regs.LazyFlagArgSrc)) 2587 { 2588 t_act(); 2589 } else { 2590 f_act(); 2591 } 2592} 2593 2594LOCALPROC my_reg_call cctrue_CmpW_PL(cond_actP t_act, cond_actP f_act) 2595{ 2596 if (((si4b)(V_regs.LazyFlagArgDst - V_regs.LazyFlagArgSrc)) >= 0) { 2597 t_act(); 2598 } else { 2599 f_act(); 2600 } 2601} 2602 2603LOCALPROC my_reg_call cctrue_CmpW_MI(cond_actP t_act, cond_actP f_act) 2604{ 2605 if (((si4b)(V_regs.LazyFlagArgDst - V_regs.LazyFlagArgSrc)) < 0) { 2606 t_act(); 2607 } else { 2608 f_act(); 2609 } 2610} 2611 2612LOCALPROC my_reg_call cctrue_CmpW_GE(cond_actP t_act, cond_actP f_act) 2613{ 2614 if (((si4b)V_regs.LazyFlagArgDst) >= ((si4b)V_regs.LazyFlagArgSrc)) 2615 { 2616 t_act(); 2617 } else { 2618 f_act(); 2619 } 2620} 2621 2622LOCALPROC my_reg_call cctrue_CmpW_LT(cond_actP t_act, cond_actP f_act) 2623{ 2624 if (((si4b)V_regs.LazyFlagArgDst) < ((si4b)V_regs.LazyFlagArgSrc)) { 2625 t_act(); 2626 } else { 2627 f_act(); 2628 } 2629} 2630 2631LOCALPROC my_reg_call cctrue_CmpW_GT(cond_actP t_act, cond_actP f_act) 2632{ 2633 if (((si4b)V_regs.LazyFlagArgDst) > ((si4b)V_regs.LazyFlagArgSrc)) { 2634 t_act(); 2635 } else { 2636 f_act(); 2637 } 2638} 2639 2640LOCALPROC my_reg_call cctrue_CmpW_LE(cond_actP t_act, cond_actP f_act) 2641{ 2642 if (((si4b)V_regs.LazyFlagArgDst) <= ((si4b)V_regs.LazyFlagArgSrc)) 2643 { 2644 t_act(); 2645 } else { 2646 f_act(); 2647 } 2648} 2649 2650LOCALPROC my_reg_call cctrue_CmpL_HI(cond_actP t_act, cond_actP f_act) 2651{ 2652 if (((ui5b)V_regs.LazyFlagArgDst) > ((ui5b)V_regs.LazyFlagArgSrc)) { 2653 t_act(); 2654 } else { 2655 f_act(); 2656 } 2657} 2658 2659LOCALPROC my_reg_call cctrue_CmpL_LS(cond_actP t_act, cond_actP f_act) 2660{ 2661 if (((ui5b)V_regs.LazyFlagArgDst) <= ((ui5b)V_regs.LazyFlagArgSrc)) 2662 { 2663 t_act(); 2664 } else { 2665 f_act(); 2666 } 2667} 2668 2669LOCALPROC my_reg_call cctrue_CmpL_CC(cond_actP t_act, cond_actP f_act) 2670{ 2671 if (((ui5b)V_regs.LazyFlagArgDst) >= ((ui5b)V_regs.LazyFlagArgSrc)) 2672 { 2673 t_act(); 2674 } else { 2675 f_act(); 2676 } 2677} 2678 2679LOCALPROC my_reg_call cctrue_CmpL_CS(cond_actP t_act, cond_actP f_act) 2680{ 2681 if (((ui5b)V_regs.LazyFlagArgDst) < ((ui5b)V_regs.LazyFlagArgSrc)) { 2682 t_act(); 2683 } else { 2684 f_act(); 2685 } 2686} 2687 2688LOCALPROC my_reg_call cctrue_CmpL_NE(cond_actP t_act, cond_actP f_act) 2689{ 2690 if (V_regs.LazyFlagArgDst != V_regs.LazyFlagArgSrc) { 2691 t_act(); 2692 } else { 2693 f_act(); 2694 } 2695} 2696 2697LOCALPROC my_reg_call cctrue_CmpL_EQ(cond_actP t_act, cond_actP f_act) 2698{ 2699 if (V_regs.LazyFlagArgDst == V_regs.LazyFlagArgSrc) { 2700 t_act(); 2701 } else { 2702 f_act(); 2703 } 2704} 2705 2706LOCALPROC my_reg_call cctrue_CmpL_PL(cond_actP t_act, cond_actP f_act) 2707{ 2708 if ((((si5b)(V_regs.LazyFlagArgDst - V_regs.LazyFlagArgSrc)) >= 0)) 2709 { 2710 t_act(); 2711 } else { 2712 f_act(); 2713 } 2714} 2715 2716LOCALPROC my_reg_call cctrue_CmpL_MI(cond_actP t_act, cond_actP f_act) 2717{ 2718 if ((((si5b)(V_regs.LazyFlagArgDst - V_regs.LazyFlagArgSrc)) < 0)) { 2719 t_act(); 2720 } else { 2721 f_act(); 2722 } 2723} 2724 2725LOCALPROC my_reg_call cctrue_CmpL_GE(cond_actP t_act, cond_actP f_act) 2726{ 2727 if (((si5b)V_regs.LazyFlagArgDst) >= ((si5b)V_regs.LazyFlagArgSrc)) 2728 { 2729 t_act(); 2730 } else { 2731 f_act(); 2732 } 2733} 2734 2735LOCALPROC my_reg_call cctrue_CmpL_LT(cond_actP t_act, cond_actP f_act) 2736{ 2737 if (((si5b)V_regs.LazyFlagArgDst) < ((si5b)V_regs.LazyFlagArgSrc)) { 2738 t_act(); 2739 } else { 2740 f_act(); 2741 } 2742} 2743 2744LOCALPROC my_reg_call cctrue_CmpL_GT(cond_actP t_act, cond_actP f_act) 2745{ 2746 if (((si5b)V_regs.LazyFlagArgDst) > ((si5b)V_regs.LazyFlagArgSrc)) { 2747 t_act(); 2748 } else { 2749 f_act(); 2750 } 2751} 2752 2753LOCALPROC my_reg_call cctrue_CmpL_LE(cond_actP t_act, cond_actP f_act) 2754{ 2755 if (((si5b)V_regs.LazyFlagArgDst) <= ((si5b)V_regs.LazyFlagArgSrc)) 2756 { 2757 t_act(); 2758 } else { 2759 f_act(); 2760 } 2761} 2762 2763LOCALPROC my_reg_call cctrue_Asr_CC(cond_actP t_act, cond_actP f_act) 2764{ 2765 if (0 == 2766 ((V_regs.LazyFlagArgDst >> (V_regs.LazyFlagArgSrc - 1)) & 1)) 2767 { 2768 t_act(); 2769 } else { 2770 f_act(); 2771 } 2772} 2773 2774LOCALPROC my_reg_call cctrue_Asr_CS(cond_actP t_act, cond_actP f_act) 2775{ 2776 if (0 != 2777 ((V_regs.LazyFlagArgDst >> (V_regs.LazyFlagArgSrc - 1)) & 1)) 2778 { 2779 t_act(); 2780 } else { 2781 f_act(); 2782 } 2783} 2784 2785LOCALPROC my_reg_call cctrue_AslB_CC(cond_actP t_act, cond_actP f_act) 2786{ 2787 if (0 == 2788 ((V_regs.LazyFlagArgDst >> (8 - V_regs.LazyFlagArgSrc)) & 1)) 2789 { 2790 t_act(); 2791 } else { 2792 f_act(); 2793 } 2794} 2795 2796LOCALPROC my_reg_call cctrue_AslB_CS(cond_actP t_act, cond_actP f_act) 2797{ 2798 if (0 != 2799 ((V_regs.LazyFlagArgDst >> (8 - V_regs.LazyFlagArgSrc)) & 1)) 2800 { 2801 t_act(); 2802 } else { 2803 f_act(); 2804 } 2805} 2806 2807LOCALPROC my_reg_call cctrue_AslB_VC(cond_actP t_act, cond_actP f_act) 2808{ 2809 ui5r cnt = V_regs.LazyFlagArgSrc; 2810 ui5r dst = ui5r_FromSByte(V_regs.LazyFlagArgDst << cnt); 2811 2812 if (Ui5rASR(dst, cnt) == V_regs.LazyFlagArgDst) { 2813 t_act(); 2814 } else { 2815 f_act(); 2816 } 2817} 2818 2819LOCALPROC my_reg_call cctrue_AslB_VS(cond_actP t_act, cond_actP f_act) 2820{ 2821 ui5r cnt = V_regs.LazyFlagArgSrc; 2822 ui5r dst = ui5r_FromSByte(V_regs.LazyFlagArgDst << cnt); 2823 2824 if (Ui5rASR(dst, cnt) != V_regs.LazyFlagArgDst) { 2825 t_act(); 2826 } else { 2827 f_act(); 2828 } 2829} 2830 2831LOCALPROC my_reg_call cctrue_AslW_CC(cond_actP t_act, cond_actP f_act) 2832{ 2833 if (0 == 2834 ((V_regs.LazyFlagArgDst >> (16 - V_regs.LazyFlagArgSrc)) & 1)) 2835 { 2836 t_act(); 2837 } else { 2838 f_act(); 2839 } 2840} 2841 2842LOCALPROC my_reg_call cctrue_AslW_CS(cond_actP t_act, cond_actP f_act) 2843{ 2844 if (0 != 2845 ((V_regs.LazyFlagArgDst >> (16 - V_regs.LazyFlagArgSrc)) & 1)) 2846 { 2847 t_act(); 2848 } else { 2849 f_act(); 2850 } 2851} 2852 2853LOCALPROC my_reg_call cctrue_AslW_VC(cond_actP t_act, cond_actP f_act) 2854{ 2855 ui5r cnt = V_regs.LazyFlagArgSrc; 2856 ui5r dst = ui5r_FromSWord(V_regs.LazyFlagArgDst << cnt); 2857 2858 if (Ui5rASR(dst, cnt) == V_regs.LazyFlagArgDst) { 2859 t_act(); 2860 } else { 2861 f_act(); 2862 } 2863} 2864 2865LOCALPROC my_reg_call cctrue_AslW_VS(cond_actP t_act, cond_actP f_act) 2866{ 2867 ui5r cnt = V_regs.LazyFlagArgSrc; 2868 ui5r dst = ui5r_FromSWord(V_regs.LazyFlagArgDst << cnt); 2869 2870 if (Ui5rASR(dst, cnt) != V_regs.LazyFlagArgDst) { 2871 t_act(); 2872 } else { 2873 f_act(); 2874 } 2875} 2876 2877LOCALPROC my_reg_call cctrue_AslL_CC(cond_actP t_act, cond_actP f_act) 2878{ 2879 if (0 == 2880 ((V_regs.LazyFlagArgDst >> (32 - V_regs.LazyFlagArgSrc)) & 1)) 2881 { 2882 t_act(); 2883 } else { 2884 f_act(); 2885 } 2886} 2887 2888LOCALPROC my_reg_call cctrue_AslL_CS(cond_actP t_act, cond_actP f_act) 2889{ 2890 if (0 != 2891 ((V_regs.LazyFlagArgDst >> (32 - V_regs.LazyFlagArgSrc)) & 1)) 2892 { 2893 t_act(); 2894 } else { 2895 f_act(); 2896 } 2897} 2898 2899LOCALPROC my_reg_call cctrue_AslL_VC(cond_actP t_act, cond_actP f_act) 2900{ 2901 ui5r cnt = V_regs.LazyFlagArgSrc; 2902 ui5r dst = ui5r_FromSLong(V_regs.LazyFlagArgDst << cnt); 2903 2904 if (Ui5rASR(dst, cnt) == V_regs.LazyFlagArgDst) { 2905 t_act(); 2906 } else { 2907 f_act(); 2908 } 2909} 2910 2911LOCALPROC my_reg_call cctrue_AslL_VS(cond_actP t_act, cond_actP f_act) 2912{ 2913 ui5r cnt = V_regs.LazyFlagArgSrc; 2914 ui5r dst = ui5r_FromSLong(V_regs.LazyFlagArgDst << cnt); 2915 2916 if (Ui5rASR(dst, cnt) != V_regs.LazyFlagArgDst) { 2917 t_act(); 2918 } else { 2919 f_act(); 2920 } 2921} 2922 2923FORWARDPROC my_reg_call cctrue_Dflt(cond_actP t_act, cond_actP f_act); 2924 2925#endif /* UseLazyCC */ 2926 2927#if UseLazyCC 2928#define CCdispSz (16 * kNumLazyFlagsKinds) 2929#else 2930#define CCdispSz 16 2931#endif 2932 2933typedef void (my_reg_call *cctrueP)(cond_actP t_act, cond_actP f_act); 2934 2935LOCALVAR const cctrueP cctrueDispatch[CCdispSz + 1] = { 2936 cctrue_T /* kLazyFlagsDefault T */, 2937 cctrue_F /* kLazyFlagsDefault F */, 2938 cctrue_HI /* kLazyFlagsDefault HI */, 2939 cctrue_LS /* kLazyFlagsDefault LS */, 2940 cctrue_CC /* kLazyFlagsDefault CC */, 2941 cctrue_CS /* kLazyFlagsDefault CS */, 2942 cctrue_NE /* kLazyFlagsDefault NE */, 2943 cctrue_EQ /* kLazyFlagsDefault EQ */, 2944 cctrue_VC /* kLazyFlagsDefault VC */, 2945 cctrue_VS /* kLazyFlagsDefault VS */, 2946 cctrue_PL /* kLazyFlagsDefault PL */, 2947 cctrue_MI /* kLazyFlagsDefault MI */, 2948 cctrue_GE /* kLazyFlagsDefault GE */, 2949 cctrue_LT /* kLazyFlagsDefault LT */, 2950 cctrue_GT /* kLazyFlagsDefault GT */, 2951 cctrue_LE /* kLazyFlagsDefault LE */, 2952 2953#if UseLazyCC 2954 cctrue_T /* kLazyFlagsTstB T */, 2955 cctrue_F /* kLazyFlagsTstB F */, 2956 cctrue_Dflt /* kLazyFlagsTstB HI */, 2957 cctrue_Dflt /* kLazyFlagsTstB LS */, 2958 cctrue_Dflt /* kLazyFlagsTstB CC */, 2959 cctrue_Dflt /* kLazyFlagsTstB CS */, 2960 cctrue_Dflt /* kLazyFlagsTstB NE */, 2961 cctrue_Dflt /* kLazyFlagsTstB EQ */, 2962 cctrue_Dflt /* kLazyFlagsTstB VC */, 2963 cctrue_Dflt /* kLazyFlagsTstB VS */, 2964 cctrue_Dflt /* kLazyFlagsTstB PL */, 2965 cctrue_Dflt /* kLazyFlagsTstB MI */, 2966 cctrue_Dflt /* kLazyFlagsTstB GE */, 2967 cctrue_Dflt /* kLazyFlagsTstB LT */, 2968 cctrue_Dflt /* kLazyFlagsTstB GT */, 2969 cctrue_Dflt /* kLazyFlagsTstB LE */, 2970 2971 cctrue_T /* kLazyFlagsTstW T */, 2972 cctrue_F /* kLazyFlagsTstW F */, 2973 cctrue_Dflt /* kLazyFlagsTstW HI */, 2974 cctrue_Dflt /* kLazyFlagsTstW LS */, 2975 cctrue_Dflt /* kLazyFlagsTstW CC */, 2976 cctrue_Dflt /* kLazyFlagsTstW CS */, 2977 cctrue_Dflt /* kLazyFlagsTstW NE */, 2978 cctrue_Dflt /* kLazyFlagsTstW EQ */, 2979 cctrue_Dflt /* kLazyFlagsTstW VC */, 2980 cctrue_Dflt /* kLazyFlagsTstW VS */, 2981 cctrue_Dflt /* kLazyFlagsTstW PL */, 2982 cctrue_Dflt /* kLazyFlagsTstW MI */, 2983 cctrue_Dflt /* kLazyFlagsTstW GE */, 2984 cctrue_Dflt /* kLazyFlagsTstW LT */, 2985 cctrue_Dflt /* kLazyFlagsTstW GT */, 2986 cctrue_Dflt /* kLazyFlagsTstW LE */, 2987 2988 cctrue_T /* kLazyFlagsTstL T */, 2989 cctrue_F /* kLazyFlagsTstL F */, 2990 cctrue_TstL_HI /* kLazyFlagsTstL HI */, 2991 cctrue_TstL_LS /* kLazyFlagsTstL LS */, 2992 cctrue_T /* cctrue_TstL_CC */ /* kLazyFlagsTstL CC */, 2993 cctrue_F /* cctrue_TstL_CS */ /* kLazyFlagsTstL CS */, 2994 cctrue_TstL_NE /* kLazyFlagsTstL NE */, 2995 cctrue_TstL_EQ /* kLazyFlagsTstL EQ */, 2996 cctrue_T /* cctrue_Dflt */ /* kLazyFlagsTstL VC */, 2997 cctrue_F /* cctrue_Dflt */ /* kLazyFlagsTstL VS */, 2998 cctrue_TstL_PL /* kLazyFlagsTstL PL */, 2999 cctrue_TstL_MI /* kLazyFlagsTstL MI */, 3000 cctrue_TstL_GE /* kLazyFlagsTstL GE */, 3001 cctrue_TstL_LT /* kLazyFlagsTstL LT */, 3002 cctrue_TstL_GT /* kLazyFlagsTstL GT */, 3003 cctrue_TstL_LE /* kLazyFlagsTstL LE */, 3004 3005 cctrue_T /* kLazyFlagsCmpB T */, 3006 cctrue_F /* kLazyFlagsCmpB F */, 3007 cctrue_CmpB_HI /* kLazyFlagsCmpB HI */, 3008 cctrue_CmpB_LS /* kLazyFlagsCmpB LS */, 3009 cctrue_CmpB_CC /* kLazyFlagsCmpB CC */, 3010 cctrue_CmpB_CS /* kLazyFlagsCmpB CS */, 3011 cctrue_CmpB_NE /* kLazyFlagsCmpB NE */, 3012 cctrue_CmpB_EQ /* kLazyFlagsCmpB EQ */, 3013 cctrue_Dflt /* kLazyFlagsCmpB VC */, 3014 cctrue_Dflt /* kLazyFlagsCmpB VS */, 3015 cctrue_CmpB_PL /* kLazyFlagsCmpB PL */, 3016 cctrue_CmpB_MI /* kLazyFlagsCmpB MI */, 3017 cctrue_CmpB_GE /* kLazyFlagsCmpB GE */, 3018 cctrue_CmpB_LT /* kLazyFlagsCmpB LT */, 3019 cctrue_CmpB_GT /* kLazyFlagsCmpB GT */, 3020 cctrue_CmpB_LE /* kLazyFlagsCmpB LE */, 3021 3022 cctrue_T /* kLazyFlagsCmpW T */, 3023 cctrue_F /* kLazyFlagsCmpW F */, 3024 cctrue_CmpW_HI /* kLazyFlagsCmpW HI */, 3025 cctrue_CmpW_LS /* kLazyFlagsCmpW LS */, 3026 cctrue_CmpW_CC /* kLazyFlagsCmpW CC */, 3027 cctrue_CmpW_CS /* kLazyFlagsCmpW CS */, 3028 cctrue_CmpW_NE /* kLazyFlagsCmpW NE */, 3029 cctrue_CmpW_EQ /* kLazyFlagsCmpW EQ */, 3030 cctrue_Dflt /* kLazyFlagsCmpW VC */, 3031 cctrue_Dflt /* kLazyFlagsCmpW VS */, 3032 cctrue_CmpW_PL /* kLazyFlagsCmpW PL */, 3033 cctrue_CmpW_MI /* kLazyFlagsCmpW MI */, 3034 cctrue_CmpW_GE /* kLazyFlagsCmpW GE */, 3035 cctrue_CmpW_LT /* kLazyFlagsCmpW LT */, 3036 cctrue_CmpW_GT /* kLazyFlagsCmpW GT */, 3037 cctrue_CmpW_LE /* kLazyFlagsCmpW LE */, 3038 3039 cctrue_T /* kLazyFlagsCmpL T */, 3040 cctrue_F /* kLazyFlagsCmpL F */, 3041 cctrue_CmpL_HI /* kLazyFlagsCmpL HI */, 3042 cctrue_CmpL_LS /* kLazyFlagsCmpL LS */, 3043 cctrue_CmpL_CC /* kLazyFlagsCmpL CC */, 3044 cctrue_CmpL_CS /* kLazyFlagsCmpL CS */, 3045 cctrue_CmpL_NE /* kLazyFlagsCmpL NE */, 3046 cctrue_CmpL_EQ /* kLazyFlagsCmpL EQ */, 3047 cctrue_Dflt /* kLazyFlagsCmpL VC */, 3048 cctrue_Dflt /* kLazyFlagsCmpL VS */, 3049 cctrue_CmpL_PL /* kLazyFlagsCmpL PL */, 3050 cctrue_CmpL_MI /* kLazyFlagsCmpL MI */, 3051 cctrue_CmpL_GE /* kLazyFlagsCmpL GE */, 3052 cctrue_CmpL_LT /* kLazyFlagsCmpL LT */, 3053 cctrue_CmpL_GT /* kLazyFlagsCmpL GT */, 3054 cctrue_CmpL_LE /* kLazyFlagsCmpL LE */, 3055 3056 cctrue_T /* kLazyFlagsSubB T */, 3057 cctrue_F /* kLazyFlagsSubB F */, 3058 cctrue_CmpB_HI /* kLazyFlagsSubB HI */, 3059 cctrue_CmpB_LS /* kLazyFlagsSubB LS */, 3060 cctrue_CmpB_CC /* kLazyFlagsSubB CC */, 3061 cctrue_CmpB_CS /* kLazyFlagsSubB CS */, 3062 cctrue_CmpB_NE /* kLazyFlagsSubB NE */, 3063 cctrue_CmpB_EQ /* kLazyFlagsSubB EQ */, 3064 cctrue_Dflt /* kLazyFlagsSubB VC */, 3065 cctrue_Dflt /* kLazyFlagsSubB VS */, 3066 cctrue_CmpB_PL /* kLazyFlagsSubB PL */, 3067 cctrue_CmpB_MI /* kLazyFlagsSubB MI */, 3068 cctrue_CmpB_GE /* kLazyFlagsSubB GE */, 3069 cctrue_CmpB_LT /* kLazyFlagsSubB LT */, 3070 cctrue_CmpB_GT /* kLazyFlagsSubB GT */, 3071 cctrue_CmpB_LE /* kLazyFlagsSubB LE */, 3072 3073 cctrue_T /* kLazyFlagsSubW T */, 3074 cctrue_F /* kLazyFlagsSubW F */, 3075 cctrue_CmpW_HI /* kLazyFlagsSubW HI */, 3076 cctrue_CmpW_LS /* kLazyFlagsSubW LS */, 3077 cctrue_CmpW_CC /* kLazyFlagsSubW CC */, 3078 cctrue_CmpW_CS /* kLazyFlagsSubW CS */, 3079 cctrue_CmpW_NE /* kLazyFlagsSubW NE */, 3080 cctrue_CmpW_EQ /* kLazyFlagsSubW EQ */, 3081 cctrue_Dflt /* kLazyFlagsSubW VC */, 3082 cctrue_Dflt /* kLazyFlagsSubW VS */, 3083 cctrue_CmpW_PL /* kLazyFlagsSubW PL */, 3084 cctrue_CmpW_MI /* kLazyFlagsSubW MI */, 3085 cctrue_CmpW_GE /* kLazyFlagsSubW GE */, 3086 cctrue_CmpW_LT /* kLazyFlagsSubW LT */, 3087 cctrue_CmpW_GT /* kLazyFlagsSubW GT */, 3088 cctrue_CmpW_LE /* kLazyFlagsSubW LE */, 3089 3090 cctrue_T /* kLazyFlagsSubL T */, 3091 cctrue_F /* kLazyFlagsSubL F */, 3092 cctrue_CmpL_HI /* kLazyFlagsSubL HI */, 3093 cctrue_CmpL_LS /* kLazyFlagsSubL LS */, 3094 cctrue_CmpL_CC /* kLazyFlagsSubL CC */, 3095 cctrue_CmpL_CS /* kLazyFlagsSubL CS */, 3096 cctrue_CmpL_NE /* kLazyFlagsSubL NE */, 3097 cctrue_CmpL_EQ /* kLazyFlagsSubL EQ */, 3098 cctrue_Dflt /* kLazyFlagsSubL VC */, 3099 cctrue_Dflt /* kLazyFlagsSubL VS */, 3100 cctrue_CmpL_PL /* kLazyFlagsSubL PL */, 3101 cctrue_CmpL_MI /* kLazyFlagsSubL MI */, 3102 cctrue_CmpL_GE /* kLazyFlagsSubL GE */, 3103 cctrue_CmpL_LT /* kLazyFlagsSubL LT */, 3104 cctrue_CmpL_GT /* kLazyFlagsSubL GT */, 3105 cctrue_CmpL_LE /* kLazyFlagsSubL LE */, 3106 3107 cctrue_T /* kLazyFlagsAddB T */, 3108 cctrue_F /* kLazyFlagsAddB F */, 3109 cctrue_Dflt /* kLazyFlagsAddB HI */, 3110 cctrue_Dflt /* kLazyFlagsAddB LS */, 3111 cctrue_Dflt /* kLazyFlagsAddB CC */, 3112 cctrue_Dflt /* kLazyFlagsAddB CS */, 3113 cctrue_Dflt /* kLazyFlagsAddB NE */, 3114 cctrue_Dflt /* kLazyFlagsAddB EQ */, 3115 cctrue_Dflt /* kLazyFlagsAddB VC */, 3116 cctrue_Dflt /* kLazyFlagsAddB VS */, 3117 cctrue_Dflt /* kLazyFlagsAddB PL */, 3118 cctrue_Dflt /* kLazyFlagsAddB MI */, 3119 cctrue_Dflt /* kLazyFlagsAddB GE */, 3120 cctrue_Dflt /* kLazyFlagsAddB LT */, 3121 cctrue_Dflt /* kLazyFlagsAddB GT */, 3122 cctrue_Dflt /* kLazyFlagsAddB LE */, 3123 3124 cctrue_T /* kLazyFlagsAddW T */, 3125 cctrue_F /* kLazyFlagsAddW F */, 3126 cctrue_Dflt /* kLazyFlagsAddW HI */, 3127 cctrue_Dflt /* kLazyFlagsAddW LS */, 3128 cctrue_Dflt /* kLazyFlagsAddW CC */, 3129 cctrue_Dflt /* kLazyFlagsAddW CS */, 3130 cctrue_Dflt /* kLazyFlagsAddW NE */, 3131 cctrue_Dflt /* kLazyFlagsAddW EQ */, 3132 cctrue_Dflt /* kLazyFlagsAddW VC */, 3133 cctrue_Dflt /* kLazyFlagsAddW VS */, 3134 cctrue_Dflt /* kLazyFlagsAddW PL */, 3135 cctrue_Dflt /* kLazyFlagsAddW MI */, 3136 cctrue_Dflt /* kLazyFlagsAddW GE */, 3137 cctrue_Dflt /* kLazyFlagsAddW LT */, 3138 cctrue_Dflt /* kLazyFlagsAddW GT */, 3139 cctrue_Dflt /* kLazyFlagsAddW LE */, 3140 3141 cctrue_T /* kLazyFlagsAddL T */, 3142 cctrue_F /* kLazyFlagsAddL F */, 3143 cctrue_Dflt /* kLazyFlagsAddL HI */, 3144 cctrue_Dflt /* kLazyFlagsAddL LS */, 3145 cctrue_Dflt /* kLazyFlagsAddL CC */, 3146 cctrue_Dflt /* kLazyFlagsAddL CS */, 3147 cctrue_Dflt /* kLazyFlagsAddL NE */, 3148 cctrue_Dflt /* kLazyFlagsAddL EQ */, 3149 cctrue_Dflt /* kLazyFlagsAddL VC */, 3150 cctrue_Dflt /* kLazyFlagsAddL VS */, 3151 cctrue_Dflt /* kLazyFlagsAddL PL */, 3152 cctrue_Dflt /* kLazyFlagsAddL MI */, 3153 cctrue_Dflt /* kLazyFlagsAddL GE */, 3154 cctrue_Dflt /* kLazyFlagsAddL LT */, 3155 cctrue_Dflt /* kLazyFlagsAddL GT */, 3156 cctrue_Dflt /* kLazyFlagsAddL LE */, 3157 3158 cctrue_T /* kLazyFlagsNegB T */, 3159 cctrue_F /* kLazyFlagsNegB F */, 3160 cctrue_Dflt /* kLazyFlagsNegB HI */, 3161 cctrue_Dflt /* kLazyFlagsNegB LS */, 3162 cctrue_Dflt /* kLazyFlagsNegB CC */, 3163 cctrue_Dflt /* kLazyFlagsNegB CS */, 3164 cctrue_Dflt /* kLazyFlagsNegB NE */, 3165 cctrue_Dflt /* kLazyFlagsNegB EQ */, 3166 cctrue_Dflt /* kLazyFlagsNegB VC */, 3167 cctrue_Dflt /* kLazyFlagsNegB VS */, 3168 cctrue_Dflt /* kLazyFlagsNegB PL */, 3169 cctrue_Dflt /* kLazyFlagsNegB MI */, 3170 cctrue_Dflt /* kLazyFlagsNegB GE */, 3171 cctrue_Dflt /* kLazyFlagsNegB LT */, 3172 cctrue_Dflt /* kLazyFlagsNegB GT */, 3173 cctrue_Dflt /* kLazyFlagsNegB LE */, 3174 3175 cctrue_T /* kLazyFlagsNegW T */, 3176 cctrue_F /* kLazyFlagsNegW F */, 3177 cctrue_Dflt /* kLazyFlagsNegW HI */, 3178 cctrue_Dflt /* kLazyFlagsNegW LS */, 3179 cctrue_Dflt /* kLazyFlagsNegW CC */, 3180 cctrue_Dflt /* kLazyFlagsNegW CS */, 3181 cctrue_Dflt /* kLazyFlagsNegW NE */, 3182 cctrue_Dflt /* kLazyFlagsNegW EQ */, 3183 cctrue_Dflt /* kLazyFlagsNegW VC */, 3184 cctrue_Dflt /* kLazyFlagsNegW VS */, 3185 cctrue_Dflt /* kLazyFlagsNegW PL */, 3186 cctrue_Dflt /* kLazyFlagsNegW MI */, 3187 cctrue_Dflt /* kLazyFlagsNegW GE */, 3188 cctrue_Dflt /* kLazyFlagsNegW LT */, 3189 cctrue_Dflt /* kLazyFlagsNegW GT */, 3190 cctrue_Dflt /* kLazyFlagsNegW LE */, 3191 3192 cctrue_T /* kLazyFlagsNegL T */, 3193 cctrue_F /* kLazyFlagsNegL F */, 3194 cctrue_Dflt /* kLazyFlagsNegL HI */, 3195 cctrue_Dflt /* kLazyFlagsNegL LS */, 3196 cctrue_Dflt /* kLazyFlagsNegL CC */, 3197 cctrue_Dflt /* kLazyFlagsNegL CS */, 3198 cctrue_Dflt /* kLazyFlagsNegL NE */, 3199 cctrue_Dflt /* kLazyFlagsNegL EQ */, 3200 cctrue_Dflt /* kLazyFlagsNegL VC */, 3201 cctrue_Dflt /* kLazyFlagsNegL VS */, 3202 cctrue_Dflt /* kLazyFlagsNegL PL */, 3203 cctrue_Dflt /* kLazyFlagsNegL MI */, 3204 cctrue_Dflt /* kLazyFlagsNegL GE */, 3205 cctrue_Dflt /* kLazyFlagsNegL LT */, 3206 cctrue_Dflt /* kLazyFlagsNegL GT */, 3207 cctrue_Dflt /* kLazyFlagsNegL LE */, 3208 3209 cctrue_T /* kLazyFlagsAsrB T */, 3210 cctrue_F /* kLazyFlagsAsrB F */, 3211 cctrue_Dflt /* kLazyFlagsAsrB HI */, 3212 cctrue_Dflt /* kLazyFlagsAsrB LS */, 3213 cctrue_Asr_CC /* kLazyFlagsAsrB CC */, 3214 cctrue_Asr_CS /* kLazyFlagsAsrB CS */, 3215 cctrue_Dflt /* kLazyFlagsAsrB NE */, 3216 cctrue_Dflt /* kLazyFlagsAsrB EQ */, 3217 cctrue_Dflt /* kLazyFlagsAsrB VC */, 3218 cctrue_Dflt /* kLazyFlagsAsrB VS */, 3219 cctrue_Dflt /* kLazyFlagsAsrB PL */, 3220 cctrue_Dflt /* kLazyFlagsAsrB MI */, 3221 cctrue_Dflt /* kLazyFlagsAsrB GE */, 3222 cctrue_Dflt /* kLazyFlagsAsrB LT */, 3223 cctrue_Dflt /* kLazyFlagsAsrB GT */, 3224 cctrue_Dflt /* kLazyFlagsAsrB LE */, 3225 3226 cctrue_T /* kLazyFlagsAsrW T */, 3227 cctrue_F /* kLazyFlagsAsrW F */, 3228 cctrue_Dflt /* kLazyFlagsAsrW HI */, 3229 cctrue_Dflt /* kLazyFlagsAsrW LS */, 3230 cctrue_Asr_CC /* kLazyFlagsAsrW CC */, 3231 cctrue_Asr_CS /* kLazyFlagsAsrW CS */, 3232 cctrue_Dflt /* kLazyFlagsAsrW NE */, 3233 cctrue_Dflt /* kLazyFlagsAsrW EQ */, 3234 cctrue_Dflt /* kLazyFlagsAsrW VC */, 3235 cctrue_Dflt /* kLazyFlagsAsrW VS */, 3236 cctrue_Dflt /* kLazyFlagsAsrW PL */, 3237 cctrue_Dflt /* kLazyFlagsAsrW MI */, 3238 cctrue_Dflt /* kLazyFlagsAsrW GE */, 3239 cctrue_Dflt /* kLazyFlagsAsrW LT */, 3240 cctrue_Dflt /* kLazyFlagsAsrW GT */, 3241 cctrue_Dflt /* kLazyFlagsAsrW LE */, 3242 3243 cctrue_T /* kLazyFlagsAsrL T */, 3244 cctrue_F /* kLazyFlagsAsrL F */, 3245 cctrue_Dflt /* kLazyFlagsAsrL HI */, 3246 cctrue_Dflt /* kLazyFlagsAsrL LS */, 3247 cctrue_Asr_CC /* kLazyFlagsAsrL CC */, 3248 cctrue_Asr_CS /* kLazyFlagsAsrL CS */, 3249 cctrue_Dflt /* kLazyFlagsAsrL NE */, 3250 cctrue_Dflt /* kLazyFlagsAsrL EQ */, 3251 cctrue_Dflt /* kLazyFlagsAsrL VC */, 3252 cctrue_Dflt /* kLazyFlagsAsrL VS */, 3253 cctrue_Dflt /* kLazyFlagsAsrL PL */, 3254 cctrue_Dflt /* kLazyFlagsAsrL MI */, 3255 cctrue_Dflt /* kLazyFlagsAsrL GE */, 3256 cctrue_Dflt /* kLazyFlagsAsrL LT */, 3257 cctrue_Dflt /* kLazyFlagsAsrL GT */, 3258 cctrue_Dflt /* kLazyFlagsAsrL LE */, 3259 3260 cctrue_T /* kLazyFlagsAslB T */, 3261 cctrue_F /* kLazyFlagsAslB F */, 3262 cctrue_Dflt /* kLazyFlagsAslB HI */, 3263 cctrue_Dflt /* kLazyFlagsAslB LS */, 3264 cctrue_AslB_CC /* kLazyFlagsAslB CC */, 3265 cctrue_AslB_CS /* kLazyFlagsAslB CS */, 3266 cctrue_Dflt /* kLazyFlagsAslB NE */, 3267 cctrue_Dflt /* kLazyFlagsAslB EQ */, 3268 cctrue_AslB_VC /* kLazyFlagsAslB VC */, 3269 cctrue_AslB_VS /* kLazyFlagsAslB VS */, 3270 cctrue_Dflt /* kLazyFlagsAslB PL */, 3271 cctrue_Dflt /* kLazyFlagsAslB MI */, 3272 cctrue_Dflt /* kLazyFlagsAslB GE */, 3273 cctrue_Dflt /* kLazyFlagsAslB LT */, 3274 cctrue_Dflt /* kLazyFlagsAslB GT */, 3275 cctrue_Dflt /* kLazyFlagsAslB LE */, 3276 3277 cctrue_T /* kLazyFlagsAslW T */, 3278 cctrue_F /* kLazyFlagsAslW F */, 3279 cctrue_Dflt /* kLazyFlagsAslW HI */, 3280 cctrue_Dflt /* kLazyFlagsAslW LS */, 3281 cctrue_AslW_CC /* kLazyFlagsAslW CC */, 3282 cctrue_AslW_CS /* kLazyFlagsAslW CS */, 3283 cctrue_Dflt /* kLazyFlagsAslW NE */, 3284 cctrue_Dflt /* kLazyFlagsAslW EQ */, 3285 cctrue_AslW_VC /* kLazyFlagsAslW VC */, 3286 cctrue_AslW_VS /* kLazyFlagsAslW VS */, 3287 cctrue_Dflt /* kLazyFlagsAslW PL */, 3288 cctrue_Dflt /* kLazyFlagsAslW MI */, 3289 cctrue_Dflt /* kLazyFlagsAslW GE */, 3290 cctrue_Dflt /* kLazyFlagsAslW LT */, 3291 cctrue_Dflt /* kLazyFlagsAslW GT */, 3292 cctrue_Dflt /* kLazyFlagsAslW LE */, 3293 3294 cctrue_T /* kLazyFlagsAslL T */, 3295 cctrue_F /* kLazyFlagsAslL F */, 3296 cctrue_Dflt /* kLazyFlagsAslL HI */, 3297 cctrue_Dflt /* kLazyFlagsAslL LS */, 3298 cctrue_AslL_CC /* kLazyFlagsAslL CC */, 3299 cctrue_AslL_CS /* kLazyFlagsAslL CS */, 3300 cctrue_Dflt /* kLazyFlagsAslL NE */, 3301 cctrue_Dflt /* kLazyFlagsAslL EQ */, 3302 cctrue_AslL_VC /* kLazyFlagsAslL VC */, 3303 cctrue_AslL_VS /* kLazyFlagsAslL VS */, 3304 cctrue_Dflt /* kLazyFlagsAslL PL */, 3305 cctrue_Dflt /* kLazyFlagsAslL MI */, 3306 cctrue_Dflt /* kLazyFlagsAslL GE */, 3307 cctrue_Dflt /* kLazyFlagsAslL LT */, 3308 cctrue_Dflt /* kLazyFlagsAslL GT */, 3309 cctrue_Dflt /* kLazyFlagsAslL LE */, 3310 3311#if UseLazyZ 3312 cctrue_T /* kLazyFlagsZSet T */, 3313 cctrue_F /* kLazyFlagsZSet F */, 3314 cctrue_Dflt /* kLazyFlagsZSet HI */, 3315 cctrue_Dflt /* kLazyFlagsZSet LS */, 3316 cctrue_Dflt /* kLazyFlagsZSet CC */, 3317 cctrue_Dflt /* kLazyFlagsZSet CS */, 3318 cctrue_NE /* kLazyFlagsZSet NE */, 3319 cctrue_EQ /* kLazyFlagsZSet EQ */, 3320 cctrue_Dflt /* kLazyFlagsZSet VC */, 3321 cctrue_Dflt /* kLazyFlagsZSet VS */, 3322 cctrue_Dflt /* kLazyFlagsZSet PL */, 3323 cctrue_Dflt /* kLazyFlagsZSet MI */, 3324 cctrue_Dflt /* kLazyFlagsZSet GE */, 3325 cctrue_Dflt /* kLazyFlagsZSet LT */, 3326 cctrue_Dflt /* kLazyFlagsZSet GT */, 3327 cctrue_Dflt /* kLazyFlagsZSet LE */, 3328#endif 3329#endif /* UseLazyCC */ 3330 3331 0 3332}; 3333 3334#if UseLazyCC 3335LOCALINLINEPROC cctrue(cond_actP t_act, cond_actP f_act) 3336{ 3337 (cctrueDispatch[V_regs.LazyFlagKind * 16 3338 + V_regs.CurDecOpY.v[0].ArgDat])(t_act, f_act); 3339} 3340#endif 3341 3342 3343LOCALPROC NeedDefaultLazyXFlagSubB(void) 3344{ 3345 XFLG = Bool2Bit(((ui3b)V_regs.LazyXFlagArgDst) 3346 < ((ui3b)V_regs.LazyXFlagArgSrc)); 3347 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3348} 3349 3350LOCALPROC NeedDefaultLazyXFlagSubW(void) 3351{ 3352 XFLG = Bool2Bit(((ui4b)V_regs.LazyXFlagArgDst) 3353 < ((ui4b)V_regs.LazyXFlagArgSrc)); 3354 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3355} 3356 3357LOCALPROC NeedDefaultLazyXFlagSubL(void) 3358{ 3359 XFLG = Bool2Bit(((ui5b)V_regs.LazyXFlagArgDst) 3360 < ((ui5b)V_regs.LazyXFlagArgSrc)); 3361 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3362} 3363 3364LOCALPROC NeedDefaultLazyXFlagAddB(void) 3365{ 3366 ui3b src = (ui3b)V_regs.LazyXFlagArgSrc; 3367 ui3b dst = (ui3b)V_regs.LazyXFlagArgDst; 3368 ui3b result = dst + src; 3369 3370 XFLG = Bool2Bit(result < src); 3371 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3372} 3373 3374LOCALPROC NeedDefaultLazyXFlagAddW(void) 3375{ 3376 ui4b src = (ui4b)V_regs.LazyXFlagArgSrc; 3377 ui4b dst = (ui4b)V_regs.LazyXFlagArgDst; 3378 ui4b result = dst + src; 3379 3380 XFLG = Bool2Bit(result < src); 3381 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3382} 3383 3384LOCALPROC NeedDefaultLazyXFlagAddL(void) 3385{ 3386 ui5b src = (ui5b)V_regs.LazyXFlagArgSrc; 3387 ui5b dst = (ui5b)V_regs.LazyXFlagArgDst; 3388 ui5b result = dst + src; 3389 3390 XFLG = Bool2Bit(result < src); 3391 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3392} 3393 3394LOCALPROC NeedDefaultLazyXFlagNegB(void) 3395{ 3396 XFLG = Bool2Bit(((ui3b)0) 3397 < ((ui3b)V_regs.LazyXFlagArgDst)); 3398 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3399} 3400 3401LOCALPROC NeedDefaultLazyXFlagNegW(void) 3402{ 3403 XFLG = Bool2Bit(((ui4b)0) 3404 < ((ui4b)V_regs.LazyXFlagArgDst)); 3405 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3406} 3407 3408LOCALPROC NeedDefaultLazyXFlagNegL(void) 3409{ 3410 XFLG = Bool2Bit(((ui5b)0) 3411 < ((ui5b)V_regs.LazyXFlagArgDst)); 3412 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3413} 3414 3415LOCALPROC NeedDefaultLazyXFlagAsr(void) 3416{ 3417 ui5r cnt = V_regs.LazyFlagArgSrc; 3418 ui5r dst = V_regs.LazyFlagArgDst; 3419 3420 XFLG = ((dst >> (cnt - 1)) & 1); 3421 3422 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3423} 3424 3425LOCALPROC NeedDefaultLazyXFlagAslB(void) 3426{ 3427 XFLG = (V_regs.LazyFlagArgDst >> (8 - V_regs.LazyFlagArgSrc)) & 1; 3428 3429 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3430} 3431 3432LOCALPROC NeedDefaultLazyXFlagAslW(void) 3433{ 3434 XFLG = (V_regs.LazyFlagArgDst >> (16 - V_regs.LazyFlagArgSrc)) & 1; 3435 3436 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3437} 3438 3439LOCALPROC NeedDefaultLazyXFlagAslL(void) 3440{ 3441 XFLG = (V_regs.LazyFlagArgDst >> (32 - V_regs.LazyFlagArgSrc)) & 1; 3442 3443 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3444} 3445 3446LOCALPROC NeedDefaultLazyXFlagDefault(void) 3447{ 3448} 3449 3450typedef void (*NeedLazyFlagP)(void); 3451 3452LOCALVAR const NeedLazyFlagP 3453 NeedLazyXFlagDispatch[kNumLazyFlagsKinds + 1] = 3454{ 3455 NeedDefaultLazyXFlagDefault /* kLazyFlagsDefault */, 3456 0 /* kLazyFlagsTstB */, 3457 0 /* kLazyFlagsTstW */, 3458 0 /* kLazyFlagsTstL */, 3459 0 /* kLazyFlagsCmpB */, 3460 0 /* kLazyFlagsCmpW */, 3461 0 /* kLazyFlagsCmpL */, 3462 NeedDefaultLazyXFlagSubB /* kLazyFlagsSubB */, 3463 NeedDefaultLazyXFlagSubW /* kLazyFlagsSubW */, 3464 NeedDefaultLazyXFlagSubL /* kLazyFlagsSubL */, 3465 NeedDefaultLazyXFlagAddB /* kLazyFlagsAddB */, 3466 NeedDefaultLazyXFlagAddW /* kLazyFlagsAddW */, 3467 NeedDefaultLazyXFlagAddL /* kLazyFlagsAddL */, 3468 NeedDefaultLazyXFlagNegB /* kLazyFlagsNegB */, 3469 NeedDefaultLazyXFlagNegW /* kLazyFlagsNegW */, 3470 NeedDefaultLazyXFlagNegL /* kLazyFlagsNegL */, 3471 NeedDefaultLazyXFlagAsr /* kLazyFlagsAsrB */, 3472 NeedDefaultLazyXFlagAsr /* kLazyFlagsAsrW */, 3473 NeedDefaultLazyXFlagAsr /* kLazyFlagsAsrL */, 3474 NeedDefaultLazyXFlagAslB /* kLazyFlagsAslB */, 3475 NeedDefaultLazyXFlagAslW /* kLazyFlagsAslW */, 3476 NeedDefaultLazyXFlagAslL /* kLazyFlagsAslL */, 3477#if UseLazyZ 3478 0 /* kLazyFlagsZSet */, 3479#endif 3480 3481 0 3482}; 3483 3484LOCALPROC NeedDefaultLazyXFlag(void) 3485{ 3486#if ForceFlagsEval 3487 if (kLazyFlagsDefault != V_regs.LazyXFlagKind) { 3488 ReportAbnormalID(0x0103, 3489 "not kLazyFlagsDefault in NeedDefaultLazyXFlag"); 3490 } 3491#else 3492 (NeedLazyXFlagDispatch[V_regs.LazyXFlagKind])(); 3493#endif 3494} 3495 3496LOCALPROC NeedDefaultLazyFlagsTstL(void) 3497{ 3498 ui5r dst = V_regs.LazyFlagArgDst; 3499 3500 VFLG = CFLG = 0; 3501 ZFLG = Bool2Bit(dst == 0); 3502 NFLG = Bool2Bit(ui5r_MSBisSet(dst)); 3503 3504 V_regs.LazyFlagKind = kLazyFlagsDefault; 3505 NeedDefaultLazyXFlag(); 3506} 3507 3508LOCALPROC NeedDefaultLazyFlagsCmpB(void) 3509{ 3510 ui5r src = V_regs.LazyFlagArgSrc; 3511 ui5r dst = V_regs.LazyFlagArgDst; 3512 ui5r result0 = dst - src; 3513 ui5r result1 = ui5r_FromUByte(dst) 3514 - ui5r_FromUByte(src); 3515 ui5r result = ui5r_FromSByte(result0); 3516 3517 ZFLG = Bool2Bit(result == 0); 3518 NFLG = Bool2Bit(ui5r_MSBisSet(result)); 3519 VFLG = (((result0 >> 1) ^ result0) >> 7) & 1; 3520 CFLG = (result1 >> 8) & 1; 3521 3522 V_regs.LazyFlagKind = kLazyFlagsDefault; 3523 NeedDefaultLazyXFlag(); 3524} 3525 3526LOCALPROC NeedDefaultLazyFlagsCmpW(void) 3527{ 3528 ui5r result0 = V_regs.LazyFlagArgDst - V_regs.LazyFlagArgSrc; 3529 ui5r result = ui5r_FromSWord(result0); 3530 3531 ZFLG = Bool2Bit(result == 0); 3532 NFLG = Bool2Bit(ui5r_MSBisSet(result)); 3533 3534 VFLG = (((result0 >> 1) ^ result0) >> 15) & 1; 3535 { 3536 ui5r result1 = ui5r_FromUWord(V_regs.LazyFlagArgDst) 3537 - ui5r_FromUWord(V_regs.LazyFlagArgSrc); 3538 3539 CFLG = (result1 >> 16) & 1; 3540 } 3541 3542 V_regs.LazyFlagKind = kLazyFlagsDefault; 3543 NeedDefaultLazyXFlag(); 3544} 3545 3546LOCALPROC NeedDefaultLazyFlagsCmpL(void) 3547{ 3548 ui5r src = V_regs.LazyFlagArgSrc; 3549 ui5r dst = V_regs.LazyFlagArgDst; 3550 ui5r result = ui5r_FromSLong(dst - src); 3551 3552 ZFLG = Bool2Bit(result == 0); 3553 3554 { 3555 flagtype flgn = Bool2Bit(ui5r_MSBisSet(result)); 3556 flagtype flgs = Bool2Bit(ui5r_MSBisSet(src)); 3557 flagtype flgo = Bool2Bit(ui5r_MSBisSet(dst)) ^ 1; 3558 flagtype flgsando = flgs & flgo; 3559 flagtype flgsoro = flgs | flgo; 3560 3561 NFLG = flgn; 3562 VFLG = ((flgn | flgsoro) ^ 1) | (flgn & flgsando); 3563 CFLG = flgsando | (flgn & flgsoro); 3564 } 3565 3566 V_regs.LazyFlagKind = kLazyFlagsDefault; 3567 NeedDefaultLazyXFlag(); 3568} 3569 3570LOCALPROC NeedDefaultLazyFlagsSubB(void) 3571{ 3572 ui5r src = V_regs.LazyFlagArgSrc; 3573 ui5r dst = V_regs.LazyFlagArgDst; 3574 ui5r result0 = dst - src; 3575 ui5r result1 = ui5r_FromUByte(dst) 3576 - ui5r_FromUByte(src); 3577 ui5r result = ui5r_FromSByte(result0); 3578 3579 ZFLG = Bool2Bit(result == 0); 3580 NFLG = Bool2Bit(ui5r_MSBisSet(result)); 3581 VFLG = (((result0 >> 1) ^ result0) >> 7) & 1; 3582 CFLG = (result1 >> 8) & 1; 3583 3584 XFLG = CFLG; 3585 V_regs.LazyFlagKind = kLazyFlagsDefault; 3586 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3587} 3588 3589LOCALPROC NeedDefaultLazyFlagsSubW(void) 3590{ 3591 ui5r result0 = V_regs.LazyFlagArgDst - V_regs.LazyFlagArgSrc; 3592 ui5r result = ui5r_FromSWord(result0); 3593 3594 ZFLG = Bool2Bit(result == 0); 3595 NFLG = Bool2Bit(ui5r_MSBisSet(result)); 3596 3597 VFLG = (((result0 >> 1) ^ result0) >> 15) & 1; 3598 { 3599 ui5r result1 = ui5r_FromUWord(V_regs.LazyFlagArgDst) 3600 - ui5r_FromUWord(V_regs.LazyFlagArgSrc); 3601 3602 CFLG = (result1 >> 16) & 1; 3603 } 3604 3605 XFLG = CFLG; 3606 V_regs.LazyFlagKind = kLazyFlagsDefault; 3607 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3608} 3609 3610LOCALPROC NeedDefaultLazyFlagsSubL(void) 3611{ 3612 ui5r src = V_regs.LazyFlagArgSrc; 3613 ui5r dst = V_regs.LazyFlagArgDst; 3614 ui5r result = ui5r_FromSLong(dst - src); 3615 3616 ZFLG = Bool2Bit(result == 0); 3617 3618 { 3619 flagtype flgn = Bool2Bit(ui5r_MSBisSet(result)); 3620 flagtype flgs = Bool2Bit(ui5r_MSBisSet(src)); 3621 flagtype flgo = Bool2Bit(ui5r_MSBisSet(dst)) ^ 1; 3622 flagtype flgsando = flgs & flgo; 3623 flagtype flgsoro = flgs | flgo; 3624 3625 NFLG = flgn; 3626 VFLG = ((flgn | flgsoro) ^ 1) | (flgn & flgsando); 3627 CFLG = flgsando | (flgn & flgsoro); 3628 } 3629 3630 XFLG = CFLG; 3631 V_regs.LazyFlagKind = kLazyFlagsDefault; 3632 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3633} 3634 3635LOCALPROC NeedDefaultLazyFlagsAddB(void) 3636{ 3637 ui5r src = V_regs.LazyFlagArgSrc; 3638 ui5r dst = V_regs.LazyFlagArgDst; 3639 ui5r result0 = dst + src; 3640 ui5r result1 = ui5r_FromUByte(dst) 3641 + ui5r_FromUByte(src); 3642 ui5r result = ui5r_FromSByte(result0); 3643 3644 ZFLG = Bool2Bit(result == 0); 3645 NFLG = Bool2Bit(ui5r_MSBisSet(result)); 3646 VFLG = (((result0 >> 1) ^ result0) >> 7) & 1; 3647 CFLG = (result1 >> 8); 3648 3649 XFLG = CFLG; 3650 V_regs.LazyFlagKind = kLazyFlagsDefault; 3651 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3652} 3653 3654LOCALPROC NeedDefaultLazyFlagsAddW(void) 3655{ 3656 ui5r src = V_regs.LazyFlagArgSrc; 3657 ui5r dst = V_regs.LazyFlagArgDst; 3658 ui5r result0 = dst + src; 3659 ui5r result1 = ui5r_FromUWord(dst) 3660 + ui5r_FromUWord(src); 3661 ui5r result = ui5r_FromSWord(result0); 3662 3663 ZFLG = Bool2Bit(result == 0); 3664 NFLG = Bool2Bit(ui5r_MSBisSet(result)); 3665 VFLG = (((result0 >> 1) ^ result0) >> 15) & 1; 3666 CFLG = (result1 >> 16); 3667 3668 XFLG = CFLG; 3669 V_regs.LazyFlagKind = kLazyFlagsDefault; 3670 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3671} 3672 3673#if 0 3674LOCALPROC NeedDefaultLazyFlagsAddCommon(ui5r result) 3675{ 3676 ZFLG = Bool2Bit(result == 0); 3677 { 3678 flagtype flgn = Bool2Bit(ui5r_MSBisSet(result)); 3679 flagtype flgs = Bool2Bit(ui5r_MSBisSet(V_regs.LazyFlagArgSrc)); 3680 flagtype flgo = Bool2Bit(ui5r_MSBisSet(V_regs.LazyFlagArgDst)); 3681 flagtype flgsando = flgs & flgo; 3682 flagtype flgsoro = flgs | flgo; 3683 3684 NFLG = flgn; 3685 flgn ^= 1; 3686 VFLG = ((flgn | flgsoro) ^ 1) | (flgn & flgsando); 3687 CFLG = flgsando | (flgn & flgsoro); 3688 } 3689 3690 XFLG = CFLG; 3691 V_regs.LazyFlagKind = kLazyFlagsDefault; 3692 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3693} 3694#endif 3695 3696LOCALPROC NeedDefaultLazyFlagsAddL(void) 3697{ 3698#if 1 3699 ui5r src = V_regs.LazyFlagArgSrc; 3700 ui5r dst = V_regs.LazyFlagArgDst; 3701 ui5r result = ui5r_FromSLong(dst + src); 3702 3703 ZFLG = Bool2Bit(result == 0); 3704 NFLG = Bool2Bit(ui5r_MSBisSet(result)); 3705 3706 { 3707 ui5r result1; 3708 ui5r result0; 3709 ui5r MidCarry = (ui5r_FromUWord(dst) 3710 + ui5r_FromUWord(src)) >> 16; 3711 3712 dst >>= 16; 3713 src >>= 16; 3714 3715 result1 = ui5r_FromUWord(dst) 3716 + ui5r_FromUWord(src) 3717 + MidCarry; 3718 CFLG = (result1 >> 16); 3719 result0 = ui5r_FromSWord(dst) 3720 + ui5r_FromSWord(src) 3721 + MidCarry; 3722 VFLG = (((result0 >> 1) ^ result0) >> 15) & 1; 3723 } 3724 3725 XFLG = CFLG; 3726 V_regs.LazyFlagKind = kLazyFlagsDefault; 3727 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3728#else 3729 ui5r result = ui5r_FromSLong(V_regs.LazyFlagArgDst 3730 + V_regs.LazyFlagArgSrc); 3731 3732 NeedDefaultLazyFlagsAddCommon(result); 3733#endif 3734} 3735 3736LOCALPROC NeedDefaultLazyFlagsNegCommon(ui5r dstvalue, ui5r result) 3737{ 3738 flagtype flgs = Bool2Bit(ui5r_MSBisSet(dstvalue)); 3739 flagtype flgn = Bool2Bit(ui5r_MSBisSet(result)); 3740 3741 ZFLG = Bool2Bit(result == 0); 3742 NFLG = flgn; 3743 VFLG = flgs & flgn; 3744 CFLG = flgs | flgn; 3745 3746 XFLG = CFLG; 3747 V_regs.LazyFlagKind = kLazyFlagsDefault; 3748 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3749} 3750 3751LOCALPROC NeedDefaultLazyFlagsNegB(void) 3752{ 3753 ui5r dstvalue = V_regs.LazyFlagArgDst; 3754 ui5r result = ui5r_FromSByte(0 - dstvalue); 3755 3756 NeedDefaultLazyFlagsNegCommon(dstvalue, result); 3757} 3758 3759LOCALPROC NeedDefaultLazyFlagsNegW(void) 3760{ 3761 ui5r dstvalue = V_regs.LazyFlagArgDst; 3762 ui5r result = ui5r_FromSWord(0 - dstvalue); 3763 3764 NeedDefaultLazyFlagsNegCommon(dstvalue, result); 3765} 3766 3767LOCALPROC NeedDefaultLazyFlagsNegL(void) 3768{ 3769 ui5r dstvalue = V_regs.LazyFlagArgDst; 3770 ui5r result = ui5r_FromSLong(0 - dstvalue); 3771 3772 NeedDefaultLazyFlagsNegCommon(dstvalue, result); 3773} 3774 3775LOCALPROC NeedDefaultLazyFlagsAsr(void) 3776{ 3777 ui5r cnt = V_regs.LazyFlagArgSrc; 3778 ui5r dst = V_regs.LazyFlagArgDst; 3779 3780 NFLG = Bool2Bit(ui5r_MSBisSet(dst)); 3781 VFLG = 0; 3782 3783 CFLG = ((dst >> (cnt - 1)) & 1); 3784 dst = Ui5rASR(dst, cnt); 3785 ZFLG = Bool2Bit(dst == 0); 3786 3787 XFLG = CFLG; 3788 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3789 V_regs.LazyFlagKind = kLazyFlagsDefault; 3790} 3791 3792LOCALPROC NeedDefaultLazyFlagsAslB(void) 3793{ 3794 ui5r cnt = V_regs.LazyFlagArgSrc; 3795 ui5r dst = V_regs.LazyFlagArgDst; 3796 ui5r dstvalue0 = dst; 3797 ui5r comparevalue; 3798 3799 dst = dst << (cnt - 1); 3800 dst = ui5r_FromSByte(dst); 3801 CFLG = Bool2Bit(ui5r_MSBisSet(dst)); 3802 dst = dst << 1; 3803 dst = ui5r_FromSByte(dst); 3804 comparevalue = Ui5rASR(dst, cnt); 3805 VFLG = Bool2Bit(comparevalue != dstvalue0); 3806 ZFLG = Bool2Bit(dst == 0); 3807 NFLG = Bool2Bit(ui5r_MSBisSet(dst)); 3808 3809 XFLG = CFLG; 3810 V_regs.LazyFlagKind = kLazyFlagsDefault; 3811 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3812} 3813 3814LOCALPROC NeedDefaultLazyFlagsAslW(void) 3815{ 3816 ui5r cnt = V_regs.LazyFlagArgSrc; 3817 ui5r dst = V_regs.LazyFlagArgDst; 3818 ui5r dstvalue0 = dst; 3819 ui5r comparevalue; 3820 3821 dst = dst << (cnt - 1); 3822 dst = ui5r_FromSWord(dst); 3823 CFLG = Bool2Bit(ui5r_MSBisSet(dst)); 3824 dst = dst << 1; 3825 dst = ui5r_FromSWord(dst); 3826 comparevalue = Ui5rASR(dst, cnt); 3827 VFLG = Bool2Bit(comparevalue != dstvalue0); 3828 ZFLG = Bool2Bit(dst == 0); 3829 NFLG = Bool2Bit(ui5r_MSBisSet(dst)); 3830 3831 XFLG = CFLG; 3832 V_regs.LazyFlagKind = kLazyFlagsDefault; 3833 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3834} 3835 3836LOCALPROC NeedDefaultLazyFlagsAslL(void) 3837{ 3838 ui5r cnt = V_regs.LazyFlagArgSrc; 3839 ui5r dst = V_regs.LazyFlagArgDst; 3840 ui5r dstvalue0 = dst; 3841 ui5r comparevalue; 3842 3843 dst = dst << (cnt - 1); 3844 dst = ui5r_FromSLong(dst); 3845 CFLG = Bool2Bit(ui5r_MSBisSet(dst)); 3846 dst = dst << 1; 3847 dst = ui5r_FromSLong(dst); 3848 comparevalue = Ui5rASR(dst, cnt); 3849 VFLG = Bool2Bit(comparevalue != dstvalue0); 3850 ZFLG = Bool2Bit(dst == 0); 3851 NFLG = Bool2Bit(ui5r_MSBisSet(dst)); 3852 3853 XFLG = CFLG; 3854 V_regs.LazyFlagKind = kLazyFlagsDefault; 3855 V_regs.LazyXFlagKind = kLazyFlagsDefault; 3856} 3857 3858#if UseLazyZ 3859FORWARDPROC NeedDefaultLazyFlagsZSet(void); 3860#endif 3861 3862LOCALVAR const NeedLazyFlagP 3863 NeedLazyFlagDispatch[kNumLazyFlagsKinds + 1] = 3864{ 3865 NeedDefaultLazyXFlag /* kLazyFlagsDefault */, 3866 0 /* kLazyFlagsTstB */, 3867 0 /* kLazyFlagsTstW */, 3868 NeedDefaultLazyFlagsTstL /* kLazyFlagsTstL */, 3869 NeedDefaultLazyFlagsCmpB /* kLazyFlagsCmpB */, 3870 NeedDefaultLazyFlagsCmpW /* kLazyFlagsCmpW */, 3871 NeedDefaultLazyFlagsCmpL /* kLazyFlagsCmpL */, 3872 NeedDefaultLazyFlagsSubB /* kLazyFlagsSubB */, 3873 NeedDefaultLazyFlagsSubW /* kLazyFlagsSubW */, 3874 NeedDefaultLazyFlagsSubL /* kLazyFlagsSubL */, 3875 NeedDefaultLazyFlagsAddB /* kLazyFlagsAddB */, 3876 NeedDefaultLazyFlagsAddW /* kLazyFlagsAddW */, 3877 NeedDefaultLazyFlagsAddL /* kLazyFlagsAddL */, 3878 NeedDefaultLazyFlagsNegB /* kLazyFlagsNegB */, 3879 NeedDefaultLazyFlagsNegW /* kLazyFlagsNegW */, 3880 NeedDefaultLazyFlagsNegL /* kLazyFlagsNegL */, 3881 NeedDefaultLazyFlagsAsr /* kLazyFlagsAsrB */, 3882 NeedDefaultLazyFlagsAsr /* kLazyFlagsAsrW */, 3883 NeedDefaultLazyFlagsAsr /* kLazyFlagsAsrL */, 3884 NeedDefaultLazyFlagsAslB /* kLazyFlagsAslB */, 3885 NeedDefaultLazyFlagsAslW /* kLazyFlagsAslW */, 3886 NeedDefaultLazyFlagsAslL /* kLazyFlagsAslL */, 3887#if UseLazyZ 3888 NeedDefaultLazyFlagsZSet /* kLazyFlagsZSet */, 3889#endif 3890 3891 0 3892}; 3893 3894LOCALPROC NeedDefaultLazyAllFlags0(void) 3895{ 3896 (NeedLazyFlagDispatch[V_regs.LazyFlagKind])(); 3897} 3898 3899#if ForceFlagsEval 3900LOCALPROC NeedDefaultLazyAllFlags(void) 3901{ 3902 if (kLazyFlagsDefault != V_regs.LazyFlagKind) { 3903 ReportAbnormalID(0x0104, 3904 "not kLazyFlagsDefault in NeedDefaultLazyAllFlags"); 3905#if dbglog_HAVE 3906 dbglog_writelnNum("LazyFlagKind", V_regs.LazyFlagKind); 3907#endif 3908 } 3909} 3910#else 3911#define NeedDefaultLazyAllFlags NeedDefaultLazyAllFlags0 3912#endif 3913 3914#if ForceFlagsEval 3915#define HaveSetUpFlags NeedDefaultLazyAllFlags0 3916#else 3917#define HaveSetUpFlags() 3918#endif 3919 3920#if UseLazyZ 3921LOCALPROC NeedDefaultLazyFlagsZSet(void) 3922{ 3923 flagtype SaveZFLG = ZFLG; 3924 3925 V_regs.LazyFlagKind = V_regs.LazyFlagZSavedKind; 3926 NeedDefaultLazyAllFlags(); 3927 3928 ZFLG = SaveZFLG; 3929} 3930#endif 3931 3932#if UseLazyCC 3933LOCALPROC my_reg_call cctrue_Dflt(cond_actP t_act, cond_actP f_act) 3934{ 3935 NeedDefaultLazyAllFlags(); 3936 cctrue(t_act, f_act); 3937} 3938#endif 3939 3940#if ! UseLazyCC 3941LOCALINLINEPROC cctrue(cond_actP t_act, cond_actP f_act) 3942{ 3943 NeedDefaultLazyAllFlags(); 3944 (cctrueDispatch[V_regs.CurDecOpY.v[0].ArgDat])(t_act, f_act); 3945} 3946#endif 3947 3948 3949#define LOCALIPROC LOCALPROC /* LOCALPROCUSEDONCE */ 3950 3951LOCALIPROC DoCodeCmpB(void) 3952{ 3953 ui5r dstvalue = DecodeGetSrcGetDstValue(); 3954 3955 V_regs.LazyFlagKind = kLazyFlagsCmpB; 3956 V_regs.LazyFlagArgSrc = V_regs.SrcVal; 3957 V_regs.LazyFlagArgDst = dstvalue; 3958 3959 HaveSetUpFlags(); 3960} 3961 3962LOCALIPROC DoCodeCmpW(void) 3963{ 3964 ui5r dstvalue = DecodeGetSrcGetDstValue(); 3965 3966 V_regs.LazyFlagKind = kLazyFlagsCmpW; 3967 V_regs.LazyFlagArgSrc = V_regs.SrcVal; 3968 V_regs.LazyFlagArgDst = dstvalue; 3969 3970 HaveSetUpFlags(); 3971} 3972 3973LOCALIPROC DoCodeCmpL(void) 3974{ 3975 ui5r dstvalue = DecodeGetSrcGetDstValue(); 3976 3977 V_regs.LazyFlagKind = kLazyFlagsCmpL; 3978 V_regs.LazyFlagArgSrc = V_regs.SrcVal; 3979 V_regs.LazyFlagArgDst = dstvalue; 3980 3981 HaveSetUpFlags(); 3982} 3983 3984LOCALIPROC DoCodeMoveL(void) 3985{ 3986 ui5r src = DecodeGetSrcValue(); 3987 3988 V_regs.LazyFlagKind = kLazyFlagsTstL; 3989 V_regs.LazyFlagArgDst = src; 3990 3991 HaveSetUpFlags(); 3992 3993 DecodeSetDstValue(src); 3994} 3995 3996LOCALIPROC DoCodeMoveW(void) 3997{ 3998 ui5r src = DecodeGetSrcValue(); 3999 4000 V_regs.LazyFlagKind = kLazyFlagsTstL; 4001 V_regs.LazyFlagArgDst = src; 4002 4003 HaveSetUpFlags(); 4004 4005 DecodeSetDstValue(src); 4006} 4007 4008LOCALIPROC DoCodeMoveB(void) 4009{ 4010 ui5r src = DecodeGetSrcValue(); 4011 4012 V_regs.LazyFlagKind = kLazyFlagsTstL; 4013 V_regs.LazyFlagArgDst = src; 4014 4015 HaveSetUpFlags(); 4016 4017 DecodeSetDstValue(src); 4018} 4019 4020LOCALIPROC DoCodeTst(void) 4021{ 4022 /* Tst 01001010ssmmmrrr */ 4023 4024 ui5r srcvalue = DecodeGetDstValue(); 4025 4026 V_regs.LazyFlagKind = kLazyFlagsTstL; 4027 V_regs.LazyFlagArgDst = srcvalue; 4028 4029 HaveSetUpFlags(); 4030} 4031 4032LOCALIPROC DoCodeBraB(void) 4033{ 4034 si5r offset = (si5r)(si3b)(ui3b)(V_regs.CurDecOpY.v[1].ArgDat); 4035 ui3p s = V_pc_p + offset; 4036 4037 V_pc_p = s; 4038 4039#if USE_PCLIMIT 4040 if (my_cond_rare(s >= V_pc_pHi) 4041 || my_cond_rare(s < V_regs.pc_pLo)) 4042 { 4043 Recalc_PC_Block(); 4044 } 4045#endif 4046} 4047 4048LOCALIPROC DoCodeBraW(void) 4049{ 4050 si5r offset = (si5r)(si4b)(ui4b)do_get_mem_word(V_pc_p); 4051 /* note that pc not incremented here */ 4052 ui3p s = V_pc_p + offset; 4053 4054 V_pc_p = s; 4055 4056#if USE_PCLIMIT 4057 if (my_cond_rare(s >= V_pc_pHi) 4058 || my_cond_rare(s < V_regs.pc_pLo)) 4059 { 4060 Recalc_PC_Block(); 4061 } 4062#endif 4063} 4064 4065#if WantCloserCyc 4066LOCALPROC DoCodeBccB_t(void) 4067{ 4068 V_MaxCyclesToGo -= (10 * kCycleScale + 2 * RdAvgXtraCyc); 4069 DoCodeBraB(); 4070} 4071#else 4072#define DoCodeBccB_t DoCodeBraB 4073#endif 4074 4075LOCALPROC DoCodeBccB_f(void) 4076{ 4077#if WantCloserCyc 4078 V_MaxCyclesToGo -= (8 * kCycleScale + RdAvgXtraCyc); 4079#endif 4080 /* do nothing */ 4081} 4082 4083LOCALIPROC DoCodeBccB(void) 4084{ 4085 /* Bcc 0110ccccnnnnnnnn */ 4086 cctrue(DoCodeBccB_t, DoCodeBccB_f); 4087} 4088 4089LOCALPROC SkipiWord(void) 4090{ 4091 V_pc_p += 2; 4092 4093#if USE_PCLIMIT 4094 if (my_cond_rare(V_pc_p >= V_pc_pHi)) { 4095 Recalc_PC_Block(); 4096 } 4097#endif 4098} 4099 4100#if WantCloserCyc 4101LOCALPROC DoCodeBccW_t(void) 4102{ 4103 V_MaxCyclesToGo -= (10 * kCycleScale + 2 * RdAvgXtraCyc); 4104 DoCodeBraW(); 4105} 4106#else 4107#define DoCodeBccW_t DoCodeBraW 4108#endif 4109 4110#if WantCloserCyc 4111LOCALPROC DoCodeBccW_f(void) 4112{ 4113 V_MaxCyclesToGo -= (12 * kCycleScale + 2 * RdAvgXtraCyc); 4114 SkipiWord(); 4115} 4116#else 4117#define DoCodeBccW_f SkipiWord 4118#endif 4119 4120LOCALIPROC DoCodeBccW(void) 4121{ 4122 /* Bcc 0110ccccnnnnnnnn */ 4123 cctrue(DoCodeBccW_t, DoCodeBccW_f); 4124} 4125 4126 4127LOCALIPROC DoCodeDBF(void) 4128{ 4129 /* DBcc 0101cccc11001ddd */ 4130 4131 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 4132 ui5r *dstp = &V_regs.regs[dstreg]; 4133 ui5r dstvalue = ui5r_FromSWord(*dstp); 4134 4135 --dstvalue; 4136#if LittleEndianUnaligned 4137 *(ui4b *)dstp = dstvalue; 4138#else 4139 *dstp = (*dstp & ~ 0xffff) | ((dstvalue) & 0xffff); 4140#endif 4141 4142 if ((si5b)dstvalue == -1) { 4143#if WantCloserCyc 4144 V_MaxCyclesToGo -= (14 * kCycleScale + 3 * RdAvgXtraCyc); 4145#endif 4146 SkipiWord(); 4147 } else { 4148#if WantCloserCyc 4149 V_MaxCyclesToGo -= (10 * kCycleScale + 2 * RdAvgXtraCyc); 4150#endif 4151 DoCodeBraW(); 4152 } 4153} 4154 4155#if WantCloserCyc 4156LOCALPROC DoCodeDBcc_t(void) 4157{ 4158 V_MaxCyclesToGo -= (12 * kCycleScale + 2 * RdAvgXtraCyc); 4159 SkipiWord(); 4160} 4161#else 4162#define DoCodeDBcc_t SkipiWord 4163#endif 4164 4165LOCALIPROC DoCodeDBcc(void) 4166{ 4167 /* DBcc 0101cccc11001ddd */ 4168 4169 cctrue(DoCodeDBcc_t, DoCodeDBF); 4170} 4171 4172LOCALIPROC DoCodeSwap(void) 4173{ 4174 /* Swap 0100100001000rrr */ 4175 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 4176 ui5r *dstp = &V_regs.regs[dstreg]; 4177 ui5r src = *dstp; 4178 ui5r dst = ui5r_FromSLong(((src >> 16) & 0xFFFF) 4179 | ((src & 0xFFFF) << 16)); 4180 4181 V_regs.LazyFlagKind = kLazyFlagsTstL; 4182 V_regs.LazyFlagArgDst = dst; 4183 4184 HaveSetUpFlags(); 4185 4186 *dstp = dst; 4187} 4188 4189LOCALIPROC DoCodeMoveA(void) /* MOVE */ 4190{ 4191 ui5r src = DecodeGetSrcValue(); 4192 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 4193 4194 m68k_areg(dstreg) = src; 4195} 4196 4197LOCALIPROC DoCodeMoveQ(void) 4198{ 4199 /* MoveQ 0111ddd0nnnnnnnn */ 4200 ui5r src = ui5r_FromSByte(V_regs.CurDecOpY.v[0].ArgDat); 4201 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 4202 4203 V_regs.LazyFlagKind = kLazyFlagsTstL; 4204 V_regs.LazyFlagArgDst = src; 4205 4206 HaveSetUpFlags(); 4207 4208 m68k_dreg(dstreg) = src; 4209} 4210 4211LOCALIPROC DoCodeAddB(void) 4212{ 4213 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4214 ui5r srcvalue = V_regs.SrcVal; 4215 ui5r result = ui5r_FromSByte(dstvalue + srcvalue); 4216 4217 V_regs.LazyFlagKind = kLazyFlagsAddB; 4218 V_regs.LazyFlagArgSrc = srcvalue; 4219 V_regs.LazyFlagArgDst = dstvalue; 4220 4221 V_regs.LazyXFlagKind = kLazyFlagsAddB; 4222 V_regs.LazyXFlagArgSrc = srcvalue; 4223 V_regs.LazyXFlagArgDst = dstvalue; 4224 4225 HaveSetUpFlags(); 4226 4227 ArgSetDstValue(result); 4228} 4229 4230LOCALIPROC DoCodeAddW(void) 4231{ 4232 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4233 ui5r srcvalue = V_regs.SrcVal; 4234 ui5r result = ui5r_FromSWord(dstvalue + srcvalue); 4235 4236 V_regs.LazyFlagKind = kLazyFlagsAddW; 4237 V_regs.LazyFlagArgSrc = srcvalue; 4238 V_regs.LazyFlagArgDst = dstvalue; 4239 4240 V_regs.LazyXFlagKind = kLazyFlagsAddW; 4241 V_regs.LazyXFlagArgSrc = srcvalue; 4242 V_regs.LazyXFlagArgDst = dstvalue; 4243 4244 HaveSetUpFlags(); 4245 4246 ArgSetDstValue(result); 4247} 4248 4249LOCALIPROC DoCodeAddL(void) 4250{ 4251 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4252 ui5r srcvalue = V_regs.SrcVal; 4253 ui5r result = ui5r_FromSLong(dstvalue + srcvalue); 4254 4255 V_regs.LazyFlagKind = kLazyFlagsAddL; 4256 V_regs.LazyFlagArgSrc = srcvalue; 4257 V_regs.LazyFlagArgDst = dstvalue; 4258 4259 V_regs.LazyXFlagKind = kLazyFlagsAddL; 4260 V_regs.LazyXFlagArgSrc = srcvalue; 4261 V_regs.LazyXFlagArgDst = dstvalue; 4262 4263 HaveSetUpFlags(); 4264 4265 ArgSetDstValue(result); 4266} 4267 4268LOCALIPROC DoCodeSubB(void) 4269{ 4270 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4271 ui5r srcvalue = V_regs.SrcVal; 4272 ui5r result = ui5r_FromSByte(dstvalue - srcvalue); 4273 4274 V_regs.LazyFlagKind = kLazyFlagsSubB; 4275 V_regs.LazyFlagArgSrc = srcvalue; 4276 V_regs.LazyFlagArgDst = dstvalue; 4277 4278 V_regs.LazyXFlagKind = kLazyFlagsSubB; 4279 V_regs.LazyXFlagArgSrc = srcvalue; 4280 V_regs.LazyXFlagArgDst = dstvalue; 4281 4282 HaveSetUpFlags(); 4283 4284 ArgSetDstValue(result); 4285} 4286 4287LOCALIPROC DoCodeSubW(void) 4288{ 4289 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4290 ui5r srcvalue = V_regs.SrcVal; 4291 ui5r result = ui5r_FromSWord(dstvalue - srcvalue); 4292 4293 V_regs.LazyFlagKind = kLazyFlagsSubW; 4294 V_regs.LazyFlagArgSrc = srcvalue; 4295 V_regs.LazyFlagArgDst = dstvalue; 4296 4297 V_regs.LazyXFlagKind = kLazyFlagsSubW; 4298 V_regs.LazyXFlagArgSrc = srcvalue; 4299 V_regs.LazyXFlagArgDst = dstvalue; 4300 4301 HaveSetUpFlags(); 4302 4303 ArgSetDstValue(result); 4304} 4305 4306LOCALIPROC DoCodeSubL(void) 4307{ 4308 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4309 ui5r srcvalue = V_regs.SrcVal; 4310 ui5r result = ui5r_FromSLong(dstvalue - srcvalue); 4311 4312 V_regs.LazyFlagKind = kLazyFlagsSubL; 4313 V_regs.LazyFlagArgSrc = srcvalue; 4314 V_regs.LazyFlagArgDst = dstvalue; 4315 4316 V_regs.LazyXFlagKind = kLazyFlagsSubL; 4317 V_regs.LazyXFlagArgSrc = srcvalue; 4318 V_regs.LazyXFlagArgDst = dstvalue; 4319 4320 HaveSetUpFlags(); 4321 4322 ArgSetDstValue(result); 4323} 4324 4325LOCALIPROC DoCodeLea(void) 4326{ 4327 /* Lea 0100aaa111mmmrrr */ 4328 ui5r DstAddr = DecodeDst(); 4329 ui5r dstreg = V_regs.CurDecOpY.v[0].ArgDat; 4330 4331 m68k_areg(dstreg) = DstAddr; 4332} 4333 4334LOCALIPROC DoCodePEA(void) 4335{ 4336 /* PEA 0100100001mmmrrr */ 4337 ui5r DstAddr = DecodeDst(); 4338 4339 m68k_areg(7) -= 4; 4340 put_long(m68k_areg(7), DstAddr); 4341} 4342 4343LOCALIPROC DoCodeBsrB(void) 4344{ 4345 m68k_areg(7) -= 4; 4346 put_long(m68k_areg(7), m68k_getpc()); 4347 DoCodeBraB(); 4348} 4349 4350LOCALIPROC DoCodeBsrW(void) 4351{ 4352 m68k_areg(7) -= 4; 4353 put_long(m68k_areg(7), m68k_getpc() + 2); 4354 DoCodeBraW(); 4355} 4356 4357#define m68k_logExceptions (dbglog_HAVE && 0) 4358 4359 4360#ifndef WantDumpAJump 4361#define WantDumpAJump 0 4362#endif 4363 4364#if WantDumpAJump 4365LOCALPROCUSEDONCE DumpAJump(CPTR toaddr) 4366{ 4367 CPTR fromaddr = m68k_getpc(); 4368 if ((toaddr > fromaddr) || (toaddr < V_regs.pc)) 4369 { 4370 dbglog_writeHex(fromaddr); 4371 dbglog_writeCStr(","); 4372 dbglog_writeHex(toaddr); 4373 dbglog_writeReturn(); 4374 } 4375} 4376#endif 4377 4378LOCALPROC my_reg_call m68k_setpc(CPTR newpc) 4379{ 4380#if WantDumpAJump 4381 DumpAJump(newpc); 4382#endif 4383 4384#if 0 4385 if (newpc == 0xBD50 /* 401AB4 */) { 4386 /* Debugger(); */ 4387 /* Exception(5); */ /* try and get macsbug */ 4388 } 4389#endif 4390 4391 V_pc_p = V_regs.pc_pLo + (newpc - V_regs.pc); 4392 if (my_cond_rare(V_pc_p >= V_pc_pHi) 4393 || my_cond_rare(V_pc_p < V_regs.pc_pLo)) 4394 { 4395 Recalc_PC_Block(); 4396 } 4397} 4398 4399LOCALIPROC DoCodeJsr(void) 4400{ 4401 /* Jsr 0100111010mmmrrr */ 4402 ui5r DstAddr = DecodeDst(); 4403 4404 m68k_areg(7) -= 4; 4405 put_long(m68k_areg(7), m68k_getpc()); 4406 m68k_setpc(DstAddr); 4407} 4408 4409LOCALIPROC DoCodeLinkA6(void) 4410{ 4411 CPTR stackp = m68k_areg(7); 4412 stackp -= 4; 4413 put_long(stackp, m68k_areg(6)); 4414 m68k_areg(6) = stackp; 4415 m68k_areg(7) = stackp + nextiSWord(); 4416} 4417 4418LOCALIPROC DoCodeUnlkA6(void) 4419{ 4420 ui5r src = m68k_areg(6); 4421 m68k_areg(6) = get_long(src); 4422 m68k_areg(7) = src + 4; 4423} 4424 4425LOCALIPROC DoCodeRts(void) 4426{ 4427 /* Rts 0100111001110101 */ 4428 ui5r NewPC = get_long(m68k_areg(7)); 4429 m68k_areg(7) += 4; 4430 m68k_setpc(NewPC); 4431} 4432 4433LOCALIPROC DoCodeJmp(void) 4434{ 4435 /* JMP 0100111011mmmrrr */ 4436 ui5r DstAddr = DecodeDst(); 4437 4438 m68k_setpc(DstAddr); 4439} 4440 4441LOCALIPROC DoCodeClr(void) 4442{ 4443 /* Clr 01000010ssmmmrrr */ 4444 4445 V_regs.LazyFlagKind = kLazyFlagsTstL; 4446 V_regs.LazyFlagArgDst = 0; 4447 4448 HaveSetUpFlags(); 4449 4450 DecodeSetDstValue(0); 4451} 4452 4453LOCALIPROC DoCodeAddA(void) 4454{ 4455 /* ADDA 1101dddm11mmmrrr */ 4456 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4457 4458 ArgSetDstValue(dstvalue + V_regs.SrcVal); 4459} 4460 4461LOCALIPROC DoCodeSubA(void) 4462{ 4463 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4464 4465 ArgSetDstValue(dstvalue - V_regs.SrcVal); 4466} 4467 4468LOCALIPROC DoCodeCmpA(void) 4469{ 4470 ui5r dstvalue = DecodeGetSrcGetDstValue(); 4471 4472 V_regs.LazyFlagKind = kLazyFlagsCmpL; 4473 V_regs.LazyFlagArgSrc = V_regs.SrcVal; 4474 V_regs.LazyFlagArgDst = dstvalue; 4475 4476 HaveSetUpFlags(); 4477} 4478 4479LOCALFUNC ui4rr m68k_getCR(void) 4480{ 4481 NeedDefaultLazyAllFlags(); 4482 4483 return (XFLG << 4) | (NFLG << 3) | (ZFLG << 2) 4484 | (VFLG << 1) | CFLG; 4485} 4486 4487LOCALPROC my_reg_call m68k_setCR(ui4rr newcr) 4488{ 4489 XFLG = (newcr >> 4) & 1; 4490 NFLG = (newcr >> 3) & 1; 4491 ZFLG = (newcr >> 2) & 1; 4492 VFLG = (newcr >> 1) & 1; 4493 CFLG = newcr & 1; 4494 4495 V_regs.LazyFlagKind = kLazyFlagsDefault; 4496 V_regs.LazyXFlagKind = kLazyFlagsDefault; 4497} 4498 4499 4500LOCALFUNC ui4rr m68k_getSR(void) 4501{ 4502 return m68k_getCR() 4503 | (V_regs.t1 << 15) 4504#if Use68020 4505 | (V_regs.t0 << 14) 4506#endif 4507 | (V_regs.s << 13) 4508#if Use68020 4509 | (V_regs.m << 12) 4510#endif 4511 | (V_regs.intmask << 8); 4512} 4513 4514LOCALPROC NeedToGetOut(void) 4515{ 4516 if (V_MaxCyclesToGo <= 0) { 4517 /* 4518 already have gotten out, and exception processing has 4519 caused another exception, such as because a bad 4520 stack pointer pointing to a memory mapped device. 4521 */ 4522 } else { 4523 V_regs.MoreCyclesToGo += V_MaxCyclesToGo; 4524 /* not counting the current instruction */ 4525 V_MaxCyclesToGo = 0; 4526 } 4527} 4528 4529LOCALPROC SetExternalInterruptPending(void) 4530{ 4531 V_regs.ExternalInterruptPending = trueblnr; 4532 NeedToGetOut(); 4533} 4534 4535LOCALPROC my_reg_call m68k_setSR(ui4rr newsr) 4536{ 4537 CPTR *pnewstk; 4538 CPTR *poldstk = (V_regs.s != 0) ? ( 4539#if Use68020 4540 (V_regs.m != 0) ? &V_regs.msp : 4541#endif 4542 &V_regs.isp) : &V_regs.usp; 4543 ui5r oldintmask = V_regs.intmask; 4544 4545 V_regs.t1 = (newsr >> 15) & 1; 4546#if Use68020 4547 V_regs.t0 = (newsr >> 14) & 1; 4548 if (V_regs.t0 != 0) { 4549 ReportAbnormalID(0x0105, "t0 flag set in m68k_setSR"); 4550 } 4551#endif 4552 V_regs.s = (newsr >> 13) & 1; 4553#if Use68020 4554 V_regs.m = (newsr >> 12) & 1; 4555 if (V_regs.m != 0) { 4556 ReportAbnormalID(0x0106, "m flag set in m68k_setSR"); 4557 } 4558#endif 4559 V_regs.intmask = (newsr >> 8) & 7; 4560 4561 pnewstk = (V_regs.s != 0) ? ( 4562#if Use68020 4563 (V_regs.m != 0) ? &V_regs.msp : 4564#endif 4565 &V_regs.isp) : &V_regs.usp; 4566 4567 if (poldstk != pnewstk) { 4568 *poldstk = m68k_areg(7); 4569 m68k_areg(7) = *pnewstk; 4570 } 4571 4572 if (V_regs.intmask != oldintmask) { 4573 SetExternalInterruptPending(); 4574 } 4575 4576 if (V_regs.t1 != 0) { 4577 NeedToGetOut(); 4578 } else { 4579 /* V_regs.TracePending = falseblnr; */ 4580 } 4581 4582 m68k_setCR(newsr); 4583} 4584 4585LOCALPROC my_reg_call ExceptionTo(CPTR newpc 4586#if Use68020 4587 , int nr 4588#endif 4589 ) 4590{ 4591 ui4rr saveSR = m68k_getSR(); 4592 4593 if (0 == V_regs.s) { 4594 V_regs.usp = m68k_areg(7); 4595 m68k_areg(7) = 4596#if Use68020 4597 (V_regs.m != 0) ? V_regs.msp : 4598#endif 4599 V_regs.isp; 4600 V_regs.s = 1; 4601 } 4602#if Use68020 4603 switch (nr) { 4604 case 5: /* Zero Divide */ 4605 case 6: /* CHK, CHK2 */ 4606 case 7: /* cpTRAPcc, TRAPCcc, TRAPv */ 4607 case 9: /* Trace */ 4608 m68k_areg(7) -= 4; 4609 put_long(m68k_areg(7), m68k_getpc()); 4610 m68k_areg(7) -= 2; 4611 put_word(m68k_areg(7), 0x2000 + nr * 4); 4612 break; 4613 default: 4614 m68k_areg(7) -= 2; 4615 put_word(m68k_areg(7), nr * 4); 4616 break; 4617 } 4618 /* if V_regs.m should make throw away stack frame */ 4619#endif 4620 m68k_areg(7) -= 4; 4621 put_long(m68k_areg(7), m68k_getpc()); 4622 m68k_areg(7) -= 2; 4623 put_word(m68k_areg(7), saveSR); 4624 m68k_setpc(newpc); 4625 V_regs.t1 = 0; 4626#if Use68020 4627 V_regs.t0 = 0; 4628 V_regs.m = 0; 4629#endif 4630 V_regs.TracePending = falseblnr; 4631} 4632 4633LOCALPROC my_reg_call Exception(int nr) 4634{ 4635 ExceptionTo(get_long(4 * nr 4636#if Use68020 4637 + V_regs.vbr 4638#endif 4639 ) 4640#if Use68020 4641 , nr 4642#endif 4643 ); 4644} 4645 4646 4647LOCALIPROC DoCodeA(void) 4648{ 4649 BackupPC(); 4650 Exception(0xA); 4651} 4652 4653LOCALFUNC ui4rr nextiword_nm(void) 4654/* NOT sign extended */ 4655{ 4656 return nextiword(); 4657} 4658 4659LOCALIPROC DoCodeMOVEMRmML(void) 4660{ 4661 /* MOVEM reg to mem 01001000111100rrr */ 4662 si4b z; 4663 ui5r regmask = nextiword_nm(); 4664 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 4665 ui5r *dstp = &V_regs.regs[dstreg]; 4666 ui5r p = *dstp; 4667 4668#if Use68020 4669 { 4670 int n = 0; 4671 4672 for (z = 0; z < 16; ++z) { 4673 if ((regmask & (1 << z)) != 0) { 4674 n++; 4675 } 4676 } 4677 *dstp = p - n * 4; 4678 } 4679#endif 4680 for (z = 16; --z >= 0; ) { 4681 if ((regmask & (1 << (15 - z))) != 0) { 4682#if WantCloserCyc 4683 V_MaxCyclesToGo -= (8 * kCycleScale + 2 * WrAvgXtraCyc); 4684#endif 4685 p -= 4; 4686 put_long(p, V_regs.regs[z]); 4687 } 4688 } 4689#if ! Use68020 4690 *dstp = p; 4691#endif 4692} 4693 4694LOCALIPROC DoCodeMOVEMApRL(void) 4695{ 4696 /* MOVEM mem to reg 01001100111011rrr */ 4697 si4b z; 4698 ui5r regmask = nextiword_nm(); 4699 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 4700 ui5r *dstp = &V_regs.regs[dstreg]; 4701 ui5r p = *dstp; 4702 4703 for (z = 0; z < 16; ++z) { 4704 if ((regmask & (1 << z)) != 0) { 4705#if WantCloserCyc 4706 V_MaxCyclesToGo -= (8 * kCycleScale + 2 * RdAvgXtraCyc); 4707#endif 4708 V_regs.regs[z] = get_long(p); 4709 p += 4; 4710 } 4711 } 4712 *dstp = p; 4713} 4714 4715LOCALPROC my_reg_call SetCCRforAddX(ui5r dstvalue, ui5r srcvalue, 4716 ui5r result) 4717{ 4718 ZFLG &= Bool2Bit(result == 0); 4719 4720 { 4721 flagtype flgs = Bool2Bit(ui5r_MSBisSet(srcvalue)); 4722 flagtype flgo = Bool2Bit(ui5r_MSBisSet(dstvalue)); 4723 flagtype flgsando = flgs & flgo; 4724 flagtype flgsoro = flgs | flgo; 4725 flagtype flgn = Bool2Bit(ui5r_MSBisSet(result)); 4726 4727 NFLG = flgn; 4728 flgn ^= 1; 4729 VFLG = ((flgn | flgsoro) ^ 1) | (flgn & flgsando); 4730 XFLG = CFLG = flgsando | (flgn & flgsoro); 4731 } 4732 4733 ArgSetDstValue(result); 4734} 4735 4736LOCALIPROC DoCodeAddXB(void) 4737{ 4738 NeedDefaultLazyAllFlags(); 4739 4740 { 4741 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4742 ui5r srcvalue = V_regs.SrcVal; 4743 ui5r result = ui5r_FromSByte(XFLG + dstvalue + srcvalue); 4744 4745 SetCCRforAddX(dstvalue, srcvalue, result); 4746 } 4747} 4748 4749LOCALIPROC DoCodeAddXW(void) 4750{ 4751 if ((kLazyFlagsDefault != V_regs.LazyFlagKind) 4752 || (kLazyFlagsDefault != V_regs.LazyXFlagKind)) 4753 { 4754 NeedDefaultLazyAllFlags(); 4755 } 4756 4757 { 4758 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4759 ui5r srcvalue = V_regs.SrcVal; 4760 ui5r result = ui5r_FromSWord(XFLG + dstvalue + srcvalue); 4761 4762 SetCCRforAddX(dstvalue, srcvalue, result); 4763 } 4764} 4765 4766LOCALIPROC DoCodeAddXL(void) 4767{ 4768 if (kLazyFlagsAddL == V_regs.LazyFlagKind) { 4769 ui5r src = V_regs.LazyFlagArgSrc; 4770 ui5r dst = V_regs.LazyFlagArgDst; 4771 ui5r result = ui5r_FromULong(dst + src); 4772 4773 ZFLG = Bool2Bit(result == 0); 4774 XFLG = Bool2Bit(result < src); 4775 4776 V_regs.LazyFlagKind = kLazyFlagsDefault; 4777 V_regs.LazyXFlagKind = kLazyFlagsDefault; 4778 } else 4779 if ((kLazyFlagsDefault == V_regs.LazyFlagKind) 4780 && (kLazyFlagsDefault == V_regs.LazyXFlagKind)) 4781 { 4782 /* ok */ 4783 } else 4784 { 4785 NeedDefaultLazyAllFlags(); 4786 } 4787 4788 { 4789 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4790 ui5r srcvalue = V_regs.SrcVal; 4791 ui5r result = ui5r_FromSLong(XFLG + dstvalue + srcvalue); 4792 4793 SetCCRforAddX(dstvalue, srcvalue, result); 4794 } 4795} 4796 4797LOCALPROC my_reg_call SetCCRforSubX(ui5r dstvalue, ui5r srcvalue, 4798 ui5r result) 4799{ 4800 ZFLG &= Bool2Bit(result == 0); 4801 4802 { 4803 flagtype flgs = Bool2Bit(ui5r_MSBisSet(srcvalue)); 4804 flagtype flgo = Bool2Bit(ui5r_MSBisSet(dstvalue)) ^ 1; 4805 flagtype flgsando = flgs & flgo; 4806 flagtype flgsoro = flgs | flgo; 4807 flagtype flgn = Bool2Bit(ui5r_MSBisSet(result)); 4808 4809 NFLG = flgn; 4810 VFLG = ((flgn | flgsoro) ^ 1) | (flgn & flgsando); 4811 XFLG = CFLG = flgsando | (flgn & flgsoro); 4812 } 4813 4814 ArgSetDstValue(result); 4815} 4816 4817LOCALIPROC DoCodeSubXB(void) 4818{ 4819 NeedDefaultLazyAllFlags(); 4820 4821 { 4822 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4823 ui5r srcvalue = V_regs.SrcVal; 4824 ui5r result = ui5r_FromSByte(dstvalue - srcvalue - XFLG); 4825 4826 SetCCRforSubX(dstvalue, srcvalue, result); 4827 } 4828} 4829 4830LOCALIPROC DoCodeSubXW(void) 4831{ 4832 if ((kLazyFlagsDefault != V_regs.LazyFlagKind) 4833 || (kLazyFlagsDefault != V_regs.LazyXFlagKind)) 4834 { 4835 NeedDefaultLazyAllFlags(); 4836 } 4837 4838 { 4839 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4840 ui5r srcvalue = V_regs.SrcVal; 4841 ui5r result = ui5r_FromSWord(dstvalue - srcvalue - XFLG); 4842 4843 SetCCRforSubX(dstvalue, srcvalue, result); 4844 } 4845} 4846 4847LOCALIPROC DoCodeSubXL(void) 4848{ 4849 if (kLazyFlagsSubL == V_regs.LazyFlagKind) { 4850 ui5r src = V_regs.LazyFlagArgSrc; 4851 ui5r dst = V_regs.LazyFlagArgDst; 4852 ui5r result = ui5r_FromSLong(dst - src); 4853 4854 ZFLG = Bool2Bit(result == 0); 4855 XFLG = Bool2Bit(((ui5b)dst) < ((ui5b)src)); 4856 4857 V_regs.LazyFlagKind = kLazyFlagsDefault; 4858 V_regs.LazyXFlagKind = kLazyFlagsDefault; 4859 } else 4860 if ((kLazyFlagsDefault == V_regs.LazyFlagKind) 4861 && (kLazyFlagsDefault == V_regs.LazyXFlagKind)) 4862 { 4863 /* ok */ 4864 } else 4865 { 4866 NeedDefaultLazyAllFlags(); 4867 } 4868 4869 { 4870 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4871 ui5r srcvalue = V_regs.SrcVal; 4872 ui5r result = ui5r_FromSLong(dstvalue - srcvalue - XFLG); 4873 4874 SetCCRforSubX(dstvalue, srcvalue, result); 4875 } 4876} 4877 4878LOCALPROC my_reg_call DoCodeNullShift(ui5r dstvalue) 4879{ 4880 V_regs.LazyFlagKind = kLazyFlagsTstL; 4881 V_regs.LazyFlagArgDst = dstvalue; 4882 4883 HaveSetUpFlags(); 4884 4885 ArgSetDstValue(dstvalue); 4886} 4887 4888LOCALPROC DoCodeOverAsl(ui5r dstvalue) 4889{ 4890 XFLG = CFLG = 0; 4891 VFLG = Bool2Bit(0 != dstvalue); 4892 ZFLG = 1; 4893 NFLG = 0; 4894 4895 V_regs.LazyXFlagKind = kLazyFlagsDefault; 4896 V_regs.LazyFlagKind = kLazyFlagsDefault; 4897 4898 ArgSetDstValue(0); 4899} 4900 4901LOCALPROC my_reg_call DoCodeMaxAsr(ui5r dstvalue) 4902{ 4903 XFLG = CFLG = dstvalue & 1; 4904 VFLG = Bool2Bit(0 != dstvalue); 4905 ZFLG = 1; 4906 NFLG = 0; 4907 4908 V_regs.LazyXFlagKind = kLazyFlagsDefault; 4909 V_regs.LazyFlagKind = kLazyFlagsDefault; 4910 4911 ArgSetDstValue(0); 4912} 4913 4914LOCALIPROC DoCodeAslB(void) 4915{ 4916 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4917 ui5r cnt = V_regs.SrcVal & 63; 4918 4919 if (0 == cnt) { 4920 DoCodeNullShift(dstvalue); 4921 } else { 4922#if WantCloserCyc 4923 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 4924#endif 4925 4926 if (cnt >= 8) { 4927 if (cnt == 8) { 4928 DoCodeMaxAsr(dstvalue); 4929 } else { 4930 DoCodeOverAsl(dstvalue); 4931 } 4932 } else { 4933 ui5r result = ui5r_FromSByte(dstvalue << cnt); 4934 4935 V_regs.LazyFlagKind = kLazyFlagsAslB; 4936 V_regs.LazyFlagArgSrc = cnt; 4937 V_regs.LazyFlagArgDst = dstvalue; 4938 4939 V_regs.LazyXFlagKind = kLazyFlagsAslB; 4940 V_regs.LazyXFlagArgSrc = cnt; 4941 V_regs.LazyXFlagArgDst = dstvalue; 4942 4943 HaveSetUpFlags(); 4944 4945 ArgSetDstValue(result); 4946 } 4947 } 4948} 4949 4950LOCALIPROC DoCodeAslW(void) 4951{ 4952 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4953 ui5r cnt = V_regs.SrcVal & 63; 4954 4955 if (0 == cnt) { 4956 DoCodeNullShift(dstvalue); 4957 } else { 4958#if WantCloserCyc 4959 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 4960#endif 4961 4962 if (cnt >= 16) { 4963 if (cnt == 16) { 4964 DoCodeMaxAsr(dstvalue); 4965 } else { 4966 DoCodeOverAsl(dstvalue); 4967 } 4968 } else { 4969 ui5r result = ui5r_FromSWord(dstvalue << cnt); 4970 4971 V_regs.LazyFlagKind = kLazyFlagsAslW; 4972 V_regs.LazyFlagArgSrc = cnt; 4973 V_regs.LazyFlagArgDst = dstvalue; 4974 4975 V_regs.LazyXFlagKind = kLazyFlagsAslW; 4976 V_regs.LazyXFlagArgSrc = cnt; 4977 V_regs.LazyXFlagArgDst = dstvalue; 4978 4979 HaveSetUpFlags(); 4980 4981 ArgSetDstValue(result); 4982 } 4983 } 4984} 4985 4986LOCALIPROC DoCodeAslL(void) 4987{ 4988 ui5r dstvalue = DecodeGetSrcSetDstValue(); 4989 ui5r cnt = V_regs.SrcVal & 63; 4990 4991 if (0 == cnt) { 4992 DoCodeNullShift(dstvalue); 4993 } else { 4994#if WantCloserCyc 4995 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 4996#endif 4997 4998 if (cnt >= 32) { 4999 if (cnt == 32) { 5000 DoCodeMaxAsr(dstvalue); 5001 } else { 5002 DoCodeOverAsl(dstvalue); 5003 } 5004 } else { 5005 ui5r result = ui5r_FromSLong(dstvalue << cnt); 5006 5007 V_regs.LazyFlagKind = kLazyFlagsAslL; 5008 V_regs.LazyFlagArgSrc = cnt; 5009 V_regs.LazyFlagArgDst = dstvalue; 5010 5011 V_regs.LazyXFlagKind = kLazyFlagsAslL; 5012 V_regs.LazyXFlagArgSrc = cnt; 5013 V_regs.LazyXFlagArgDst = dstvalue; 5014 5015 HaveSetUpFlags(); 5016 5017 ArgSetDstValue(result); 5018 } 5019 } 5020} 5021 5022LOCALPROC DoCodeOverShift(void) 5023{ 5024 XFLG = CFLG = 0; 5025 ZFLG = 1; 5026 NFLG = 0; 5027 VFLG = 0; 5028 5029 V_regs.LazyXFlagKind = kLazyFlagsDefault; 5030 V_regs.LazyFlagKind = kLazyFlagsDefault; 5031 5032 ArgSetDstValue(0); 5033} 5034 5035LOCALPROC DoCodeOverShiftN(void) 5036{ 5037 NFLG = 1; 5038 VFLG = 0; 5039 CFLG = 1; 5040 XFLG = CFLG; 5041 ZFLG = 0; 5042 5043 V_regs.LazyXFlagKind = kLazyFlagsDefault; 5044 V_regs.LazyFlagKind = kLazyFlagsDefault; 5045 5046 ArgSetDstValue(~ 0); 5047} 5048 5049LOCALPROC DoCodeOverAShift(ui5r dstvalue) 5050{ 5051 if (ui5r_MSBisSet(dstvalue)) { 5052 DoCodeOverShiftN(); 5053 } else { 5054 DoCodeOverShift(); 5055 } 5056} 5057 5058LOCALIPROC DoCodeAsrB(void) 5059{ 5060 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5061 ui5r cnt = V_regs.SrcVal & 63; 5062 5063 if (0 == cnt) { 5064 DoCodeNullShift(dstvalue); 5065 } else { 5066#if WantCloserCyc 5067 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5068#endif 5069 5070 if (cnt >= 8) { 5071 DoCodeOverAShift(dstvalue); 5072 } else { 5073 ui5r result = Ui5rASR(dstvalue, cnt); 5074 5075 V_regs.LazyFlagKind = kLazyFlagsAsrB; 5076 V_regs.LazyFlagArgSrc = cnt; 5077 V_regs.LazyFlagArgDst = dstvalue; 5078 5079 V_regs.LazyXFlagKind = kLazyFlagsAsrB; 5080 V_regs.LazyXFlagArgSrc = cnt; 5081 V_regs.LazyXFlagArgDst = dstvalue; 5082 5083 HaveSetUpFlags(); 5084 5085 ArgSetDstValue(result); 5086 } 5087 } 5088} 5089 5090LOCALIPROC DoCodeAsrW(void) 5091{ 5092 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5093 ui5r cnt = V_regs.SrcVal & 63; 5094 5095 if (0 == cnt) { 5096 DoCodeNullShift(dstvalue); 5097 } else { 5098#if WantCloserCyc 5099 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5100#endif 5101 5102 if (cnt >= 16) { 5103 DoCodeOverAShift(dstvalue); 5104 } else { 5105 ui5r result = Ui5rASR(dstvalue, cnt); 5106 5107 V_regs.LazyFlagKind = kLazyFlagsAsrW; 5108 V_regs.LazyFlagArgSrc = cnt; 5109 V_regs.LazyFlagArgDst = dstvalue; 5110 5111 V_regs.LazyXFlagKind = kLazyFlagsAsrW; 5112 V_regs.LazyXFlagArgSrc = cnt; 5113 V_regs.LazyXFlagArgDst = dstvalue; 5114 5115 HaveSetUpFlags(); 5116 5117 ArgSetDstValue(result); 5118 } 5119 } 5120} 5121 5122LOCALIPROC DoCodeAsrL(void) 5123{ 5124 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5125 ui5r cnt = V_regs.SrcVal & 63; 5126 5127 if (0 == cnt) { 5128 DoCodeNullShift(dstvalue); 5129 } else { 5130#if WantCloserCyc 5131 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5132#endif 5133 5134 if (cnt >= 32) { 5135 DoCodeOverAShift(dstvalue); 5136 } else { 5137 ui5r result = Ui5rASR(dstvalue, cnt); 5138 5139 V_regs.LazyFlagKind = kLazyFlagsAsrL; 5140 V_regs.LazyFlagArgSrc = cnt; 5141 V_regs.LazyFlagArgDst = dstvalue; 5142 5143 V_regs.LazyXFlagKind = kLazyFlagsAsrL; 5144 V_regs.LazyXFlagArgSrc = cnt; 5145 V_regs.LazyXFlagArgDst = dstvalue; 5146 5147 HaveSetUpFlags(); 5148 5149 ArgSetDstValue(result); 5150 } 5151 } 5152} 5153 5154LOCALPROC my_reg_call DoCodeMaxLslShift(ui5r dstvalue) 5155{ 5156 XFLG = CFLG = dstvalue & 1; 5157 ZFLG = 1; 5158 NFLG = 0; 5159 VFLG = 0; 5160 5161 V_regs.LazyXFlagKind = kLazyFlagsDefault; 5162 V_regs.LazyFlagKind = kLazyFlagsDefault; 5163 5164 ArgSetDstValue(0); 5165} 5166 5167LOCALIPROC DoCodeLslB(void) 5168{ 5169 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5170 ui5r cnt = V_regs.SrcVal & 63; 5171 5172 if (0 == cnt) { 5173 DoCodeNullShift(dstvalue); 5174 } else { 5175#if WantCloserCyc 5176 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5177#endif 5178 5179 if (cnt >= 8) { 5180 if (cnt == 8) { 5181 DoCodeMaxLslShift(dstvalue); 5182 } else { 5183 DoCodeOverShift(); 5184 } 5185 } else { 5186 CFLG = (dstvalue >> (8 - cnt)) & 1; 5187 dstvalue = dstvalue << cnt; 5188 dstvalue = ui5r_FromSByte(dstvalue); 5189 5190 ZFLG = Bool2Bit(dstvalue == 0); 5191 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5192 VFLG = 0; 5193 XFLG = CFLG; 5194 V_regs.LazyXFlagKind = kLazyFlagsDefault; 5195 V_regs.LazyFlagKind = kLazyFlagsDefault; 5196 5197 ArgSetDstValue(dstvalue); 5198 } 5199 } 5200} 5201 5202LOCALIPROC DoCodeLslW(void) 5203{ 5204 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5205 ui5r cnt = V_regs.SrcVal & 63; 5206 5207 if (0 == cnt) { 5208 DoCodeNullShift(dstvalue); 5209 } else { 5210#if WantCloserCyc 5211 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5212#endif 5213 5214 if (cnt >= 16) { 5215 if (cnt == 16) { 5216 DoCodeMaxLslShift(dstvalue); 5217 } else { 5218 DoCodeOverShift(); 5219 } 5220 } else { 5221 CFLG = (dstvalue >> (16 - cnt)) & 1; 5222 dstvalue = dstvalue << cnt; 5223 dstvalue = ui5r_FromSWord(dstvalue); 5224 5225 ZFLG = Bool2Bit(dstvalue == 0); 5226 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5227 VFLG = 0; 5228 XFLG = CFLG; 5229 V_regs.LazyXFlagKind = kLazyFlagsDefault; 5230 V_regs.LazyFlagKind = kLazyFlagsDefault; 5231 5232 ArgSetDstValue(dstvalue); 5233 } 5234 } 5235} 5236 5237LOCALIPROC DoCodeLslL(void) 5238{ 5239 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5240 ui5r cnt = V_regs.SrcVal & 63; 5241 5242 if (0 == cnt) { 5243 DoCodeNullShift(dstvalue); 5244 } else { 5245#if WantCloserCyc 5246 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5247#endif 5248 5249 if (cnt >= 32) { 5250 if (cnt == 32) { 5251 DoCodeMaxLslShift(dstvalue); 5252 } else { 5253 DoCodeOverShift(); 5254 } 5255 } else { 5256 CFLG = (dstvalue >> (32 - cnt)) & 1; 5257 dstvalue = dstvalue << cnt; 5258 dstvalue = ui5r_FromSLong(dstvalue); 5259 5260 ZFLG = Bool2Bit(dstvalue == 0); 5261 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5262 VFLG = 0; 5263 XFLG = CFLG; 5264 V_regs.LazyXFlagKind = kLazyFlagsDefault; 5265 V_regs.LazyFlagKind = kLazyFlagsDefault; 5266 5267 ArgSetDstValue(dstvalue); 5268 } 5269 } 5270} 5271 5272LOCALIPROC DoCodeLsrB(void) 5273{ 5274 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5275 ui5r cnt = V_regs.SrcVal & 63; 5276 5277#if WantCloserCyc 5278 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5279#endif 5280 5281 if (0 == cnt) { 5282 DoCodeNullShift(dstvalue); 5283 } else if (cnt > 32) { 5284 DoCodeOverShift(); 5285 } else { 5286 dstvalue = ui5r_FromUByte(dstvalue); 5287 dstvalue = dstvalue >> (cnt - 1); 5288 CFLG = XFLG = (dstvalue & 1); 5289 dstvalue = dstvalue >> 1; 5290 ZFLG = Bool2Bit(dstvalue == 0); 5291 NFLG = 0 /* Bool2Bit(ui5r_MSBisSet(dstvalue)) */; 5292 /* if cnt != 0, always false */ 5293 VFLG = 0; 5294 V_regs.LazyXFlagKind = kLazyFlagsDefault; 5295 V_regs.LazyFlagKind = kLazyFlagsDefault; 5296 5297 ArgSetDstValue(dstvalue); 5298 } 5299} 5300 5301LOCALIPROC DoCodeLsrW(void) 5302{ 5303 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5304 ui5r cnt = V_regs.SrcVal & 63; 5305 5306#if WantCloserCyc 5307 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5308#endif 5309 5310 if (0 == cnt) { 5311 DoCodeNullShift(dstvalue); 5312 } else if (cnt > 32) { 5313 DoCodeOverShift(); 5314 } else { 5315 dstvalue = ui5r_FromUWord(dstvalue); 5316 dstvalue = dstvalue >> (cnt - 1); 5317 CFLG = XFLG = (dstvalue & 1); 5318 dstvalue = dstvalue >> 1; 5319 ZFLG = Bool2Bit(dstvalue == 0); 5320 NFLG = 0 /* Bool2Bit(ui5r_MSBisSet(dstvalue)) */; 5321 /* if cnt != 0, always false */ 5322 VFLG = 0; 5323 V_regs.LazyXFlagKind = kLazyFlagsDefault; 5324 V_regs.LazyFlagKind = kLazyFlagsDefault; 5325 5326 ArgSetDstValue(dstvalue); 5327 } 5328} 5329 5330LOCALIPROC DoCodeLsrL(void) 5331{ 5332 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5333 ui5r cnt = V_regs.SrcVal & 63; 5334 5335#if WantCloserCyc 5336 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5337#endif 5338 5339 if (0 == cnt) { 5340 DoCodeNullShift(dstvalue); 5341 } else if (cnt > 32) { 5342 DoCodeOverShift(); 5343 } else { 5344 dstvalue = ui5r_FromULong(dstvalue); 5345 dstvalue = dstvalue >> (cnt - 1); 5346 CFLG = XFLG = (dstvalue & 1); 5347 dstvalue = dstvalue >> 1; 5348 ZFLG = Bool2Bit(dstvalue == 0); 5349 NFLG = 0 /* Bool2Bit(ui5r_MSBisSet(dstvalue)) */; 5350 /* if cnt != 0, always false */ 5351 VFLG = 0; 5352 V_regs.LazyXFlagKind = kLazyFlagsDefault; 5353 V_regs.LazyFlagKind = kLazyFlagsDefault; 5354 5355 ArgSetDstValue(dstvalue); 5356 } 5357} 5358 5359LOCALFUNC ui5r DecodeGetSrcSetDstValueDfltFlags_nm(void) 5360{ 5361 NeedDefaultLazyAllFlags(); 5362 5363 return DecodeGetSrcSetDstValue(); 5364} 5365 5366LOCALPROC my_reg_call DoCodeNullXShift(ui5r dstvalue) 5367{ 5368 CFLG = XFLG; 5369 5370 ZFLG = Bool2Bit(dstvalue == 0); 5371 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5372 VFLG = 0; 5373 5374 ArgSetDstValue(dstvalue); 5375} 5376 5377LOCALIPROC DoCodeRxlB(void) 5378{ 5379 ui5r dstvalue = DecodeGetSrcSetDstValueDfltFlags_nm(); 5380 ui5r cnt = V_regs.SrcVal & 63; 5381 5382 if (0 == cnt) { 5383 DoCodeNullXShift(dstvalue); 5384 } else { 5385#if WantCloserCyc 5386 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5387#endif 5388 5389 for (; cnt; --cnt) { 5390 CFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5391 dstvalue = (dstvalue << 1) | XFLG; 5392 dstvalue = ui5r_FromSByte(dstvalue); 5393 XFLG = CFLG; 5394 } 5395 5396 ZFLG = Bool2Bit(dstvalue == 0); 5397 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5398 VFLG = 0; 5399 5400 ArgSetDstValue(dstvalue); 5401 } 5402} 5403 5404LOCALIPROC DoCodeRxlW(void) 5405{ 5406 ui5r dstvalue = DecodeGetSrcSetDstValueDfltFlags_nm(); 5407 ui5r cnt = V_regs.SrcVal & 63; 5408 5409 if (0 == cnt) { 5410 DoCodeNullXShift(dstvalue); 5411 } else { 5412#if WantCloserCyc 5413 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5414#endif 5415 5416 for (; cnt; --cnt) { 5417 CFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5418 dstvalue = (dstvalue << 1) | XFLG; 5419 dstvalue = ui5r_FromSWord(dstvalue); 5420 XFLG = CFLG; 5421 } 5422 5423 ZFLG = Bool2Bit(dstvalue == 0); 5424 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5425 VFLG = 0; 5426 5427 ArgSetDstValue(dstvalue); 5428 } 5429} 5430 5431LOCALIPROC DoCodeRxlL(void) 5432{ 5433 ui5r dstvalue = DecodeGetSrcSetDstValueDfltFlags_nm(); 5434 ui5r cnt = V_regs.SrcVal & 63; 5435 5436 if (0 == cnt) { 5437 DoCodeNullXShift(dstvalue); 5438 } else { 5439#if WantCloserCyc 5440 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5441#endif 5442 5443 for (; cnt; --cnt) { 5444 CFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5445 dstvalue = (dstvalue << 1) | XFLG; 5446 dstvalue = ui5r_FromSLong(dstvalue); 5447 XFLG = CFLG; 5448 } 5449 5450 ZFLG = Bool2Bit(dstvalue == 0); 5451 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5452 VFLG = 0; 5453 5454 ArgSetDstValue(dstvalue); 5455 } 5456} 5457 5458LOCALIPROC DoCodeRxrB(void) 5459{ 5460 ui5r dstvalue = DecodeGetSrcSetDstValueDfltFlags_nm(); 5461 ui5r cnt = V_regs.SrcVal & 63; 5462 5463 if (0 == cnt) { 5464 DoCodeNullXShift(dstvalue); 5465 } else { 5466#if WantCloserCyc 5467 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5468#endif 5469 5470 dstvalue = ui5r_FromUByte(dstvalue); 5471 for (; cnt; --cnt) { 5472 CFLG = dstvalue & 1; 5473 dstvalue = (dstvalue >> 1) | (((ui5r)XFLG) << 7); 5474 XFLG = CFLG; 5475 } 5476 dstvalue = ui5r_FromSByte(dstvalue); 5477 5478 ZFLG = Bool2Bit(dstvalue == 0); 5479 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5480 VFLG = 0; 5481 5482 ArgSetDstValue(dstvalue); 5483 } 5484} 5485 5486LOCALIPROC DoCodeRxrW(void) 5487{ 5488 ui5r dstvalue = DecodeGetSrcSetDstValueDfltFlags_nm(); 5489 ui5r cnt = V_regs.SrcVal & 63; 5490 5491 if (0 == cnt) { 5492 DoCodeNullXShift(dstvalue); 5493 } else { 5494#if WantCloserCyc 5495 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5496#endif 5497 5498 dstvalue = ui5r_FromUWord(dstvalue); 5499 for (; cnt; --cnt) { 5500 CFLG = dstvalue & 1; 5501 dstvalue = (dstvalue >> 1) | (((ui5r)XFLG) << 15); 5502 XFLG = CFLG; 5503 } 5504 dstvalue = ui5r_FromSWord(dstvalue); 5505 5506 ZFLG = Bool2Bit(dstvalue == 0); 5507 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5508 VFLG = 0; 5509 5510 ArgSetDstValue(dstvalue); 5511 } 5512} 5513 5514LOCALIPROC DoCodeRxrL(void) 5515{ 5516 ui5r dstvalue = DecodeGetSrcSetDstValueDfltFlags_nm(); 5517 ui5r cnt = V_regs.SrcVal & 63; 5518 5519 if (0 == cnt) { 5520 DoCodeNullXShift(dstvalue); 5521 } else { 5522#if WantCloserCyc 5523 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5524#endif 5525 5526 dstvalue = ui5r_FromULong(dstvalue); 5527 for (; cnt; --cnt) { 5528 CFLG = dstvalue & 1; 5529 dstvalue = (dstvalue >> 1) | (((ui5r)XFLG) << 31); 5530 XFLG = CFLG; 5531 } 5532 dstvalue = ui5r_FromSLong(dstvalue); 5533 5534 ZFLG = Bool2Bit(dstvalue == 0); 5535 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5536 VFLG = 0; 5537 5538 ArgSetDstValue(dstvalue); 5539 } 5540} 5541 5542LOCALIPROC DoCodeRolB(void) 5543{ 5544 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5545 ui5r cnt = V_regs.SrcVal & 63; 5546 5547#if WantCloserCyc 5548 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5549#endif 5550 5551 if (0 == cnt) { 5552 DoCodeNullShift(dstvalue); 5553 } else { 5554 cnt &= 7; 5555 if (0 != cnt) { 5556 ui3b dst = (ui3b)dstvalue; 5557 5558 dst = (dst >> (8 - cnt)) 5559 | ((dst & ((1 << (8 - cnt)) - 1)) 5560 << cnt); 5561 5562 dstvalue = (ui5r)(si5r)(si3b)dst; 5563 } 5564 ZFLG = Bool2Bit(dstvalue == 0); 5565 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5566 VFLG = 0; 5567 CFLG = (dstvalue & 1); 5568 V_regs.LazyFlagKind = kLazyFlagsDefault; 5569 5570 ArgSetDstValue(dstvalue); 5571 } 5572} 5573 5574LOCALIPROC DoCodeRolW(void) 5575{ 5576 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5577 ui5r cnt = V_regs.SrcVal & 63; 5578 5579#if WantCloserCyc 5580 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5581#endif 5582 5583 if (0 == cnt) { 5584 DoCodeNullShift(dstvalue); 5585 } else { 5586 cnt &= 15; 5587 if (0 != cnt) { 5588 ui4b dst = (ui4b)dstvalue; 5589 5590 dst = (dst >> (16 - cnt)) 5591 | ((dst & ((1 << (16 - cnt)) - 1)) 5592 << cnt); 5593 5594 dstvalue = (ui5r)(si5r)(si4b)dst; 5595 } 5596 ZFLG = Bool2Bit(dstvalue == 0); 5597 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5598 VFLG = 0; 5599 CFLG = (dstvalue & 1); 5600 V_regs.LazyFlagKind = kLazyFlagsDefault; 5601 5602 ArgSetDstValue(dstvalue); 5603 } 5604} 5605 5606LOCALIPROC DoCodeRolL(void) 5607{ 5608 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5609 ui5r cnt = V_regs.SrcVal & 63; 5610 5611#if WantCloserCyc 5612 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5613#endif 5614 5615 if (0 == cnt) { 5616 DoCodeNullShift(dstvalue); 5617 } else { 5618 cnt &= 31; 5619 if (0 != cnt) { 5620 ui5b dst = (ui5b)dstvalue; 5621 5622 dst = (dst >> (32 - cnt)) 5623 | ((dst & ((1 << (32 - cnt)) - 1)) 5624 << cnt); 5625 5626 dstvalue = (ui5r)(si5r)(si5b)dst; 5627 } 5628 ZFLG = Bool2Bit(dstvalue == 0); 5629 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5630 VFLG = 0; 5631 CFLG = (dstvalue & 1); 5632 V_regs.LazyFlagKind = kLazyFlagsDefault; 5633 5634 ArgSetDstValue(dstvalue); 5635 } 5636} 5637 5638LOCALIPROC DoCodeRorB(void) 5639{ 5640 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5641 ui5r cnt = V_regs.SrcVal & 63; 5642 5643#if WantCloserCyc 5644 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5645#endif 5646 5647 if (0 == cnt) { 5648 DoCodeNullShift(dstvalue); 5649 } else { 5650 cnt &= 7; 5651 if (0 != cnt) { 5652 ui3b dst = (ui3b)dstvalue; 5653 5654 dst = (dst >> cnt) 5655 | ((dst & ((1 << cnt) - 1)) 5656 << (8 - cnt)); 5657 5658 dstvalue = (ui5r)(si5r)(si3b)dst; 5659 } 5660 ZFLG = Bool2Bit(dstvalue == 0); 5661 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5662 VFLG = 0; 5663 CFLG = NFLG; 5664 5665 V_regs.LazyFlagKind = kLazyFlagsDefault; 5666 5667 ArgSetDstValue(dstvalue); 5668 } 5669} 5670 5671LOCALIPROC DoCodeRorW(void) 5672{ 5673 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5674 ui5r cnt = V_regs.SrcVal & 63; 5675 5676#if WantCloserCyc 5677 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5678#endif 5679 5680 if (0 == cnt) { 5681 DoCodeNullShift(dstvalue); 5682 } else { 5683 cnt &= 15; 5684 if (0 != cnt) { 5685 ui4b dst = (ui4b)dstvalue; 5686 5687 dst = (dst >> cnt) 5688 | ((dst & ((1 << cnt) - 1)) 5689 << (16 - cnt)); 5690 5691 dstvalue = (ui5r)(si5r)(si4b)dst; 5692 } 5693 ZFLG = Bool2Bit(dstvalue == 0); 5694 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5695 VFLG = 0; 5696 CFLG = NFLG; 5697 5698 V_regs.LazyFlagKind = kLazyFlagsDefault; 5699 5700 ArgSetDstValue(dstvalue); 5701 } 5702} 5703 5704LOCALIPROC DoCodeRorL(void) 5705{ 5706 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5707 ui5r cnt = V_regs.SrcVal & 63; 5708 5709#if WantCloserCyc 5710 V_MaxCyclesToGo -= (cnt * 2 * kCycleScale); 5711#endif 5712 5713 if (0 == cnt) { 5714 DoCodeNullShift(dstvalue); 5715 } else { 5716 cnt &= 31; 5717 if (0 != cnt) { 5718 ui5b dst = (ui5b)dstvalue; 5719 5720 dst = (dst >> cnt) 5721 | ((dst & ((1 << cnt) - 1)) 5722 << (32 - cnt)); 5723 5724 dstvalue = (ui5r)(si5r)(si5b)dst; 5725 } 5726 ZFLG = Bool2Bit(dstvalue == 0); 5727 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 5728 VFLG = 0; 5729 CFLG = NFLG; 5730 5731 V_regs.LazyFlagKind = kLazyFlagsDefault; 5732 5733 ArgSetDstValue(dstvalue); 5734 } 5735} 5736 5737 5738#if UseLazyZ 5739LOCALPROC WillSetZFLG(void) 5740{ 5741 if (kLazyFlagsZSet == V_regs.LazyFlagKind) { 5742 /* ok */ 5743 } else if (kLazyFlagsDefault == V_regs.LazyFlagKind) { 5744 /* also ok */ 5745 } else { 5746 V_regs.LazyFlagZSavedKind = V_regs.LazyFlagKind; 5747 V_regs.LazyFlagKind = kLazyFlagsZSet; 5748 } 5749} 5750#else 5751#define WillSetZFLG NeedDefaultLazyAllFlags 5752#endif 5753 5754LOCALINLINEFUNC ui5r DecodeGetSrcGetDstValueSetZ(void) 5755{ 5756 WillSetZFLG(); 5757 5758 return DecodeGetSrcSetDstValue(); 5759} 5760 5761LOCALIPROC DoCodeBTstB(void) 5762{ 5763 ui5r dstvalue = DecodeGetSrcGetDstValueSetZ(); 5764 ui5r srcvalue = V_regs.SrcVal & 7; 5765 5766 ZFLG = ((dstvalue >> srcvalue) ^ 1) & 1; 5767} 5768 5769LOCALIPROC DoCodeBTstL(void) 5770{ 5771 ui5r dstvalue = DecodeGetSrcGetDstValueSetZ(); 5772 ui5r srcvalue = V_regs.SrcVal & 31; 5773 5774 ZFLG = ((dstvalue >> srcvalue) ^ 1) & 1; 5775} 5776 5777LOCALINLINEFUNC ui5r DecodeGetSrcSetDstValueSetZ(void) 5778{ 5779 WillSetZFLG(); 5780 5781 return DecodeGetSrcSetDstValue(); 5782} 5783 5784LOCALIPROC DoCodeBChgB(void) 5785{ 5786 ui5r dstvalue = DecodeGetSrcSetDstValueSetZ(); 5787 ui5r srcvalue = V_regs.SrcVal & 7; 5788 5789 ZFLG = ((dstvalue >> srcvalue) ^ 1) & 1; 5790 5791 dstvalue ^= (1 << srcvalue); 5792 ArgSetDstValue(dstvalue); 5793} 5794 5795LOCALIPROC DoCodeBChgL(void) 5796{ 5797 ui5r dstvalue = DecodeGetSrcSetDstValueSetZ(); 5798 ui5r srcvalue = V_regs.SrcVal & 31; 5799 5800 ZFLG = ((dstvalue >> srcvalue) ^ 1) & 1; 5801 5802 dstvalue ^= (1 << srcvalue); 5803 ArgSetDstValue(dstvalue); 5804} 5805 5806LOCALIPROC DoCodeBClrB(void) 5807{ 5808 ui5r dstvalue = DecodeGetSrcSetDstValueSetZ(); 5809 ui5r srcvalue = V_regs.SrcVal & 7; 5810 5811 ZFLG = ((dstvalue >> srcvalue) ^ 1) & 1; 5812 5813 dstvalue &= ~ (1 << srcvalue); 5814 ArgSetDstValue(dstvalue); 5815} 5816 5817LOCALIPROC DoCodeBClrL(void) 5818{ 5819 ui5r dstvalue = DecodeGetSrcSetDstValueSetZ(); 5820 ui5r srcvalue = V_regs.SrcVal & 31; 5821 5822 ZFLG = ((dstvalue >> srcvalue) ^ 1) & 1; 5823 5824 dstvalue &= ~ (1 << srcvalue); 5825 ArgSetDstValue(dstvalue); 5826} 5827 5828LOCALIPROC DoCodeBSetB(void) 5829{ 5830 ui5r dstvalue = DecodeGetSrcSetDstValueSetZ(); 5831 ui5r srcvalue = V_regs.SrcVal & 7; 5832 5833 ZFLG = ((dstvalue >> srcvalue) ^ 1) & 1; 5834 5835 dstvalue |= (1 << srcvalue); 5836 ArgSetDstValue(dstvalue); 5837} 5838 5839LOCALIPROC DoCodeBSetL(void) 5840{ 5841 ui5r dstvalue = DecodeGetSrcSetDstValueSetZ(); 5842 ui5r srcvalue = V_regs.SrcVal & 31; 5843 5844 ZFLG = ((dstvalue >> srcvalue) ^ 1) & 1; 5845 5846 dstvalue |= (1 << srcvalue); 5847 ArgSetDstValue(dstvalue); 5848} 5849 5850LOCALIPROC DoCodeAnd(void) 5851{ 5852 /* DoBinOpAnd(DecodeI_xxxxxxxxssmmmrrr()); */ 5853 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5854 5855 dstvalue &= V_regs.SrcVal; 5856 /* 5857 don't need to extend, since excess high 5858 bits all the same as desired high bit. 5859 */ 5860 5861 V_regs.LazyFlagKind = kLazyFlagsTstL; 5862 V_regs.LazyFlagArgDst = dstvalue; 5863 5864 HaveSetUpFlags(); 5865 5866 ArgSetDstValue(dstvalue); 5867} 5868 5869LOCALIPROC DoCodeOr(void) 5870{ 5871 /* DoBinOr(DecodeI_xxxxxxxxssmmmrrr()); */ 5872 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5873 5874 dstvalue |= V_regs.SrcVal; 5875 /* 5876 don't need to extend, since excess high 5877 bits all the same as desired high bit. 5878 */ 5879 5880 V_regs.LazyFlagKind = kLazyFlagsTstL; 5881 V_regs.LazyFlagArgDst = dstvalue; 5882 5883 HaveSetUpFlags(); 5884 5885 ArgSetDstValue(dstvalue); 5886} 5887 5888LOCALIPROC DoCodeEor(void) 5889{ 5890 /* Eor 1011ddd1ssmmmrrr */ 5891 /* DoBinOpEor(DecodeDEa_xxxxdddxssmmmrrr()); */ 5892 ui5r dstvalue = DecodeGetSrcSetDstValue(); 5893 5894 dstvalue ^= V_regs.SrcVal; 5895 /* 5896 don't need to extend, since excess high 5897 bits all the same as desired high bit. 5898 */ 5899 5900 V_regs.LazyFlagKind = kLazyFlagsTstL; 5901 V_regs.LazyFlagArgDst = dstvalue; 5902 5903 HaveSetUpFlags(); 5904 5905 ArgSetDstValue(dstvalue); 5906} 5907 5908LOCALIPROC DoCodeNot(void) 5909{ 5910 /* Not 01000110ssmmmrrr */ 5911 ui5r dstvalue = DecodeGetSetDstValue(); 5912 5913 dstvalue = ~ dstvalue; 5914 5915 V_regs.LazyFlagKind = kLazyFlagsTstL; 5916 V_regs.LazyFlagArgDst = dstvalue; 5917 5918 HaveSetUpFlags(); 5919 5920 ArgSetDstValue(dstvalue); 5921} 5922 5923LOCALPROC DoCodeScc_t(void) 5924{ 5925#if WantCloserCyc 5926 if (kAMdRegB == V_regs.CurDecOpY.v[1].AMd) { 5927 V_MaxCyclesToGo -= (2 * kCycleScale); 5928 } 5929#endif 5930 DecodeSetDstValue(0xff); 5931} 5932 5933LOCALPROC DoCodeScc_f(void) 5934{ 5935 DecodeSetDstValue(0); 5936} 5937 5938LOCALIPROC DoCodeScc(void) 5939{ 5940 /* Scc 0101cccc11mmmrrr */ 5941 cctrue(DoCodeScc_t, DoCodeScc_f); 5942} 5943 5944LOCALIPROC DoCodeEXTL(void) 5945{ 5946 /* EXT.L */ 5947 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 5948 ui5r *dstp = &V_regs.regs[dstreg]; 5949 ui5r dstvalue = ui5r_FromSWord(*dstp); 5950 5951 V_regs.LazyFlagKind = kLazyFlagsTstL; 5952 V_regs.LazyFlagArgDst = dstvalue; 5953 5954 HaveSetUpFlags(); 5955 5956 *dstp = dstvalue; 5957} 5958 5959LOCALIPROC DoCodeEXTW(void) 5960{ 5961 /* EXT.W */ 5962 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 5963 ui5r *dstp = &V_regs.regs[dstreg]; 5964 ui5r dstvalue = ui5r_FromSByte(*dstp); 5965 5966 V_regs.LazyFlagKind = kLazyFlagsTstL; 5967 V_regs.LazyFlagArgDst = dstvalue; 5968 5969 HaveSetUpFlags(); 5970 5971#if LittleEndianUnaligned 5972 *(ui4b *)dstp = dstvalue; 5973#else 5974 *dstp = (*dstp & ~ 0xffff) | (dstvalue & 0xffff); 5975#endif 5976} 5977 5978LOCALIPROC DoCodeNegB(void) 5979{ 5980 ui5r dstvalue = DecodeGetSetDstValue(); 5981 ui5r result = ui5r_FromSByte(0 - dstvalue); 5982 5983 V_regs.LazyFlagKind = kLazyFlagsNegB; 5984 V_regs.LazyFlagArgDst = dstvalue; 5985 V_regs.LazyXFlagKind = kLazyFlagsNegB; 5986 V_regs.LazyXFlagArgDst = dstvalue; 5987 5988 HaveSetUpFlags(); 5989 5990 ArgSetDstValue(result); 5991} 5992 5993LOCALIPROC DoCodeNegW(void) 5994{ 5995 ui5r dstvalue = DecodeGetSetDstValue(); 5996 ui5r result = ui5r_FromSWord(0 - dstvalue); 5997 5998 V_regs.LazyFlagKind = kLazyFlagsNegW; 5999 V_regs.LazyFlagArgDst = dstvalue; 6000 V_regs.LazyXFlagKind = kLazyFlagsNegW; 6001 V_regs.LazyXFlagArgDst = dstvalue; 6002 6003 HaveSetUpFlags(); 6004 6005 ArgSetDstValue(result); 6006} 6007 6008LOCALIPROC DoCodeNegL(void) 6009{ 6010 ui5r dstvalue = DecodeGetSetDstValue(); 6011 ui5r result = ui5r_FromSLong(0 - dstvalue); 6012 6013 V_regs.LazyFlagKind = kLazyFlagsNegL; 6014 V_regs.LazyFlagArgDst = dstvalue; 6015 V_regs.LazyXFlagKind = kLazyFlagsNegL; 6016 V_regs.LazyXFlagArgDst = dstvalue; 6017 6018 HaveSetUpFlags(); 6019 6020 ArgSetDstValue(result); 6021} 6022 6023LOCALPROC my_reg_call SetCCRforNegX(ui5r dstvalue, ui5r result) 6024{ 6025 ZFLG &= Bool2Bit(result == 0); 6026 6027 { 6028 flagtype flgs = Bool2Bit(ui5r_MSBisSet(dstvalue)); 6029 flagtype flgn = Bool2Bit(ui5r_MSBisSet(result)); 6030 6031 NFLG = flgn; 6032 VFLG = flgs & flgn; 6033 XFLG = CFLG = flgs | flgn; 6034 } 6035 6036 ArgSetDstValue(result); 6037} 6038 6039LOCALIPROC DoCodeNegXB(void) 6040{ 6041 NeedDefaultLazyAllFlags(); 6042 6043 { 6044 ui5r dstvalue = DecodeGetSetDstValue(); 6045 ui5r result = ui5r_FromSByte(0 - (XFLG + dstvalue)); 6046 6047 SetCCRforNegX(dstvalue, result); 6048 } 6049} 6050 6051LOCALIPROC DoCodeNegXW(void) 6052{ 6053 if ((kLazyFlagsDefault != V_regs.LazyFlagKind) 6054 || (kLazyFlagsDefault != V_regs.LazyXFlagKind)) 6055 { 6056 NeedDefaultLazyAllFlags(); 6057 } 6058 6059 { 6060 ui5r dstvalue = DecodeGetSetDstValue(); 6061 ui5r result = ui5r_FromSWord(0 - (XFLG + dstvalue)); 6062 6063 SetCCRforNegX(dstvalue, result); 6064 } 6065} 6066 6067LOCALIPROC DoCodeNegXL(void) 6068{ 6069 if (kLazyFlagsNegL == V_regs.LazyFlagKind) { 6070 NeedDefaultLazyFlagsNegL(); 6071 } else 6072 if ((kLazyFlagsDefault == V_regs.LazyFlagKind) 6073 && (kLazyFlagsDefault == V_regs.LazyXFlagKind)) 6074 { 6075 /* ok */ 6076 } else 6077 { 6078 NeedDefaultLazyAllFlags(); 6079 } 6080 6081 { 6082 ui5r dstvalue = DecodeGetSetDstValue(); 6083 ui5r result = ui5r_FromSLong(0 - (XFLG + dstvalue)); 6084 6085 SetCCRforNegX(dstvalue, result); 6086 } 6087} 6088 6089LOCALIPROC DoCodeMulU(void) 6090{ 6091 /* MulU 1100ddd011mmmrrr */ 6092 ui5r srcvalue = DecodeGetSrcValue(); 6093 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6094 ui5r *dstp = &V_regs.regs[dstreg]; 6095 ui5r dstvalue = *dstp; 6096 6097 dstvalue = ui5r_FromSLong(ui5r_FromUWord(dstvalue) 6098 * ui5r_FromUWord(srcvalue)); 6099#if WantCloserCyc 6100 { 6101 ui5r v = srcvalue; 6102 6103 while (v != 0) { 6104 if ((v & 1) != 0) { 6105 V_MaxCyclesToGo -= (2 * kCycleScale); 6106 } 6107 v >>= 1; 6108 } 6109 } 6110#endif 6111 6112 V_regs.LazyFlagKind = kLazyFlagsTstL; 6113 V_regs.LazyFlagArgDst = dstvalue; 6114 6115 HaveSetUpFlags(); 6116 6117 *dstp = dstvalue; 6118} 6119 6120LOCALIPROC DoCodeMulS(void) 6121{ 6122 /* MulS 1100ddd111mmmrrr */ 6123 ui5r srcvalue = DecodeGetSrcValue(); 6124 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6125 ui5r *dstp = &V_regs.regs[dstreg]; 6126 ui5r dstvalue = *dstp; 6127 6128 dstvalue = ui5r_FromSLong((si5b)(si4b)dstvalue 6129 * (si5b)(si4b)srcvalue); 6130#if WantCloserCyc 6131 { 6132 ui5r v = (srcvalue << 1); 6133 6134 while (v != 0) { 6135 if ((v & 1) != ((v >> 1) & 1)) { 6136 V_MaxCyclesToGo -= (2 * kCycleScale); 6137 } 6138 v >>= 1; 6139 } 6140 } 6141#endif 6142 6143 V_regs.LazyFlagKind = kLazyFlagsTstL; 6144 V_regs.LazyFlagArgDst = dstvalue; 6145 6146 HaveSetUpFlags(); 6147 6148 *dstp = dstvalue; 6149} 6150 6151LOCALIPROC DoCodeDivU(void) 6152{ 6153 /* DivU 1000ddd011mmmrrr */ 6154 ui5r srcvalue = DecodeGetSrcValue(); 6155 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6156 ui5r *dstp = &V_regs.regs[dstreg]; 6157 ui5r dstvalue = *dstp; 6158 6159 if (srcvalue == 0) { 6160#if WantCloserCyc 6161 V_MaxCyclesToGo -= 6162 (38 * kCycleScale + 3 * RdAvgXtraCyc + 3 * WrAvgXtraCyc); 6163#endif 6164 Exception(5); 6165#if m68k_logExceptions 6166 dbglog_WriteNote("*** zero devide exception"); 6167#endif 6168 } else { 6169 ui5b newv = (ui5b)dstvalue / (ui5b)(ui4b)srcvalue; 6170 ui5b rem = (ui5b)dstvalue % (ui5b)(ui4b)srcvalue; 6171#if WantCloserCyc 6172 V_MaxCyclesToGo -= (133 * kCycleScale); 6173#endif 6174 if (newv > 0xffff) { 6175 NeedDefaultLazyAllFlags(); 6176 6177 VFLG = NFLG = 1; 6178 CFLG = 0; 6179 } else { 6180 VFLG = CFLG = 0; 6181 ZFLG = Bool2Bit(((si4b)(newv)) == 0); 6182 NFLG = Bool2Bit(((si4b)(newv)) < 0); 6183 6184 V_regs.LazyFlagKind = kLazyFlagsDefault; 6185 6186 newv = (newv & 0xffff) | ((ui5b)rem << 16); 6187 dstvalue = newv; 6188 } 6189 } 6190 6191 *dstp = dstvalue; 6192} 6193 6194LOCALIPROC DoCodeDivS(void) 6195{ 6196 /* DivS 1000ddd111mmmrrr */ 6197 ui5r srcvalue = DecodeGetSrcValue(); 6198 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6199 ui5r *dstp = &V_regs.regs[dstreg]; 6200 ui5r dstvalue = *dstp; 6201 6202 if (srcvalue == 0) { 6203#if WantCloserCyc 6204 V_MaxCyclesToGo -= 6205 (38 * kCycleScale + 3 * RdAvgXtraCyc + 3 * WrAvgXtraCyc); 6206#endif 6207 Exception(5); 6208#if m68k_logExceptions 6209 dbglog_WriteNote("*** zero devide exception"); 6210#endif 6211 } else { 6212 si5b newv = (si5b)dstvalue / (si5b)(si4b)srcvalue; 6213 ui4b rem = (si5b)dstvalue % (si5b)(si4b)srcvalue; 6214#if WantCloserCyc 6215 V_MaxCyclesToGo -= (150 * kCycleScale); 6216#endif 6217 if (((newv & 0xffff8000) != 0) && 6218 ((newv & 0xffff8000) != 0xffff8000)) 6219 { 6220 NeedDefaultLazyAllFlags(); 6221 6222 VFLG = NFLG = 1; 6223 CFLG = 0; 6224 } else { 6225 if (((si4b)rem < 0) != ((si5b)dstvalue < 0)) { 6226 rem = - rem; 6227 } 6228 VFLG = CFLG = 0; 6229 ZFLG = Bool2Bit(((si4b)(newv)) == 0); 6230 NFLG = Bool2Bit(((si4b)(newv)) < 0); 6231 6232 V_regs.LazyFlagKind = kLazyFlagsDefault; 6233 6234 newv = (newv & 0xffff) | ((ui5b)rem << 16); 6235 dstvalue = newv; 6236 } 6237 } 6238 6239 *dstp = dstvalue; 6240} 6241 6242LOCALIPROC DoCodeExg(void) 6243{ 6244 /* Exg dd 1100ddd101000rrr, opsize = 4 */ 6245 /* Exg aa 1100ddd101001rrr, opsize = 4 */ 6246 /* Exg da 1100ddd110001rrr, opsize = 4 */ 6247 6248 ui5r srcreg = V_regs.CurDecOpY.v[0].ArgDat; 6249 ui5r *srcp = &V_regs.regs[srcreg]; 6250 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6251 ui5r *dstp = &V_regs.regs[dstreg]; 6252 ui5r srcvalue = *srcp; 6253 6254 *srcp = *dstp; 6255 *dstp = srcvalue; 6256} 6257 6258LOCALIPROC DoCodeMoveEaCR(void) 6259{ 6260 /* 0100010011mmmrrr */ 6261 m68k_setCR(DecodeGetDstValue()); 6262} 6263 6264LOCALPROC DoPrivilegeViolation(void) 6265{ 6266#if WantCloserCyc 6267 V_MaxCyclesToGo += GetDcoCycles(V_regs.CurDecOp); 6268 V_MaxCyclesToGo -= 6269 (34 * kCycleScale + 4 * RdAvgXtraCyc + 3 * WrAvgXtraCyc); 6270#endif 6271 BackupPC(); 6272 Exception(8); 6273#if m68k_logExceptions 6274 dbglog_WriteNote("*** Privilege Violation exception"); 6275#endif 6276} 6277 6278LOCALIPROC DoCodeMoveSREa(void) 6279{ 6280 /* Move from SR 0100000011mmmrrr */ 6281#if Use68020 6282 if (0 == V_regs.s) { 6283 DoPrivilegeViolation(); 6284 } else 6285#endif 6286 { 6287 DecodeSetDstValue(m68k_getSR()); 6288 } 6289} 6290 6291LOCALIPROC DoCodeMoveEaSR(void) 6292{ 6293 /* 0100011011mmmrrr */ 6294 if (0 == V_regs.s) { 6295 DoPrivilegeViolation(); 6296 } else { 6297 m68k_setSR(DecodeGetDstValue()); 6298 } 6299} 6300 6301LOCALIPROC DoCodeOrISR(void) 6302{ 6303 if (0 == V_regs.s) { 6304 DoPrivilegeViolation(); 6305 } else { 6306 V_regs.SrcVal = nextiword_nm(); 6307 6308 m68k_setSR(m68k_getSR() | V_regs.SrcVal); 6309 } 6310} 6311 6312LOCALIPROC DoCodeAndISR(void) 6313{ 6314 if (0 == V_regs.s) { 6315 DoPrivilegeViolation(); 6316 } else { 6317 V_regs.SrcVal = nextiword_nm(); 6318 6319 m68k_setSR(m68k_getSR() & V_regs.SrcVal); 6320 } 6321} 6322 6323LOCALIPROC DoCodeEorISR(void) 6324{ 6325 if (0 == V_regs.s) { 6326 DoPrivilegeViolation(); 6327 } else { 6328 V_regs.SrcVal = nextiword_nm(); 6329 6330 m68k_setSR(m68k_getSR() ^ V_regs.SrcVal); 6331 } 6332} 6333 6334LOCALIPROC DoCodeOrICCR(void) 6335{ 6336 V_regs.SrcVal = nextiword_nm(); 6337 6338 m68k_setCR(m68k_getCR() | V_regs.SrcVal); 6339} 6340 6341LOCALIPROC DoCodeAndICCR(void) 6342{ 6343 V_regs.SrcVal = nextiword_nm(); 6344 6345 m68k_setCR(m68k_getCR() & V_regs.SrcVal); 6346} 6347 6348LOCALIPROC DoCodeEorICCR(void) 6349{ 6350 V_regs.SrcVal = nextiword_nm(); 6351 6352 m68k_setCR(m68k_getCR() ^ V_regs.SrcVal); 6353} 6354 6355LOCALIPROC DoCodeMOVEMApRW(void) 6356{ 6357 /* MOVEM mem to reg 01001100110011rrr */ 6358 si4b z; 6359 ui5r regmask = nextiword_nm(); 6360 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6361 ui5r *dstp = &V_regs.regs[dstreg]; 6362 ui5r p = *dstp; 6363 6364 for (z = 0; z < 16; ++z) { 6365 if ((regmask & (1 << z)) != 0) { 6366#if WantCloserCyc 6367 V_MaxCyclesToGo -= (4 * kCycleScale + RdAvgXtraCyc); 6368#endif 6369 V_regs.regs[z] = get_word(p); 6370 p += 2; 6371 } 6372 } 6373 *dstp = p; 6374} 6375 6376LOCALIPROC DoCodeMOVEMRmMW(void) 6377{ 6378 /* MOVEM reg to mem 01001000110100rrr */ 6379 si4b z; 6380 ui5r regmask = nextiword_nm(); 6381 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6382 ui5r *dstp = &V_regs.regs[dstreg]; 6383 ui5r p = *dstp; 6384 6385#if Use68020 6386 { 6387 int n = 0; 6388 6389 for (z = 0; z < 16; ++z) { 6390 if ((regmask & (1 << z)) != 0) { 6391 n++; 6392 } 6393 } 6394 *dstp = p - n * 2; 6395 } 6396#endif 6397 for (z = 16; --z >= 0; ) { 6398 if ((regmask & (1 << (15 - z))) != 0) { 6399#if WantCloserCyc 6400 V_MaxCyclesToGo -= (4 * kCycleScale + WrAvgXtraCyc); 6401#endif 6402 p -= 2; 6403 put_word(p, V_regs.regs[z]); 6404 } 6405 } 6406#if ! Use68020 6407 *dstp = p; 6408#endif 6409} 6410 6411LOCALIPROC DoCodeMOVEMrmW(void) 6412{ 6413 /* MOVEM reg to mem 010010001ssmmmrrr */ 6414 si4b z; 6415 ui5r regmask = nextiword_nm(); 6416 ui5r p = DecodeDst(); 6417 6418 for (z = 0; z < 16; ++z) { 6419 if ((regmask & (1 << z)) != 0) { 6420#if WantCloserCyc 6421 V_MaxCyclesToGo -= 6422 (4 * kCycleScale + WrAvgXtraCyc); 6423#endif 6424 put_word(p, V_regs.regs[z]); 6425 p += 2; 6426 } 6427 } 6428} 6429 6430LOCALIPROC DoCodeMOVEMrmL(void) 6431{ 6432 /* MOVEM reg to mem 010010001ssmmmrrr */ 6433 si4b z; 6434 ui5r regmask = nextiword_nm(); 6435 ui5r p = DecodeDst(); 6436 6437 for (z = 0; z < 16; ++z) { 6438 if ((regmask & (1 << z)) != 0) { 6439#if WantCloserCyc 6440 V_MaxCyclesToGo -= 6441 (8 * kCycleScale + 2 * WrAvgXtraCyc); 6442#endif 6443 put_long(p, V_regs.regs[z]); 6444 p += 4; 6445 } 6446 } 6447} 6448 6449LOCALIPROC DoCodeMOVEMmrW(void) 6450{ 6451 /* MOVEM mem to reg 0100110011smmmrrr */ 6452 si4b z; 6453 ui5r regmask = nextiword_nm(); 6454 ui5r p = DecodeDst(); 6455 6456 for (z = 0; z < 16; ++z) { 6457 if ((regmask & (1 << z)) != 0) { 6458#if WantCloserCyc 6459 V_MaxCyclesToGo -= 6460 (4 * kCycleScale + RdAvgXtraCyc); 6461#endif 6462 V_regs.regs[z] = get_word(p); 6463 p += 2; 6464 } 6465 } 6466} 6467 6468LOCALIPROC DoCodeMOVEMmrL(void) 6469{ 6470 /* MOVEM mem to reg 0100110011smmmrrr */ 6471 si4b z; 6472 ui5r regmask = nextiword_nm(); 6473 ui5r p = DecodeDst(); 6474 6475 for (z = 0; z < 16; ++z) { 6476 if ((regmask & (1 << z)) != 0) { 6477#if WantCloserCyc 6478 V_MaxCyclesToGo -= 6479 (8 * kCycleScale + 2 * RdAvgXtraCyc); 6480#endif 6481 V_regs.regs[z] = get_long(p); 6482 p += 4; 6483 } 6484 } 6485} 6486 6487LOCALIPROC DoCodeAbcd(void) 6488{ 6489 /* ABCD r 1100ddd100000rrr */ 6490 /* ABCD m 1100ddd100001rrr */ 6491 6492 ui5r dstvalue = DecodeGetSrcSetDstValueDfltFlags_nm(); 6493 ui5r srcvalue = V_regs.SrcVal; 6494 6495 { 6496 /* if (V_regs.opsize != 1) a bug */ 6497 int flgs = ui5r_MSBisSet(srcvalue); 6498 int flgo = ui5r_MSBisSet(dstvalue); 6499 ui4b newv_lo = 6500 (srcvalue & 0xF) + (dstvalue & 0xF) + XFLG; 6501 ui4b newv_hi = (srcvalue & 0xF0) + (dstvalue & 0xF0); 6502 ui4b newv; 6503 6504 if (newv_lo > 9) { 6505 newv_lo += 6; 6506 } 6507 newv = newv_hi + newv_lo; 6508 CFLG = XFLG = Bool2Bit((newv & 0x1F0) > 0x90); 6509 if (CFLG != 0) { 6510 newv += 0x60; 6511 } 6512 dstvalue = ui5r_FromSByte(newv); 6513 if (dstvalue != 0) { 6514 ZFLG = 0; 6515 } 6516 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 6517 VFLG = Bool2Bit((flgs != flgo) && ((NFLG != 0) != flgo)); 6518 /* 6519 but according to my reference book, 6520 VFLG is Undefined for ABCD 6521 */ 6522 } 6523 6524 ArgSetDstValue(dstvalue); 6525} 6526 6527LOCALIPROC DoCodeSbcd(void) 6528{ 6529 ui5r dstvalue = DecodeGetSrcSetDstValueDfltFlags_nm(); 6530 ui5r srcvalue = V_regs.SrcVal; 6531 6532 { 6533 int flgs = ui5r_MSBisSet(srcvalue); 6534 int flgo = ui5r_MSBisSet(dstvalue); 6535 ui4b newv_lo = 6536 (dstvalue & 0xF) - (srcvalue & 0xF) - XFLG; 6537 ui4b newv_hi = (dstvalue & 0xF0) - (srcvalue & 0xF0); 6538 ui4b newv; 6539 6540 if (newv_lo > 9) { 6541 newv_lo -= 6; 6542 newv_hi -= 0x10; 6543 } 6544 newv = newv_hi + (newv_lo & 0xF); 6545 CFLG = XFLG = Bool2Bit((newv_hi & 0x1F0) > 0x90); 6546 if (CFLG != 0) { 6547 newv -= 0x60; 6548 } 6549 dstvalue = ui5r_FromSByte(newv); 6550 if (dstvalue != 0) { 6551 ZFLG = 0; 6552 } 6553 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 6554 VFLG = Bool2Bit((flgs != flgo) && ((NFLG != 0) != flgo)); 6555 /* 6556 but according to my reference book, 6557 VFLG is Undefined for SBCD 6558 */ 6559 } 6560 6561 ArgSetDstValue(dstvalue); 6562} 6563 6564LOCALIPROC DoCodeNbcd(void) 6565{ 6566 /* Nbcd 0100100000mmmrrr */ 6567 ui5r dstvalue = DecodeGetSetDstValue(); 6568 6569 NeedDefaultLazyAllFlags(); 6570 6571 { 6572 ui4b newv_lo = - (dstvalue & 0xF) - XFLG; 6573 ui4b newv_hi = - (dstvalue & 0xF0); 6574 ui4b newv; 6575 6576 if (newv_lo > 9) { 6577 newv_lo -= 6; 6578 newv_hi -= 0x10; 6579 } 6580 newv = newv_hi + (newv_lo & 0xF); 6581 CFLG = XFLG = Bool2Bit((newv_hi & 0x1F0) > 0x90); 6582 if (CFLG != 0) { 6583 newv -= 0x60; 6584 } 6585 6586 dstvalue = ui5r_FromSByte(newv); 6587 NFLG = Bool2Bit(ui5r_MSBisSet(dstvalue)); 6588 if (dstvalue != 0) { 6589 ZFLG = 0; 6590 } 6591 } 6592 6593 ArgSetDstValue(dstvalue); 6594} 6595 6596LOCALIPROC DoCodeRte(void) 6597{ 6598 /* Rte 0100111001110011 */ 6599 if (0 == V_regs.s) { 6600 DoPrivilegeViolation(); 6601 } else { 6602 ui5r NewPC; 6603 CPTR stackp = m68k_areg(7); 6604 ui5r NewSR = get_word(stackp); 6605 stackp += 2; 6606 NewPC = get_long(stackp); 6607 stackp += 4; 6608 6609#if Use68020 6610 { 6611 ui4b format = get_word(stackp); 6612 stackp += 2; 6613 6614 switch ((format >> 12) & 0x0F) { 6615 case 0: 6616 /* ReportAbnormal("rte stack frame format 0"); */ 6617 break; 6618 case 1: 6619 ReportAbnormalID(0x0107, 6620 "rte stack frame format 1"); 6621 NewPC = m68k_getpc() - 2; 6622 /* rerun instruction */ 6623 break; 6624 case 2: 6625 ReportAbnormalID(0x0108, 6626 "rte stack frame format 2"); 6627 stackp += 4; 6628 break; 6629 case 9: 6630 ReportAbnormalID(0x0109, 6631 "rte stack frame format 9"); 6632 stackp += 12; 6633 break; 6634 case 10: 6635 ReportAbnormalID(0x010A, 6636 "rte stack frame format 10"); 6637 stackp += 24; 6638 break; 6639 case 11: 6640 ReportAbnormalID(0x010B, 6641 "rte stack frame format 11"); 6642 stackp += 84; 6643 break; 6644 default: 6645 ReportAbnormalID(0x010C, 6646 "unknown rte stack frame format"); 6647 Exception(14); 6648 return; 6649 break; 6650 } 6651 } 6652#endif 6653 m68k_areg(7) = stackp; 6654 m68k_setSR(NewSR); 6655 m68k_setpc(NewPC); 6656 } 6657} 6658 6659LOCALIPROC DoCodeNop(void) 6660{ 6661 /* Nop 0100111001110001 */ 6662} 6663 6664LOCALIPROC DoCodeMoveP0(void) 6665{ 6666 /* MoveP 0000ddd1mm001aaa */ 6667 ui5r srcreg = V_regs.CurDecOpY.v[0].ArgDat; 6668 ui5r *srcp = &V_regs.regs[srcreg]; 6669 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6670 ui5r *dstp = &V_regs.regs[dstreg]; 6671 6672 ui5r Displacement = nextiword_nm(); 6673 /* shouldn't this sign extend ? */ 6674 CPTR memp = *srcp + Displacement; 6675 6676 ui4r val = ((get_byte(memp) & 0x00FF) << 8) 6677 | (get_byte(memp + 2) & 0x00FF); 6678 6679 *dstp = 6680 (*dstp & ~ 0xffff) | (val & 0xffff); 6681 6682#if 0 6683 if ((Displacement & 0x00008000) != 0) { 6684 /* **** for testing only **** */ 6685 BackupPC(); 6686 op_illg(); 6687 } 6688#endif 6689} 6690 6691LOCALIPROC DoCodeMoveP1(void) 6692{ 6693 /* MoveP 0000ddd1mm001aaa */ 6694 ui5r srcreg = V_regs.CurDecOpY.v[0].ArgDat; 6695 ui5r *srcp = &V_regs.regs[srcreg]; 6696 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6697 ui5r *dstp = &V_regs.regs[dstreg]; 6698 6699 ui5r Displacement = nextiword_nm(); 6700 /* shouldn't this sign extend ? */ 6701 CPTR memp = *srcp + Displacement; 6702 6703 ui5r val = ((get_byte(memp) & 0x00FF) << 24) 6704 | ((get_byte(memp + 2) & 0x00FF) << 16) 6705 | ((get_byte(memp + 4) & 0x00FF) << 8) 6706 | (get_byte(memp + 6) & 0x00FF); 6707 6708 *dstp = val; 6709} 6710 6711LOCALIPROC DoCodeMoveP2(void) 6712{ 6713 /* MoveP 0000ddd1mm001aaa */ 6714 ui5r srcreg = V_regs.CurDecOpY.v[0].ArgDat; 6715 ui5r *srcp = &V_regs.regs[srcreg]; 6716 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6717 ui5r *dstp = &V_regs.regs[dstreg]; 6718 6719 ui5r Displacement = nextiword_nm(); 6720 /* shouldn't this sign extend ? */ 6721 CPTR memp = *srcp + Displacement; 6722 6723 ui4r val = *dstp; 6724 6725 put_byte(memp, val >> 8); 6726 put_byte(memp + 2, val); 6727} 6728 6729LOCALIPROC DoCodeMoveP3(void) 6730{ 6731 /* MoveP 0000ddd1mm001aaa */ 6732 ui5r srcreg = V_regs.CurDecOpY.v[0].ArgDat; 6733 ui5r *srcp = &V_regs.regs[srcreg]; 6734 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6735 ui5r *dstp = &V_regs.regs[dstreg]; 6736 6737 ui5r Displacement = nextiword_nm(); 6738 /* shouldn't this sign extend ? */ 6739 CPTR memp = *srcp + Displacement; 6740 6741 ui5r val = *dstp; 6742 6743 put_byte(memp, val >> 24); 6744 put_byte(memp + 2, val >> 16); 6745 put_byte(memp + 4, val >> 8); 6746 put_byte(memp + 6, val); 6747} 6748 6749LOCALPROC op_illg(void) 6750{ 6751 BackupPC(); 6752 Exception(4); 6753#if m68k_logExceptions 6754 dbglog_WriteNote("*** illegal instruction exception"); 6755#endif 6756} 6757 6758LOCALIPROC DoCodeChk(void) 6759{ 6760 ui5r dstvalue = DecodeGetSrcGetDstValue(); 6761 ui5r srcvalue = V_regs.SrcVal; 6762 6763 if (ui5r_MSBisSet(srcvalue)) { 6764 NeedDefaultLazyAllFlags(); 6765 6766#if WantCloserCyc 6767 V_MaxCyclesToGo -= 6768 (30 * kCycleScale + 3 * RdAvgXtraCyc + 3 * WrAvgXtraCyc); 6769#endif 6770 NFLG = 1; 6771 Exception(6); 6772 } else if (((si5r)srcvalue) > ((si5r)dstvalue)) { 6773 NeedDefaultLazyAllFlags(); 6774 6775#if WantCloserCyc 6776 V_MaxCyclesToGo -= 6777 (30 * kCycleScale + 3 * RdAvgXtraCyc + 3 * WrAvgXtraCyc); 6778#endif 6779 NFLG = 0; 6780 Exception(6); 6781 } 6782} 6783 6784LOCALIPROC DoCodeTrap(void) 6785{ 6786 /* Trap 010011100100vvvv */ 6787 Exception(V_regs.CurDecOpY.v[1].ArgDat); 6788} 6789 6790LOCALIPROC DoCodeTrapV(void) 6791{ 6792 /* TrapV 0100111001110110 */ 6793 NeedDefaultLazyAllFlags(); 6794 6795 if (VFLG != 0) { 6796#if WantCloserCyc 6797 V_MaxCyclesToGo += GetDcoCycles(V_regs.CurDecOp); 6798 V_MaxCyclesToGo -= 6799 (34 * kCycleScale + 4 * RdAvgXtraCyc + 3 * WrAvgXtraCyc); 6800#endif 6801 Exception(7); 6802 } 6803} 6804 6805LOCALIPROC DoCodeRtr(void) 6806{ 6807 /* Rtr 0100111001110111 */ 6808 ui5r NewPC; 6809 CPTR stackp = m68k_areg(7); 6810 ui5r NewCR = get_word(stackp); 6811 stackp += 2; 6812 NewPC = get_long(stackp); 6813 stackp += 4; 6814 m68k_areg(7) = stackp; 6815 m68k_setCR(NewCR); 6816 m68k_setpc(NewPC); 6817} 6818 6819LOCALIPROC DoCodeLink(void) 6820{ 6821 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6822 ui5r *dstp = &V_regs.regs[dstreg]; 6823 CPTR stackp = m68k_areg(7); 6824 6825 stackp -= 4; 6826 m68k_areg(7) = stackp; /* only matters if dstreg == 7 + 8 */ 6827 put_long(stackp, *dstp); 6828 *dstp = stackp; 6829 m68k_areg(7) += ui5r_FromSWord(nextiword_nm()); 6830} 6831 6832LOCALIPROC DoCodeUnlk(void) 6833{ 6834 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6835 ui5r *dstp = &V_regs.regs[dstreg]; 6836 6837 if (dstreg != 7 + 8) { 6838 ui5r src = *dstp; 6839 *dstp = get_long(src); 6840 m68k_areg(7) = src + 4; 6841 } else { 6842 /* wouldn't expect this to happen */ 6843 m68k_areg(7) = get_long(m68k_areg(7)) + 4; 6844 } 6845} 6846 6847LOCALIPROC DoCodeMoveRUSP(void) 6848{ 6849 /* MOVE USP 0100111001100aaa */ 6850 if (0 == V_regs.s) { 6851 DoPrivilegeViolation(); 6852 } else { 6853 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6854 ui5r *dstp = &V_regs.regs[dstreg]; 6855 6856 V_regs.usp = *dstp; 6857 } 6858} 6859 6860LOCALIPROC DoCodeMoveUSPR(void) 6861{ 6862 /* MOVE USP 0100111001101aaa */ 6863 if (0 == V_regs.s) { 6864 DoPrivilegeViolation(); 6865 } else { 6866 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 6867 ui5r *dstp = &V_regs.regs[dstreg]; 6868 6869 *dstp = V_regs.usp; 6870 } 6871} 6872 6873LOCALIPROC DoCodeTas(void) 6874{ 6875 /* Tas 0100101011mmmrrr */ 6876 ui5r dstvalue = DecodeGetSetDstValue(); 6877 6878 V_regs.LazyFlagKind = kLazyFlagsTstL; 6879 V_regs.LazyFlagArgDst = dstvalue; 6880 6881 HaveSetUpFlags(); 6882 6883 dstvalue |= 0x80; 6884 6885 ArgSetDstValue(dstvalue); 6886} 6887 6888LOCALIPROC DoCodeFdefault(void) 6889{ 6890 BackupPC(); 6891 Exception(0xB); 6892} 6893 6894LOCALPROC m68k_setstopped(void) 6895{ 6896 /* not implemented. doesn't seemed to be used on Mac Plus */ 6897 Exception(4); /* fake an illegal instruction */ 6898#if m68k_logExceptions 6899 dbglog_WriteNote("*** set stopped"); 6900#endif 6901} 6902 6903LOCALIPROC DoCodeStop(void) 6904{ 6905 /* Stop 0100111001110010 */ 6906 if (0 == V_regs.s) { 6907 DoPrivilegeViolation(); 6908 } else { 6909 m68k_setSR(nextiword_nm()); 6910 m68k_setstopped(); 6911 } 6912} 6913 6914FORWARDPROC local_customreset(void); 6915 6916LOCALIPROC DoCodeReset(void) 6917{ 6918 /* Reset 0100111001110000 */ 6919 if (0 == V_regs.s) { 6920 DoPrivilegeViolation(); 6921 } else { 6922 local_customreset(); 6923 } 6924} 6925 6926#if Use68020 6927LOCALIPROC DoCodeCallMorRtm(void) 6928{ 6929 /* CALLM or RTM 0000011011mmmrrr */ 6930 ReportAbnormalID(0x010D, "CALLM or RTM instruction"); 6931} 6932#endif 6933 6934#if Use68020 6935LOCALIPROC DoCodeMoveCCREa(void) 6936{ 6937 /* Move from CCR 0100001011mmmrrr */ 6938 DecodeSetDstValue(m68k_getCR()); 6939} 6940#endif 6941 6942#if Use68020 || EmFPU 6943LOCALIPROC DoCodeBraL(void) 6944{ 6945 /* Bra 0110ccccnnnnnnnn */ 6946 si5r offset = ((si5b)(ui5b)nextilong()) - 4; 6947 ui3p s = V_pc_p + offset; 6948 6949 V_pc_p = s; 6950 6951#if USE_PCLIMIT 6952 if (my_cond_rare(s >= V_pc_pHi) 6953 || my_cond_rare(s < V_regs.pc_pLo)) 6954 { 6955 Recalc_PC_Block(); 6956 } 6957#endif 6958} 6959#endif 6960 6961#if Use68020 || EmFPU 6962LOCALPROC SkipiLong(void) 6963{ 6964 V_pc_p += 4; 6965 6966#if USE_PCLIMIT 6967 if (my_cond_rare(V_pc_p >= V_pc_pHi)) { 6968 Recalc_PC_Block(); 6969 } 6970#endif 6971} 6972#endif 6973 6974#if Use68020 6975LOCALIPROC DoCodeBccL(void) 6976{ 6977 /* Bcc 0110ccccnnnnnnnn */ 6978 cctrue(DoCodeBraL, SkipiLong); 6979} 6980#endif 6981 6982#if Use68020 6983LOCALIPROC DoCodeBsrL(void) 6984{ 6985 si5r offset = ((si5b)(ui5b)nextilong()) - 4; 6986 ui3p s = V_pc_p + offset; 6987 6988 m68k_areg(7) -= 4; 6989 put_long(m68k_areg(7), m68k_getpc()); 6990 V_pc_p = s; 6991 6992#if USE_PCLIMIT 6993 if (my_cond_rare(s >= V_pc_pHi) 6994 || my_cond_rare(s < V_regs.pc_pLo)) 6995 { 6996 Recalc_PC_Block(); 6997 } 6998#endif 6999 7000 /* ReportAbnormal("long branch in DoCode6"); */ 7001 /* Used by various Apps */ 7002} 7003#endif 7004 7005#if Use68020 7006LOCALIPROC DoCodeEXTBL(void) 7007{ 7008 /* EXTB.L */ 7009 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 7010 ui5r *dstp = &V_regs.regs[dstreg]; 7011 ui5r dstvalue = ui5r_FromSByte(*dstp); 7012 7013 V_regs.LazyFlagKind = kLazyFlagsTstL; 7014 V_regs.LazyFlagArgDst = dstvalue; 7015 7016 HaveSetUpFlags(); 7017 7018 *dstp = dstvalue; 7019} 7020#endif 7021 7022#if Use68020 7023LOCALPROC DoCHK2orCMP2(void) 7024{ 7025 /* CHK2 or CMP2 00000ss011mmmrrr */ 7026 ui5r regv; 7027 ui5r lower; 7028 ui5r upper; 7029 ui5r extra = nextiword_nm(); 7030 ui5r DstAddr = DecodeDst(); 7031 ui5r srcreg = (extra >> 12) & 0x0F; 7032 ui5r *srcp = &V_regs.regs[srcreg]; 7033 7034 /* ReportAbnormal("CHK2 or CMP2 instruction"); */ 7035 switch (V_regs.CurDecOpY.v[0].ArgDat) { 7036 case 1: 7037 if ((extra & 0x8000) == 0) { 7038 regv = ui5r_FromSByte(*srcp); 7039 } else { 7040 regv = ui5r_FromSLong(*srcp); 7041 } 7042 lower = get_byte(DstAddr); 7043 upper = get_byte(DstAddr + 1); 7044 break; 7045 case 2: 7046 if ((extra & 0x8000) == 0) { 7047 regv = ui5r_FromSWord(*srcp); 7048 } else { 7049 regv = ui5r_FromSLong(*srcp); 7050 } 7051 lower = get_word(DstAddr); 7052 upper = get_word(DstAddr + 2); 7053 break; 7054 default: 7055#if ExtraAbnormalReports 7056 if (4 != V_regs.CurDecOpY.v[0].ArgDat) { 7057 ReportAbnormalID(0x010E, 7058 "illegal opsize in CHK2 or CMP2"); 7059 } 7060#endif 7061 if ((extra & 0x8000) == 0) { 7062 regv = ui5r_FromSLong(*srcp); 7063 } else { 7064 regv = ui5r_FromSLong(*srcp); 7065 } 7066 lower = get_long(DstAddr); 7067 upper = get_long(DstAddr + 4); 7068 break; 7069 } 7070 7071 NeedDefaultLazyAllFlags(); 7072 7073 ZFLG = Bool2Bit((upper == regv) || (lower == regv)); 7074 CFLG = Bool2Bit((((si5r)lower) <= ((si5r)upper)) 7075 ? (((si5r)regv) < ((si5r)lower) 7076 || ((si5r)regv) > ((si5r)upper)) 7077 : (((si5r)regv) > ((si5r)upper) 7078 || ((si5r)regv) < ((si5r)lower))); 7079 7080 if ((extra & 0x800) && (CFLG != 0)) { 7081 Exception(6); 7082 } 7083} 7084#endif 7085 7086#if Use68020 7087LOCALPROC DoCAS(void) 7088{ 7089 /* CAS 00001ss011mmmrrr */ 7090 ui5r srcvalue; 7091 ui5r dstvalue; 7092 7093 ui4b src = nextiword_nm(); 7094 int ru = (src >> 6) & 7; 7095 int rc = src & 7; 7096 7097 ReportAbnormalID(0x010F, "CAS instruction"); 7098 switch (V_regs.CurDecOpY.v[0].ArgDat) { 7099 case 1: 7100 srcvalue = ui5r_FromSByte(V_regs.regs[rc]); 7101 break; 7102 case 2: 7103 srcvalue = ui5r_FromSWord(V_regs.regs[rc]); 7104 break; 7105 default: 7106#if ExtraAbnormalReports 7107 if (4 != V_regs.CurDecOpY.v[0].ArgDat) { 7108 ReportAbnormalID(0x0110, "illegal opsize in DoCAS"); 7109 } 7110#endif 7111 srcvalue = ui5r_FromSLong(V_regs.regs[rc]); 7112 break; 7113 } 7114 dstvalue = DecodeGetSetDstValue(); 7115 7116 { 7117 int flgs = ((si5b)srcvalue) < 0; 7118 int flgo = ((si5b)dstvalue) < 0; 7119 ui5r newv = dstvalue - srcvalue; 7120 if (V_regs.CurDecOpY.v[0].ArgDat == 1) { 7121 newv = ui5r_FromSByte(newv); 7122 } else if (V_regs.CurDecOpY.v[0].ArgDat == 2) { 7123 newv = ui5r_FromSWord(newv); 7124 } else { 7125 newv = ui5r_FromSLong(newv); 7126 } 7127 ZFLG = Bool2Bit(((si5b)newv) == 0); 7128 NFLG = Bool2Bit(((si5b)newv) < 0); 7129 VFLG = Bool2Bit((flgs != flgo) && ((NFLG != 0) != flgo)); 7130 CFLG = Bool2Bit( 7131 (flgs && ! flgo) || ((NFLG != 0) && ((! flgo) || flgs))); 7132 7133 V_regs.LazyFlagKind = kLazyFlagsDefault; 7134 7135 if (ZFLG != 0) { 7136 ArgSetDstValue(m68k_dreg(ru)); 7137 } else { 7138 V_regs.ArgAddr.rga = &V_regs.regs[rc]; 7139 7140 if (V_regs.CurDecOpY.v[0].ArgDat == 2) { 7141 *V_regs.ArgAddr.rga = 7142 (*V_regs.ArgAddr.rga & ~ 0xffff) 7143 | ((dstvalue) & 0xffff); 7144 } else if (V_regs.CurDecOpY.v[0].ArgDat < 2) { 7145 *V_regs.ArgAddr.rga = 7146 (*V_regs.ArgAddr.rga & ~ 0xff) 7147 | ((dstvalue) & 0xff); 7148 } else { 7149 *V_regs.ArgAddr.rga = dstvalue; 7150 } 7151 } 7152 } 7153} 7154#endif 7155 7156#if Use68020 7157LOCALPROC DoCAS2(void) 7158{ 7159 /* CAS2 00001ss011111100 */ 7160 ui5b extra = nextilong(); 7161 int dc2 = extra & 7; 7162 int du2 = (extra >> 6) & 7; 7163 int dc1 = (extra >> 16) & 7; 7164 int du1 = (extra >> 22) & 7; 7165 CPTR rn1 = V_regs.regs[(extra >> 28) & 0x0F]; 7166 CPTR rn2 = V_regs.regs[(extra >> 12) & 0x0F]; 7167 si5b src = m68k_dreg(dc1); 7168 si5r dst1; 7169 si5r dst2; 7170 7171 ReportAbnormalID(0x0111, "DoCAS2 instruction"); 7172 if (V_regs.CurDecOpY.v[0].ArgDat == 2) { 7173 dst1 = get_word(rn1); 7174 dst2 = get_word(rn2); 7175 src = (si5b)(si4b)src; 7176 } else { 7177 dst1 = get_long(rn1); 7178 dst2 = get_long(rn2); 7179 } 7180 { 7181 int flgs = src < 0; 7182 int flgo = dst1 < 0; 7183 si5b newv = dst1 - src; 7184 if (V_regs.CurDecOpY.v[0].ArgDat == 2) { 7185 newv = (ui4b)newv; 7186 } 7187 ZFLG = Bool2Bit(newv == 0); 7188 NFLG = Bool2Bit(newv < 0); 7189 VFLG = Bool2Bit((flgs != flgo) && ((NFLG != 0) != flgo)); 7190 CFLG = Bool2Bit( 7191 (flgs && ! flgo) || ((NFLG != 0) && ((! flgo) || flgs))); 7192 7193 V_regs.LazyFlagKind = kLazyFlagsDefault; 7194 7195 if (ZFLG != 0) { 7196 src = m68k_dreg(dc2); 7197 if (V_regs.CurDecOpY.v[0].ArgDat == 2) { 7198 src = (si5b)(si4b)src; 7199 } 7200 flgs = src < 0; 7201 flgo = dst2 < 0; 7202 newv = dst2 - src; 7203 if (V_regs.CurDecOpY.v[0].ArgDat == 2) { 7204 newv = (ui4b)newv; 7205 } 7206 ZFLG = Bool2Bit(newv == 0); 7207 NFLG = Bool2Bit(newv < 0); 7208 VFLG = Bool2Bit((flgs != flgo) && ((NFLG != 0) != flgo)); 7209 CFLG = Bool2Bit((flgs && ! flgo) 7210 || ((NFLG != 0) && ((! flgo) || flgs))); 7211 7212 V_regs.LazyFlagKind = kLazyFlagsDefault; 7213 if (ZFLG != 0) { 7214 if (V_regs.CurDecOpY.v[0].ArgDat == 2) { 7215 put_word(rn1, m68k_dreg(du1)); 7216 put_word(rn2, m68k_dreg(du2)); 7217 } else { 7218 put_word(rn1, m68k_dreg(du1)); 7219 put_word(rn2, m68k_dreg(du2)); 7220 } 7221 } 7222 } 7223 } 7224 if (ZFLG == 0) { 7225 if (V_regs.CurDecOpY.v[0].ArgDat == 2) { 7226 m68k_dreg(du1) = 7227 (m68k_dreg(du1) & ~ 0xffff) | ((ui5b)dst1 & 0xffff); 7228 m68k_dreg(du2) = 7229 (m68k_dreg(du2) & ~ 0xffff) | ((ui5b)dst2 & 0xffff); 7230 } else { 7231 m68k_dreg(du1) = dst1; 7232 m68k_dreg(du2) = dst2; 7233 } 7234 } 7235} 7236#endif 7237 7238#if Use68020 7239LOCALPROC DoMOVES(void) 7240{ 7241 /* MoveS 00001110ssmmmrrr */ 7242 ReportAbnormalID(0x0112, "MoveS instruction"); 7243 if (0 == V_regs.s) { 7244 DoPrivilegeViolation(); 7245 } else { 7246 ui4b extra = nextiword_nm(); 7247 if (extra & 0x0800) { 7248 ui5b src = V_regs.regs[(extra >> 12) & 0x0F]; 7249 DecodeSetDstValue(src); 7250 } else { 7251 ui5r srcvalue = DecodeGetDstValue(); 7252 ui5b rr = (extra >> 12) & 7; 7253 if (extra & 0x8000) { 7254 m68k_areg(rr) = srcvalue; 7255 } else { 7256 V_regs.ArgAddr.rga = &V_regs.regs[rr]; 7257 7258 if (V_regs.CurDecOpY.v[0].ArgDat == 2) { 7259 *V_regs.ArgAddr.rga = 7260 (*V_regs.ArgAddr.rga & ~ 0xffff) 7261 | ((srcvalue) & 0xffff); 7262 } else if (V_regs.CurDecOpY.v[0].ArgDat < 2) { 7263 *V_regs.ArgAddr.rga = 7264 (*V_regs.ArgAddr.rga & ~ 0xff) 7265 | ((srcvalue) & 0xff); 7266 } else { 7267 *V_regs.ArgAddr.rga = srcvalue; 7268 } 7269 } 7270 } 7271 } 7272} 7273#endif 7274 7275#define ui5b_lo(x) ((x) & 0x0000FFFF) 7276#define ui5b_hi(x) (((x) >> 16) & 0x0000FFFF) 7277 7278#if Use68020 7279struct ui6r0 { 7280 ui5b hi; 7281 ui5b lo; 7282}; 7283typedef struct ui6r0 ui6r0; 7284#endif 7285 7286#if Use68020 7287LOCALPROC Ui6r_Negate(ui6r0 *v) 7288{ 7289 v->hi = ~ v->hi; 7290 v->lo = - v->lo; 7291 if (v->lo == 0) { 7292 v->hi++; 7293 } 7294} 7295#endif 7296 7297#if Use68020 7298LOCALFUNC blnr my_reg_call Ui6r_IsZero(ui6r0 *v) 7299{ 7300 return (v->hi == 0) && (v->lo == 0); 7301} 7302#endif 7303 7304#if Use68020 7305LOCALFUNC blnr my_reg_call Ui6r_IsNeg(ui6r0 *v) 7306{ 7307 return ((si5b)v->hi) < 0; 7308} 7309#endif 7310 7311#if Use68020 7312LOCALPROC mul_unsigned(ui5b src1, ui5b src2, ui6r0 *dst) 7313{ 7314 ui5b src1_lo = ui5b_lo(src1); 7315 ui5b src2_lo = ui5b_lo(src2); 7316 ui5b src1_hi = ui5b_hi(src1); 7317 ui5b src2_hi = ui5b_hi(src2); 7318 7319 ui5b r0 = src1_lo * src2_lo; 7320 ui5b r1 = src1_hi * src2_lo; 7321 ui5b r2 = src1_lo * src2_hi; 7322 ui5b r3 = src1_hi * src2_hi; 7323 7324 ui5b ra1 = ui5b_hi(r0) + ui5b_lo(r1) + ui5b_lo(r2); 7325 7326 dst->lo = (ui5b_lo(ra1) << 16) | ui5b_lo(r0); 7327 dst->hi = ui5b_hi(ra1) + ui5b_hi(r1) + ui5b_hi(r2) + r3; 7328} 7329#endif 7330 7331#if Use68020 7332LOCALFUNC blnr div_unsigned(ui6r0 *src, ui5b div, 7333 ui5b *quot, ui5b *rem) 7334{ 7335 int i; 7336 ui5b q = 0; 7337 ui5b cbit = 0; 7338 ui5b src_hi = src->hi; 7339 ui5b src_lo = src->lo; 7340 7341 if (div <= src_hi) { 7342 return trueblnr; 7343 } 7344 for (i = 0 ; i < 32 ; i++) { 7345 cbit = src_hi & 0x80000000ul; 7346 src_hi <<= 1; 7347 if (src_lo & 0x80000000ul) { 7348 src_hi++; 7349 } 7350 src_lo <<= 1; 7351 q = q << 1; 7352 if (cbit || div <= src_hi) { 7353 q |= 1; 7354 src_hi -= div; 7355 } 7356 } 7357 *quot = q; 7358 *rem = src_hi; 7359 return falseblnr; 7360} 7361#endif 7362 7363#if Use68020 7364LOCALIPROC DoCodeMulL(void) 7365{ 7366 /* MULU 0100110000mmmrrr 0rrr0s0000000rrr */ 7367 /* MULS 0100110000mmmrrr 0rrr1s0000000rrr */ 7368 ui6r0 dst; 7369 ui4b extra = nextiword(); 7370 ui5b r2 = (extra >> 12) & 7; 7371 ui5b dstvalue = m68k_dreg(r2); 7372 ui5r srcvalue = DecodeGetDstValue(); 7373 7374 if (extra & 0x800) { 7375 /* MULS.L - signed */ 7376 7377 si5b src1 = (si5b)srcvalue; 7378 si5b src2 = (si5b)dstvalue; 7379 blnr s1 = src1 < 0; 7380 blnr s2 = src2 < 0; 7381 blnr sr = s1 != s2; 7382 7383 /* ReportAbnormal("MULS.L"); */ 7384 /* used by Sys 7.5.5 boot extensions */ 7385 if (s1) { 7386 src1 = - src1; 7387 } 7388 if (s2) { 7389 src2 = - src2; 7390 } 7391 mul_unsigned((ui5b)src1, (ui5b)src2, &dst); 7392 if (sr) { 7393 Ui6r_Negate(&dst); 7394 } 7395 VFLG = CFLG = 0; 7396 ZFLG = Bool2Bit(Ui6r_IsZero(&dst)); 7397 NFLG = Bool2Bit(Ui6r_IsNeg(&dst)); 7398 7399 V_regs.LazyFlagKind = kLazyFlagsDefault; 7400 7401 if (extra & 0x400) { 7402 m68k_dreg(extra & 7) = dst.hi; 7403 } else { 7404 if ((dst.lo & 0x80000000) != 0) { 7405 if ((dst.hi & 0xffffffff) != 0xffffffff) { 7406 VFLG = 1; 7407 } 7408 } else { 7409 if (dst.hi != 0) { 7410 VFLG = 1; 7411 } 7412 } 7413 } 7414 } else { 7415 /* MULU.L - unsigned */ 7416 7417 /* ReportAbnormal("MULU.U"); */ 7418 /* Used by various Apps */ 7419 7420 mul_unsigned(srcvalue, dstvalue, &dst); 7421 7422 VFLG = CFLG = 0; 7423 ZFLG = Bool2Bit(Ui6r_IsZero(&dst)); 7424 NFLG = Bool2Bit(Ui6r_IsNeg(&dst)); 7425 7426 V_regs.LazyFlagKind = kLazyFlagsDefault; 7427 7428 if (extra & 0x400) { 7429 m68k_dreg(extra & 7) = dst.hi; 7430 } else { 7431 if (dst.hi != 0) { 7432 VFLG = 1; 7433 } 7434 } 7435 } 7436 m68k_dreg(r2) = dst.lo; 7437} 7438#endif 7439 7440#if Use68020 7441LOCALIPROC DoCodeDivL(void) 7442{ 7443 /* DIVU 0100110001mmmrrr 0rrr0s0000000rrr */ 7444 /* DIVS 0100110001mmmrrr 0rrr1s0000000rrr */ 7445 /* ReportAbnormal("DIVS/DIVU long"); */ 7446 ui6r0 v2; 7447 ui5b quot; 7448 ui5b rem; 7449 ui4b extra = nextiword(); 7450 ui5b rDr = extra & 7; 7451 ui5b rDq = (extra >> 12) & 7; 7452 ui5r src = (ui5b)(si5b)DecodeGetDstValue(); 7453 7454 if (src == 0) { 7455 Exception(5); 7456#if m68k_logExceptions 7457 dbglog_WriteNote("*** zero devide exception"); 7458#endif 7459 return; 7460 } 7461 if (0 != (extra & 0x0800)) { 7462 /* signed variant */ 7463 blnr sr; 7464 blnr s2; 7465 blnr s1 = ((si5b)src < 0); 7466 7467 v2.lo = (si5b)m68k_dreg(rDq); 7468 if (extra & 0x0400) { 7469 v2.hi = (si5b)m68k_dreg(rDr); 7470 } else { 7471 v2.hi = ((si5b)v2.lo) < 0 ? -1 : 0; 7472 } 7473 s2 = Ui6r_IsNeg(&v2); 7474 sr = (s1 != s2); 7475 if (s2) { 7476 Ui6r_Negate(&v2); 7477 } 7478 if (s1) { 7479 src = - src; 7480 } 7481 if (div_unsigned(&v2, src, &quot, &rem) 7482 || (sr ? quot > 0x80000000 : quot > 0x7fffffff)) 7483 { 7484 NeedDefaultLazyAllFlags(); 7485 7486 VFLG = NFLG = 1; 7487 CFLG = 0; 7488 } else { 7489 if (sr) { 7490 quot = - quot; 7491 } 7492 if (((si5b)rem < 0) != s2) { 7493 rem = - rem; 7494 } 7495 VFLG = CFLG = 0; 7496 ZFLG = Bool2Bit(((si5b)quot) == 0); 7497 NFLG = Bool2Bit(((si5b)quot) < 0); 7498 7499 V_regs.LazyFlagKind = kLazyFlagsDefault; 7500 7501 m68k_dreg(rDr) = rem; 7502 m68k_dreg(rDq) = quot; 7503 } 7504 } else { 7505 /* unsigned */ 7506 7507 v2.lo = (ui5b)m68k_dreg(rDq); 7508 if (extra & 0x400) { 7509 v2.hi = (ui5b)m68k_dreg(rDr); 7510 } else { 7511 v2.hi = 0; 7512 } 7513 if (div_unsigned(&v2, src, &quot, &rem)) { 7514 NeedDefaultLazyAllFlags(); 7515 7516 VFLG = NFLG = 1; 7517 CFLG = 0; 7518 } else { 7519 VFLG = CFLG = 0; 7520 ZFLG = Bool2Bit(((si5b)quot) == 0); 7521 NFLG = Bool2Bit(((si5b)quot) < 0); 7522 7523 V_regs.LazyFlagKind = kLazyFlagsDefault; 7524 7525 m68k_dreg(rDr) = rem; 7526 m68k_dreg(rDq) = quot; 7527 } 7528 } 7529} 7530#endif 7531 7532#if Use68020 7533LOCALIPROC DoMoveToControl(void) 7534{ 7535 if (0 == V_regs.s) { 7536 DoPrivilegeViolation(); 7537 } else { 7538 ui4b src = nextiword_nm(); 7539 int regno = (src >> 12) & 0x0F; 7540 ui5b v = V_regs.regs[regno]; 7541 7542 switch (src & 0x0FFF) { 7543 case 0x0000: 7544 V_regs.sfc = v & 7; 7545 /* ReportAbnormal("DoMoveToControl: sfc"); */ 7546 /* happens on entering macsbug */ 7547 break; 7548 case 0x0001: 7549 V_regs.dfc = v & 7; 7550 /* ReportAbnormal("DoMoveToControl: dfc"); */ 7551 break; 7552 case 0x0002: 7553 V_regs.cacr = v & 0x3; 7554 /* ReportAbnormal("DoMoveToControl: cacr"); */ 7555 /* used by Sys 7.5.5 boot */ 7556 break; 7557 case 0x0800: 7558 V_regs.usp = v; 7559 ReportAbnormalID(0x0113, "DoMoveToControl: usp"); 7560 break; 7561 case 0x0801: 7562 V_regs.vbr = v; 7563 /* ReportAbnormal("DoMoveToControl: vbr"); */ 7564 /* happens on entering macsbug */ 7565 break; 7566 case 0x0802: 7567 V_regs.caar = v &0xfc; 7568 /* ReportAbnormal("DoMoveToControl: caar"); */ 7569 /* happens on entering macsbug */ 7570 break; 7571 case 0x0803: 7572 V_regs.msp = v; 7573 if (V_regs.m == 1) { 7574 m68k_areg(7) = V_regs.msp; 7575 } 7576 /* ReportAbnormal("DoMoveToControl: msp"); */ 7577 /* happens on entering macsbug */ 7578 break; 7579 case 0x0804: 7580 V_regs.isp = v; 7581 if (V_regs.m == 0) { 7582 m68k_areg(7) = V_regs.isp; 7583 } 7584 ReportAbnormalID(0x0114, "DoMoveToControl: isp"); 7585 break; 7586 default: 7587 op_illg(); 7588 ReportAbnormalID(0x0115, 7589 "DoMoveToControl: unknown reg"); 7590 break; 7591 } 7592 } 7593} 7594#endif 7595 7596#if Use68020 7597LOCALIPROC DoMoveFromControl(void) 7598{ 7599 if (0 == V_regs.s) { 7600 DoPrivilegeViolation(); 7601 } else { 7602 ui5b v; 7603 ui4b src = nextiword_nm(); 7604 int regno = (src >> 12) & 0x0F; 7605 7606 switch (src & 0x0FFF) { 7607 case 0x0000: 7608 v = V_regs.sfc; 7609 /* ReportAbnormal("DoMoveFromControl: sfc"); */ 7610 /* happens on entering macsbug */ 7611 break; 7612 case 0x0001: 7613 v = V_regs.dfc; 7614 /* ReportAbnormal("DoMoveFromControl: dfc"); */ 7615 /* happens on entering macsbug */ 7616 break; 7617 case 0x0002: 7618 v = V_regs.cacr; 7619 /* ReportAbnormal("DoMoveFromControl: cacr"); */ 7620 /* used by Sys 7.5.5 boot */ 7621 break; 7622 case 0x0800: 7623 v = V_regs.usp; 7624 ReportAbnormalID(0x0116, "DoMoveFromControl: usp"); 7625 break; 7626 case 0x0801: 7627 v = V_regs.vbr; 7628 /* ReportAbnormal("DoMoveFromControl: vbr"); */ 7629 /* happens on entering macsbug */ 7630 break; 7631 case 0x0802: 7632 v = V_regs.caar; 7633 /* ReportAbnormal("DoMoveFromControl: caar"); */ 7634 /* happens on entering macsbug */ 7635 break; 7636 case 0x0803: 7637 v = (V_regs.m == 1) 7638 ? m68k_areg(7) 7639 : V_regs.msp; 7640 /* ReportAbnormal("DoMoveFromControl: msp"); */ 7641 /* happens on entering macsbug */ 7642 break; 7643 case 0x0804: 7644 v = (V_regs.m == 0) 7645 ? m68k_areg(7) 7646 : V_regs.isp; 7647 ReportAbnormalID(0x0117, "DoMoveFromControl: isp"); 7648 break; 7649 default: 7650 v = 0; 7651 ReportAbnormalID(0x0118, 7652 "DoMoveFromControl: unknown reg"); 7653 op_illg(); 7654 break; 7655 } 7656 V_regs.regs[regno] = v; 7657 } 7658} 7659#endif 7660 7661#if Use68020 7662LOCALIPROC DoCodeBkpt(void) 7663{ 7664 /* BKPT 0100100001001rrr */ 7665 ReportAbnormalID(0x0119, "BKPT instruction"); 7666 op_illg(); 7667} 7668#endif 7669 7670#if Use68020 7671LOCALIPROC DoCodeRtd(void) 7672{ 7673 /* Rtd 0100111001110100 */ 7674 ui5r NewPC = get_long(m68k_areg(7)); 7675 si5b offs = nextiSWord(); 7676 /* ReportAbnormal("RTD"); */ 7677 /* used by Sys 7.5.5 boot */ 7678 m68k_areg(7) += (4 + offs); 7679 m68k_setpc(NewPC); 7680} 7681#endif 7682 7683#if Use68020 7684LOCALIPROC DoCodeLinkL(void) 7685{ 7686 /* Link.L 0100100000001rrr */ 7687 7688 ui5r dstreg = V_regs.CurDecOpY.v[1].ArgDat; 7689 ui5r *dstp = &V_regs.regs[dstreg]; 7690 CPTR stackp = m68k_areg(7); 7691 7692 ReportAbnormalID(0x011A, "Link.L"); 7693 7694 stackp -= 4; 7695 m68k_areg(7) = stackp; /* only matters if dstreg == 7 + 8 */ 7696 put_long(stackp, *dstp); 7697 *dstp = stackp; 7698 m68k_areg(7) += (si5b)nextilong(); 7699} 7700#endif 7701 7702#if Use68020 7703LOCALPROC DoCodeTRAPcc_t(void) 7704{ 7705 ReportAbnormalID(0x011B, "TRAPcc trapping"); 7706 Exception(7); 7707 /* pc pushed onto stack wrong */ 7708} 7709#endif 7710 7711#if Use68020 7712LOCALPROC DoCodeTRAPcc_f(void) 7713{ 7714} 7715#endif 7716 7717#if Use68020 7718LOCALIPROC DoCodeTRAPcc(void) 7719{ 7720 /* TRAPcc 0101cccc11111sss */ 7721 /* ReportAbnormal("TRAPcc"); */ 7722 switch (V_regs.CurDecOpY.v[1].ArgDat) { 7723 case 2: 7724 ReportAbnormalID(0x011C, "TRAPcc word data"); 7725 SkipiWord(); 7726 break; 7727 case 3: 7728 ReportAbnormalID(0x011D, "TRAPcc long data"); 7729 SkipiLong(); 7730 break; 7731 case 4: 7732 /* ReportAbnormal("TRAPcc no data"); */ 7733 /* no optional data */ 7734 break; 7735 default: 7736 ReportAbnormalID(0x011E, "TRAPcc illegal format"); 7737 op_illg(); 7738 break; 7739 } 7740 cctrue(DoCodeTRAPcc_t, DoCodeTRAPcc_f); 7741} 7742#endif 7743 7744#if Use68020 7745LOCALIPROC DoCodePack(void) 7746{ 7747 ui5r offs = nextiSWord(); 7748 ui5r val = DecodeGetSrcValue(); 7749 7750 ReportAbnormalID(0x011F, "PACK"); 7751 7752 val += offs; 7753 val = ((val >> 4) & 0xf0) | (val & 0xf); 7754 7755 DecodeSetDstValue(val); 7756} 7757#endif 7758 7759#if Use68020 7760LOCALIPROC DoCodeUnpk(void) 7761{ 7762 ui5r offs = nextiSWord(); 7763 ui5r val = DecodeGetSrcValue(); 7764 7765 ReportAbnormalID(0x0120, "UNPK"); 7766 7767 val = (((val & 0xF0) << 4) | (val & 0x0F)) + offs; 7768 7769 DecodeSetDstValue(val); 7770} 7771#endif 7772 7773#if Use68020 7774LOCALIPROC DoBitField(void) 7775{ 7776 ui5b tmp; 7777 ui5b newtmp; 7778 CPTR dsta; 7779 ui5b bf0; 7780 ui3b bf1; 7781 ui5b dstreg = V_regs.CurDecOpY.v[1].ArgDat; 7782 ui4b extra = nextiword(); 7783 ui5b offset = ((extra & 0x0800) != 0) 7784 ? m68k_dreg((extra >> 6) & 7) 7785 : ((extra >> 6) & 0x1f); 7786 ui5b width = ((extra & 0x0020) != 0) 7787 ? m68k_dreg(extra & 7) 7788 : extra; 7789 ui3b bfa[5]; 7790 ui5b offwid; 7791 7792 /* ReportAbnormal("Bit Field operator"); */ 7793 /* width = ((width - 1) & 0x1f) + 1; */ /* 0 -> 32 */ 7794 width &= 0x001F; /* except width == 0 really means 32 */ 7795 if (V_regs.CurDecOpY.v[0].AMd == 0) { 7796 bf0 = m68k_dreg(dstreg); 7797 offset &= 0x1f; 7798 tmp = bf0; 7799 if (0 != offset) { 7800 tmp = (tmp << offset) | (tmp >> (32 - offset)); 7801 } 7802 } else { 7803 /* 7804 V_regs.ArgKind == AKMemory, 7805 otherwise illegal and don't get here 7806 */ 7807 dsta = DecodeDst(); 7808 dsta += Ui5rASR(offset, 3); 7809 offset &= 7; 7810 offwid = offset + ((width == 0) ? 32 : width); 7811 7812 /* if (offwid > 0) */ { 7813 bf1 = get_byte(dsta); 7814 bfa[0] = bf1; 7815 tmp = ((ui5b)bf1) << (24 + offset); 7816 } 7817 if (offwid > 8) { 7818 bf1 = get_byte(dsta + 1); 7819 bfa[1] = bf1; 7820 tmp |= ((ui5b)bf1) << (16 + offset); 7821 } 7822 if (offwid > 16) { 7823 bf1 = get_byte(dsta + 2); 7824 bfa[2] = bf1; 7825 tmp |= ((ui5r)bf1) << (8 + offset); 7826 } 7827 if (offwid > 24) { 7828 bf1 = get_byte(dsta + 3); 7829 bfa[3] = bf1; 7830 tmp |= ((ui5r)bf1) << (offset); 7831 } 7832 if (offwid > 32) { 7833 bf1 = get_byte(dsta + 4); 7834 bfa[4] = bf1; 7835 tmp |= ((ui5r)bf1) >> (8 - offset); 7836 } 7837 } 7838 7839 NFLG = Bool2Bit(((si5b)tmp) < 0); 7840 if (width != 0) { 7841 tmp >>= (32 - width); 7842 } 7843 ZFLG = (tmp == 0); 7844 VFLG = 0; 7845 CFLG = 0; 7846 7847 V_regs.LazyFlagKind = kLazyFlagsDefault; 7848 7849 newtmp = tmp; 7850 7851 switch (V_regs.CurDecOpY.v[0].ArgDat) { 7852 case 0: /* BFTST */ 7853 /* do nothing */ 7854 break; 7855 case 1: /* BFEXTU */ 7856 m68k_dreg((extra >> 12) & 7) = tmp; 7857 break; 7858 case 2: /* BFCHG */ 7859 newtmp = ~ newtmp; 7860 if (width != 0) { 7861 newtmp &= ((1 << width) - 1); 7862 } 7863 break; 7864 case 3: /* BFEXTS */ 7865 if (NFLG != 0) { 7866 m68k_dreg((extra >> 12) & 7) = tmp 7867 | ((width == 0) ? 0 : (-1 << width)); 7868 } else { 7869 m68k_dreg((extra >> 12) & 7) = tmp; 7870 } 7871 break; 7872 case 4: /* BFCLR */ 7873 newtmp = 0; 7874 break; 7875 case 5: /* BFFFO */ 7876 { 7877 ui5b mask = 1 << ((width == 0) ? 31 : (width - 1)); 7878 ui5r i = offset; 7879 7880 while ((0 != mask) && (0 == (tmp & mask))) { 7881 mask >>= 1; 7882 i++; 7883 } 7884 m68k_dreg((extra >> 12) & 7) = i; 7885 } 7886 break; 7887 case 6: /* BFSET */ 7888 newtmp = (width == 0) ? ~ 0 : ((1 << width) - 1); 7889 break; 7890 case 7: /* BFINS */ 7891 newtmp = m68k_dreg((extra >> 12) & 7); 7892 if (width != 0) { 7893 newtmp &= ((1 << width) - 1); 7894 } 7895 7896 /* 7897 flags set from new value 7898 unlike BFSET/BFCLR/BFCHG 7899 */ 7900 { 7901 ui5b t = newtmp; 7902 7903 if (width != 0) { 7904 t <<= (32 - width); 7905 } 7906 7907 NFLG = Bool2Bit(((si5b)t) < 0); 7908 ZFLG = (0 == t); 7909 } 7910 break; 7911 } 7912 7913 if (newtmp != tmp) { 7914 7915 if (width != 0) { 7916 newtmp <<= (32 - width); 7917 } 7918 7919 if (V_regs.CurDecOpY.v[0].AMd == 0) { 7920 ui5b mask = ~ 0; 7921 7922 if (width != 0) { 7923 mask <<= (32 - width); 7924 } 7925 7926 if (0 != offset) { 7927 newtmp = (newtmp >> offset) | (newtmp << (32 - offset)); 7928 mask = (mask >> offset) | (mask << (32 - offset)); 7929 } 7930 7931 bf0 = (bf0 & ~ mask) | (newtmp); 7932 m68k_dreg(dstreg) = bf0; 7933 } else { 7934 7935 /* if (offwid > 0) */ { 7936 ui3b mask = ~ (0xFF >> offset); 7937 7938 bf1 = newtmp >> (24 + offset); 7939 if (offwid < 8) { 7940 mask |= (0xFF >> offwid); 7941 } 7942 if (mask != 0) { 7943 bf1 |= bfa[0] & mask; 7944 } 7945 put_byte(dsta + 0, bf1); 7946 } 7947 if (offwid > 8) { 7948 bf1 = newtmp >> (16 + offset); 7949 if (offwid < 16) { 7950 bf1 |= (bfa[1] & (0xFF >> (offwid - 8))); 7951 } 7952 put_byte(dsta + 1, bf1); 7953 } 7954 if (offwid > 16) { 7955 bf1 = newtmp >> (8 + offset); 7956 if (offwid < 24) { 7957 bf1 |= (bfa[2] & (0xFF >> (offwid - 16))); 7958 } 7959 put_byte(dsta + 2, bf1); 7960 } 7961 if (offwid > 24) { 7962 bf1 = newtmp >> (offset); 7963 if (offwid < 32) { 7964 bf1 |= (bfa[3] & (0xFF >> (offwid - 24))); 7965 } 7966 put_byte(dsta + 3, bf1); 7967 } 7968 if (offwid > 32) { 7969 bf1 = newtmp << (8 - offset); 7970 bf1 |= (bfa[4] & (0xFF >> (offwid - 32))); 7971 put_byte(dsta + 4, bf1); 7972 } 7973 } 7974 } 7975} 7976#endif 7977 7978#if EmMMU | EmFPU 7979LOCALFUNC blnr DecodeModeRegister(ui5b sz) 7980{ 7981 blnr IsOk; 7982 ui4r Dat = V_regs.CurDecOpY.v[0].ArgDat; 7983 ui4r themode = (Dat >> 3) & 7; 7984 ui4r thereg = Dat & 7; 7985 7986 switch (themode) { 7987 case 0 : 7988 V_regs.ArgKind = AKRegister; 7989 V_regs.ArgAddr.rga = &V_regs.regs[thereg]; 7990 IsOk = trueblnr; 7991 break; 7992 case 1 : 7993 V_regs.ArgKind = AKRegister; 7994 V_regs.ArgAddr.rga = &V_regs.regs[thereg + 8]; 7995 IsOk = trueblnr; 7996 break; 7997 case 2 : 7998 V_regs.ArgKind = AKMemory; 7999 V_regs.ArgAddr.mem = m68k_areg(thereg); 8000 IsOk = trueblnr; 8001 break; 8002 case 3 : 8003 V_regs.ArgKind = AKMemory; 8004 V_regs.ArgAddr.mem = m68k_areg(thereg); 8005 if ((thereg == 7) && (sz == 1)) { 8006 m68k_areg(thereg) += 2; 8007 } else { 8008 m68k_areg(thereg) += sz; 8009 } 8010 IsOk = trueblnr; 8011 break; 8012 case 4 : 8013 V_regs.ArgKind = AKMemory; 8014 if ((thereg == 7) && (sz == 1)) { 8015 m68k_areg(thereg) -= 2; 8016 } else { 8017 m68k_areg(thereg) -= sz; 8018 } 8019 V_regs.ArgAddr.mem = m68k_areg(thereg); 8020 IsOk = trueblnr; 8021 break; 8022 case 5 : 8023 V_regs.ArgKind = AKMemory; 8024 V_regs.ArgAddr.mem = m68k_areg(thereg) 8025 + nextiSWord(); 8026 IsOk = trueblnr; 8027 break; 8028 case 6 : 8029 V_regs.ArgKind = AKMemory; 8030 V_regs.ArgAddr.mem = get_disp_ea(m68k_areg(thereg)); 8031 IsOk = trueblnr; 8032 break; 8033 case 7 : 8034 switch (thereg) { 8035 case 0 : 8036 V_regs.ArgKind = AKMemory; 8037 V_regs.ArgAddr.mem = nextiSWord(); 8038 IsOk = trueblnr; 8039 break; 8040 case 1 : 8041 V_regs.ArgKind = AKMemory; 8042 V_regs.ArgAddr.mem = nextilong(); 8043 IsOk = trueblnr; 8044 break; 8045 case 2 : 8046 V_regs.ArgKind = AKMemory; 8047 V_regs.ArgAddr.mem = m68k_getpc(); 8048 V_regs.ArgAddr.mem += nextiSWord(); 8049 IsOk = trueblnr; 8050 break; 8051 case 3 : 8052 V_regs.ArgKind = AKMemory; 8053 V_regs.ArgAddr.mem = get_disp_ea(m68k_getpc()); 8054 IsOk = trueblnr; 8055 break; 8056 case 4 : 8057 V_regs.ArgKind = AKMemory; 8058 V_regs.ArgAddr.mem = m68k_getpc(); 8059 if (sz == 1) { 8060 ++V_regs.ArgAddr.mem; 8061 } 8062 m68k_setpc(V_regs.ArgAddr.mem + sz); 8063 IsOk = trueblnr; 8064 break; 8065 default: 8066 IsOk = falseblnr; 8067 break; 8068 } 8069 break; 8070 default: 8071 IsOk = falseblnr; 8072 break; 8073 } 8074 8075 return IsOk; 8076} 8077#endif 8078 8079#if EmMMU | EmFPU 8080LOCALFUNC ui5r GetArgValueL(void) 8081{ 8082 ui5r v; 8083 8084 if (AKMemory == V_regs.ArgKind) { 8085 v = get_long(V_regs.ArgAddr.mem); 8086 } else { 8087 /* must be AKRegister */ 8088 v = ui5r_FromSLong(*V_regs.ArgAddr.rga); 8089 } 8090 8091 return v; 8092} 8093#endif 8094 8095#if EmMMU | EmFPU 8096LOCALFUNC ui5r GetArgValueW(void) 8097{ 8098 ui5r v; 8099 8100 if (AKMemory == V_regs.ArgKind) { 8101 v = get_word(V_regs.ArgAddr.mem); 8102 } else { 8103 /* must be AKRegister */ 8104 v = ui5r_FromSWord(*V_regs.ArgAddr.rga); 8105 } 8106 8107 return v; 8108} 8109#endif 8110 8111#if EmMMU | EmFPU 8112LOCALFUNC ui5r GetArgValueB(void) 8113{ 8114 ui5r v; 8115 8116 if (AKMemory == V_regs.ArgKind) { 8117 v = get_byte(V_regs.ArgAddr.mem); 8118 } else { 8119 /* must be AKRegister */ 8120 v = ui5r_FromSByte(*V_regs.ArgAddr.rga); 8121 } 8122 8123 return v; 8124} 8125#endif 8126 8127#if EmMMU | EmFPU 8128LOCALPROC SetArgValueL(ui5r v) 8129{ 8130 if (AKMemory == V_regs.ArgKind) { 8131 put_long(V_regs.ArgAddr.mem, v); 8132 } else { 8133 /* must be AKRegister */ 8134 *V_regs.ArgAddr.rga = v; 8135 } 8136} 8137#endif 8138 8139#if EmMMU | EmFPU 8140LOCALPROC SetArgValueW(ui5r v) 8141{ 8142 if (AKMemory == V_regs.ArgKind) { 8143 put_word(V_regs.ArgAddr.mem, v); 8144 } else { 8145 /* must be AKRegister */ 8146 *V_regs.ArgAddr.rga = 8147 (*V_regs.ArgAddr.rga & ~ 0xffff) | ((v) & 0xffff); 8148 } 8149} 8150#endif 8151 8152#if EmMMU | EmFPU 8153LOCALPROC SetArgValueB(ui5r v) 8154{ 8155 if (AKMemory == V_regs.ArgKind) { 8156 put_byte(V_regs.ArgAddr.mem, v); 8157 } else { 8158 /* must be AKRegister */ 8159 *V_regs.ArgAddr.rga = 8160 (*V_regs.ArgAddr.rga & ~ 0xff) | ((v) & 0xff); 8161 } 8162} 8163#endif 8164 8165 8166#if EmMMU 8167LOCALIPROC DoCodeMMU(void) 8168{ 8169 /* 8170 Emulate enough of MMU for System 7.5.5 universal 8171 to boot on Mac Plus 68020. There is one 8172 spurious "PMOVE TC, (A0)". 8173 And implement a few more PMOVE operations seen 8174 when running Disk Copy 6.3.3 and MacsBug. 8175 */ 8176 ui4r opcode = ((ui4r)(V_regs.CurDecOpY.v[0].AMd) << 8) 8177 | V_regs.CurDecOpY.v[0].ArgDat; 8178 if (opcode == 0xF010) { 8179 ui4b ew = (int)nextiword_nm(); 8180 if (ew == 0x4200) { 8181 /* PMOVE TC, (A0) */ 8182 /* fprintf(stderr, "0xF010 0x4200\n"); */ 8183 if (DecodeModeRegister(4)) { 8184 SetArgValueL(0); 8185 return; 8186 } 8187 } else if ((ew == 0x4E00) || (ew == 0x4A00)) { 8188 /* PMOVE CRP, (A0) and PMOVE SRP, (A0) */ 8189 /* fprintf(stderr, "0xF010 %x\n", ew); */ 8190 if (DecodeModeRegister(4)) { 8191 SetArgValueL(0x7FFF0001); 8192 V_regs.ArgAddr.mem += 4; 8193 SetArgValueL(0); 8194 return; 8195 } 8196 } else if (ew == 0x6200) { 8197 /* PMOVE MMUSR, (A0) */ 8198 /* fprintf(stderr, "0xF010 %x\n", ew); */ 8199 if (DecodeModeRegister(2)) { 8200 SetArgValueW(0); 8201 return; 8202 } 8203 } 8204 /* fprintf(stderr, "extensions %x\n", ew); */ 8205 BackupPC(); 8206 } 8207 /* fprintf(stderr, "opcode %x\n", (int)opcode); */ 8208 ReportAbnormalID(0x0121, "MMU op"); 8209 DoCodeFdefault(); 8210} 8211#endif 8212 8213#if EmFPU 8214 8215#include "FPMATHEM.h" 8216#include "FPCPEMDV.h" 8217 8218#endif 8219 8220#if HaveGlbReg 8221LOCALPROC Em_Swap(void) 8222{ 8223#ifdef r_pc_p 8224 { 8225 ui3p t = g_pc_p; 8226 g_pc_p = regs.pc_p; 8227 regs.pc_p = t; 8228 } 8229#endif 8230#ifdef r_MaxCyclesToGo 8231 { 8232 si5rr t = g_MaxCyclesToGo; 8233 g_MaxCyclesToGo = regs.MaxCyclesToGo; 8234 regs.MaxCyclesToGo = t; 8235 } 8236#endif 8237#ifdef r_pc_pHi 8238 { 8239 ui3p t = g_pc_pHi; 8240 g_pc_pHi = regs.pc_pHi; 8241 regs.pc_pHi = t; 8242 } 8243#endif 8244#ifdef r_regs 8245 { 8246 struct regstruct *t = g_regs; 8247 g_regs = regs.save_regs; 8248 regs.save_regs = t; 8249 } 8250#endif 8251} 8252#endif 8253 8254#if HaveGlbReg 8255#define Em_Enter Em_Swap 8256#else 8257#define Em_Enter() 8258#endif 8259 8260#if HaveGlbReg 8261#define Em_Exit Em_Swap 8262#else 8263#define Em_Exit() 8264#endif 8265 8266#if HaveGlbReg 8267LOCALFUNC blnr LocalMemAccessNtfy(ATTep pT) 8268{ 8269 blnr v; 8270 8271 Em_Exit(); 8272 v = MemAccessNtfy(pT); 8273 Em_Enter(); 8274 8275 return v; 8276} 8277#else 8278#define LocalMemAccessNtfy MemAccessNtfy 8279#endif 8280 8281#if HaveGlbReg 8282LOCALFUNC ui5b LocalMMDV_Access(ATTep p, ui5b Data, 8283 blnr WriteMem, blnr ByteSize, CPTR addr) 8284{ 8285 ui5b v; 8286 8287 Em_Exit(); 8288 v = MMDV_Access(p, Data, WriteMem, ByteSize, addr); 8289 Em_Enter(); 8290 8291 return v; 8292} 8293#else 8294#define LocalMMDV_Access MMDV_Access 8295#endif 8296 8297LOCALPROC local_customreset(void) 8298{ 8299 Em_Exit(); 8300 customreset(); 8301 Em_Enter(); 8302} 8303 8304LOCALFUNC ATTep LocalFindATTel(CPTR addr) 8305{ 8306 ATTep prev; 8307 ATTep p; 8308 8309 p = V_regs.HeadATTel; 8310 if ((addr & p->cmpmask) != p->cmpvalu) { 8311 do { 8312 prev = p; 8313 p = p->Next; 8314 } while ((addr & p->cmpmask) != p->cmpvalu); 8315 8316 { 8317 ATTep next = p->Next; 8318 8319 if (nullpr == next) { 8320 /* don't move the end guard */ 8321 } else { 8322 /* move to first */ 8323 prev->Next = next; 8324 p->Next = V_regs.HeadATTel; 8325 V_regs.HeadATTel = p; 8326 } 8327 } 8328 } 8329 8330 return p; 8331} 8332 8333LOCALPROC SetUpMATC( 8334 MATCp CurMATC, 8335 ATTep p) 8336{ 8337 CurMATC->cmpmask = p->cmpmask; 8338 CurMATC->usemask = p->usemask; 8339 CurMATC->cmpvalu = p->cmpvalu; 8340 CurMATC->usebase = p->usebase; 8341} 8342 8343LOCALFUNC ui5r my_reg_call get_byte_ext(CPTR addr) 8344{ 8345 ATTep p; 8346 ui3p m; 8347 ui5r AccFlags; 8348 ui5r Data; 8349 8350Label_Retry: 8351 p = LocalFindATTel(addr); 8352 AccFlags = p->Access; 8353 8354 if (0 != (AccFlags & kATTA_readreadymask)) { 8355 SetUpMATC(&V_regs.MATCrdB, p); 8356 m = p->usebase + (addr & p->usemask); 8357 8358 Data = *m; 8359 } else if (0 != (AccFlags & kATTA_mmdvmask)) { 8360 Data = LocalMMDV_Access(p, 0, falseblnr, trueblnr, addr); 8361 } else if (0 != (AccFlags & kATTA_ntfymask)) { 8362 if (LocalMemAccessNtfy(p)) { 8363 goto Label_Retry; 8364 } else { 8365 Data = 0; /* fail */ 8366 } 8367 } else { 8368 Data = 0; /* fail */ 8369 } 8370 8371 return ui5r_FromSByte(Data); 8372} 8373 8374LOCALPROC my_reg_call put_byte_ext(CPTR addr, ui5r b) 8375{ 8376 ATTep p; 8377 ui3p m; 8378 ui5r AccFlags; 8379 8380Label_Retry: 8381 p = LocalFindATTel(addr); 8382 AccFlags = p->Access; 8383 8384 if (0 != (AccFlags & kATTA_writereadymask)) { 8385 SetUpMATC(&V_regs.MATCwrB, p); 8386 m = p->usebase + (addr & p->usemask); 8387 *m = b; 8388 } else if (0 != (AccFlags & kATTA_mmdvmask)) { 8389 (void) LocalMMDV_Access(p, b & 0x00FF, 8390 trueblnr, trueblnr, addr); 8391 } else if (0 != (AccFlags & kATTA_ntfymask)) { 8392 if (LocalMemAccessNtfy(p)) { 8393 goto Label_Retry; 8394 } else { 8395 /* fail */ 8396 } 8397 } else { 8398 /* fail */ 8399 } 8400} 8401 8402LOCALFUNC ui5r my_reg_call get_word_ext(CPTR addr) 8403{ 8404 ui5r Data; 8405 8406 if (0 != (addr & 0x01)) { 8407 ui5r hi = get_byte(addr); 8408 ui5r lo = get_byte(addr + 1); 8409 Data = ((hi << 8) & 0x0000FF00) 8410 | (lo & 0x000000FF); 8411 } else { 8412 ATTep p; 8413 ui3p m; 8414 ui5r AccFlags; 8415 8416Label_Retry: 8417 p = LocalFindATTel(addr); 8418 AccFlags = p->Access; 8419 8420 if (0 != (AccFlags & kATTA_readreadymask)) { 8421 SetUpMATC(&V_regs.MATCrdW, p); 8422 V_regs.MATCrdW.cmpmask |= 0x01; 8423 m = p->usebase + (addr & p->usemask); 8424 Data = do_get_mem_word(m); 8425 } else if (0 != (AccFlags & kATTA_mmdvmask)) { 8426 Data = LocalMMDV_Access(p, 0, falseblnr, falseblnr, addr); 8427 } else if (0 != (AccFlags & kATTA_ntfymask)) { 8428 if (LocalMemAccessNtfy(p)) { 8429 goto Label_Retry; 8430 } else { 8431 Data = 0; /* fail */ 8432 } 8433 } else { 8434 Data = 0; /* fail */ 8435 } 8436 } 8437 8438 return ui5r_FromSWord(Data); 8439} 8440 8441LOCALPROC my_reg_call put_word_ext(CPTR addr, ui5r w) 8442{ 8443 if (0 != (addr & 0x01)) { 8444 put_byte(addr, w >> 8); 8445 put_byte(addr + 1, w); 8446 } else { 8447 ATTep p; 8448 ui3p m; 8449 ui5r AccFlags; 8450 8451Label_Retry: 8452 p = LocalFindATTel(addr); 8453 AccFlags = p->Access; 8454 8455 if (0 != (AccFlags & kATTA_writereadymask)) { 8456 SetUpMATC(&V_regs.MATCwrW, p); 8457 V_regs.MATCwrW.cmpmask |= 0x01; 8458 m = p->usebase + (addr & p->usemask); 8459 do_put_mem_word(m, w); 8460 } else if (0 != (AccFlags & kATTA_mmdvmask)) { 8461 (void) LocalMMDV_Access(p, w & 0x0000FFFF, 8462 trueblnr, falseblnr, addr); 8463 } else if (0 != (AccFlags & kATTA_ntfymask)) { 8464 if (LocalMemAccessNtfy(p)) { 8465 goto Label_Retry; 8466 } else { 8467 /* fail */ 8468 } 8469 } else { 8470 /* fail */ 8471 } 8472 } 8473} 8474 8475LOCALFUNC ui5r my_reg_call get_long_misaligned_ext(CPTR addr) 8476{ 8477 ui5r hi = get_word(addr); 8478 ui5r lo = get_word(addr + 2); 8479 ui5r Data = ((hi << 16) & 0xFFFF0000) 8480 | (lo & 0x0000FFFF); 8481 8482 return ui5r_FromSLong(Data); 8483} 8484 8485LOCALPROC my_reg_call put_long_misaligned_ext(CPTR addr, ui5r l) 8486{ 8487 put_word(addr, l >> 16); 8488 put_word(addr + 2, l); 8489} 8490 8491#if FasterAlignedL 8492LOCALFUNC ui5r my_reg_call get_long_ext(CPTR addr) 8493{ 8494 ui5r Data; 8495 8496 if (0 != (addr & 0x03)) { 8497 ui5r hi = get_word(addr); 8498 ui5r lo = get_word(addr + 2); 8499 Data = ((hi << 16) & 0xFFFF0000) 8500 | (lo & 0x0000FFFF); 8501 } else { 8502 ATTep p; 8503 ui3p m; 8504 ui5r AccFlags; 8505 8506Label_Retry: 8507 p = LocalFindATTel(addr); 8508 AccFlags = p->Access; 8509 8510 if (0 != (AccFlags & kATTA_readreadymask)) { 8511 SetUpMATC(&V_regs.MATCrdL, p); 8512 V_regs.MATCrdL.cmpmask |= 0x03; 8513 m = p->usebase + (addr & p->usemask); 8514 Data = do_get_mem_long(m); 8515 } else if (0 != (AccFlags & kATTA_mmdvmask)) { 8516 ui5r hi = LocalMMDV_Access(p, 0, 8517 falseblnr, falseblnr, addr); 8518 ui5r lo = LocalMMDV_Access(p, 0, 8519 falseblnr, falseblnr, addr + 2); 8520 Data = ((hi << 16) & 0xFFFF0000) 8521 | (lo & 0x0000FFFF); 8522 } else if (0 != (AccFlags & kATTA_ntfymask)) { 8523 if (LocalMemAccessNtfy(p)) { 8524 goto Label_Retry; 8525 } else { 8526 Data = 0; /* fail */ 8527 } 8528 } else { 8529 Data = 0; /* fail */ 8530 } 8531 } 8532 8533 return ui5r_FromSLong(Data); 8534} 8535#endif 8536 8537#if FasterAlignedL 8538LOCALPROC my_reg_call put_long_ext(CPTR addr, ui5r l) 8539{ 8540 if (0 != (addr & 0x03)) { 8541 put_word(addr, l >> 16); 8542 put_word(addr + 2, l); 8543 } else { 8544 ATTep p; 8545 ui3p m; 8546 ui5r AccFlags; 8547 8548Label_Retry: 8549 p = LocalFindATTel(addr); 8550 AccFlags = p->Access; 8551 8552 if (0 != (AccFlags & kATTA_writereadymask)) { 8553 SetUpMATC(&V_regs.MATCwrL, p); 8554 V_regs.MATCwrL.cmpmask |= 0x03; 8555 m = p->usebase + (addr & p->usemask); 8556 do_put_mem_long(m, l); 8557 } else if (0 != (AccFlags & kATTA_mmdvmask)) { 8558 (void) LocalMMDV_Access(p, (l >> 16) & 0x0000FFFF, 8559 trueblnr, falseblnr, addr); 8560 (void) LocalMMDV_Access(p, l & 0x0000FFFF, 8561 trueblnr, falseblnr, addr + 2); 8562 } else if (0 != (AccFlags & kATTA_ntfymask)) { 8563 if (LocalMemAccessNtfy(p)) { 8564 goto Label_Retry; 8565 } else { 8566 /* fail */ 8567 } 8568 } else { 8569 /* fail */ 8570 } 8571 } 8572} 8573#endif 8574 8575LOCALPROC Recalc_PC_Block(void) 8576{ 8577 ATTep p; 8578 CPTR curpc = m68k_getpc(); 8579 8580Label_Retry: 8581 p = LocalFindATTel(curpc); 8582 if (my_cond_rare(0 == (p->Access & kATTA_readreadymask))) { 8583 if (0 != (p->Access & kATTA_ntfymask)) { 8584 if (LocalMemAccessNtfy(p)) { 8585 goto Label_Retry; 8586 } 8587 } 8588 /* in trouble if get here */ 8589#if ExtraAbnormalReports 8590 ReportAbnormalID(0x0122, "Recalc_PC_Block fails"); 8591 /* happens on Restart */ 8592#endif 8593 8594 V_regs.pc_pLo = V_regs.fakeword; 8595 V_pc_p = V_regs.pc_pLo; 8596 V_pc_pHi = V_regs.pc_pLo + 2; 8597 V_regs.pc = curpc; 8598 } else { 8599 ui5r m2 = p->usemask & ~ p->cmpmask; 8600 m2 = m2 & ~ (m2 + 1); 8601 8602 V_pc_p = p->usebase + (curpc & p->usemask); 8603 V_regs.pc_pLo = V_pc_p - (curpc & m2); 8604 V_pc_pHi = V_regs.pc_pLo + m2 + 1; 8605 V_regs.pc = curpc - (V_pc_p - V_regs.pc_pLo); 8606 } 8607} 8608 8609LOCALFUNC ui5r my_reg_call Recalc_PC_BlockReturnUi5r(ui5r v) 8610{ 8611 /* 8612 Used to prevent compiler from saving 8613 register on the stack in calling 8614 functions, when Recalc_PC_Block isn't being called. 8615 */ 8616 Recalc_PC_Block(); 8617 8618 return v; 8619} 8620 8621LOCALFUNC ui5r nextilong_ext(void) 8622{ 8623 ui5r r; 8624 8625 V_pc_p -= 4; 8626 8627 { 8628 ui5r hi = nextiword(); 8629 ui5r lo = nextiword(); 8630 r = ((hi << 16) & 0xFFFF0000) 8631 | (lo & 0x0000FFFF); 8632 } 8633 8634 return r; 8635} 8636 8637LOCALPROC DoCheckExternalInterruptPending(void) 8638{ 8639 ui3r level = *V_regs.fIPL; 8640 if ((level > V_regs.intmask) || (level == 7)) { 8641#if WantCloserCyc 8642 V_MaxCyclesToGo -= 8643 (44 * kCycleScale + 5 * RdAvgXtraCyc + 3 * WrAvgXtraCyc); 8644#endif 8645 Exception(24 + level); 8646 V_regs.intmask = level; 8647 } 8648} 8649 8650LOCALPROC do_trace(void) 8651{ 8652 V_regs.TracePending = trueblnr; 8653 NeedToGetOut(); 8654} 8655 8656GLOBALPROC m68k_go_nCycles(ui5b n) 8657{ 8658 Em_Enter(); 8659 V_MaxCyclesToGo += (n + V_regs.ResidualCycles); 8660 while (V_MaxCyclesToGo > 0) { 8661 8662#if 0 8663 if (V_regs.ResetPending) { 8664 m68k_DoReset(); 8665 } 8666#endif 8667 if (V_regs.TracePending) { 8668#if WantCloserCyc 8669 V_MaxCyclesToGo -= (34 * kCycleScale 8670 + 4 * RdAvgXtraCyc + 3 * WrAvgXtraCyc); 8671#endif 8672 Exception(9); 8673 } 8674 if (V_regs.ExternalInterruptPending) { 8675 V_regs.ExternalInterruptPending = falseblnr; 8676 DoCheckExternalInterruptPending(); 8677 } 8678 if (V_regs.t1 != 0) { 8679 do_trace(); 8680 } 8681 m68k_go_MaxCycles(); 8682 V_MaxCyclesToGo += V_regs.MoreCyclesToGo; 8683 V_regs.MoreCyclesToGo = 0; 8684 } 8685 8686 V_regs.ResidualCycles = V_MaxCyclesToGo; 8687 V_MaxCyclesToGo = 0; 8688 Em_Exit(); 8689} 8690 8691GLOBALFUNC si5r GetCyclesRemaining(void) 8692{ 8693 si5r v; 8694 8695 Em_Enter(); 8696 v = V_regs.MoreCyclesToGo + V_MaxCyclesToGo; 8697 Em_Exit(); 8698 8699 return v; 8700} 8701 8702GLOBALPROC SetCyclesRemaining(si5r n) 8703{ 8704 Em_Enter(); 8705 8706 if (V_MaxCyclesToGo >= n) { 8707 V_regs.MoreCyclesToGo = 0; 8708 V_MaxCyclesToGo = n; 8709 } else { 8710 V_regs.MoreCyclesToGo = n - V_MaxCyclesToGo; 8711 } 8712 8713 Em_Exit(); 8714} 8715 8716GLOBALFUNC ATTep FindATTel(CPTR addr) 8717{ 8718 ATTep v; 8719 8720 Em_Enter(); 8721 v = LocalFindATTel(addr); 8722 Em_Exit(); 8723 8724 return v; 8725} 8726 8727GLOBALFUNC ui3r get_vm_byte(CPTR addr) 8728{ 8729 ui3r v; 8730 8731 Em_Enter(); 8732 v = (ui3b) get_byte(addr); 8733 Em_Exit(); 8734 8735 return v; 8736} 8737 8738GLOBALFUNC ui4r get_vm_word(CPTR addr) 8739{ 8740 ui4r v; 8741 8742 Em_Enter(); 8743 v = (ui4b) get_word(addr); 8744 Em_Exit(); 8745 8746 return v; 8747} 8748 8749GLOBALFUNC ui5r get_vm_long(CPTR addr) 8750{ 8751 ui5r v; 8752 8753 Em_Enter(); 8754 v = (ui5b) get_long(addr); 8755 Em_Exit(); 8756 8757 return v; 8758} 8759 8760GLOBALPROC put_vm_byte(CPTR addr, ui3r b) 8761{ 8762 Em_Enter(); 8763 put_byte(addr, ui5r_FromSByte(b)); 8764 Em_Exit(); 8765} 8766 8767GLOBALPROC put_vm_word(CPTR addr, ui4r w) 8768{ 8769 Em_Enter(); 8770 put_word(addr, ui5r_FromSWord(w)); 8771 Em_Exit(); 8772} 8773 8774GLOBALPROC put_vm_long(CPTR addr, ui5r l) 8775{ 8776 Em_Enter(); 8777 put_long(addr, ui5r_FromSLong(l)); 8778 Em_Exit(); 8779} 8780 8781GLOBALPROC SetHeadATTel(ATTep p) 8782{ 8783 Em_Enter(); 8784 8785 V_regs.MATCrdB.cmpmask = 0; 8786 V_regs.MATCrdB.cmpvalu = 0xFFFFFFFF; 8787 V_regs.MATCwrB.cmpmask = 0; 8788 V_regs.MATCwrB.cmpvalu = 0xFFFFFFFF; 8789 V_regs.MATCrdW.cmpmask = 0; 8790 V_regs.MATCrdW.cmpvalu = 0xFFFFFFFF; 8791 V_regs.MATCwrW.cmpmask = 0; 8792 V_regs.MATCwrW.cmpvalu = 0xFFFFFFFF; 8793#if FasterAlignedL 8794 V_regs.MATCrdL.cmpmask = 0; 8795 V_regs.MATCrdL.cmpvalu = 0xFFFFFFFF; 8796 V_regs.MATCwrL.cmpmask = 0; 8797 V_regs.MATCwrL.cmpvalu = 0xFFFFFFFF; 8798#endif 8799 /* force Recalc_PC_Block soon */ 8800 V_regs.pc = m68k_getpc(); 8801 V_regs.pc_pLo = V_pc_p; 8802 V_pc_pHi = V_regs.pc_pLo + 2; 8803 V_regs.HeadATTel = p; 8804 8805 Em_Exit(); 8806} 8807 8808GLOBALPROC DiskInsertedPsuedoException(CPTR newpc, ui5b data) 8809{ 8810 Em_Enter(); 8811 ExceptionTo(newpc 8812#if Use68020 8813 , 0 8814#endif 8815 ); 8816 m68k_areg(7) -= 4; 8817 put_long(m68k_areg(7), data); 8818 Em_Exit(); 8819} 8820 8821GLOBALPROC m68k_IPLchangeNtfy(void) 8822{ 8823 Em_Enter(); 8824 { 8825 ui3r level = *V_regs.fIPL; 8826 8827 if ((level > V_regs.intmask) || (level == 7)) { 8828 SetExternalInterruptPending(); 8829 } 8830 } 8831 Em_Exit(); 8832} 8833 8834#if WantDumpTable 8835LOCALPROC InitDumpTable(void) 8836{ 8837 si5b i; 8838 8839 for (i = 0; i < kNumIKinds; ++i) { 8840 DumpTable[i] = 0; 8841 } 8842} 8843 8844LOCALPROC DumpATable(ui5b *p, ui5b n) 8845{ 8846 si5b i; 8847 8848 for (i = 0; i < n; ++i) { 8849 dbglog_writeNum(p[i]); 8850 dbglog_writeReturn(); 8851 } 8852} 8853 8854EXPORTPROC DoDumpTable(void); 8855GLOBALPROC DoDumpTable(void) 8856{ 8857 DumpATable(DumpTable, kNumIKinds); 8858} 8859#endif 8860 8861GLOBALPROC m68k_reset(void) 8862{ 8863 Em_Enter(); 8864 8865#if WantDumpTable 8866 InitDumpTable(); 8867#endif 8868 V_MaxCyclesToGo = 0; 8869 V_regs.MoreCyclesToGo = 0; 8870 V_regs.ResidualCycles = 0; 8871 V_pc_p = (ui3p)nullpr; 8872 V_pc_pHi = (ui3p)nullpr; 8873 V_regs.pc_pLo = (ui3p)nullpr; 8874 8875 do_put_mem_word(V_regs.fakeword, 0x4AFC); 8876 /* illegal instruction opcode */ 8877 8878#if 0 8879 V_regs.ResetPending = trueblnr; 8880 NeedToGetOut(); 8881#else 8882/* Sets the MC68000 reset jump vector... */ 8883 m68k_setpc(get_long(0x00000004)); 8884 8885/* Sets the initial stack vector... */ 8886 m68k_areg(7) = get_long(0x00000000); 8887 8888 V_regs.s = 1; 8889#if Use68020 8890 V_regs.m = 0; 8891 V_regs.t0 = 0; 8892#endif 8893 V_regs.t1 = 0; 8894 ZFLG = CFLG = NFLG = VFLG = 0; 8895 8896 V_regs.LazyFlagKind = kLazyFlagsDefault; 8897 V_regs.LazyXFlagKind = kLazyFlagsDefault; 8898 8899 V_regs.ExternalInterruptPending = falseblnr; 8900 V_regs.TracePending = falseblnr; 8901 V_regs.intmask = 7; 8902 8903#if Use68020 8904 V_regs.sfc = 0; 8905 V_regs.dfc = 0; 8906 V_regs.vbr = 0; 8907 V_regs.cacr = 0; 8908 V_regs.caar = 0; 8909#endif 8910#endif 8911 8912 Em_Exit(); 8913} 8914 8915#if SmallGlobals 8916GLOBALPROC MINEM68K_ReserveAlloc(void) 8917{ 8918 ReserveAllocOneBlock((ui3p *)&regs.disp_table, 8919 disp_table_sz * 8, 6, falseblnr); 8920} 8921#endif 8922 8923GLOBALPROC MINEM68K_Init( 8924 ui3b *fIPL) 8925{ 8926 regs.fIPL = fIPL; 8927#ifdef r_regs 8928 regs.save_regs = &regs; 8929#endif 8930 8931 M68KITAB_setup(regs.disp_table); 8932}