Sigrid Haflínudóttirfirst dirty version of the portd7ad0686 years agoHistory
8924 lines · 184.7 KB · C
RawDownload
/*	MINEM68K.c 	Copyright (C) 2009 Bernd Schmidt, Paul C. Pratt 	You can redistribute this file and/or modify it under the terms	of version 2 of the GNU General Public License as published by	the Free Software Foundation.  You should have received a copy	of the license along with this file; see the file COPYING. 	This file is distributed in the hope that it will be useful,	but WITHOUT ANY WARRANTY; without even the implied warranty of	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the	license for more details.*/ /*	EMulator of 68K cpu with GENeric c code (not assembly) 	This code descends from a simple 68000 emulator that I	(Paul C. Pratt) wrote long ago. That emulator ran on a 680x0,	and used the cpu it ran on to do some of the work. This	descendent fills in those holes with code from the	Un*x Amiga Emulator by Bernd Schmidt, as found being used in vMac. 	This emulator is about 10 times smaller than the UAE,	at the cost of being 2 to 3 times slower. 	FPU Emulation added 9/12/2009 by Ross Martin		(this code now located in "FPCPEMDV.h")*/ #ifndef AllFiles#include "SYSDEPNS.h" #include "MYOSGLUE.h"#include "ENDIANAC.h"#include "EMCONFIG.h"#include "GLOBGLUE.h" #include "M68KITAB.h" #if WantDisasm#include "DISAM68K.h"#endif#endif #include "MINEM68K.h" /*	ReportAbnormalID unused 0x0123 - 0x01FF*/ #ifndef DisableLazyFlagAll#define DisableLazyFlagAll 0#endif	/*		useful for debugging, to tell if an observed bug is		being cause by lazy flag evaluation stuff.		Can also disable parts of it individually:	*/ #ifndef ForceFlagsEval#if DisableLazyFlagAll#define ForceFlagsEval 1#else#define ForceFlagsEval 0#endif#endif #ifndef UseLazyZ#if DisableLazyFlagAll || ForceFlagsEval#define UseLazyZ 0#else#define UseLazyZ 1#endif#endif #ifndef UseLazyCC#if DisableLazyFlagAll#define UseLazyCC 0#else#define UseLazyCC 1#endif#endif  typedef unsigned char flagtype; /* must be 0 or 1, not boolean */  /* Memory Address Translation Cache record */ struct MATCr {	ui5r cmpmask;	ui5r cmpvalu;	ui5r usemask;	ui3p usebase;};typedef struct MATCr MATCr;typedef MATCr *MATCp; #ifndef USE_PCLIMIT#define USE_PCLIMIT 1#endif #define AKMemory 0#define AKRegister 1 union ArgAddrT {	ui5r mem;	ui5r *rga;};typedef union ArgAddrT ArgAddrT; enum {	kLazyFlagsDefault,	kLazyFlagsTstB,	kLazyFlagsTstW,	kLazyFlagsTstL,	kLazyFlagsCmpB,	kLazyFlagsCmpW,	kLazyFlagsCmpL,	kLazyFlagsSubB,	kLazyFlagsSubW,	kLazyFlagsSubL,	kLazyFlagsAddB,	kLazyFlagsAddW,	kLazyFlagsAddL,	kLazyFlagsNegB,	kLazyFlagsNegW,	kLazyFlagsNegL,	kLazyFlagsAsrB,	kLazyFlagsAsrW,	kLazyFlagsAsrL,	kLazyFlagsAslB,	kLazyFlagsAslW,	kLazyFlagsAslL,#if UseLazyZ	kLazyFlagsZSet,#endif 	kNumLazyFlagsKinds}; typedef void (my_reg_call *ArgSetDstP)(ui5r f); #define FasterAlignedL 0	/*		If most long memory access is long aligned,		this should be faster. But on the Mac, this		doesn't seem to be the case, so an		unpredictable branch slows it down.	*/ #ifndef HaveGlbReg#define HaveGlbReg 0#endif LOCALVAR struct regstruct{	ui5r regs[16]; /* Data and Address registers */ 	ui3p pc_p;	ui3p pc_pHi;	si5rr MaxCyclesToGo; #if WantCloserCyc	DecOpR *CurDecOp;#endif	DecOpYR CurDecOpY; 	ui3r LazyFlagKind;	ui3r LazyXFlagKind;#if UseLazyZ	ui3r LazyFlagZSavedKind;#endif	ui5r LazyFlagArgSrc;	ui5r LazyFlagArgDst;	ui5r LazyXFlagArgSrc;	ui5r LazyXFlagArgDst; 	ArgAddrT ArgAddr;	ArgSetDstP ArgSetDst;	ui5b SrcVal; 	ui3p pc_pLo;	ui5r pc; /* Program Counter */ 	MATCr MATCrdB;	MATCr MATCwrB;	MATCr MATCrdW;	MATCr MATCwrW;#if FasterAlignedL	MATCr MATCrdL;	MATCr MATCwrL;#endif	ATTep HeadATTel; 	si5r MoreCyclesToGo;	si5r ResidualCycles;	ui3b fakeword[2]; 	/* Status Register */	ui5r intmask; /* bits 10-8 : interrupt priority mask */	flagtype t1; /* bit 15: Trace mode 1 */#if Use68020	flagtype t0; /* bit 14: Trace mode 0 */#endif	flagtype s; /* bit 13: Supervisor or user privilege level */#if Use68020	flagtype m; /* bit 12: Master or interrupt mode */#endif 	flagtype x; /* bit 4: eXtend */	flagtype n; /* bit 3: Negative */	flagtype z; /* bit 2: Zero */	flagtype v; /* bit 1: oVerflow */	flagtype c; /* bit 0: Carry */ #if EmMMU | EmFPU	ui5b ArgKind;#endif 	blnr TracePending;	blnr ExternalInterruptPending;#if 0	blnr ResetPending;#endif	ui3b *fIPL;#ifdef r_regs	struct regstruct *save_regs;#endif 	CPTR usp; /* User Stack Pointer */	CPTR isp; /* Interrupt Stack Pointer */#if Use68020	CPTR msp; /* Master Stack Pointer */	ui5b sfc; /* Source Function Code register */	ui5b dfc; /* Destination Function Code register */	ui5b vbr; /* Vector Base Register */	ui5b cacr; /* Cache Control Register */		/*			bit 0 : Enable Cache			bit 1 : Freeze Cache			bit 2 : Clear Entry In Cache (write only)			bit 3 : Clear Cache (write only)		*/	ui5b caar; /* Cache Address Register */#endif #define disp_table_sz (256 * 256)#if SmallGlobals	DecOpR *disp_table;#else	DecOpR disp_table[disp_table_sz];#endif} regs; #define ui5r_MSBisSet(x) (((si5r)(x)) < 0) #define Bool2Bit(x) ((x) ? 1 : 0)  #ifdef r_regsregister struct regstruct *g_regs asm (r_regs);#define V_regs (*g_regs)#else#define V_regs regs#endif #ifdef r_pc_pregister ui3p g_pc_p asm (r_pc_p);#define V_pc_p g_pc_p#else#define V_pc_p V_regs.pc_p#endif #ifdef r_MaxCyclesToGoregister si5rr g_MaxCyclesToGo asm (r_MaxCyclesToGo);#define V_MaxCyclesToGo g_MaxCyclesToGo#else#define V_MaxCyclesToGo V_regs.MaxCyclesToGo#endif #ifdef r_pc_pHiregister ui3p g_pc_pHi asm (r_pc_pHi);#define V_pc_pHi g_pc_pHi#else#define V_pc_pHi V_regs.pc_pHi#endif #define ZFLG V_regs.z#define NFLG V_regs.n#define CFLG V_regs.c#define VFLG V_regs.v#define XFLG V_regs.x #define m68k_dreg(num) (V_regs.regs[(num)])#define m68k_areg(num) (V_regs.regs[(num) + 8])  #ifndef WantDumpTable#define WantDumpTable 0#endif #if WantDumpTableLOCALVAR ui5b DumpTable[kNumIKinds];#endif #if USE_PCLIMITFORWARDPROC Recalc_PC_Block(void);FORWARDFUNC ui5r my_reg_call Recalc_PC_BlockReturnUi5r(ui5r v);#endif LOCALINLINEFUNC ui4r nextiword(void)/* NOT sign extended */{	ui4r r = do_get_mem_word(V_pc_p);	V_pc_p += 2; #if USE_PCLIMIT	if (my_cond_rare(V_pc_p >= V_pc_pHi)) {		Recalc_PC_Block();	}#endif 	return r;} LOCALINLINEFUNC ui5r nextiSByte(void){	ui5r r = ui5r_FromSByte(do_get_mem_byte(V_pc_p + 1));	V_pc_p += 2; #if USE_PCLIMIT	if (my_cond_rare(V_pc_p >= V_pc_pHi)) {		return Recalc_PC_BlockReturnUi5r(r);	}#endif 	return r;} LOCALINLINEFUNC ui5r nextiSWord(void)/* NOT sign extended */{	ui5r r = ui5r_FromSWord(do_get_mem_word(V_pc_p));	V_pc_p += 2; #if USE_PCLIMIT	if (my_cond_rare(V_pc_p >= V_pc_pHi)) {		return Recalc_PC_BlockReturnUi5r(r);	}#endif 	return r;} FORWARDFUNC ui5r nextilong_ext(void); LOCALINLINEFUNC ui5r nextilong(void){	ui5r r = do_get_mem_long(V_pc_p);	V_pc_p += 4; #if USE_PCLIMIT	/* could be two words in different blocks */	if (my_cond_rare(V_pc_p >= V_pc_pHi)) {		r = nextilong_ext();	}#endif 	return r;} LOCALINLINEPROC BackupPC(void){	V_pc_p -= 2; #if USE_PCLIMIT	if (my_cond_rare(V_pc_p < V_regs.pc_pLo)) {		Recalc_PC_Block();	}#endif} LOCALINLINEFUNC CPTR m68k_getpc(void){	return V_regs.pc + (V_pc_p - V_regs.pc_pLo);}  FORWARDPROC DoCodeTst(void);FORWARDPROC DoCodeCmpB(void);FORWARDPROC DoCodeCmpW(void);FORWARDPROC DoCodeCmpL(void);FORWARDPROC DoCodeBccB(void);FORWARDPROC DoCodeBccW(void);FORWARDPROC DoCodeBraB(void);FORWARDPROC DoCodeBraW(void);FORWARDPROC DoCodeDBcc(void);FORWARDPROC DoCodeDBF(void);FORWARDPROC DoCodeSwap(void);FORWARDPROC DoCodeMoveL(void);FORWARDPROC DoCodeMoveW(void);FORWARDPROC DoCodeMoveB(void);FORWARDPROC DoCodeMoveA(void);FORWARDPROC DoCodeMoveQ(void);FORWARDPROC DoCodeAddB(void);FORWARDPROC DoCodeAddW(void);FORWARDPROC DoCodeAddL(void);FORWARDPROC DoCodeSubB(void);FORWARDPROC DoCodeSubW(void);FORWARDPROC DoCodeSubL(void);FORWARDPROC DoCodeLea(void);FORWARDPROC DoCodePEA(void);FORWARDPROC DoCodeA(void);FORWARDPROC DoCodeBsrB(void);FORWARDPROC DoCodeBsrW(void);FORWARDPROC DoCodeJsr(void);FORWARDPROC DoCodeLinkA6(void);FORWARDPROC DoCodeMOVEMRmML(void);FORWARDPROC DoCodeMOVEMApRL(void);FORWARDPROC DoCodeUnlkA6(void);FORWARDPROC DoCodeRts(void);FORWARDPROC DoCodeJmp(void);FORWARDPROC DoCodeClr(void);FORWARDPROC DoCodeAddA(void);FORWARDPROC DoCodeSubA(void);FORWARDPROC DoCodeCmpA(void);FORWARDPROC DoCodeAddXB(void);FORWARDPROC DoCodeAddXW(void);FORWARDPROC DoCodeAddXL(void);FORWARDPROC DoCodeSubXB(void);FORWARDPROC DoCodeSubXW(void);FORWARDPROC DoCodeSubXL(void);FORWARDPROC DoCodeAslB(void);FORWARDPROC DoCodeAslW(void);FORWARDPROC DoCodeAslL(void);FORWARDPROC DoCodeAsrB(void);FORWARDPROC DoCodeAsrW(void);FORWARDPROC DoCodeAsrL(void);FORWARDPROC DoCodeLslB(void);FORWARDPROC DoCodeLslW(void);FORWARDPROC DoCodeLslL(void);FORWARDPROC DoCodeLsrB(void);FORWARDPROC DoCodeLsrW(void);FORWARDPROC DoCodeLsrL(void);FORWARDPROC DoCodeRxlB(void);FORWARDPROC DoCodeRxlW(void);FORWARDPROC DoCodeRxlL(void);FORWARDPROC DoCodeRxrB(void);FORWARDPROC DoCodeRxrW(void);FORWARDPROC DoCodeRxrL(void);FORWARDPROC DoCodeRolB(void);FORWARDPROC DoCodeRolW(void);FORWARDPROC DoCodeRolL(void);FORWARDPROC DoCodeRorB(void);FORWARDPROC DoCodeRorW(void);FORWARDPROC DoCodeRorL(void);FORWARDPROC DoCodeBTstB(void);FORWARDPROC DoCodeBChgB(void);FORWARDPROC DoCodeBClrB(void);FORWARDPROC DoCodeBSetB(void);FORWARDPROC DoCodeBTstL(void);FORWARDPROC DoCodeBChgL(void);FORWARDPROC DoCodeBClrL(void);FORWARDPROC DoCodeBSetL(void);FORWARDPROC DoCodeAnd(void);FORWARDPROC DoCodeOr(void);FORWARDPROC DoCodeEor(void);FORWARDPROC DoCodeNot(void);FORWARDPROC DoCodeScc(void);FORWARDPROC DoCodeNegXB(void);FORWARDPROC DoCodeNegXW(void);FORWARDPROC DoCodeNegXL(void);FORWARDPROC DoCodeNegB(void);FORWARDPROC DoCodeNegW(void);FORWARDPROC DoCodeNegL(void);FORWARDPROC DoCodeEXTW(void);FORWARDPROC DoCodeEXTL(void);FORWARDPROC DoCodeMulU(void);FORWARDPROC DoCodeMulS(void);FORWARDPROC DoCodeDivU(void);FORWARDPROC DoCodeDivS(void);FORWARDPROC DoCodeExg(void);FORWARDPROC DoCodeMoveEaCR(void);FORWARDPROC DoCodeMoveSREa(void);FORWARDPROC DoCodeMoveEaSR(void);FORWARDPROC DoCodeOrISR(void);FORWARDPROC DoCodeAndISR(void);FORWARDPROC DoCodeEorISR(void);FORWARDPROC DoCodeOrICCR(void);FORWARDPROC DoCodeAndICCR(void);FORWARDPROC DoCodeEorICCR(void);FORWARDPROC DoCodeMOVEMApRW(void);FORWARDPROC DoCodeMOVEMRmMW(void);FORWARDPROC DoCodeMOVEMrmW(void);FORWARDPROC DoCodeMOVEMrmL(void);FORWARDPROC DoCodeMOVEMmrW(void);

Lines 1–500 of 8924.

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t