diff options
Diffstat (limited to 'trunk/src/emu/cpu/v60/op2.c')
-rw-r--r-- | trunk/src/emu/cpu/v60/op2.c | 353 |
1 files changed, 353 insertions, 0 deletions
diff --git a/trunk/src/emu/cpu/v60/op2.c b/trunk/src/emu/cpu/v60/op2.c new file mode 100644 index 00000000000..d5895775d87 --- /dev/null +++ b/trunk/src/emu/cpu/v60/op2.c @@ -0,0 +1,353 @@ + + +#define F2END(cs) \ + return 2 + (cs)->amlength1 + (cs)->amlength2; + +#define F2LOADOPFLOAT(cs, num) \ + if ((cs)->flag##num) \ + appf = u2f((cs)->reg[(cs)->op##num]); \ + else \ + appf = u2f((cs)->program->read_dword_unaligned((cs)->op##num)); + +#define F2STOREOPFLOAT(cs,num) \ + if ((cs)->flag##num) \ + (cs)->reg[(cs)->op##num] = f2u(appf); \ + else \ + (cs)->program->write_dword_unaligned((cs)->op##num, f2u(appf)); + +static void F2DecodeFirstOperand(v60_state *cpustate, UINT32 (*DecodeOp1)(v60_state *), UINT8 dim1) +{ + cpustate->moddim = dim1; + cpustate->modm = cpustate->instflags & 0x40; + cpustate->modadd = cpustate->PC + 2; + cpustate->amlength1 = DecodeOp1(cpustate); + cpustate->op1 = cpustate->amout; + cpustate->flag1 = cpustate->amflag; +} + +static void F2DecodeSecondOperand(v60_state *cpustate, UINT32 (*DecodeOp2)(v60_state *), UINT8 dim2) +{ + cpustate->moddim = dim2; + cpustate->modm = cpustate->instflags & 0x20; + cpustate->modadd = cpustate->PC + 2 + cpustate->amlength1; + cpustate->amlength2 = DecodeOp2(cpustate); + cpustate->op2 = cpustate->amout; + cpustate->flag2 = cpustate->amflag; +} + +static void F2WriteSecondOperand(v60_state *cpustate, UINT8 dim2) +{ + cpustate->moddim = dim2; + cpustate->modm = cpustate->instflags & 0x20; + cpustate->modadd = cpustate->PC + 2 + cpustate->amlength1; + cpustate->amlength2 = WriteAM(cpustate); +} + +static UINT32 opCVTWS(v60_state *cpustate) +{ + float val; + + F2DecodeFirstOperand(cpustate, ReadAM, 2); + + // Convert to float + val = (float)(INT32)cpustate->op1; + cpustate->modwritevalw = f2u(val); + + cpustate->_OV = 0; + cpustate->_CY = (val < 0.0f); + cpustate->_S = ((cpustate->modwritevalw & 0x80000000) != 0); + cpustate->_Z = (val == 0.0f); + + F2WriteSecondOperand(cpustate, 2); + F2END(cpustate); +} + +static UINT32 opCVTSW(v60_state *cpustate) +{ + float val; + + F2DecodeFirstOperand(cpustate, ReadAM, 2); + + // Convert to UINT32 + val = u2f(cpustate->op1); + cpustate->modwritevalw = (UINT32)val; + + cpustate->_OV = 0; + cpustate->_CY =(val < 0.0f); + cpustate->_S = ((cpustate->modwritevalw & 0x80000000) != 0); + cpustate->_Z = (val == 0.0f); + + F2WriteSecondOperand(cpustate, 2); + F2END(cpustate); +} + +static UINT32 opMOVFS(v60_state *cpustate) +{ + F2DecodeFirstOperand(cpustate, ReadAM, 2); + cpustate->modwritevalw = cpustate->op1; + F2WriteSecondOperand(cpustate, 2); + F2END(cpustate); +} + +static UINT32 opNEGFS(v60_state *cpustate) +{ + float appf; + + F2DecodeFirstOperand(cpustate, ReadAM, 2); + F2DecodeSecondOperand(cpustate, ReadAMAddress, 2); + + appf = -u2f(cpustate->op1); + + cpustate->_OV = 0; + cpustate->_CY = (appf < 0.0f); + cpustate->_S = ((f2u(appf) & 0x80000000) != 0); + cpustate->_Z = (appf == 0.0f); + + F2STOREOPFLOAT(cpustate, 2); + F2END(cpustate) +} + +static UINT32 opABSFS(v60_state *cpustate) +{ + float appf; + + F2DecodeFirstOperand(cpustate, ReadAM, 2); + F2DecodeSecondOperand(cpustate, ReadAMAddress, 2); + + appf = u2f(cpustate->op1); + + if(appf < 0) + appf = -appf; + + cpustate->_OV = 0; + cpustate->_CY = 0; + cpustate->_S = ((f2u(appf) & 0x80000000) != 0); + cpustate->_Z = (appf == 0.0f); + + F2STOREOPFLOAT(cpustate, 2); + F2END(cpustate) +} + +static UINT32 opADDFS(v60_state *cpustate) +{ + UINT32 appw; + float appf; + + F2DecodeFirstOperand(cpustate, ReadAM, 2); + F2DecodeSecondOperand(cpustate, ReadAMAddress, 2); + + F2LOADOPFLOAT(cpustate, 2); + + appf += u2f(cpustate->op1); + + appw = f2u(appf); + cpustate->_OV = cpustate->_CY = 0; + cpustate->_S = ((appw & 0x80000000) != 0); + cpustate->_Z = (appw == 0); + + F2STOREOPFLOAT(cpustate, 2); + F2END(cpustate) +} + +static UINT32 opSUBFS(v60_state *cpustate) +{ + UINT32 appw; + float appf; + + F2DecodeFirstOperand(cpustate, ReadAM, 2); + F2DecodeSecondOperand(cpustate, ReadAMAddress, 2); + + F2LOADOPFLOAT(cpustate, 2); + + appf -= u2f(cpustate->op1); + + appw = f2u(appf); + cpustate->_OV = cpustate->_CY = 0; + cpustate->_S = ((appw & 0x80000000) != 0); + cpustate->_Z = (appw == 0); + + F2STOREOPFLOAT(cpustate, 2); + F2END(cpustate) +} + +static UINT32 opMULFS(v60_state *cpustate) +{ + UINT32 appw; + float appf; + + F2DecodeFirstOperand(cpustate, ReadAM, 2); + F2DecodeSecondOperand(cpustate, ReadAMAddress, 2); + + F2LOADOPFLOAT(cpustate, 2); + + appf *= u2f(cpustate->op1); + + appw = f2u(appf); + cpustate->_OV = cpustate->_CY = 0; + cpustate->_S = ((appw & 0x80000000) != 0); + cpustate->_Z = (appw == 0); + + F2STOREOPFLOAT(cpustate, 2); + F2END(cpustate) +} + +static UINT32 opDIVFS(v60_state *cpustate) +{ + UINT32 appw; + float appf; + + F2DecodeFirstOperand(cpustate, ReadAM, 2); + F2DecodeSecondOperand(cpustate, ReadAMAddress, 2); + + F2LOADOPFLOAT(cpustate, 2); + + appf /= u2f(cpustate->op1); + + appw = f2u(appf); + cpustate->_OV = cpustate->_CY = 0; + cpustate->_S = ((appw & 0x80000000) != 0); + cpustate->_Z = (appw == 0); + + F2STOREOPFLOAT(cpustate, 2); + F2END(cpustate) +} + +static UINT32 opSCLFS(v60_state *cpustate) +{ + UINT32 appw; + float appf; + + F2DecodeFirstOperand(cpustate, ReadAM, 1); + F2DecodeSecondOperand(cpustate, ReadAMAddress, 2); + + F2LOADOPFLOAT(cpustate, 2); + + if ((INT16)cpustate->op1 < 0) + appf /= 1 << -(INT16)cpustate->op1; + else + appf *= 1 << cpustate->op1; + + appw = f2u(appf); + cpustate->_OV = cpustate->_CY = 0; + cpustate->_S = ((appw & 0x80000000) != 0); + cpustate->_Z = (appw == 0); + + F2STOREOPFLOAT(cpustate, 2); + F2END(cpustate) +} + +static UINT32 opCMPF(v60_state *cpustate) +{ + float appf; + + F2DecodeFirstOperand(cpustate, ReadAM, 2); + F2DecodeSecondOperand(cpustate, ReadAM, 2); + + appf = u2f(cpustate->op2) - u2f(cpustate->op1); + + cpustate->_Z = (appf == 0); + cpustate->_S = (appf < 0); + cpustate->_OV = 0; + cpustate->_CY = 0; + + F2END(cpustate); +} + +static UINT32 op5FUNHANDLED(v60_state *cpustate) +{ + fatalerror("Unhandled 5F opcode at %08x", cpustate->PC); + return 0; /* never reached, fatalerror won't return */ +} + +static UINT32 op5CUNHANDLED(v60_state *cpustate) +{ + fatalerror("Unhandled 5C opcode at %08x", cpustate->PC); + return 0; /* never reached, fatalerror won't return */ +} + +static UINT32 (*const Op5FTable[32])(v60_state *) = +{ + opCVTWS, + opCVTSW, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED, + op5FUNHANDLED +}; + +static UINT32 (*const Op5CTable[32])(v60_state *) = +{ + opCMPF, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + opMOVFS, + opNEGFS, + opABSFS, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + + opSCLFS, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + opADDFS, + opSUBFS, + opMULFS, + opDIVFS, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED, + op5CUNHANDLED +}; + + +static UINT32 op5F(v60_state *cpustate) +{ + cpustate->instflags = OpRead8(cpustate, cpustate->PC + 1); + return Op5FTable[cpustate->instflags & 0x1F](cpustate); +} + + +static UINT32 op5C(v60_state *cpustate) +{ + cpustate->instflags = OpRead8(cpustate, cpustate->PC + 1); + return Op5CTable[cpustate->instflags & 0x1F](cpustate); +} |