mirror of
https://github.com/RaySollium99/picodrive.git
synced 2025-09-05 15:27:46 -04:00
famec: eliminate global context ptr
saves like 25-35K of .text current compile resource usage on i5-6600K: cpu mem gcc 5.4.0: 17.0 1.1g clang 3.8: 1686 2.3g FAMEC_NO_GOTOS: gcc 5.4.0: 8.4 0.4g clang 3.8: 20.0 0.15g vs2008/O2: ~1800 ? vs2008/O1: ~720 ?
This commit is contained in:
parent
12f23dac6f
commit
7669591e08
7 changed files with 346 additions and 371 deletions
|
@ -143,8 +143,6 @@ typedef struct
|
||||||
unsigned long Fetch[M68K_FETCHBANK1];
|
unsigned long Fetch[M68K_FETCHBANK1];
|
||||||
} M68K_CONTEXT;
|
} M68K_CONTEXT;
|
||||||
|
|
||||||
extern M68K_CONTEXT *g_m68kcontext;
|
|
||||||
|
|
||||||
typedef enum
|
typedef enum
|
||||||
{
|
{
|
||||||
fm68k_reason_emulate = 0,
|
fm68k_reason_emulate = 0,
|
||||||
|
@ -163,7 +161,7 @@ int fm68k_reset(M68K_CONTEXT *ctx);
|
||||||
int fm68k_emulate(M68K_CONTEXT *ctx, int n, fm68k_call_reason reason);
|
int fm68k_emulate(M68K_CONTEXT *ctx, int n, fm68k_call_reason reason);
|
||||||
int fm68k_would_interrupt(M68K_CONTEXT *ctx); // to be called from fm68k_emulate()
|
int fm68k_would_interrupt(M68K_CONTEXT *ctx); // to be called from fm68k_emulate()
|
||||||
|
|
||||||
unsigned fm68k_get_pc(M68K_CONTEXT *ctx);
|
unsigned int fm68k_get_pc(const M68K_CONTEXT *ctx);
|
||||||
|
|
||||||
// PICODRIVE_HACK
|
// PICODRIVE_HACK
|
||||||
int fm68k_idle_install(void);
|
int fm68k_idle_install(void);
|
||||||
|
|
253
cpu/fame/famec.c
253
cpu/fame/famec.c
|
@ -228,21 +228,21 @@ typedef signed int s32;
|
||||||
// internals core macros
|
// internals core macros
|
||||||
/////////////////////////
|
/////////////////////////
|
||||||
|
|
||||||
#define DREG(X) (m68kcontext.dreg[(X)].D)
|
#define DREG(X) (ctx->dreg[(X)].D)
|
||||||
#define DREGu32(X) (m68kcontext.dreg[(X)].D)
|
#define DREGu32(X) (ctx->dreg[(X)].D)
|
||||||
#define DREGs32(X) (m68kcontext.dreg[(X)].SD)
|
#define DREGs32(X) (ctx->dreg[(X)].SD)
|
||||||
#define DREGu16(X) (m68kcontext.dreg[(X)].W)
|
#define DREGu16(X) (ctx->dreg[(X)].W)
|
||||||
#define DREGs16(X) (m68kcontext.dreg[(X)].SW)
|
#define DREGs16(X) (ctx->dreg[(X)].SW)
|
||||||
#define DREGu8(X) (m68kcontext.dreg[(X)].B)
|
#define DREGu8(X) (ctx->dreg[(X)].B)
|
||||||
#define DREGs8(X) (m68kcontext.dreg[(X)].SB)
|
#define DREGs8(X) (ctx->dreg[(X)].SB)
|
||||||
|
|
||||||
#define AREG(X) (m68kcontext.areg[(X)].D)
|
#define AREG(X) (ctx->areg[(X)].D)
|
||||||
#define AREGu32(X) (m68kcontext.areg[(X)].D)
|
#define AREGu32(X) (ctx->areg[(X)].D)
|
||||||
#define AREGs32(X) (m68kcontext.areg[(X)].SD)
|
#define AREGs32(X) (ctx->areg[(X)].SD)
|
||||||
#define AREGu16(X) (m68kcontext.areg[(X)].W)
|
#define AREGu16(X) (ctx->areg[(X)].W)
|
||||||
#define AREGs16(X) (m68kcontext.areg[(X)].SW)
|
#define AREGs16(X) (ctx->areg[(X)].SW)
|
||||||
|
|
||||||
#define ASP (m68kcontext.asp)
|
#define ASP (ctx->asp)
|
||||||
|
|
||||||
#define LSL(A, C) ((A) << (C))
|
#define LSL(A, C) ((A) << (C))
|
||||||
#define LSR(A, C) ((A) >> (C))
|
#define LSR(A, C) ((A) >> (C))
|
||||||
|
@ -271,39 +271,39 @@ typedef signed int s32;
|
||||||
|
|
||||||
#ifdef FAMEC_ROLL_INLINE
|
#ifdef FAMEC_ROLL_INLINE
|
||||||
#define RET(A) \
|
#define RET(A) \
|
||||||
m68kcontext.io_cycle_counter -= (A); \
|
ctx->io_cycle_counter -= (A); \
|
||||||
if (m68kcontext.io_cycle_counter <= 0) goto famec_Exec_End; \
|
if (ctx->io_cycle_counter <= 0) goto famec_Exec_End; \
|
||||||
NEXT
|
NEXT
|
||||||
#else
|
#else
|
||||||
#define RET(A) \
|
#define RET(A) \
|
||||||
m68kcontext.io_cycle_counter -= (A); \
|
ctx->io_cycle_counter -= (A); \
|
||||||
if (m68kcontext.io_cycle_counter <= 0) goto famec_Exec_End; \
|
if (ctx->io_cycle_counter <= 0) goto famec_Exec_End; \
|
||||||
goto famec_Exec;
|
goto famec_Exec;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define RET0() \
|
#define RET0() \
|
||||||
m68kcontext.io_cycle_counter = -6; \
|
ctx->io_cycle_counter = -6; \
|
||||||
goto famec_End;
|
goto famec_End;
|
||||||
|
|
||||||
#else
|
#else
|
||||||
|
|
||||||
#define NEXT \
|
#define NEXT \
|
||||||
do{ \
|
do { \
|
||||||
FETCH_WORD(Opcode); \
|
FETCH_WORD(Opcode); \
|
||||||
JumpTable[Opcode](); \
|
JumpTable[Opcode](ctx); \
|
||||||
}while(m68kcontext.io_cycle_counter>0);
|
} while (ctx->io_cycle_counter > 0);
|
||||||
|
|
||||||
#define RET(A) \
|
#define RET(A) \
|
||||||
m68kcontext.io_cycle_counter -= (A); \
|
ctx->io_cycle_counter -= (A); \
|
||||||
return;
|
return;
|
||||||
|
|
||||||
#define RET0() \
|
#define RET0() \
|
||||||
m68kcontext.io_cycle_counter = -6; \
|
ctx->io_cycle_counter = -6; \
|
||||||
return;
|
return;
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define M68K_PPL (m68kcontext.sr >> 8) & 7
|
#define M68K_PPL (ctx->sr >> 8) & 7
|
||||||
|
|
||||||
#define GET_PC \
|
#define GET_PC \
|
||||||
(u32)((uptr)PC - BasePC)
|
(u32)((uptr)PC - BasePC)
|
||||||
|
@ -321,7 +321,7 @@ typedef signed int s32;
|
||||||
{ \
|
{ \
|
||||||
u32 pc = A; \
|
u32 pc = A; \
|
||||||
FORCE_ALIGNMENT(pc); \
|
FORCE_ALIGNMENT(pc); \
|
||||||
BasePC = m68kcontext.Fetch[(pc >> M68K_FETCHSFT) & M68K_FETCHMASK]; \
|
BasePC = ctx->Fetch[(pc >> M68K_FETCHSFT) & M68K_FETCHMASK]; \
|
||||||
PC = (u16*)((pc & M68K_ADR_MASK) + BasePC); \
|
PC = (u16*)((pc & M68K_ADR_MASK) + BasePC); \
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -331,7 +331,7 @@ typedef signed int s32;
|
||||||
{ \
|
{ \
|
||||||
u32 pc = A; \
|
u32 pc = A; \
|
||||||
FORCE_ALIGNMENT(pc); \
|
FORCE_ALIGNMENT(pc); \
|
||||||
BasePC = m68kcontext.Fetch[(pc >> M68K_FETCHSFT) & M68K_FETCHMASK]; \
|
BasePC = ctx->Fetch[(pc >> M68K_FETCHSFT) & M68K_FETCHMASK]; \
|
||||||
BasePC -= pc & 0xFF000000; \
|
BasePC -= pc & 0xFF000000; \
|
||||||
PC = (u16*)(pc + BasePC); \
|
PC = (u16*)(pc + BasePC); \
|
||||||
}
|
}
|
||||||
|
@ -346,29 +346,29 @@ typedef signed int s32;
|
||||||
// CCnt = io_cycle_counter;
|
// CCnt = io_cycle_counter;
|
||||||
|
|
||||||
#define READ_BYTE_F(A, D) \
|
#define READ_BYTE_F(A, D) \
|
||||||
D = m68kcontext.read_byte(A) & 0xFF;
|
D = ctx->read_byte(A) & 0xFF;
|
||||||
|
|
||||||
#define READ_WORD_F(A, D) \
|
#define READ_WORD_F(A, D) \
|
||||||
D = m68kcontext.read_word(A) & 0xFFFF;
|
D = ctx->read_word(A) & 0xFFFF;
|
||||||
|
|
||||||
#define READ_LONG_F(A, D) \
|
#define READ_LONG_F(A, D) \
|
||||||
D = m68kcontext.read_long(A);
|
D = ctx->read_long(A);
|
||||||
|
|
||||||
#define READSX_LONG_F READ_LONG_F
|
#define READSX_LONG_F READ_LONG_F
|
||||||
|
|
||||||
#define WRITE_LONG_F(A, D) \
|
#define WRITE_LONG_F(A, D) \
|
||||||
m68kcontext.write_long(A, D);
|
ctx->write_long(A, D);
|
||||||
|
|
||||||
#define WRITE_LONG_DEC_F(A, D) \
|
#define WRITE_LONG_DEC_F(A, D) \
|
||||||
m68kcontext.write_word((A) + 2, (D) & 0xFFFF); \
|
ctx->write_word((A) + 2, (D) & 0xFFFF); \
|
||||||
m68kcontext.write_word((A), (D) >> 16);
|
ctx->write_word((A), (D) >> 16);
|
||||||
|
|
||||||
#define PUSH_32_F(D) \
|
#define PUSH_32_F(D) \
|
||||||
AREG(7) -= 4; \
|
AREG(7) -= 4; \
|
||||||
m68kcontext.write_long(AREG(7), D);
|
ctx->write_long(AREG(7), D);
|
||||||
|
|
||||||
#define POP_32_F(D) \
|
#define POP_32_F(D) \
|
||||||
D = m68kcontext.read_long(AREG(7)); \
|
D = ctx->read_long(AREG(7)); \
|
||||||
AREG(7) += 4;
|
AREG(7) += 4;
|
||||||
|
|
||||||
#ifndef FAME_BIG_ENDIAN
|
#ifndef FAME_BIG_ENDIAN
|
||||||
|
@ -440,23 +440,23 @@ typedef signed int s32;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define READSX_BYTE_F(A, D) \
|
#define READSX_BYTE_F(A, D) \
|
||||||
D = (s8)m68kcontext.read_byte(A);
|
D = (s8)ctx->read_byte(A);
|
||||||
|
|
||||||
#define READSX_WORD_F(A, D) \
|
#define READSX_WORD_F(A, D) \
|
||||||
D = (s16)m68kcontext.read_word(A);
|
D = (s16)ctx->read_word(A);
|
||||||
|
|
||||||
|
|
||||||
#define WRITE_BYTE_F(A, D) \
|
#define WRITE_BYTE_F(A, D) \
|
||||||
m68kcontext.write_byte(A, D);
|
ctx->write_byte(A, D);
|
||||||
|
|
||||||
#define WRITE_WORD_F(A, D) \
|
#define WRITE_WORD_F(A, D) \
|
||||||
m68kcontext.write_word(A, D);
|
ctx->write_word(A, D);
|
||||||
|
|
||||||
#define PUSH_16_F(D) \
|
#define PUSH_16_F(D) \
|
||||||
m68kcontext.write_word(AREG(7) -= 2, D); \
|
ctx->write_word(AREG(7) -= 2, D); \
|
||||||
|
|
||||||
#define POP_16_F(D) \
|
#define POP_16_F(D) \
|
||||||
D = (u16)m68kcontext.read_word(AREG(7)); \
|
D = (u16)ctx->read_word(AREG(7)); \
|
||||||
AREG(7) += 2;
|
AREG(7) += 2;
|
||||||
|
|
||||||
#define GET_CCR \
|
#define GET_CCR \
|
||||||
|
@ -501,17 +501,17 @@ typedef signed int s32;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define CHECK_INT_TO_JUMP(CLK) \
|
#define CHECK_INT_TO_JUMP(CLK) \
|
||||||
if (interrupt_chk__()) \
|
if (interrupt_chk__(ctx)) \
|
||||||
{ \
|
{ \
|
||||||
cycles_needed=m68kcontext.io_cycle_counter-(CLK); \
|
cycles_needed=ctx->io_cycle_counter-(CLK); \
|
||||||
m68kcontext.io_cycle_counter=(CLK); \
|
ctx->io_cycle_counter=(CLK); \
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
#ifdef FAMEC_CHECK_BRANCHES
|
#ifdef FAMEC_CHECK_BRANCHES
|
||||||
|
|
||||||
#ifdef FAMEC_NO_GOTOS
|
#ifdef FAMEC_NO_GOTOS
|
||||||
#define CHECK_BRANCH_EXCEPTION_GOTO_END m68kcontext.io_cycle_counter=0; return;
|
#define CHECK_BRANCH_EXCEPTION_GOTO_END ctx->io_cycle_counter=0; return;
|
||||||
#else
|
#else
|
||||||
#define CHECK_BRANCH_EXCEPTION_GOTO_END goto famec_Exec_End;
|
#define CHECK_BRANCH_EXCEPTION_GOTO_END goto famec_Exec_End;
|
||||||
#endif
|
#endif
|
||||||
|
@ -520,8 +520,8 @@ typedef signed int s32;
|
||||||
if ((_PC_)&1) \
|
if ((_PC_)&1) \
|
||||||
{ \
|
{ \
|
||||||
u32 new_PC, pr_PC=GET_PC; \
|
u32 new_PC, pr_PC=GET_PC; \
|
||||||
m68kcontext.execinfo |= FM68K_EMULATE_GROUP_0; \
|
ctx->execinfo |= FM68K_EMULATE_GROUP_0; \
|
||||||
new_PC = execute_exception_group_0(M68K_ADDRESS_ERROR_EX, 0, pr_PC, 0x12 ); \
|
new_PC = execute_exception_group_0(ctx, M68K_ADDRESS_ERROR_EX, 0, pr_PC, 0x12 ); \
|
||||||
SET_PC(new_PC); \
|
SET_PC(new_PC); \
|
||||||
CHECK_BRANCH_EXCEPTION_GOTO_END \
|
CHECK_BRANCH_EXCEPTION_GOTO_END \
|
||||||
}
|
}
|
||||||
|
@ -529,30 +529,25 @@ typedef signed int s32;
|
||||||
#define CHECK_BRANCH_EXCEPTION(_PC_)
|
#define CHECK_BRANCH_EXCEPTION(_PC_)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#ifdef FAMEC_NO_GOTOS
|
||||||
|
#define Opcode ctx->Opcode
|
||||||
|
#define cycles_needed ctx->cycles_needed
|
||||||
|
#define PC ctx->PC
|
||||||
|
#define BasePC ctx->BasePC
|
||||||
|
#define flag_C ctx->flag_C
|
||||||
|
#define flag_V ctx->flag_V
|
||||||
|
#define flag_NotZ ctx->flag_NotZ
|
||||||
|
#define flag_N ctx->flag_N
|
||||||
|
#define flag_X ctx->flag_X
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define flag_T ctx->flag_T
|
||||||
|
#define flag_S ctx->flag_S
|
||||||
|
#define flag_I ctx->flag_I
|
||||||
|
|
||||||
// global variable
|
// global variable
|
||||||
///////////////////
|
///////////////////
|
||||||
|
|
||||||
/* Current CPU context */
|
|
||||||
M68K_CONTEXT *g_m68kcontext;
|
|
||||||
#define m68kcontext (*g_m68kcontext)
|
|
||||||
|
|
||||||
#ifdef FAMEC_NO_GOTOS
|
|
||||||
#define Opcode m68kcontext.Opcode
|
|
||||||
#define cycles_needed m68kcontext.cycles_needed
|
|
||||||
#define PC m68kcontext.PC
|
|
||||||
#define BasePC m68kcontext.BasePC
|
|
||||||
#define flag_C m68kcontext.flag_C
|
|
||||||
#define flag_V m68kcontext.flag_V
|
|
||||||
#define flag_NotZ m68kcontext.flag_NotZ
|
|
||||||
#define flag_N m68kcontext.flag_N
|
|
||||||
#define flag_X m68kcontext.flag_X
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define flag_T m68kcontext.flag_T
|
|
||||||
#define flag_S m68kcontext.flag_S
|
|
||||||
#define flag_I m68kcontext.flag_I
|
|
||||||
|
|
||||||
static u32 initialised = 0;
|
static u32 initialised = 0;
|
||||||
|
|
||||||
#ifdef PICODRIVE_HACK
|
#ifdef PICODRIVE_HACK
|
||||||
|
@ -560,7 +555,7 @@ extern M68K_CONTEXT PicoCpuFS68k;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Custom function handler */
|
/* Custom function handler */
|
||||||
typedef void (*opcode_func)(void);
|
typedef void (*opcode_func)(M68K_CONTEXT *ctx);
|
||||||
|
|
||||||
static opcode_func JumpTable[0x10000];
|
static opcode_func JumpTable[0x10000];
|
||||||
|
|
||||||
|
@ -679,30 +674,28 @@ int fm68k_reset(M68K_CONTEXT *ctx)
|
||||||
if (!initialised)
|
if (!initialised)
|
||||||
init_jump_table();
|
init_jump_table();
|
||||||
|
|
||||||
g_m68kcontext = ctx;
|
|
||||||
|
|
||||||
// Si la CPU esta en ejecucion, salir con M68K_RUNNING
|
// Si la CPU esta en ejecucion, salir con M68K_RUNNING
|
||||||
if (m68kcontext.execinfo & M68K_RUNNING)
|
if (ctx->execinfo & M68K_RUNNING)
|
||||||
return M68K_RUNNING;
|
return M68K_RUNNING;
|
||||||
|
|
||||||
// Resetear registros
|
// Resetear registros
|
||||||
//memset(&m68kcontext.dreg[0], 0, 16*4);
|
//memset(&ctx->dreg[0], 0, 16*4);
|
||||||
|
|
||||||
// Resetear interrupts, execinfo y ASP
|
// Resetear interrupts, execinfo y ASP
|
||||||
m68kcontext.interrupts[0] = 0;
|
ctx->interrupts[0] = 0;
|
||||||
m68kcontext.execinfo = 0;
|
ctx->execinfo = 0;
|
||||||
ASP = 0;
|
ASP = 0;
|
||||||
|
|
||||||
// Fijar registro de estado
|
// Fijar registro de estado
|
||||||
m68kcontext.sr = (m68kcontext.sr & 0xff) | 0x2700;
|
ctx->sr = (ctx->sr & 0xff) | 0x2700;
|
||||||
|
|
||||||
// Obtener puntero de pila inicial y PC
|
// Obtener puntero de pila inicial y PC
|
||||||
AREG(7) = m68kcontext.read_long(0);
|
AREG(7) = ctx->read_long(0);
|
||||||
m68kcontext.pc = m68kcontext.read_long(4);
|
ctx->pc = ctx->read_long(4);
|
||||||
|
|
||||||
#ifdef FAMEC_DEBUG
|
#ifdef FAMEC_DEBUG
|
||||||
puts("Reset 68k done!\n");
|
puts("Reset 68k done!\n");
|
||||||
printf("PC = 0x%08X\n",m68kcontext.pc);
|
printf("PC = 0x%08X\n",ctx->pc);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
return M68K_OK;
|
return M68K_OK;
|
||||||
|
@ -714,39 +707,39 @@ int fm68k_reset(M68K_CONTEXT *ctx)
|
||||||
/* No recibe parametros */
|
/* No recibe parametros */
|
||||||
/* Retorna 68k PC */
|
/* Retorna 68k PC */
|
||||||
/****************************************************************************/
|
/****************************************************************************/
|
||||||
u32 fm68k_get_pc(M68K_CONTEXT *context)
|
u32 fm68k_get_pc(const M68K_CONTEXT *ctx)
|
||||||
{
|
{
|
||||||
#ifdef FAMEC_NO_GOTOS
|
#ifdef FAMEC_NO_GOTOS
|
||||||
return (context->execinfo & M68K_RUNNING)?(uptr)PC-BasePC:context->pc;
|
return (ctx->execinfo & M68K_RUNNING)?(uptr)PC-BasePC:ctx->pc;
|
||||||
#else
|
#else
|
||||||
return context->pc; // approximate PC in this mode
|
return ctx->pc; // approximate PC in this mode
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//////////////////////////
|
//////////////////////////
|
||||||
// Chequea las interrupciones y las inicia
|
// Chequea las interrupciones y las inicia
|
||||||
static FAMEC_EXTRA_INLINE s32 interrupt_chk__(void)
|
static FAMEC_EXTRA_INLINE s32 interrupt_chk__(M68K_CONTEXT *ctx)
|
||||||
{
|
{
|
||||||
if (m68kcontext.interrupts[0] > flag_I)
|
if (ctx->interrupts[0] > flag_I)
|
||||||
return m68kcontext.interrupts[0];
|
return ctx->interrupts[0];
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int fm68k_would_interrupt(M68K_CONTEXT *ctx)
|
int fm68k_would_interrupt(M68K_CONTEXT *ctx)
|
||||||
{
|
{
|
||||||
return interrupt_chk__();
|
return interrupt_chk__(ctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
static FAMEC_EXTRA_INLINE u32 execute_exception(s32 vect, u32 oldPC, u32 oldSR)
|
static FAMEC_EXTRA_INLINE u32 execute_exception(M68K_CONTEXT *ctx, s32 vect, u32 oldPC, u32 oldSR)
|
||||||
{
|
{
|
||||||
u32 newPC;
|
u32 newPC;
|
||||||
//u32 oldSR = GET_SR;
|
//u32 oldSR = GET_SR;
|
||||||
|
|
||||||
m68kcontext.io_cycle_counter -= exception_cycle_table[vect];
|
ctx->io_cycle_counter -= exception_cycle_table[vect];
|
||||||
#ifdef FAMEC_EMULATE_TRACE
|
#ifdef FAMEC_EMULATE_TRACE
|
||||||
m68kcontext.execinfo &= ~FM68K_EMULATE_TRACE;
|
ctx->execinfo &= ~FM68K_EMULATE_TRACE;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
PRE_IO
|
PRE_IO
|
||||||
|
@ -785,12 +778,12 @@ static FAMEC_EXTRA_INLINE u32 execute_exception(s32 vect, u32 oldPC, u32 oldSR)
|
||||||
return newPC;
|
return newPC;
|
||||||
}
|
}
|
||||||
|
|
||||||
static FAMEC_EXTRA_INLINE u32 execute_exception_group_0(s32 vect, s32 addr, u16 spec_info, u32 oldSR)
|
static FAMEC_EXTRA_INLINE u32 execute_exception_group_0(M68K_CONTEXT *ctx, s32 vect, s32 addr, u16 spec_info, u32 oldSR)
|
||||||
{
|
{
|
||||||
u32 newPC;
|
u32 newPC;
|
||||||
u16 inst_reg = 0;
|
u16 inst_reg = 0;
|
||||||
newPC = execute_exception(vect, addr, oldSR);
|
newPC = execute_exception(ctx, vect, addr, oldSR);
|
||||||
//if (!(m68kcontext.icust_handler && m68kcontext.icust_handler[vect]))
|
//if (!(ctx->icust_handler && ctx->icust_handler[vect]))
|
||||||
{
|
{
|
||||||
PUSH_16_F(inst_reg);
|
PUSH_16_F(inst_reg);
|
||||||
PUSH_32_F(addr);
|
PUSH_32_F(addr);
|
||||||
|
@ -802,7 +795,7 @@ static FAMEC_EXTRA_INLINE u32 execute_exception_group_0(s32 vect, s32 addr, u16
|
||||||
|
|
||||||
#ifdef FAMEC_NO_GOTOS
|
#ifdef FAMEC_NO_GOTOS
|
||||||
|
|
||||||
#define OPCODE(N_OP) static void OP_##N_OP(void)
|
#define OPCODE(N_OP) static void OP_##N_OP(M68K_CONTEXT *ctx)
|
||||||
#define CAST_OP(N_OP) (opcode_func)&OP_##N_OP
|
#define CAST_OP(N_OP) (opcode_func)&OP_##N_OP
|
||||||
#include "famec_opcodes.h"
|
#include "famec_opcodes.h"
|
||||||
#endif
|
#endif
|
||||||
|
@ -839,21 +832,19 @@ int fm68k_emulate(M68K_CONTEXT *ctx, s32 cycles, fm68k_call_reason reason)
|
||||||
}
|
}
|
||||||
#endif // FAMEC_NO_GOTOS
|
#endif // FAMEC_NO_GOTOS
|
||||||
|
|
||||||
g_m68kcontext = ctx;
|
|
||||||
|
|
||||||
// won't emulate double fault
|
// won't emulate double fault
|
||||||
// if (m68kcontext.execinfo & M68K_FAULTED) return -1;
|
// if (ctx->execinfo & M68K_FAULTED) return -1;
|
||||||
|
|
||||||
// Cache PPL
|
// Cache PPL
|
||||||
flag_I = M68K_PPL;
|
flag_I = M68K_PPL;
|
||||||
|
|
||||||
if (m68kcontext.execinfo & FM68K_HALTED)
|
if (ctx->execinfo & FM68K_HALTED)
|
||||||
{
|
{
|
||||||
if (interrupt_chk__() <= 0)
|
if (interrupt_chk__(ctx) <= 0)
|
||||||
{
|
{
|
||||||
return cycles;
|
return cycles;
|
||||||
}
|
}
|
||||||
m68kcontext.execinfo &= ~FM68K_HALTED;
|
ctx->execinfo &= ~FM68K_HALTED;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef FAMEC_DEBUG
|
#ifdef FAMEC_DEBUG
|
||||||
|
@ -861,13 +852,13 @@ int fm68k_emulate(M68K_CONTEXT *ctx, s32 cycles, fm68k_call_reason reason)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Poner la CPU en estado de ejecucion */
|
/* Poner la CPU en estado de ejecucion */
|
||||||
m68kcontext.execinfo |= M68K_RUNNING;
|
ctx->execinfo |= M68K_RUNNING;
|
||||||
|
|
||||||
// Cache SR
|
// Cache SR
|
||||||
SET_SR(m68kcontext.sr)
|
SET_SR(ctx->sr)
|
||||||
|
|
||||||
// Fijar PC
|
// Fijar PC
|
||||||
SET_PC(m68kcontext.pc)
|
SET_PC(ctx->pc)
|
||||||
|
|
||||||
#ifdef FAMEC_DEBUG
|
#ifdef FAMEC_DEBUG
|
||||||
printf("PC: %p\n",PC);
|
printf("PC: %p\n",PC);
|
||||||
|
@ -875,33 +866,33 @@ int fm68k_emulate(M68K_CONTEXT *ctx, s32 cycles, fm68k_call_reason reason)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* guardar ciclos de ejecucion solicitados */
|
/* guardar ciclos de ejecucion solicitados */
|
||||||
m68kcontext.io_cycle_counter = cycles;
|
ctx->io_cycle_counter = cycles;
|
||||||
cycles_needed = 0;
|
cycles_needed = 0;
|
||||||
|
|
||||||
#ifdef FAMEC_EMULATE_TRACE
|
#ifdef FAMEC_EMULATE_TRACE
|
||||||
if (!(m68kcontext.execinfo & FM68K_EMULATE_TRACE))
|
if (!(ctx->execinfo & FM68K_EMULATE_TRACE))
|
||||||
#endif
|
#endif
|
||||||
{
|
{
|
||||||
s32 line=interrupt_chk__();
|
s32 line=interrupt_chk__(ctx);
|
||||||
if (line>0)
|
if (line>0)
|
||||||
{
|
{
|
||||||
/* comprobar si hay rutina de acknowledge */
|
/* comprobar si hay rutina de acknowledge */
|
||||||
if (m68kcontext.iack_handler != NULL)
|
if (ctx->iack_handler != NULL)
|
||||||
m68kcontext.iack_handler(line);
|
ctx->iack_handler(line);
|
||||||
else
|
else
|
||||||
m68kcontext.interrupts[0] = 0;
|
ctx->interrupts[0] = 0;
|
||||||
|
|
||||||
SET_PC(execute_exception(line + 0x18, GET_PC, GET_SR));
|
SET_PC(execute_exception(ctx, line + 0x18, GET_PC, GET_SR));
|
||||||
flag_I = (u32)line;
|
flag_I = (u32)line;
|
||||||
if (m68kcontext.io_cycle_counter <= 0) goto famec_End;
|
if (ctx->io_cycle_counter <= 0) goto famec_End;
|
||||||
}
|
}
|
||||||
#ifdef FAMEC_EMULATE_TRACE
|
#ifdef FAMEC_EMULATE_TRACE
|
||||||
else
|
else
|
||||||
if (flag_T)
|
if (flag_T)
|
||||||
{
|
{
|
||||||
m68kcontext.execinfo |= FM68K_EMULATE_TRACE;
|
ctx->execinfo |= FM68K_EMULATE_TRACE;
|
||||||
cycles_needed = m68kcontext.io_cycle_counter;
|
cycles_needed = ctx->io_cycle_counter;
|
||||||
m68kcontext.io_cycle_counter=0;
|
ctx->io_cycle_counter=0;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
@ -927,14 +918,14 @@ famec_Exec:
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef FAMEC_EMULATE_TRACE
|
#ifdef FAMEC_EMULATE_TRACE
|
||||||
if (m68kcontext.execinfo & FM68K_EMULATE_TRACE)
|
if (ctx->execinfo & FM68K_EMULATE_TRACE)
|
||||||
{
|
{
|
||||||
m68kcontext.io_cycle_counter += cycles_needed;
|
ctx->io_cycle_counter += cycles_needed;
|
||||||
cycles_needed = 0;
|
cycles_needed = 0;
|
||||||
m68kcontext.execinfo &= ~FM68K_EMULATE_TRACE;
|
ctx->execinfo &= ~FM68K_EMULATE_TRACE;
|
||||||
m68kcontext.execinfo |= FM68K_DO_TRACE;
|
ctx->execinfo |= FM68K_DO_TRACE;
|
||||||
SET_PC(execute_exception(M68K_TRACE_EX, GET_PC, GET_SR));
|
SET_PC(execute_exception(ctx, M68K_TRACE_EX, GET_PC, GET_SR));
|
||||||
if (m68kcontext.io_cycle_counter > 0)
|
if (ctx->io_cycle_counter > 0)
|
||||||
{
|
{
|
||||||
//NEXT
|
//NEXT
|
||||||
goto famec_Exec;
|
goto famec_Exec;
|
||||||
|
@ -945,24 +936,24 @@ famec_Exec:
|
||||||
if (cycles_needed != 0)
|
if (cycles_needed != 0)
|
||||||
{
|
{
|
||||||
u32 line;
|
u32 line;
|
||||||
m68kcontext.io_cycle_counter += cycles_needed;
|
ctx->io_cycle_counter += cycles_needed;
|
||||||
cycles_needed = 0;
|
cycles_needed = 0;
|
||||||
//if (m68kcontext.io_cycle_counter <= 0) goto famec_End;
|
//if (ctx->io_cycle_counter <= 0) goto famec_End;
|
||||||
line=interrupt_chk__();
|
line=interrupt_chk__(ctx);
|
||||||
if (line>0)
|
if (line>0)
|
||||||
{
|
{
|
||||||
if (m68kcontext.iack_handler != NULL)
|
if (ctx->iack_handler != NULL)
|
||||||
m68kcontext.iack_handler(line);
|
ctx->iack_handler(line);
|
||||||
else
|
else
|
||||||
m68kcontext.interrupts[0] = 0;
|
ctx->interrupts[0] = 0;
|
||||||
|
|
||||||
SET_PC(execute_exception(line + 0x18, GET_PC, GET_SR));
|
SET_PC(execute_exception(ctx, line + 0x18, GET_PC, GET_SR));
|
||||||
flag_I = (u32)line;
|
flag_I = (u32)line;
|
||||||
}
|
}
|
||||||
#ifdef FAMEC_EMULATE_TRACE
|
#ifdef FAMEC_EMULATE_TRACE
|
||||||
if (!(flag_T))
|
if (!(flag_T))
|
||||||
#endif
|
#endif
|
||||||
if (m68kcontext.io_cycle_counter > 0)
|
if (ctx->io_cycle_counter > 0)
|
||||||
{
|
{
|
||||||
//NEXT
|
//NEXT
|
||||||
goto famec_Exec;
|
goto famec_Exec;
|
||||||
|
@ -970,19 +961,19 @@ famec_Exec:
|
||||||
}
|
}
|
||||||
|
|
||||||
famec_End:
|
famec_End:
|
||||||
m68kcontext.sr = GET_SR;
|
ctx->sr = GET_SR;
|
||||||
m68kcontext.pc = GET_PC;
|
ctx->pc = GET_PC;
|
||||||
|
|
||||||
m68kcontext.execinfo &= ~M68K_RUNNING;
|
ctx->execinfo &= ~M68K_RUNNING;
|
||||||
|
|
||||||
#ifdef FAMEC_DEBUG
|
#ifdef FAMEC_DEBUG
|
||||||
printf("En really end...\n");
|
printf("En really end...\n");
|
||||||
printf("PC: %p\n",PC);
|
printf("PC: %p\n",PC);
|
||||||
printf("BasePC: 0x%08x\n",BasePC);
|
printf("BasePC: 0x%08x\n",BasePC);
|
||||||
printf("pc: 0x%08x\n",m68kcontext.pc);
|
printf("pc: 0x%08x\n",ctx->pc);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
return cycles - m68kcontext.io_cycle_counter;
|
return cycles - ctx->io_cycle_counter;
|
||||||
|
|
||||||
#ifndef FAMEC_NO_GOTOS
|
#ifndef FAMEC_NO_GOTOS
|
||||||
init_jump_table:
|
init_jump_table:
|
||||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -139,7 +139,6 @@ static void SekRunS68k(unsigned int to)
|
||||||
m68k_set_context(&PicoCpuMM68k);
|
m68k_set_context(&PicoCpuMM68k);
|
||||||
#elif defined(EMU_F68K)
|
#elif defined(EMU_F68K)
|
||||||
SekCycleCntS68k += fm68k_emulate(&PicoCpuFS68k, cyc_do, 0) - cyc_do;
|
SekCycleCntS68k += fm68k_emulate(&PicoCpuFS68k, cyc_do, 0) - cyc_do;
|
||||||
g_m68kcontext = &PicoCpuFM68k;
|
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -117,15 +117,10 @@ PICO_INTERNAL void SekInitS68k(void)
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
#ifdef EMU_F68K
|
#ifdef EMU_F68K
|
||||||
{
|
memset(&PicoCpuFS68k, 0, sizeof(PicoCpuFS68k));
|
||||||
void *oldcontext = g_m68kcontext;
|
fm68k_init();
|
||||||
g_m68kcontext = &PicoCpuFS68k;
|
PicoCpuFS68k.iack_handler = SekIntAckFS68k;
|
||||||
memset(&PicoCpuFS68k, 0, sizeof(PicoCpuFS68k));
|
PicoCpuFS68k.sr = 0x2704; // Z flag
|
||||||
fm68k_init();
|
|
||||||
PicoCpuFS68k.iack_handler = SekIntAckFS68k;
|
|
||||||
PicoCpuFS68k.sr = 0x2704; // Z flag
|
|
||||||
g_m68kcontext = oldcontext;
|
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -149,11 +144,7 @@ PICO_INTERNAL int SekResetS68k(void)
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
#ifdef EMU_F68K
|
#ifdef EMU_F68K
|
||||||
{
|
fm68k_reset(&PicoCpuFS68k);
|
||||||
void *oldcontext = g_m68kcontext;
|
|
||||||
fm68k_reset(&PicoCpuFS68k);
|
|
||||||
g_m68kcontext = oldcontext;
|
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -30,6 +30,7 @@ static struct Cyclone *currentC68k = NULL;
|
||||||
#define other_is_stopped() (currentC68k->state_flags&1)
|
#define other_is_stopped() (currentC68k->state_flags&1)
|
||||||
#define other_is_tracing() ((currentC68k->state_flags&2)?1:0)
|
#define other_is_tracing() ((currentC68k->state_flags&2)?1:0)
|
||||||
#elif defined(EMU_F68K)
|
#elif defined(EMU_F68K)
|
||||||
|
static struct M68K_CONTEXT *g_m68kcontext;
|
||||||
#define other_set_sub(s) g_m68kcontext=(s)?&PicoCpuFS68k:&PicoCpuFM68k;
|
#define other_set_sub(s) g_m68kcontext=(s)?&PicoCpuFS68k:&PicoCpuFM68k;
|
||||||
#define other_get_sr() g_m68kcontext->sr
|
#define other_get_sr() g_m68kcontext->sr
|
||||||
#define other_dar(i) ((unsigned int*)g_m68kcontext->dreg)[i]
|
#define other_dar(i) ((unsigned int*)g_m68kcontext->dreg)[i]
|
||||||
|
|
13
pico/sek.c
13
pico/sek.c
|
@ -128,15 +128,10 @@ PICO_INTERNAL void SekInit(void)
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
#ifdef EMU_F68K
|
#ifdef EMU_F68K
|
||||||
{
|
memset(&PicoCpuFM68k, 0, sizeof(PicoCpuFM68k));
|
||||||
void *oldcontext = g_m68kcontext;
|
fm68k_init();
|
||||||
g_m68kcontext = &PicoCpuFM68k;
|
PicoCpuFM68k.iack_handler = SekIntAckF68K;
|
||||||
memset(&PicoCpuFM68k, 0, sizeof(PicoCpuFM68k));
|
PicoCpuFM68k.sr = 0x2704; // Z flag
|
||||||
fm68k_init();
|
|
||||||
PicoCpuFM68k.iack_handler = SekIntAckF68K;
|
|
||||||
PicoCpuFM68k.sr = 0x2704; // Z flag
|
|
||||||
g_m68kcontext = oldcontext;
|
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue