Merge pull request #3063 from lioncash/func
DSPJitRegCache: Fix function casing
This commit is contained in:
commit
63c373c843
|
@ -89,12 +89,12 @@ void DSPEmitter::checkExceptions(u32 retval)
|
|||
MOV(16, M(&(g_dsp.pc)), Imm16(compilePC));
|
||||
|
||||
DSPJitRegCache c(gpr);
|
||||
gpr.saveRegs();
|
||||
gpr.SaveRegs();
|
||||
ABI_CallFunction((void *)&DSPCore_CheckExceptions);
|
||||
MOV(32, R(EAX), Imm32(retval));
|
||||
JMP(returnDispatcher, true);
|
||||
gpr.loadRegs(false);
|
||||
gpr.flushRegs(c,false);
|
||||
gpr.LoadRegs(false);
|
||||
gpr.FlushRegs(c,false);
|
||||
|
||||
SetJumpTarget(skipCheck);
|
||||
}
|
||||
|
@ -119,10 +119,10 @@ void DSPEmitter::Default(UDSPInstruction inst)
|
|||
}
|
||||
|
||||
// Fall back to interpreter
|
||||
gpr.pushRegs();
|
||||
gpr.PushRegs();
|
||||
_assert_msg_(DSPLLE, opTable[inst]->intFunc, "No function for %04x",inst);
|
||||
ABI_CallFunctionC16((void*)opTable[inst]->intFunc, inst);
|
||||
gpr.popRegs();
|
||||
gpr.PopRegs();
|
||||
}
|
||||
|
||||
void DSPEmitter::EmitInstruction(UDSPInstruction inst)
|
||||
|
@ -138,9 +138,9 @@ void DSPEmitter::EmitInstruction(UDSPInstruction inst)
|
|||
if (! extOpTable[inst & 0x7F]->jitFunc)
|
||||
{
|
||||
// Fall back to interpreter
|
||||
gpr.pushRegs();
|
||||
gpr.PushRegs();
|
||||
ABI_CallFunctionC16((void*)extOpTable[inst & 0x7F]->intFunc, inst);
|
||||
gpr.popRegs();
|
||||
gpr.PopRegs();
|
||||
INFO_LOG(DSPLLE, "Instruction not JITed(ext part): %04x\n", inst);
|
||||
ext_is_jit = false;
|
||||
}
|
||||
|
@ -155,9 +155,9 @@ void DSPEmitter::EmitInstruction(UDSPInstruction inst)
|
|||
if (!extOpTable[inst & 0xFF]->jitFunc)
|
||||
{
|
||||
// Fall back to interpreter
|
||||
gpr.pushRegs();
|
||||
gpr.PushRegs();
|
||||
ABI_CallFunctionC16((void*)extOpTable[inst & 0xFF]->intFunc, inst);
|
||||
gpr.popRegs();
|
||||
gpr.PopRegs();
|
||||
INFO_LOG(DSPLLE, "Instruction not JITed(ext part): %04x\n", inst);
|
||||
ext_is_jit = false;
|
||||
}
|
||||
|
@ -187,9 +187,9 @@ void DSPEmitter::EmitInstruction(UDSPInstruction inst)
|
|||
{
|
||||
//need to call the online cleanup function because
|
||||
//the writeBackLog gets populated at runtime
|
||||
gpr.pushRegs();
|
||||
gpr.PushRegs();
|
||||
ABI_CallFunction((void*)::applyWriteBackLog);
|
||||
gpr.popRegs();
|
||||
gpr.PopRegs();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -215,7 +215,7 @@ void DSPEmitter::Compile(u16 start_addr)
|
|||
return;
|
||||
*/
|
||||
|
||||
gpr.loadRegs();
|
||||
gpr.LoadRegs();
|
||||
|
||||
blockLinkEntry = GetCodePtr();
|
||||
|
||||
|
@ -263,7 +263,7 @@ void DSPEmitter::Compile(u16 start_addr)
|
|||
// end of each block and in this order
|
||||
DSPJitRegCache c(gpr);
|
||||
HandleLoop();
|
||||
gpr.saveRegs();
|
||||
gpr.SaveRegs();
|
||||
if (!DSPHost::OnThread() && DSPAnalyzer::code_flags[start_addr] & DSPAnalyzer::CODE_IDLE_SKIP)
|
||||
{
|
||||
MOV(16, R(EAX), Imm16(DSP_IDLE_SKIP_CYCLES));
|
||||
|
@ -273,8 +273,8 @@ void DSPEmitter::Compile(u16 start_addr)
|
|||
MOV(16, R(EAX), Imm16(blockSize[start_addr]));
|
||||
}
|
||||
JMP(returnDispatcher, true);
|
||||
gpr.loadRegs(false);
|
||||
gpr.flushRegs(c,false);
|
||||
gpr.LoadRegs(false);
|
||||
gpr.FlushRegs(c,false);
|
||||
|
||||
SetJumpTarget(rLoopAddressExit);
|
||||
SetJumpTarget(rLoopCounterExit);
|
||||
|
@ -297,7 +297,7 @@ void DSPEmitter::Compile(u16 start_addr)
|
|||
|
||||
DSPJitRegCache c(gpr);
|
||||
//don't update g_dsp.pc -- the branch insn already did
|
||||
gpr.saveRegs();
|
||||
gpr.SaveRegs();
|
||||
if (!DSPHost::OnThread() && DSPAnalyzer::code_flags[start_addr] & DSPAnalyzer::CODE_IDLE_SKIP)
|
||||
{
|
||||
MOV(16, R(EAX), Imm16(DSP_IDLE_SKIP_CYCLES));
|
||||
|
@ -307,8 +307,8 @@ void DSPEmitter::Compile(u16 start_addr)
|
|||
MOV(16, R(EAX), Imm16(blockSize[start_addr]));
|
||||
}
|
||||
JMP(returnDispatcher, true);
|
||||
gpr.loadRegs(false);
|
||||
gpr.flushRegs(c,false);
|
||||
gpr.LoadRegs(false);
|
||||
gpr.FlushRegs(c,false);
|
||||
|
||||
SetJumpTarget(rNoBranch);
|
||||
}
|
||||
|
@ -360,7 +360,7 @@ void DSPEmitter::Compile(u16 start_addr)
|
|||
blockSize[start_addr] = 1;
|
||||
}
|
||||
|
||||
gpr.saveRegs();
|
||||
gpr.SaveRegs();
|
||||
if (!DSPHost::OnThread() && DSPAnalyzer::code_flags[start_addr] & DSPAnalyzer::CODE_IDLE_SKIP)
|
||||
{
|
||||
MOV(16, R(EAX), Imm16(DSP_IDLE_SKIP_CYCLES));
|
||||
|
|
|
@ -74,7 +74,7 @@ void DSPEmitter::andcf(const UDSPInstruction opc)
|
|||
// else
|
||||
// g_dsp.r.sr &= ~SR_LOGIC_ZERO;
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
AND(16, R(RAX), Imm16(imm));
|
||||
CMP(16, R(RAX), Imm16(imm));
|
||||
FixupBranch notLogicZero = J_CC(CC_NE);
|
||||
|
@ -83,7 +83,7 @@ void DSPEmitter::andcf(const UDSPInstruction opc)
|
|||
SetJumpTarget(notLogicZero);
|
||||
AND(16, sr_reg, Imm16(~SR_LOGIC_ZERO));
|
||||
SetJumpTarget(exit);
|
||||
gpr.putReg(DSP_REG_SR);
|
||||
gpr.PutReg(DSP_REG_SR);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -110,7 +110,7 @@ void DSPEmitter::andf(const UDSPInstruction opc)
|
|||
// else
|
||||
// g_dsp.r.sr &= ~SR_LOGIC_ZERO;
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
TEST(16, R(RAX), Imm16(imm));
|
||||
FixupBranch notLogicZero = J_CC(CC_NE);
|
||||
OR(16, sr_reg, Imm16(SR_LOGIC_ZERO));
|
||||
|
@ -118,7 +118,7 @@ void DSPEmitter::andf(const UDSPInstruction opc)
|
|||
SetJumpTarget(notLogicZero);
|
||||
AND(16, sr_reg, Imm16(~SR_LOGIC_ZERO));
|
||||
SetJumpTarget(exit);
|
||||
gpr.putReg(DSP_REG_SR);
|
||||
gpr.PutReg(DSP_REG_SR);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -170,7 +170,7 @@ void DSPEmitter::cmp(const UDSPInstruction opc)
|
|||
if (FlagsNeeded())
|
||||
{
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc0 = dsp_get_long_acc(0);
|
||||
get_long_acc(0, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -181,7 +181,7 @@ void DSPEmitter::cmp(const UDSPInstruction opc)
|
|||
// Update_SR_Register64(res, isCarry2(acc0, res), isOverflow(acc0, -acc1, res)); // CF -> influence on ABS/0xa100
|
||||
NEG(64, R(RDX));
|
||||
Update_SR_Register64_Carry(EAX, tmp1, true);
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -199,7 +199,7 @@ void DSPEmitter::cmpar(const UDSPInstruction opc)
|
|||
u8 sreg = (opc >> 11) & 0x1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 sr = dsp_get_long_acc(sreg);
|
||||
get_long_acc(sreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -212,7 +212,7 @@ void DSPEmitter::cmpar(const UDSPInstruction opc)
|
|||
// Update_SR_Register64(res, isCarry2(sr, res), isOverflow(sr, -rr, res));
|
||||
NEG(64, R(RDX));
|
||||
Update_SR_Register64_Carry(EAX, tmp1, true);
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -229,7 +229,7 @@ void DSPEmitter::cmpi(const UDSPInstruction opc)
|
|||
{
|
||||
u8 reg = (opc >> 8) & 0x1;
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 val = dsp_get_long_acc(reg);
|
||||
get_long_acc(reg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -241,7 +241,7 @@ void DSPEmitter::cmpi(const UDSPInstruction opc)
|
|||
// Update_SR_Register64(res, isCarry2(val, res), isOverflow(val, -imm, res));
|
||||
NEG(64, R(RDX));
|
||||
Update_SR_Register64_Carry(EAX, tmp1, true);
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -259,7 +259,7 @@ void DSPEmitter::cmpis(const UDSPInstruction opc)
|
|||
u8 areg = (opc >> 8) & 0x1;
|
||||
// s64 acc = dsp_get_long_acc(areg);
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
get_long_acc(areg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
// s64 val = (s8)opc;
|
||||
|
@ -270,7 +270,7 @@ void DSPEmitter::cmpis(const UDSPInstruction opc)
|
|||
// Update_SR_Register64(res, isCarry2(acc, res), isOverflow(acc, -val, res));
|
||||
NEG(64, R(RDX));
|
||||
Update_SR_Register64_Carry(EAX, tmp1, true);
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -528,7 +528,7 @@ void DSPEmitter::addr(const UDSPInstruction opc)
|
|||
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
// s64 ax = (s16)g_dsp.r[sreg];
|
||||
|
@ -549,7 +549,7 @@ void DSPEmitter::addr(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// ADDAX $acD, $axS
|
||||
|
@ -563,7 +563,7 @@ void DSPEmitter::addax(const UDSPInstruction opc)
|
|||
u8 sreg = (opc >> 9) & 0x1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -584,7 +584,7 @@ void DSPEmitter::addax(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// ADD $acD, $ac(1-D)
|
||||
|
@ -597,7 +597,7 @@ void DSPEmitter::add(const UDSPInstruction opc)
|
|||
u8 dreg = (opc >> 8) & 0x1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc0 = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -618,7 +618,7 @@ void DSPEmitter::add(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// ADDP $acD
|
||||
|
@ -631,7 +631,7 @@ void DSPEmitter::addp(const UDSPInstruction opc)
|
|||
u8 dreg = (opc >> 8) & 0x1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -652,7 +652,7 @@ void DSPEmitter::addp(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// ADDAXL $acD, $axS.l
|
||||
|
@ -667,7 +667,7 @@ void DSPEmitter::addaxl(const UDSPInstruction opc)
|
|||
u8 dreg = (opc >> 8) & 0x1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// u64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -689,7 +689,7 @@ void DSPEmitter::addaxl(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// ADDI $amR, #I
|
||||
|
@ -702,7 +702,7 @@ void DSPEmitter::addi(const UDSPInstruction opc)
|
|||
{
|
||||
u8 areg = (opc >> 8) & 0x1;
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(areg);
|
||||
get_long_acc(areg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -727,7 +727,7 @@ void DSPEmitter::addi(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(areg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// ADDIS $acD, #I
|
||||
|
@ -740,7 +740,7 @@ void DSPEmitter::addis(const UDSPInstruction opc)
|
|||
u8 dreg = (opc >> 8) & 0x1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -764,7 +764,7 @@ void DSPEmitter::addis(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// INCM $acsD
|
||||
|
@ -777,7 +777,7 @@ void DSPEmitter::incm(const UDSPInstruction opc)
|
|||
u8 dreg = (opc >> 8) & 0x1;
|
||||
s64 subtract = 0x10000;
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -797,7 +797,7 @@ void DSPEmitter::incm(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// INC $acD
|
||||
|
@ -809,7 +809,7 @@ void DSPEmitter::inc(const UDSPInstruction opc)
|
|||
{
|
||||
u8 dreg = (opc >> 8) & 0x1;
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -829,7 +829,7 @@ void DSPEmitter::inc(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
//----
|
||||
|
@ -845,7 +845,7 @@ void DSPEmitter::subr(const UDSPInstruction opc)
|
|||
u8 sreg = ((opc >> 9) & 0x3) + DSP_REG_AXL0;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -869,7 +869,7 @@ void DSPEmitter::subr(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// SUBAX $acD, $axS
|
||||
|
@ -883,7 +883,7 @@ void DSPEmitter::subax(const UDSPInstruction opc)
|
|||
u8 sreg = (opc >> 9) & 0x1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -905,7 +905,7 @@ void DSPEmitter::subax(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// SUB $acD, $ac(1-D)
|
||||
|
@ -917,7 +917,7 @@ void DSPEmitter::sub(const UDSPInstruction opc)
|
|||
{
|
||||
u8 dreg = (opc >> 8) & 0x1;
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc1 = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -939,7 +939,7 @@ void DSPEmitter::sub(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// SUBP $acD
|
||||
|
@ -951,7 +951,7 @@ void DSPEmitter::subp(const UDSPInstruction opc)
|
|||
{
|
||||
u8 dreg = (opc >> 8) & 0x1;
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -973,7 +973,7 @@ void DSPEmitter::subp(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// DECM $acsD
|
||||
|
@ -986,7 +986,7 @@ void DSPEmitter::decm(const UDSPInstruction opc)
|
|||
u8 dreg = (opc >> 8) & 0x01;
|
||||
s64 subtract = 0x10000;
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -1006,7 +1006,7 @@ void DSPEmitter::decm(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// DEC $acD
|
||||
|
@ -1018,7 +1018,7 @@ void DSPEmitter::dec(const UDSPInstruction opc)
|
|||
{
|
||||
u8 dreg = (opc >> 8) & 0x01;
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// s64 acc = dsp_get_long_acc(dreg);
|
||||
get_long_acc(dreg, tmp1);
|
||||
MOV(64, R(RAX), R(tmp1));
|
||||
|
@ -1038,7 +1038,7 @@ void DSPEmitter::dec(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
//----
|
||||
|
|
|
@ -69,14 +69,14 @@ static void ReJitConditional(const UDSPInstruction opc, DSPEmitter& emitter)
|
|||
DSPJitRegCache c1(emitter.gpr);
|
||||
FixupBranch skipCode = cond == 0xe ? emitter.J_CC(CC_E,true) : emitter.J_CC((CCFlags)(CC_NE - (cond & 1)),true);
|
||||
jitCode(opc,emitter);
|
||||
emitter.gpr.flushRegs(c1);
|
||||
emitter.gpr.FlushRegs(c1);
|
||||
emitter.SetJumpTarget(skipCode);
|
||||
}
|
||||
|
||||
static void WriteBranchExit(DSPEmitter& emitter)
|
||||
{
|
||||
DSPJitRegCache c(emitter.gpr);
|
||||
emitter.gpr.saveRegs();
|
||||
emitter.gpr.SaveRegs();
|
||||
if (DSPAnalyzer::code_flags[emitter.startAddr] & DSPAnalyzer::CODE_IDLE_SKIP)
|
||||
{
|
||||
emitter.MOV(16, R(EAX), Imm16(0x1000));
|
||||
|
@ -86,8 +86,8 @@ static void WriteBranchExit(DSPEmitter& emitter)
|
|||
emitter.MOV(16, R(EAX), Imm16(emitter.blockSize[emitter.startAddr]));
|
||||
}
|
||||
emitter.JMP(emitter.returnDispatcher, true);
|
||||
emitter.gpr.loadRegs(false);
|
||||
emitter.gpr.flushRegs(c,false);
|
||||
emitter.gpr.LoadRegs(false);
|
||||
emitter.gpr.FlushRegs(c,false);
|
||||
}
|
||||
|
||||
static void WriteBlockLink(DSPEmitter& emitter, u16 dest)
|
||||
|
@ -97,7 +97,7 @@ static void WriteBlockLink(DSPEmitter& emitter, u16 dest)
|
|||
{
|
||||
if (emitter.blockLinks[dest] != nullptr )
|
||||
{
|
||||
emitter.gpr.flushRegs();
|
||||
emitter.gpr.FlushRegs();
|
||||
// Check if we have enough cycles to execute the next block
|
||||
emitter.MOV(16, R(ECX), M(&cyclesLeft));
|
||||
emitter.CMP(16, R(ECX), Imm16(emitter.blockSize[emitter.startAddr] + emitter.blockSize[dest]));
|
||||
|
@ -300,7 +300,7 @@ void DSPEmitter::HandleLoop()
|
|||
dsp_reg_load_stack(0);
|
||||
dsp_reg_load_stack(2);
|
||||
dsp_reg_load_stack(3);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
|
||||
SetJumpTarget(loopUpdated);
|
||||
SetJumpTarget(rLoopAddrG);
|
||||
|
@ -331,7 +331,7 @@ void DSPEmitter::loop(const UDSPInstruction opc)
|
|||
dsp_reg_store_stack(0);
|
||||
MOV(16, R(RDX), Imm16(loop_pc));
|
||||
dsp_reg_store_stack(2);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
MOV(16, M(&(g_dsp.pc)), Imm16(compilePC + 1));
|
||||
FixupBranch exit = J(true);
|
||||
|
||||
|
@ -339,7 +339,7 @@ void DSPEmitter::loop(const UDSPInstruction opc)
|
|||
// dsp_skip_inst();
|
||||
MOV(16, M(&g_dsp.pc), Imm16(loop_pc + opTable[dsp_imem_read(loop_pc)]->size));
|
||||
WriteBranchExit(*this);
|
||||
gpr.flushRegs(c,false);
|
||||
gpr.FlushRegs(c,false);
|
||||
SetJumpTarget(exit);
|
||||
}
|
||||
|
||||
|
@ -402,7 +402,7 @@ void DSPEmitter::bloop(const UDSPInstruction opc)
|
|||
MOV(16, R(RDX), Imm16(loop_pc));
|
||||
dsp_reg_store_stack(2);
|
||||
MOV(16, M(&(g_dsp.pc)), Imm16(compilePC + 2));
|
||||
gpr.flushRegs(c,true);
|
||||
gpr.FlushRegs(c,true);
|
||||
FixupBranch exit = J(true);
|
||||
|
||||
SetJumpTarget(cnt);
|
||||
|
@ -410,7 +410,7 @@ void DSPEmitter::bloop(const UDSPInstruction opc)
|
|||
// dsp_skip_inst();
|
||||
MOV(16, M(&g_dsp.pc), Imm16(loop_pc + opTable[dsp_imem_read(loop_pc)]->size));
|
||||
WriteBranchExit(*this);
|
||||
gpr.flushRegs(c,false);
|
||||
gpr.FlushRegs(c,false);
|
||||
SetJumpTarget(exit);
|
||||
}
|
||||
|
||||
|
|
|
@ -14,7 +14,7 @@ using namespace Gen;
|
|||
void DSPEmitter::Update_SR_Register(Gen::X64Reg val)
|
||||
{
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
// // 0x04
|
||||
// if (_Value == 0) g_dsp.r[DSP_REG_SR] |= SR_ARITH_ZERO;
|
||||
TEST(64, R(val), R(val));
|
||||
|
@ -49,7 +49,7 @@ void DSPEmitter::Update_SR_Register(Gen::X64Reg val)
|
|||
OR(16, sr_reg, Imm16(SR_TOP2BITS));
|
||||
SetJumpTarget(cC);
|
||||
SetJumpTarget(end);
|
||||
gpr.putReg(DSP_REG_SR);
|
||||
gpr.PutReg(DSP_REG_SR);
|
||||
}
|
||||
|
||||
// In: RAX: s64 _Value
|
||||
|
@ -58,9 +58,9 @@ void DSPEmitter::Update_SR_Register64(Gen::X64Reg val)
|
|||
{
|
||||
// g_dsp.r[DSP_REG_SR] &= ~SR_CMP_MASK;
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
AND(16, sr_reg, Imm16(~SR_CMP_MASK));
|
||||
gpr.putReg(DSP_REG_SR);
|
||||
gpr.PutReg(DSP_REG_SR);
|
||||
Update_SR_Register(val);
|
||||
}
|
||||
|
||||
|
@ -70,7 +70,7 @@ void DSPEmitter::Update_SR_Register64(Gen::X64Reg val)
|
|||
void DSPEmitter::Update_SR_Register64_Carry(X64Reg val, X64Reg carry_ovfl, bool carry_eq)
|
||||
{
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
// g_dsp.r[DSP_REG_SR] &= ~SR_CMP_MASK;
|
||||
AND(16, sr_reg, Imm16(~SR_CMP_MASK));
|
||||
|
||||
|
@ -95,7 +95,7 @@ void DSPEmitter::Update_SR_Register64_Carry(X64Reg val, X64Reg carry_ovfl, bool
|
|||
OR(16, sr_reg, Imm16(SR_OVERFLOW | SR_OVERFLOW_STICKY));
|
||||
SetJumpTarget(noOverflow);
|
||||
|
||||
gpr.putReg(DSP_REG_SR);
|
||||
gpr.PutReg(DSP_REG_SR);
|
||||
if (carry_eq)
|
||||
{
|
||||
Update_SR_Register();
|
||||
|
@ -110,7 +110,7 @@ void DSPEmitter::Update_SR_Register64_Carry(X64Reg val, X64Reg carry_ovfl, bool
|
|||
void DSPEmitter::Update_SR_Register16(X64Reg val)
|
||||
{
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
AND(16, sr_reg, Imm16(~SR_CMP_MASK));
|
||||
|
||||
// // 0x04
|
||||
|
@ -139,7 +139,7 @@ void DSPEmitter::Update_SR_Register16(X64Reg val)
|
|||
OR(16, sr_reg, Imm16(SR_TOP2BITS));
|
||||
SetJumpTarget(notThree);
|
||||
SetJumpTarget(end);
|
||||
gpr.putReg(DSP_REG_SR);
|
||||
gpr.PutReg(DSP_REG_SR);
|
||||
}
|
||||
|
||||
// In: RAX: s64 _Value
|
||||
|
@ -147,7 +147,7 @@ void DSPEmitter::Update_SR_Register16(X64Reg val)
|
|||
void DSPEmitter::Update_SR_Register16_OverS32(Gen::X64Reg val)
|
||||
{
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
AND(16, sr_reg, Imm16(~SR_CMP_MASK));
|
||||
|
||||
// // 0x10
|
||||
|
@ -158,7 +158,7 @@ void DSPEmitter::Update_SR_Register16_OverS32(Gen::X64Reg val)
|
|||
OR(16, sr_reg, Imm16(SR_OVER_S32));
|
||||
SetJumpTarget(noOverS32);
|
||||
|
||||
gpr.putReg(DSP_REG_SR);
|
||||
gpr.PutReg(DSP_REG_SR);
|
||||
// // 0x20 - Checks if top bits of m are equal
|
||||
// if ((((u16)_Value >> 14) == 0) || (((u16)_Value >> 14) == 3))
|
||||
//AND(32, R(val), Imm32(0xc0000000));
|
||||
|
|
|
@ -72,13 +72,13 @@ void DSPEmitter::s(const UDSPInstruction opc)
|
|||
dsp_op_read_reg(dreg, RAX, ZERO);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1, ZERO);
|
||||
// u16 val = g_dsp.r[src];
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
increment_addr_reg(dreg);
|
||||
}
|
||||
|
@ -94,12 +94,12 @@ void DSPEmitter::sn(const UDSPInstruction opc)
|
|||
dsp_op_read_reg(dreg, RAX, ZERO);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
increase_addr_reg(dreg, dreg);
|
||||
}
|
||||
|
@ -166,12 +166,12 @@ void DSPEmitter::ls(const UDSPInstruction opc)
|
|||
dsp_op_read_reg(DSP_REG_AR3, RAX, ZERO);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg + DSP_REG_ACM0, tmp1, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
pushExtValueFromMem(dreg, DSP_REG_AR0);
|
||||
|
||||
|
@ -193,12 +193,12 @@ void DSPEmitter::lsn(const UDSPInstruction opc)
|
|||
dsp_op_read_reg(DSP_REG_AR3, RAX, ZERO);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg + DSP_REG_ACM0, tmp1, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
pushExtValueFromMem(dreg, DSP_REG_AR0);
|
||||
|
||||
|
@ -219,12 +219,12 @@ void DSPEmitter::lsm(const UDSPInstruction opc)
|
|||
dsp_op_read_reg(DSP_REG_AR3, RAX, ZERO);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg + DSP_REG_ACM0, tmp1, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
pushExtValueFromMem(dreg, DSP_REG_AR0);
|
||||
|
||||
|
@ -246,12 +246,12 @@ void DSPEmitter::lsnm(const UDSPInstruction opc)
|
|||
dsp_op_read_reg(DSP_REG_AR3, RAX, ZERO);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg + DSP_REG_ACM0, tmp1, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
pushExtValueFromMem(dreg, DSP_REG_AR0);
|
||||
|
||||
|
@ -271,12 +271,12 @@ void DSPEmitter::sl(const UDSPInstruction opc)
|
|||
dsp_op_read_reg(DSP_REG_AR0, RAX, ZERO);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg + DSP_REG_ACM0, tmp1, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
pushExtValueFromMem(dreg, DSP_REG_AR3);
|
||||
|
||||
|
@ -297,12 +297,12 @@ void DSPEmitter::sln(const UDSPInstruction opc)
|
|||
dsp_op_read_reg(DSP_REG_AR0, RAX, ZERO);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg + DSP_REG_ACM0, tmp1, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
pushExtValueFromMem(dreg, DSP_REG_AR3);
|
||||
|
||||
|
@ -323,12 +323,12 @@ void DSPEmitter::slm(const UDSPInstruction opc)
|
|||
dsp_op_read_reg(DSP_REG_AR0, RAX, ZERO);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg + DSP_REG_ACM0, tmp1, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
pushExtValueFromMem(dreg, DSP_REG_AR3);
|
||||
|
||||
|
@ -349,12 +349,12 @@ void DSPEmitter::slnm(const UDSPInstruction opc)
|
|||
dsp_op_read_reg(DSP_REG_AR0, RAX, ZERO);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg + DSP_REG_ACM0, tmp1, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
pushExtValueFromMem(dreg, DSP_REG_AR3);
|
||||
|
||||
|
@ -382,20 +382,20 @@ void DSPEmitter::ld(const UDSPInstruction opc)
|
|||
|
||||
// if (IsSameMemArea(g_dsp.r[sreg], g_dsp.r[DSP_REG_AR3])) {
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
dsp_op_read_reg(sreg, RCX, NONE);
|
||||
dsp_op_read_reg(DSP_REG_AR3, tmp, NONE);
|
||||
XOR(16, R(ECX), R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, R(ECX), Imm16(0xfc00));
|
||||
FixupBranch not_equal = J_CC(CC_NE,true);
|
||||
pushExtValueFromMem2((rreg << 1) + DSP_REG_AXL1, sreg);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
FixupBranch after = J(true);
|
||||
SetJumpTarget(not_equal); // else
|
||||
pushExtValueFromMem2((rreg << 1) + DSP_REG_AXL1, DSP_REG_AR3);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(after);
|
||||
|
||||
increment_addr_reg(sreg);
|
||||
|
@ -413,21 +413,21 @@ void DSPEmitter::ldax(const UDSPInstruction opc)
|
|||
pushExtValueFromMem(rreg + DSP_REG_AXH0, sreg);
|
||||
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
//if (IsSameMemArea(g_dsp.r[sreg], g_dsp.r[DSP_REG_AR3])) {
|
||||
dsp_op_read_reg(sreg, RCX, NONE);
|
||||
dsp_op_read_reg(DSP_REG_AR3, tmp, NONE);
|
||||
XOR(16, R(ECX), R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, R(ECX), Imm16(0xfc00));
|
||||
FixupBranch not_equal = J_CC(CC_NE, true);
|
||||
pushExtValueFromMem2(rreg + DSP_REG_AXL0, sreg);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
FixupBranch after = J(true); // else
|
||||
SetJumpTarget(not_equal);
|
||||
pushExtValueFromMem2(rreg + DSP_REG_AXL0, DSP_REG_AR3);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(after);
|
||||
|
||||
increment_addr_reg(sreg);
|
||||
|
@ -446,21 +446,21 @@ void DSPEmitter::ldn(const UDSPInstruction opc)
|
|||
pushExtValueFromMem((dreg << 1) + DSP_REG_AXL0, sreg);
|
||||
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
//if (IsSameMemArea(g_dsp.r[sreg], g_dsp.r[DSP_REG_AR3])) {
|
||||
dsp_op_read_reg(sreg, RCX, NONE);
|
||||
dsp_op_read_reg(DSP_REG_AR3, tmp, NONE);
|
||||
XOR(16, R(ECX), R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, R(ECX), Imm16(0xfc00));
|
||||
FixupBranch not_equal = J_CC(CC_NE,true);
|
||||
pushExtValueFromMem2((rreg << 1) + DSP_REG_AXL1, sreg);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
FixupBranch after = J(true);
|
||||
SetJumpTarget(not_equal); // else
|
||||
pushExtValueFromMem2((rreg << 1) + DSP_REG_AXL1, DSP_REG_AR3);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(after);
|
||||
|
||||
increase_addr_reg(sreg, sreg);
|
||||
|
@ -478,21 +478,21 @@ void DSPEmitter::ldaxn(const UDSPInstruction opc)
|
|||
pushExtValueFromMem(rreg + DSP_REG_AXH0, sreg);
|
||||
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
//if (IsSameMemArea(g_dsp.r[sreg], g_dsp.r[DSP_REG_AR3])) {
|
||||
dsp_op_read_reg(sreg, RCX, NONE);
|
||||
dsp_op_read_reg(DSP_REG_AR3, tmp, NONE);
|
||||
XOR(16, R(ECX), R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, R(ECX), Imm16(0xfc00));
|
||||
FixupBranch not_equal = J_CC(CC_NE,true);
|
||||
pushExtValueFromMem2(rreg + DSP_REG_AXL0, sreg);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
FixupBranch after = J(true); // else
|
||||
SetJumpTarget(not_equal);
|
||||
pushExtValueFromMem2(rreg + DSP_REG_AXL0, DSP_REG_AR3);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(after);
|
||||
|
||||
increase_addr_reg(sreg, sreg);
|
||||
|
@ -511,21 +511,21 @@ void DSPEmitter::ldm(const UDSPInstruction opc)
|
|||
pushExtValueFromMem((dreg << 1) + DSP_REG_AXL0, sreg);
|
||||
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
//if (IsSameMemArea(g_dsp.r[sreg], g_dsp.r[DSP_REG_AR3])) {
|
||||
dsp_op_read_reg(sreg, RCX, NONE);
|
||||
dsp_op_read_reg(DSP_REG_AR3, tmp, NONE);
|
||||
XOR(16, R(ECX), R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, R(ECX), Imm16(0xfc00));
|
||||
FixupBranch not_equal = J_CC(CC_NE,true);
|
||||
pushExtValueFromMem2((rreg << 1) + DSP_REG_AXL1, sreg);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
FixupBranch after = J(true);
|
||||
SetJumpTarget(not_equal); // else
|
||||
pushExtValueFromMem2((rreg << 1) + DSP_REG_AXL1, DSP_REG_AR3);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(after);
|
||||
|
||||
increment_addr_reg(sreg);
|
||||
|
@ -543,21 +543,21 @@ void DSPEmitter::ldaxm(const UDSPInstruction opc)
|
|||
pushExtValueFromMem(rreg + DSP_REG_AXH0, sreg);
|
||||
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
//if (IsSameMemArea(g_dsp.r[sreg], g_dsp.r[DSP_REG_AR3])) {
|
||||
dsp_op_read_reg(sreg, RCX, NONE);
|
||||
dsp_op_read_reg(DSP_REG_AR3, tmp, NONE);
|
||||
XOR(16, R(ECX), R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, R(ECX), Imm16(0xfc00));
|
||||
FixupBranch not_equal = J_CC(CC_NE,true);
|
||||
pushExtValueFromMem2(rreg + DSP_REG_AXL0, sreg);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
FixupBranch after = J(true); // else
|
||||
SetJumpTarget(not_equal);
|
||||
pushExtValueFromMem2(rreg + DSP_REG_AXL0, DSP_REG_AR3);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(after);
|
||||
|
||||
increment_addr_reg(sreg);
|
||||
|
@ -576,21 +576,21 @@ void DSPEmitter::ldnm(const UDSPInstruction opc)
|
|||
pushExtValueFromMem((dreg << 1) + DSP_REG_AXL0, sreg);
|
||||
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
//if (IsSameMemArea(g_dsp.r[sreg], g_dsp.r[DSP_REG_AR3])) {
|
||||
dsp_op_read_reg(sreg, RCX, NONE);
|
||||
dsp_op_read_reg(DSP_REG_AR3, tmp, NONE);
|
||||
XOR(16, R(ECX), R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, R(ECX), Imm16(0xfc00));
|
||||
FixupBranch not_equal = J_CC(CC_NE,true);
|
||||
pushExtValueFromMem2((rreg << 1) + DSP_REG_AXL1, sreg);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
FixupBranch after = J(true);
|
||||
SetJumpTarget(not_equal); // else
|
||||
pushExtValueFromMem2((rreg << 1) + DSP_REG_AXL1, DSP_REG_AR3);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(after);
|
||||
|
||||
increase_addr_reg(sreg, sreg);
|
||||
|
@ -608,21 +608,21 @@ void DSPEmitter::ldaxnm(const UDSPInstruction opc)
|
|||
pushExtValueFromMem(rreg + DSP_REG_AXH0, sreg);
|
||||
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
//if (IsSameMemArea(g_dsp.r[sreg], g_dsp.r[DSP_REG_AR3])) {
|
||||
dsp_op_read_reg(sreg, RCX, NONE);
|
||||
dsp_op_read_reg(DSP_REG_AR3, tmp, NONE);
|
||||
XOR(16, R(ECX), R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, R(ECX), Imm16(0xfc00));
|
||||
FixupBranch not_equal = J_CC(CC_NE,true);
|
||||
pushExtValueFromMem2(rreg + DSP_REG_AXL0, sreg);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
FixupBranch after = J(true); // else
|
||||
SetJumpTarget(not_equal);
|
||||
pushExtValueFromMem2(rreg + DSP_REG_AXL0, DSP_REG_AR3);
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(after);
|
||||
|
||||
increase_addr_reg(sreg, sreg);
|
||||
|
@ -637,12 +637,12 @@ void DSPEmitter::pushExtValueFromMem(u16 dreg, u16 sreg)
|
|||
// u16 addr = g_dsp.r[addr];
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1, ZERO);
|
||||
dmem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
MOVZX(32, 16, EBX, R(EAX));
|
||||
|
||||
|
@ -654,12 +654,12 @@ void DSPEmitter::pushExtValueFromMem2(u16 dreg, u16 sreg)
|
|||
// u16 addr = g_dsp.r[addr];
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1, ZERO);
|
||||
dmem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
SHL(32, R(EAX), Imm8(16));
|
||||
OR(32, R(EBX), R(EAX));
|
||||
|
@ -695,7 +695,7 @@ void DSPEmitter::popExtValueToReg()
|
|||
set_acc_h(storeIndex - DSP_REG_ACM0, R(RAX));
|
||||
set_acc_l(storeIndex - DSP_REG_ACM0, Imm16(0));
|
||||
//}
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(not_40bit);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -24,7 +24,7 @@ void DSPEmitter::srs(const UDSPInstruction opc)
|
|||
//u16 addr = (g_dsp.r.cr << 8) | (opc & 0xFF);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(reg, tmp1, ZERO);
|
||||
dsp_op_read_reg(DSP_REG_CR, RAX, ZERO);
|
||||
|
@ -32,7 +32,7 @@ void DSPEmitter::srs(const UDSPInstruction opc)
|
|||
OR(16, R(EAX), Imm16(opc & 0xFF));
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// LRS $(0x18+D), @M
|
||||
|
@ -45,7 +45,7 @@ void DSPEmitter::lrs(const UDSPInstruction opc)
|
|||
u8 reg = ((opc >> 8) & 0x7) + 0x18;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
//u16 addr = (g_dsp.r[DSP_REG_CR] << 8) | (opc & 0xFF);
|
||||
dsp_op_read_reg(DSP_REG_CR, tmp1, ZERO);
|
||||
|
@ -53,7 +53,7 @@ void DSPEmitter::lrs(const UDSPInstruction opc)
|
|||
OR(16, R(tmp1), Imm16(opc & 0xFF));
|
||||
dmem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
dsp_op_write_reg(reg, RAX);
|
||||
dsp_conditional_extend_accum(reg);
|
||||
|
@ -82,12 +82,12 @@ void DSPEmitter::sr(const UDSPInstruction opc)
|
|||
u16 address = dsp_imem_read(compilePC + 1);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(reg, tmp1);
|
||||
dmem_write_imm(address, tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// SI @M, #I
|
||||
|
@ -101,12 +101,12 @@ void DSPEmitter::si(const UDSPInstruction opc)
|
|||
u16 imm = dsp_imem_read(compilePC + 1);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
MOV(32, R(tmp1), Imm32((u32)imm));
|
||||
dmem_write_imm(address, tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// LRR $D, @$S
|
||||
|
@ -118,12 +118,12 @@ void DSPEmitter::lrr(const UDSPInstruction opc)
|
|||
u8 dreg = opc & 0x1f;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1);
|
||||
dmem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
dsp_op_write_reg(dreg, EAX);
|
||||
dsp_conditional_extend_accum(dreg);
|
||||
|
@ -139,12 +139,12 @@ void DSPEmitter::lrrd(const UDSPInstruction opc)
|
|||
u8 dreg = opc & 0x1f;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1);
|
||||
dmem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
dsp_op_write_reg(dreg, EAX);
|
||||
dsp_conditional_extend_accum(dreg);
|
||||
|
@ -161,12 +161,12 @@ void DSPEmitter::lrri(const UDSPInstruction opc)
|
|||
u8 dreg = opc & 0x1f;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1);
|
||||
dmem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
dsp_op_write_reg(dreg, EAX);
|
||||
dsp_conditional_extend_accum(dreg);
|
||||
|
@ -183,12 +183,12 @@ void DSPEmitter::lrrn(const UDSPInstruction opc)
|
|||
u8 dreg = opc & 0x1f;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1);
|
||||
dmem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
dsp_op_write_reg(dreg, EAX);
|
||||
dsp_conditional_extend_accum(dreg);
|
||||
|
@ -205,13 +205,13 @@ void DSPEmitter::srr(const UDSPInstruction opc)
|
|||
u8 sreg = opc & 0x1f;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1);
|
||||
dsp_op_read_reg(dreg, RAX, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// SRRD @$D, $S
|
||||
|
@ -224,13 +224,13 @@ void DSPEmitter::srrd(const UDSPInstruction opc)
|
|||
u8 sreg = opc & 0x1f;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1);
|
||||
dsp_op_read_reg(dreg, RAX, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
decrement_addr_reg(dreg);
|
||||
}
|
||||
|
@ -245,13 +245,13 @@ void DSPEmitter::srri(const UDSPInstruction opc)
|
|||
u8 sreg = opc & 0x1f;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1);
|
||||
dsp_op_read_reg(dreg, RAX, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
increment_addr_reg(dreg);
|
||||
}
|
||||
|
@ -266,13 +266,13 @@ void DSPEmitter::srrn(const UDSPInstruction opc)
|
|||
u8 sreg = opc & 0x1f;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(sreg, tmp1);
|
||||
dsp_op_read_reg(dreg, RAX, ZERO);
|
||||
dmem_write(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
increase_addr_reg(dreg, dreg);
|
||||
}
|
||||
|
@ -287,12 +287,12 @@ void DSPEmitter::ilrr(const UDSPInstruction opc)
|
|||
u16 dreg = (opc >> 8) & 1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(reg, tmp1, ZERO);
|
||||
imem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
set_acc_m(dreg, R(RAX));
|
||||
dsp_conditional_extend_accum(dreg + DSP_REG_ACM0);
|
||||
|
@ -308,12 +308,12 @@ void DSPEmitter::ilrrd(const UDSPInstruction opc)
|
|||
u16 dreg = (opc >> 8) & 1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(reg, tmp1, ZERO);
|
||||
imem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
set_acc_m(dreg, R(RAX));
|
||||
dsp_conditional_extend_accum(dreg + DSP_REG_ACM0);
|
||||
|
@ -330,12 +330,12 @@ void DSPEmitter::ilrri(const UDSPInstruction opc)
|
|||
u16 dreg = (opc >> 8) & 1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(reg, tmp1, ZERO);
|
||||
imem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
set_acc_m(dreg, R(RAX));
|
||||
dsp_conditional_extend_accum(dreg + DSP_REG_ACM0);
|
||||
|
@ -353,12 +353,12 @@ void DSPEmitter::ilrrn(const UDSPInstruction opc)
|
|||
u16 dreg = (opc >> 8) & 1;
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
|
||||
dsp_op_read_reg(reg, tmp1, ZERO);
|
||||
imem_read(tmp1);
|
||||
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
set_acc_m(dreg, R(RAX));
|
||||
dsp_conditional_extend_accum(dreg + DSP_REG_ACM0);
|
||||
|
|
|
@ -115,9 +115,9 @@ void DSPEmitter::setCompileSR(u16 bit)
|
|||
|
||||
// g_dsp.r[DSP_REG_SR] |= bit
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
OR(16, sr_reg, Imm16(bit));
|
||||
gpr.putReg(DSP_REG_SR);
|
||||
gpr.PutReg(DSP_REG_SR);
|
||||
|
||||
compileSR |= bit;
|
||||
}
|
||||
|
@ -127,9 +127,9 @@ void DSPEmitter::clrCompileSR(u16 bit)
|
|||
|
||||
// g_dsp.r[DSP_REG_SR] &= bit
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
AND(16, sr_reg, Imm16(~bit));
|
||||
gpr.putReg(DSP_REG_SR);
|
||||
gpr.PutReg(DSP_REG_SR);
|
||||
|
||||
compileSR &= ~bit;
|
||||
}
|
||||
|
|
|
@ -23,13 +23,13 @@ void DSPEmitter::multiply()
|
|||
// Conditionally multiply by 2.
|
||||
// if ((g_dsp.r.sr & SR_MUL_MODIFY) == 0)
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
TEST(16, sr_reg, Imm16(SR_MUL_MODIFY));
|
||||
FixupBranch noMult2 = J_CC(CC_NZ);
|
||||
// prod <<= 1;
|
||||
LEA(64, RAX, MRegSum(RAX,RAX));
|
||||
SetJumpTarget(noMult2);
|
||||
gpr.putReg(DSP_REG_SR, false);
|
||||
gpr.PutReg(DSP_REG_SR, false);
|
||||
// return prod;
|
||||
}
|
||||
|
||||
|
@ -77,7 +77,7 @@ void DSPEmitter::multiply_mulx(u8 axh0, u8 axh1)
|
|||
|
||||
// if ((sign == 1) && (g_dsp.r.sr & SR_MUL_UNSIGNED)) //unsigned
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
TEST(16, sr_reg, Imm16(SR_MUL_UNSIGNED));
|
||||
FixupBranch unsignedMul = J_CC(CC_NZ);
|
||||
// prod = (s16)a * (s16)b; //signed
|
||||
|
@ -87,7 +87,7 @@ void DSPEmitter::multiply_mulx(u8 axh0, u8 axh1)
|
|||
|
||||
SetJumpTarget(unsignedMul);
|
||||
DSPJitRegCache c(gpr);
|
||||
gpr.putReg(DSP_REG_SR, false);
|
||||
gpr.PutReg(DSP_REG_SR, false);
|
||||
if ((axh0==0) && (axh1==0))
|
||||
{
|
||||
// unsigned support ON if both ax?.l regs are used
|
||||
|
@ -101,11 +101,11 @@ void DSPEmitter::multiply_mulx(u8 axh0, u8 axh1)
|
|||
// mixed support ON (u16)axl.0 * (s16)axh.1
|
||||
// prod = a * (s16)b;
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
MOV(64, R(tmp), R(RAX));
|
||||
MOVZX(64, 16, RAX, R(RCX));
|
||||
IMUL(64, R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
}
|
||||
else if ((axh0==1) && (axh1==0))
|
||||
{
|
||||
|
@ -122,7 +122,7 @@ void DSPEmitter::multiply_mulx(u8 axh0, u8 axh1)
|
|||
IMUL(64, R(RCX));
|
||||
}
|
||||
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(signedMul);
|
||||
|
||||
// Conditionally multiply by 2.
|
||||
|
@ -132,7 +132,7 @@ void DSPEmitter::multiply_mulx(u8 axh0, u8 axh1)
|
|||
// prod <<= 1;
|
||||
LEA(64, RAX, MRegSum(RAX,RAX));
|
||||
SetJumpTarget(noMult2);
|
||||
gpr.putReg(DSP_REG_SR, false);
|
||||
gpr.PutReg(DSP_REG_SR, false);
|
||||
// return prod;
|
||||
}
|
||||
|
||||
|
@ -248,7 +248,7 @@ void DSPEmitter::addpaxz(const UDSPInstruction opc)
|
|||
|
||||
// s64 ax = dsp_get_long_acx(sreg);
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
get_long_acx(sreg, tmp1);
|
||||
MOV(64, R(RDX), R(tmp1));
|
||||
// s64 res = prod + (ax & ~0xffff);
|
||||
|
@ -273,7 +273,7 @@ void DSPEmitter::addpaxz(const UDSPInstruction opc)
|
|||
{
|
||||
set_long_acc(dreg, RAX);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
//----
|
||||
|
@ -432,7 +432,7 @@ void DSPEmitter::mulxac(const UDSPInstruction opc)
|
|||
|
||||
// s64 acc = dsp_get_long_acc(rreg) + dsp_get_long_prod();
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
get_long_acc(rreg, tmp1);
|
||||
get_long_prod();
|
||||
ADD(64, R(tmp1), R(RAX));
|
||||
|
@ -452,7 +452,7 @@ void DSPEmitter::mulxac(const UDSPInstruction opc)
|
|||
{
|
||||
Update_SR_Register64(tmp1);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// MULXMV $ax0.S, $ax1.T, $acR
|
||||
|
@ -470,7 +470,7 @@ void DSPEmitter::mulxmv(const UDSPInstruction opc)
|
|||
|
||||
// s64 acc = dsp_get_long_prod();
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
get_long_prod(tmp1);
|
||||
// u16 val1 = (sreg == 0) ? dsp_get_ax_l(0) : dsp_get_ax_h(0);
|
||||
dsp_op_read_reg(DSP_REG_AXL0 + sreg*2, RCX, SIGN);
|
||||
|
@ -488,7 +488,7 @@ void DSPEmitter::mulxmv(const UDSPInstruction opc)
|
|||
{
|
||||
Update_SR_Register64(tmp1);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// MULXMV $ax0.S, $ax1.T, $acR
|
||||
|
@ -507,7 +507,7 @@ void DSPEmitter::mulxmvz(const UDSPInstruction opc)
|
|||
|
||||
// s64 acc = dsp_get_long_prod_round_prodl();
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
get_long_prod_round_prodl(tmp1);
|
||||
// u16 val1 = (sreg == 0) ? dsp_get_ax_l(0) : dsp_get_ax_h(0);
|
||||
dsp_op_read_reg(DSP_REG_AXL0 + sreg*2, RCX, SIGN);
|
||||
|
@ -525,7 +525,7 @@ void DSPEmitter::mulxmvz(const UDSPInstruction opc)
|
|||
{
|
||||
Update_SR_Register64(tmp1);
|
||||
}
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
//----
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
|
||||
using namespace Gen;
|
||||
|
||||
static void* reg_ptr(size_t reg)
|
||||
static void* GetRegisterPointer(size_t reg)
|
||||
{
|
||||
switch (reg)
|
||||
{
|
||||
|
@ -117,7 +117,7 @@ DSPJitRegCache::DSPJitRegCache(DSPEmitter &_emitter)
|
|||
|
||||
for (size_t i = 0; i < regs.size(); i++)
|
||||
{
|
||||
regs[i].mem = reg_ptr(i);
|
||||
regs[i].mem = GetRegisterPointer(i);
|
||||
regs[i].size = 0;
|
||||
regs[i].dirty = false;
|
||||
regs[i].used = false;
|
||||
|
@ -192,12 +192,12 @@ DSPJitRegCache::~DSPJitRegCache()
|
|||
_assert_msg_(DSPLLE, !temporary || merged, "temporary cache not merged");
|
||||
}
|
||||
|
||||
void DSPJitRegCache::drop()
|
||||
void DSPJitRegCache::Drop()
|
||||
{
|
||||
merged = true;
|
||||
}
|
||||
|
||||
void DSPJitRegCache::flushRegs(DSPJitRegCache &cache, bool emit)
|
||||
void DSPJitRegCache::FlushRegs(DSPJitRegCache &cache, bool emit)
|
||||
{
|
||||
cache.merged = true;
|
||||
|
||||
|
@ -208,7 +208,7 @@ void DSPJitRegCache::flushRegs(DSPJitRegCache &cache, bool emit)
|
|||
if (regs[i].loc.IsSimpleReg() &&
|
||||
!cache.regs[i].loc.IsSimpleReg())
|
||||
{
|
||||
movToMemory(i);
|
||||
MovToMemory(i);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -224,7 +224,7 @@ void DSPJitRegCache::flushRegs(DSPJitRegCache &cache, bool emit)
|
|||
|
||||
if (simple_cache != simple && xregs[simple_cache].guest_reg == DSP_REG_NONE)
|
||||
{
|
||||
movToHostReg(i, simple_cache, true);
|
||||
MovToHostReg(i, simple_cache, true);
|
||||
movcnt++;
|
||||
}
|
||||
}
|
||||
|
@ -237,7 +237,7 @@ void DSPJitRegCache::flushRegs(DSPJitRegCache &cache, bool emit)
|
|||
regs[i].loc.GetSimpleReg() &&
|
||||
regs[i].loc.IsSimpleReg())
|
||||
{
|
||||
movToMemory(i);
|
||||
MovToMemory(i);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -246,8 +246,8 @@ void DSPJitRegCache::flushRegs(DSPJitRegCache &cache, bool emit)
|
|||
{
|
||||
if (cache.regs[i].loc.IsSimpleReg())
|
||||
{
|
||||
movToHostReg(i, cache.regs[i].loc.GetSimpleReg(), true);
|
||||
rotateHostReg(i, cache.regs[i].shift, true);
|
||||
MovToHostReg(i, cache.regs[i].loc.GetSimpleReg(), true);
|
||||
RotateHostReg(i, cache.regs[i].shift, true);
|
||||
}
|
||||
else if (cache.regs[i].loc.IsImm())
|
||||
{
|
||||
|
@ -307,7 +307,7 @@ void DSPJitRegCache::flushRegs(DSPJitRegCache &cache, bool emit)
|
|||
use_ctr = cache.use_ctr;
|
||||
}
|
||||
|
||||
void DSPJitRegCache::flushMemBackedRegs()
|
||||
void DSPJitRegCache::FlushMemBackedRegs()
|
||||
{
|
||||
// also needs to undo any dynamic changes to static allocated regs
|
||||
// this should have the same effect as
|
||||
|
@ -325,25 +325,25 @@ void DSPJitRegCache::flushMemBackedRegs()
|
|||
|
||||
if (regs[i].host_reg != INVALID_REG)
|
||||
{
|
||||
movToHostReg(i, regs[i].host_reg, true);
|
||||
rotateHostReg(i, 0, true);
|
||||
MovToHostReg(i, regs[i].host_reg, true);
|
||||
RotateHostReg(i, 0, true);
|
||||
}
|
||||
else if (regs[i].parentReg == DSP_REG_NONE)
|
||||
{
|
||||
movToMemory(i);
|
||||
MovToMemory(i);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void DSPJitRegCache::flushRegs()
|
||||
void DSPJitRegCache::FlushRegs()
|
||||
{
|
||||
flushMemBackedRegs();
|
||||
FlushMemBackedRegs();
|
||||
|
||||
for (size_t i = 0; i < regs.size(); i++)
|
||||
{
|
||||
if (regs[i].host_reg != INVALID_REG)
|
||||
{
|
||||
movToMemory(i);
|
||||
MovToMemory(i);
|
||||
}
|
||||
|
||||
_assert_msg_(DSPLLE,
|
||||
|
@ -405,13 +405,13 @@ void DSPJitRegCache::flushRegs()
|
|||
|
||||
static u64 ebp_store;
|
||||
|
||||
void DSPJitRegCache::loadRegs(bool emit)
|
||||
void DSPJitRegCache::LoadRegs(bool emit)
|
||||
{
|
||||
for (size_t i = 0; i < regs.size(); i++)
|
||||
{
|
||||
if (regs[i].host_reg != INVALID_REG)
|
||||
{
|
||||
movToHostReg(i, regs[i].host_reg, emit);
|
||||
MovToHostReg(i, regs[i].host_reg, emit);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -421,15 +421,15 @@ void DSPJitRegCache::loadRegs(bool emit)
|
|||
}
|
||||
}
|
||||
|
||||
void DSPJitRegCache::saveRegs()
|
||||
void DSPJitRegCache::SaveRegs()
|
||||
{
|
||||
flushRegs();
|
||||
FlushRegs();
|
||||
|
||||
for (size_t i = 0; i < regs.size(); i++)
|
||||
{
|
||||
if (regs[i].host_reg != INVALID_REG)
|
||||
{
|
||||
movToMemory(i);
|
||||
MovToMemory(i);
|
||||
}
|
||||
|
||||
_assert_msg_(DSPLLE,
|
||||
|
@ -440,15 +440,15 @@ void DSPJitRegCache::saveRegs()
|
|||
emitter.MOV(64, R(RBP), M(&ebp_store));
|
||||
}
|
||||
|
||||
void DSPJitRegCache::pushRegs()
|
||||
void DSPJitRegCache::PushRegs()
|
||||
{
|
||||
flushMemBackedRegs();
|
||||
FlushMemBackedRegs();
|
||||
|
||||
for (size_t i = 0; i < regs.size(); i++)
|
||||
{
|
||||
if (regs[i].host_reg != INVALID_REG)
|
||||
{
|
||||
movToMemory(i);
|
||||
MovToMemory(i);
|
||||
}
|
||||
|
||||
_assert_msg_(DSPLLE,
|
||||
|
@ -487,7 +487,7 @@ void DSPJitRegCache::pushRegs()
|
|||
emitter.MOV(64, R(RBP), M(&ebp_store));
|
||||
}
|
||||
|
||||
void DSPJitRegCache::popRegs()
|
||||
void DSPJitRegCache::PopRegs()
|
||||
{
|
||||
emitter.MOV(64, M(&ebp_store), R(RBP));
|
||||
|
||||
|
@ -514,12 +514,12 @@ void DSPJitRegCache::popRegs()
|
|||
{
|
||||
if (regs[i].host_reg != INVALID_REG)
|
||||
{
|
||||
movToHostReg(i, regs[i].host_reg, true);
|
||||
MovToHostReg(i, regs[i].host_reg, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
X64Reg DSPJitRegCache::makeABICallSafe(X64Reg reg)
|
||||
X64Reg DSPJitRegCache::MakeABICallSafe(X64Reg reg)
|
||||
{
|
||||
if (reg != RBP)
|
||||
{
|
||||
|
@ -528,7 +528,7 @@ X64Reg DSPJitRegCache::makeABICallSafe(X64Reg reg)
|
|||
|
||||
size_t rbp_guest = xregs[RBP].guest_reg;
|
||||
xregs[RBP].guest_reg = DSP_REG_USED;
|
||||
X64Reg safe = findSpillFreeXReg();
|
||||
X64Reg safe = FindSpillFreeXReg();
|
||||
_assert_msg_(DSPLLE, safe != INVALID_REG, "could not find register");
|
||||
if (safe == INVALID_REG)
|
||||
{
|
||||
|
@ -539,7 +539,7 @@ X64Reg DSPJitRegCache::makeABICallSafe(X64Reg reg)
|
|||
return safe;
|
||||
}
|
||||
|
||||
void DSPJitRegCache::movToHostReg(size_t reg, X64Reg host_reg, bool load)
|
||||
void DSPJitRegCache::MovToHostReg(size_t reg, X64Reg host_reg, bool load)
|
||||
{
|
||||
_assert_msg_(DSPLLE, reg < regs.size(),
|
||||
"bad register name %u", static_cast<u32>(reg));
|
||||
|
@ -585,7 +585,7 @@ void DSPJitRegCache::movToHostReg(size_t reg, X64Reg host_reg, bool load)
|
|||
}
|
||||
}
|
||||
|
||||
void DSPJitRegCache::movToHostReg(size_t reg, bool load)
|
||||
void DSPJitRegCache::MovToHostReg(size_t reg, bool load)
|
||||
{
|
||||
_assert_msg_(DSPLLE, reg < regs.size(),
|
||||
"bad register name %u", static_cast<u32>(reg));
|
||||
|
@ -606,7 +606,7 @@ void DSPJitRegCache::movToHostReg(size_t reg, bool load)
|
|||
}
|
||||
else
|
||||
{
|
||||
tmp = findSpillFreeXReg();
|
||||
tmp = FindSpillFreeXReg();
|
||||
}
|
||||
|
||||
if (tmp == INVALID_REG)
|
||||
|
@ -614,10 +614,10 @@ void DSPJitRegCache::movToHostReg(size_t reg, bool load)
|
|||
return;
|
||||
}
|
||||
|
||||
movToHostReg(reg, tmp, load);
|
||||
MovToHostReg(reg, tmp, load);
|
||||
}
|
||||
|
||||
void DSPJitRegCache::rotateHostReg(size_t reg, int shift, bool emit)
|
||||
void DSPJitRegCache::RotateHostReg(size_t reg, int shift, bool emit)
|
||||
{
|
||||
_assert_msg_(DSPLLE, reg < regs.size(),
|
||||
"bad register name %u", static_cast<u32>(reg));
|
||||
|
@ -661,7 +661,7 @@ void DSPJitRegCache::rotateHostReg(size_t reg, int shift, bool emit)
|
|||
regs[reg].shift = shift;
|
||||
}
|
||||
|
||||
void DSPJitRegCache::movToMemory(size_t reg)
|
||||
void DSPJitRegCache::MovToMemory(size_t reg)
|
||||
{
|
||||
_assert_msg_(DSPLLE, reg < regs.size(),
|
||||
"bad register name %u", static_cast<u32>(reg));
|
||||
|
@ -684,7 +684,7 @@ void DSPJitRegCache::movToMemory(size_t reg)
|
|||
//but first, check for any needed rotations
|
||||
if (regs[reg].loc.IsSimpleReg())
|
||||
{
|
||||
rotateHostReg(reg, 0, true);
|
||||
RotateHostReg(reg, 0, true);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -729,7 +729,7 @@ void DSPJitRegCache::movToMemory(size_t reg)
|
|||
regs[reg].loc = tmp;
|
||||
}
|
||||
|
||||
void DSPJitRegCache::getReg(int reg, OpArg &oparg, bool load)
|
||||
void DSPJitRegCache::GetReg(int reg, OpArg &oparg, bool load)
|
||||
{
|
||||
int real_reg;
|
||||
int shift;
|
||||
|
@ -758,13 +758,13 @@ void DSPJitRegCache::getReg(int reg, OpArg &oparg, bool load)
|
|||
}
|
||||
// no need to actually emit code for load or rotate if caller doesn't
|
||||
// use the contents, but see above for a reason to force the load
|
||||
movToHostReg(real_reg, load);
|
||||
MovToHostReg(real_reg, load);
|
||||
|
||||
// TODO: actually handle INVALID_REG
|
||||
_assert_msg_(DSPLLE, regs[real_reg].loc.IsSimpleReg(),
|
||||
"did not get host reg for %d", reg);
|
||||
|
||||
rotateHostReg(real_reg, shift, load);
|
||||
RotateHostReg(real_reg, shift, load);
|
||||
oparg = regs[real_reg].loc;
|
||||
regs[real_reg].used = true;
|
||||
|
||||
|
@ -776,7 +776,7 @@ void DSPJitRegCache::getReg(int reg, OpArg &oparg, bool load)
|
|||
if (load)
|
||||
{
|
||||
// need to do this because interpreter only does 48 bits
|
||||
// (and putReg does the same)
|
||||
// (and PutReg does the same)
|
||||
emitter.SHL(64, oparg, Imm8(64-40)); // sign extend
|
||||
emitter.SAR(64, oparg, Imm8(64-40));
|
||||
}
|
||||
|
@ -786,7 +786,7 @@ void DSPJitRegCache::getReg(int reg, OpArg &oparg, bool load)
|
|||
}
|
||||
}
|
||||
|
||||
void DSPJitRegCache::putReg(int reg, bool dirty)
|
||||
void DSPJitRegCache::PutReg(int reg, bool dirty)
|
||||
{
|
||||
int real_reg = reg;
|
||||
if (regs[reg].parentReg != DSP_REG_NONE)
|
||||
|
@ -819,11 +819,11 @@ void DSPJitRegCache::putReg(int reg, bool dirty)
|
|||
// this works on the memory, so use reg instead
|
||||
// of real_reg, since it has the right loc
|
||||
X64Reg tmp;
|
||||
getFreeXReg(tmp);
|
||||
GetFreeXReg(tmp);
|
||||
// sign extend from the bottom 8 bits.
|
||||
emitter.MOVSX(16, 8, tmp, regs[reg].loc);
|
||||
emitter.MOV(16, regs[reg].loc, R(tmp));
|
||||
putXReg(tmp);
|
||||
PutXReg(tmp);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
@ -849,10 +849,10 @@ void DSPJitRegCache::putReg(int reg, bool dirty)
|
|||
}
|
||||
}
|
||||
|
||||
void DSPJitRegCache::readReg(int sreg, X64Reg host_dreg, DSPJitSignExtend extend)
|
||||
void DSPJitRegCache::ReadReg(int sreg, X64Reg host_dreg, DSPJitSignExtend extend)
|
||||
{
|
||||
OpArg reg;
|
||||
getReg(sreg, reg);
|
||||
GetReg(sreg, reg);
|
||||
|
||||
switch (regs[sreg].size)
|
||||
{
|
||||
|
@ -891,13 +891,13 @@ void DSPJitRegCache::readReg(int sreg, X64Reg host_dreg, DSPJitSignExtend extend
|
|||
_assert_msg_(DSPLLE, 0, "unsupported memory size");
|
||||
break;
|
||||
}
|
||||
putReg(sreg, false);
|
||||
PutReg(sreg, false);
|
||||
}
|
||||
|
||||
void DSPJitRegCache::writeReg(int dreg, OpArg arg)
|
||||
void DSPJitRegCache::WriteReg(int dreg, OpArg arg)
|
||||
{
|
||||
OpArg reg;
|
||||
getReg(dreg, reg, false);
|
||||
GetReg(dreg, reg, false);
|
||||
if (arg.IsImm())
|
||||
{
|
||||
switch (regs[dreg].size)
|
||||
|
@ -941,7 +941,7 @@ void DSPJitRegCache::writeReg(int dreg, OpArg arg)
|
|||
break;
|
||||
}
|
||||
}
|
||||
putReg(dreg, true);
|
||||
PutReg(dreg, true);
|
||||
}
|
||||
|
||||
//ordered in order of prefered use
|
||||
|
@ -950,7 +950,7 @@ static X64Reg alloc_order[] = {
|
|||
R8,R9,R10,R11,R12,R13,R14,R15,RSI,RDI,RBX,RCX,RDX,RAX,RBP
|
||||
};
|
||||
|
||||
X64Reg DSPJitRegCache::spillXReg()
|
||||
X64Reg DSPJitRegCache::SpillXReg()
|
||||
{
|
||||
int max_use_ctr_diff = 0;
|
||||
X64Reg least_recent_use_reg = INVALID_REG;
|
||||
|
@ -970,7 +970,7 @@ X64Reg DSPJitRegCache::spillXReg()
|
|||
|
||||
if (least_recent_use_reg != INVALID_REG)
|
||||
{
|
||||
movToMemory(xregs[least_recent_use_reg].guest_reg);
|
||||
MovToMemory(xregs[least_recent_use_reg].guest_reg);
|
||||
return least_recent_use_reg;
|
||||
}
|
||||
|
||||
|
@ -980,7 +980,7 @@ X64Reg DSPJitRegCache::spillXReg()
|
|||
if (xregs[reg].guest_reg <= DSP_REG_MAX_MEM_BACKED &&
|
||||
!regs[xregs[reg].guest_reg].used)
|
||||
{
|
||||
movToMemory(xregs[reg].guest_reg);
|
||||
MovToMemory(xregs[reg].guest_reg);
|
||||
return reg;
|
||||
}
|
||||
}
|
||||
|
@ -988,7 +988,7 @@ X64Reg DSPJitRegCache::spillXReg()
|
|||
return INVALID_REG;
|
||||
}
|
||||
|
||||
void DSPJitRegCache::spillXReg(X64Reg reg)
|
||||
void DSPJitRegCache::SpillXReg(X64Reg reg)
|
||||
{
|
||||
if (xregs[reg].guest_reg <= DSP_REG_MAX_MEM_BACKED)
|
||||
{
|
||||
|
@ -996,7 +996,7 @@ void DSPJitRegCache::spillXReg(X64Reg reg)
|
|||
"to be spilled host reg %x(guest reg %zx) still in use!",
|
||||
reg, xregs[reg].guest_reg);
|
||||
|
||||
movToMemory(xregs[reg].guest_reg);
|
||||
MovToMemory(xregs[reg].guest_reg);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1006,7 +1006,7 @@ void DSPJitRegCache::spillXReg(X64Reg reg)
|
|||
}
|
||||
}
|
||||
|
||||
X64Reg DSPJitRegCache::findFreeXReg()
|
||||
X64Reg DSPJitRegCache::FindFreeXReg()
|
||||
{
|
||||
for (X64Reg x : alloc_order)
|
||||
{
|
||||
|
@ -1018,19 +1018,19 @@ X64Reg DSPJitRegCache::findFreeXReg()
|
|||
return INVALID_REG;
|
||||
}
|
||||
|
||||
X64Reg DSPJitRegCache::findSpillFreeXReg()
|
||||
X64Reg DSPJitRegCache::FindSpillFreeXReg()
|
||||
{
|
||||
X64Reg reg = findFreeXReg();
|
||||
X64Reg reg = FindFreeXReg();
|
||||
if (reg == INVALID_REG)
|
||||
{
|
||||
reg = spillXReg();
|
||||
reg = SpillXReg();
|
||||
}
|
||||
return reg;
|
||||
}
|
||||
|
||||
void DSPJitRegCache::getFreeXReg(X64Reg ®)
|
||||
void DSPJitRegCache::GetFreeXReg(X64Reg ®)
|
||||
{
|
||||
reg = findSpillFreeXReg();
|
||||
reg = FindSpillFreeXReg();
|
||||
|
||||
_assert_msg_(DSPLLE, reg != INVALID_REG, "could not find register");
|
||||
if (reg == INVALID_REG)
|
||||
|
@ -1040,7 +1040,7 @@ void DSPJitRegCache::getFreeXReg(X64Reg ®)
|
|||
xregs[reg].guest_reg = DSP_REG_USED;
|
||||
}
|
||||
|
||||
void DSPJitRegCache::getXReg(X64Reg reg)
|
||||
void DSPJitRegCache::GetXReg(X64Reg reg)
|
||||
{
|
||||
if (xregs[reg].guest_reg == DSP_REG_STATIC)
|
||||
{
|
||||
|
@ -1050,13 +1050,13 @@ void DSPJitRegCache::getXReg(X64Reg reg)
|
|||
|
||||
if (xregs[reg].guest_reg != DSP_REG_NONE)
|
||||
{
|
||||
spillXReg(reg);
|
||||
SpillXReg(reg);
|
||||
}
|
||||
_assert_msg_(DSPLLE, xregs[reg].guest_reg == DSP_REG_NONE, "register already in use");
|
||||
xregs[reg].guest_reg = DSP_REG_USED;
|
||||
}
|
||||
|
||||
void DSPJitRegCache::putXReg(X64Reg reg)
|
||||
void DSPJitRegCache::PutXReg(X64Reg reg)
|
||||
{
|
||||
if (xregs[reg].guest_reg == DSP_REG_STATIC)
|
||||
{
|
||||
|
@ -1065,7 +1065,7 @@ void DSPJitRegCache::putXReg(X64Reg reg)
|
|||
}
|
||||
|
||||
_assert_msg_(DSPLLE, xregs[reg].guest_reg == DSP_REG_USED,
|
||||
"putXReg without get(Free)XReg");
|
||||
"PutXReg without get(Free)XReg");
|
||||
|
||||
xregs[reg].guest_reg = DSP_REG_NONE;
|
||||
}
|
||||
|
|
|
@ -70,30 +70,30 @@ private:
|
|||
|
||||
int use_ctr;
|
||||
private:
|
||||
//find a free host reg
|
||||
Gen::X64Reg findFreeXReg();
|
||||
Gen::X64Reg spillXReg();
|
||||
Gen::X64Reg findSpillFreeXReg();
|
||||
void spillXReg(Gen::X64Reg reg);
|
||||
// Find a free host reg
|
||||
Gen::X64Reg FindFreeXReg();
|
||||
Gen::X64Reg SpillXReg();
|
||||
Gen::X64Reg FindSpillFreeXReg();
|
||||
void SpillXReg(Gen::X64Reg reg);
|
||||
|
||||
void movToHostReg(size_t reg, Gen::X64Reg host_reg, bool load);
|
||||
void movToHostReg(size_t reg, bool load);
|
||||
void rotateHostReg(size_t reg, int shift, bool emit);
|
||||
void movToMemory(size_t reg);
|
||||
void flushMemBackedRegs();
|
||||
void MovToHostReg(size_t reg, Gen::X64Reg host_reg, bool load);
|
||||
void MovToHostReg(size_t reg, bool load);
|
||||
void RotateHostReg(size_t reg, int shift, bool emit);
|
||||
void MovToMemory(size_t reg);
|
||||
void FlushMemBackedRegs();
|
||||
|
||||
public:
|
||||
DSPJitRegCache(DSPEmitter &_emitter);
|
||||
|
||||
//for branching into multiple control flows
|
||||
// For branching into multiple control flows
|
||||
DSPJitRegCache(const DSPJitRegCache &cache);
|
||||
DSPJitRegCache& operator=(const DSPJitRegCache &cache);
|
||||
|
||||
~DSPJitRegCache();
|
||||
|
||||
//merge must be done _before_ leaving the code branch, so we can fix
|
||||
//up any differences in state
|
||||
void flushRegs(DSPJitRegCache &cache, bool emit = true);
|
||||
// Merge must be done _before_ leaving the code branch, so we can fix
|
||||
// up any differences in state
|
||||
void FlushRegs(DSPJitRegCache &cache, bool emit = true);
|
||||
/* since some use cases are non-trivial, some examples:
|
||||
|
||||
//this does not modify the final state of gpr
|
||||
|
@ -101,7 +101,7 @@ public:
|
|||
FixupBranch b = JCC();
|
||||
DSPJitRegCache c = gpr;
|
||||
<code using c>
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetBranchTarget(b);
|
||||
<code using gpr>
|
||||
|
||||
|
@ -110,11 +110,11 @@ public:
|
|||
DSPJitRegCache c = gpr;
|
||||
FixupBranch b1 = JCC();
|
||||
<code using gpr>
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
FixupBranch b2 = JMP();
|
||||
SetBranchTarget(b1);
|
||||
<code using gpr>
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetBranchTarget(b2);
|
||||
<code using gpr>
|
||||
|
||||
|
@ -127,7 +127,7 @@ public:
|
|||
FixupBranch b2 = JMP();
|
||||
SetBranchTarget(b1);
|
||||
<code using gpr>
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetBranchTarget(b2);
|
||||
<code using gpr>
|
||||
|
||||
|
@ -136,43 +136,44 @@ public:
|
|||
u8* b = GetCodePtr();
|
||||
DSPJitRegCache c = gpr;
|
||||
<code using gpr>
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
JCC(b);
|
||||
<code using gpr>
|
||||
|
||||
this all is not needed when gpr would not be used at all in the
|
||||
conditional branch
|
||||
*/
|
||||
//drop this copy without warning
|
||||
void drop();
|
||||
|
||||
//prepare state so that another flushed DSPJitRegCache can take over
|
||||
void flushRegs();
|
||||
// Drop this copy without warning
|
||||
void Drop();
|
||||
|
||||
void loadRegs(bool emit=true);//load statically allocated regs from memory
|
||||
void saveRegs();//save statically allocated regs to memory
|
||||
// Prepare state so that another flushed DSPJitRegCache can take over
|
||||
void FlushRegs();
|
||||
|
||||
void pushRegs();//save registers before abi call
|
||||
void popRegs();//restore registers after abi call
|
||||
void LoadRegs(bool emit = true);// Load statically allocated regs from memory
|
||||
void SaveRegs(); // Save statically allocated regs to memory
|
||||
|
||||
//returns a register with the same contents as reg that is safe
|
||||
//to use through saveStaticRegs and for ABI-calls
|
||||
Gen::X64Reg makeABICallSafe(Gen::X64Reg reg);
|
||||
void PushRegs();// Save registers before ABI call
|
||||
void PopRegs(); // Restore registers after ABI call
|
||||
|
||||
//gives no SCALE_RIP with abs(offset) >= 0x80000000
|
||||
//32/64 bit writes allowed when the register has a _64 or _32 suffix
|
||||
//only 16 bit writes allowed without any suffix.
|
||||
void getReg(int reg, Gen::OpArg &oparg, bool load = true);
|
||||
//done with all usages of OpArg above
|
||||
void putReg(int reg, bool dirty = true);
|
||||
// Returns a register with the same contents as reg that is safe
|
||||
// to use through saveStaticRegs and for ABI-calls
|
||||
Gen::X64Reg MakeABICallSafe(Gen::X64Reg reg);
|
||||
|
||||
void readReg(int sreg, Gen::X64Reg host_dreg, DSPJitSignExtend extend);
|
||||
void writeReg(int dreg, Gen::OpArg arg);
|
||||
// Gives no SCALE_RIP with abs(offset) >= 0x80000000
|
||||
// 32/64 bit writes allowed when the register has a _64 or _32 suffix
|
||||
// only 16 bit writes allowed without any suffix.
|
||||
void GetReg(int reg, Gen::OpArg &oparg, bool load = true);
|
||||
// Done with all usages of OpArg above
|
||||
void PutReg(int reg, bool dirty = true);
|
||||
|
||||
//find a free host reg, spill if used, reserve
|
||||
void getFreeXReg(Gen::X64Reg ®);
|
||||
//spill a specific host reg if used, reserve
|
||||
void getXReg(Gen::X64Reg reg);
|
||||
//unreserve the given host reg
|
||||
void putXReg(Gen::X64Reg reg);
|
||||
void ReadReg(int sreg, Gen::X64Reg host_dreg, DSPJitSignExtend extend);
|
||||
void WriteReg(int dreg, Gen::OpArg arg);
|
||||
|
||||
// Find a free host reg, spill if used, reserve
|
||||
void GetFreeXReg(Gen::X64Reg ®);
|
||||
// Spill a specific host reg if used, reserve
|
||||
void GetXReg(Gen::X64Reg reg);
|
||||
// Unreserve the given host reg
|
||||
void PutXReg(Gen::X64Reg reg);
|
||||
};
|
||||
|
|
|
@ -21,13 +21,13 @@ void DSPEmitter::dsp_reg_stack_push(int stack_reg)
|
|||
MOV(8, M(&g_dsp.reg_stack_ptr[stack_reg]), R(AL));
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
//g_dsp.reg_stack[stack_reg][g_dsp.reg_stack_ptr[stack_reg]] = g_dsp.r[DSP_REG_ST0 + stack_reg];
|
||||
MOV(16, R(tmp1), M(&g_dsp.r.st[stack_reg]));
|
||||
MOVZX(64, 8, RAX, R(AL));
|
||||
MOV(16, MComplex(EAX, EAX, 1,
|
||||
PtrOffset(&g_dsp.reg_stack[stack_reg][0],nullptr)), R(tmp1));
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
//clobbers:
|
||||
|
@ -38,12 +38,12 @@ void DSPEmitter::dsp_reg_stack_pop(int stack_reg)
|
|||
//g_dsp.r[DSP_REG_ST0 + stack_reg] = g_dsp.reg_stack[stack_reg][g_dsp.reg_stack_ptr[stack_reg]];
|
||||
MOV(8, R(AL), M(&g_dsp.reg_stack_ptr[stack_reg]));
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
MOVZX(64, 8, RAX, R(AL));
|
||||
MOV(16, R(tmp1), MComplex(EAX, EAX, 1,
|
||||
PtrOffset(&g_dsp.reg_stack[stack_reg][0],nullptr)));
|
||||
MOV(16, M(&g_dsp.r.st[stack_reg]), R(tmp1));
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
|
||||
//g_dsp.reg_stack_ptr[stack_reg]--;
|
||||
//g_dsp.reg_stack_ptr[stack_reg] &= DSP_STACK_MASK;
|
||||
|
@ -89,7 +89,7 @@ void DSPEmitter::dsp_op_write_reg(int reg, Gen::X64Reg host_sreg)
|
|||
// 8-bit sign extended registers.
|
||||
case DSP_REG_ACH0:
|
||||
case DSP_REG_ACH1:
|
||||
gpr.writeReg(reg, R(host_sreg));
|
||||
gpr.WriteReg(reg, R(host_sreg));
|
||||
break;
|
||||
|
||||
// Stack registers.
|
||||
|
@ -101,7 +101,7 @@ void DSPEmitter::dsp_op_write_reg(int reg, Gen::X64Reg host_sreg)
|
|||
break;
|
||||
|
||||
default:
|
||||
gpr.writeReg(reg, R(host_sreg));
|
||||
gpr.WriteReg(reg, R(host_sreg));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -113,7 +113,7 @@ void DSPEmitter::dsp_op_write_reg_imm(int reg, u16 val)
|
|||
// 8-bit sign extended registers. Should look at prod.h too...
|
||||
case DSP_REG_ACH0:
|
||||
case DSP_REG_ACH1:
|
||||
gpr.writeReg(reg, Imm16((u16)(s16)(s8)(u8)val));
|
||||
gpr.WriteReg(reg, Imm16((u16)(s16)(s8)(u8)val));
|
||||
break;
|
||||
// Stack registers.
|
||||
case DSP_REG_ST0:
|
||||
|
@ -124,7 +124,7 @@ void DSPEmitter::dsp_op_write_reg_imm(int reg, u16 val)
|
|||
break;
|
||||
|
||||
default:
|
||||
gpr.writeReg(reg, Imm16(val));
|
||||
gpr.WriteReg(reg, Imm16(val));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -137,7 +137,7 @@ void DSPEmitter::dsp_conditional_extend_accum(int reg)
|
|||
case DSP_REG_ACM1:
|
||||
{
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, sr_reg, Imm16(SR_40_MODE_BIT));
|
||||
FixupBranch not_40bit = J_CC(CC_Z,true);
|
||||
|
@ -152,9 +152,9 @@ void DSPEmitter::dsp_conditional_extend_accum(int reg)
|
|||
set_acc_h(reg - DSP_REG_ACM0, R(RAX));
|
||||
set_acc_l(reg - DSP_REG_ACM0, Imm16(0));
|
||||
//}
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(not_40bit);
|
||||
gpr.putReg(DSP_REG_SR, false);
|
||||
gpr.PutReg(DSP_REG_SR, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -167,7 +167,7 @@ void DSPEmitter::dsp_conditional_extend_accum_imm(int reg, u16 val)
|
|||
case DSP_REG_ACM1:
|
||||
{
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, sr_reg, Imm16(SR_40_MODE_BIT));
|
||||
FixupBranch not_40bit = J_CC(CC_Z, true);
|
||||
|
@ -179,9 +179,9 @@ void DSPEmitter::dsp_conditional_extend_accum_imm(int reg, u16 val)
|
|||
set_acc_h(reg - DSP_REG_ACM0, Imm16((val & 0x8000)?0xffff:0x0000));
|
||||
set_acc_l(reg - DSP_REG_ACM0, Imm16(0));
|
||||
//}
|
||||
gpr.flushRegs(c);
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(not_40bit);
|
||||
gpr.putReg(DSP_REG_SR, false);
|
||||
gpr.PutReg(DSP_REG_SR, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -209,7 +209,7 @@ void DSPEmitter::dsp_op_read_reg_dont_saturate(int reg, Gen::X64Reg host_dreg, D
|
|||
}
|
||||
return;
|
||||
default:
|
||||
gpr.readReg(reg, host_dreg, extend);
|
||||
gpr.ReadReg(reg, host_dreg, extend);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
@ -241,9 +241,9 @@ void DSPEmitter::dsp_op_read_reg(int reg, Gen::X64Reg host_dreg, DSPJitSignExten
|
|||
{
|
||||
//we already know this is ACCM0 or ACCM1
|
||||
OpArg acc_reg;
|
||||
gpr.getReg(reg-DSP_REG_ACM0+DSP_REG_ACC0_64, acc_reg);
|
||||
gpr.GetReg(reg-DSP_REG_ACM0+DSP_REG_ACC0_64, acc_reg);
|
||||
OpArg sr_reg;
|
||||
gpr.getReg(DSP_REG_SR,sr_reg);
|
||||
gpr.GetReg(DSP_REG_SR,sr_reg);
|
||||
|
||||
DSPJitRegCache c(gpr);
|
||||
TEST(16, sr_reg, Imm16(SR_40_MODE_BIT));
|
||||
|
@ -276,14 +276,14 @@ void DSPEmitter::dsp_op_read_reg(int reg, Gen::X64Reg host_dreg, DSPJitSignExten
|
|||
SAR(64, R(host_dreg), Imm8(16));
|
||||
SetJumpTarget(done_positive);
|
||||
SetJumpTarget(done_negative);
|
||||
gpr.flushRegs(c);
|
||||
gpr.putReg(reg-DSP_REG_ACM0+DSP_REG_ACC0_64, false);
|
||||
gpr.FlushRegs(c);
|
||||
gpr.PutReg(reg-DSP_REG_ACM0+DSP_REG_ACC0_64, false);
|
||||
|
||||
gpr.putReg(DSP_REG_SR, false);
|
||||
gpr.PutReg(DSP_REG_SR, false);
|
||||
}
|
||||
return;
|
||||
default:
|
||||
gpr.readReg(reg, host_dreg, extend);
|
||||
gpr.ReadReg(reg, host_dreg, extend);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
@ -304,13 +304,13 @@ void DSPEmitter::increment_addr_reg(int reg)
|
|||
{
|
||||
OpArg ar_reg;
|
||||
OpArg wr_reg;
|
||||
gpr.getReg(DSP_REG_WR0+reg,wr_reg);
|
||||
gpr.GetReg(DSP_REG_WR0+reg,wr_reg);
|
||||
MOVZX(32, 16, EDX, wr_reg);
|
||||
gpr.putReg(DSP_REG_WR0+reg, false);
|
||||
gpr.getReg(DSP_REG_AR0+reg,ar_reg);
|
||||
gpr.PutReg(DSP_REG_WR0+reg, false);
|
||||
gpr.GetReg(DSP_REG_AR0+reg,ar_reg);
|
||||
MOVZX(32, 16, EAX, ar_reg);
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
//u32 nar = ar + 1;
|
||||
MOV(32, R(tmp1), R(EAX));
|
||||
ADD(32, R(EAX), Imm8(1));
|
||||
|
@ -325,11 +325,11 @@ void DSPEmitter::increment_addr_reg(int reg)
|
|||
SUB(16, R(AX), R(DX));
|
||||
SUB(16, R(AX), Imm8(1));
|
||||
SetJumpTarget(nowrap);
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutXReg(tmp1);
|
||||
// g_dsp.r.ar[reg] = nar;
|
||||
|
||||
MOV(16, ar_reg, R(AX));
|
||||
gpr.putReg(DSP_REG_AR0+reg);
|
||||
gpr.PutReg(DSP_REG_AR0+reg);
|
||||
}
|
||||
|
||||
// EAX = g_dsp.r.ar[reg]
|
||||
|
@ -338,14 +338,14 @@ void DSPEmitter::decrement_addr_reg(int reg)
|
|||
{
|
||||
OpArg ar_reg;
|
||||
OpArg wr_reg;
|
||||
gpr.getReg(DSP_REG_WR0+reg,wr_reg);
|
||||
gpr.GetReg(DSP_REG_WR0+reg,wr_reg);
|
||||
MOVZX(32, 16, EDX, wr_reg);
|
||||
gpr.putReg(DSP_REG_WR0+reg, false);
|
||||
gpr.getReg(DSP_REG_AR0+reg,ar_reg);
|
||||
gpr.PutReg(DSP_REG_WR0+reg, false);
|
||||
gpr.GetReg(DSP_REG_AR0+reg,ar_reg);
|
||||
MOVZX(32, 16, EAX, ar_reg);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
// u32 nar = ar + wr;
|
||||
// edi = nar
|
||||
LEA(32, tmp1, MRegSum(EAX, EDX));
|
||||
|
@ -364,8 +364,8 @@ void DSPEmitter::decrement_addr_reg(int reg)
|
|||
// g_dsp.r.ar[reg] = nar;
|
||||
|
||||
MOV(16, ar_reg, R(tmp1));
|
||||
gpr.putReg(DSP_REG_AR0+reg);
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutReg(DSP_REG_AR0+reg);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// Increase addr register according to the correspond ix register
|
||||
|
@ -377,17 +377,17 @@ void DSPEmitter::increase_addr_reg(int reg, int _ix_reg)
|
|||
OpArg ar_reg;
|
||||
OpArg wr_reg;
|
||||
OpArg ix_reg;
|
||||
gpr.getReg(DSP_REG_WR0+reg,wr_reg);
|
||||
gpr.GetReg(DSP_REG_WR0+reg,wr_reg);
|
||||
MOVZX(32, 16, EDX, wr_reg);
|
||||
gpr.putReg(DSP_REG_WR0+reg, false);
|
||||
gpr.getReg(DSP_REG_IX0+_ix_reg,ix_reg);
|
||||
gpr.PutReg(DSP_REG_WR0+reg, false);
|
||||
gpr.GetReg(DSP_REG_IX0+_ix_reg,ix_reg);
|
||||
MOVSX(32, 16, ECX, ix_reg);
|
||||
gpr.putReg(DSP_REG_IX0+_ix_reg, false);
|
||||
gpr.getReg(DSP_REG_AR0+reg,ar_reg);
|
||||
gpr.PutReg(DSP_REG_IX0+_ix_reg, false);
|
||||
gpr.GetReg(DSP_REG_AR0+reg,ar_reg);
|
||||
MOVZX(32, 16, EAX, ar_reg);
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
//u32 nar = ar + ix;
|
||||
//edi = nar
|
||||
LEA(32, tmp1, MRegSum(EAX, ECX));
|
||||
|
@ -433,8 +433,8 @@ void DSPEmitter::increase_addr_reg(int reg, int _ix_reg)
|
|||
// g_dsp.r.ar[reg] = nar;
|
||||
|
||||
MOV(16, ar_reg, R(tmp1));
|
||||
gpr.putReg(DSP_REG_AR0+reg);
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutReg(DSP_REG_AR0+reg);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
// Decrease addr register according to the correspond ix register
|
||||
|
@ -446,19 +446,19 @@ void DSPEmitter::decrease_addr_reg(int reg)
|
|||
OpArg ar_reg;
|
||||
OpArg wr_reg;
|
||||
OpArg ix_reg;
|
||||
gpr.getReg(DSP_REG_WR0+reg,wr_reg);
|
||||
gpr.GetReg(DSP_REG_WR0+reg,wr_reg);
|
||||
MOVZX(32, 16, EDX, wr_reg);
|
||||
gpr.putReg(DSP_REG_WR0+reg, false);
|
||||
gpr.getReg(DSP_REG_IX0+reg,ix_reg);
|
||||
gpr.PutReg(DSP_REG_WR0+reg, false);
|
||||
gpr.GetReg(DSP_REG_IX0+reg,ix_reg);
|
||||
MOVSX(32, 16, ECX, ix_reg);
|
||||
gpr.putReg(DSP_REG_IX0+reg, false);
|
||||
gpr.getReg(DSP_REG_AR0+reg,ar_reg);
|
||||
gpr.PutReg(DSP_REG_IX0+reg, false);
|
||||
gpr.GetReg(DSP_REG_AR0+reg,ar_reg);
|
||||
MOVZX(32, 16, EAX, ar_reg);
|
||||
|
||||
NOT(32, R(ECX)); //esi = ~ix
|
||||
|
||||
X64Reg tmp1;
|
||||
gpr.getFreeXReg(tmp1);
|
||||
gpr.GetFreeXReg(tmp1);
|
||||
//u32 nar = ar - ix; (ar + ~ix + 1)
|
||||
LEA(32, tmp1, MComplex(EAX, ECX, 1, 1));
|
||||
|
||||
|
@ -503,8 +503,8 @@ void DSPEmitter::decrease_addr_reg(int reg)
|
|||
//return nar
|
||||
|
||||
MOV(16, ar_reg, R(tmp1));
|
||||
gpr.putReg(DSP_REG_AR0+reg);
|
||||
gpr.putXReg(tmp1);
|
||||
gpr.PutReg(DSP_REG_AR0+reg);
|
||||
gpr.PutXReg(tmp1);
|
||||
}
|
||||
|
||||
|
||||
|
@ -526,11 +526,11 @@ void DSPEmitter::dmem_write(X64Reg value)
|
|||
SetJumpTarget(ifx);
|
||||
// Does it mean gdsp_ifx_write needs u32 rather than u16?
|
||||
DSPJitRegCache c(gpr);
|
||||
X64Reg abisafereg = gpr.makeABICallSafe(value);
|
||||
gpr.pushRegs();
|
||||
X64Reg abisafereg = gpr.MakeABICallSafe(value);
|
||||
gpr.PushRegs();
|
||||
ABI_CallFunctionRR((void *)gdsp_ifx_write, EAX, abisafereg);
|
||||
gpr.popRegs();
|
||||
gpr.flushRegs(c);
|
||||
gpr.PopRegs();
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(end);
|
||||
}
|
||||
|
||||
|
@ -546,10 +546,10 @@ void DSPEmitter::dmem_write_imm(u16 address, X64Reg value)
|
|||
case 0xf: // Fxxx HW regs
|
||||
{
|
||||
MOV(16, R(EAX), Imm16(address));
|
||||
X64Reg abisafereg = gpr.makeABICallSafe(value);
|
||||
gpr.pushRegs();
|
||||
X64Reg abisafereg = gpr.MakeABICallSafe(value);
|
||||
gpr.PushRegs();
|
||||
ABI_CallFunctionRR((void *)gdsp_ifx_write, EAX, abisafereg);
|
||||
gpr.popRegs();
|
||||
gpr.PopRegs();
|
||||
break;
|
||||
}
|
||||
default: // Unmapped/non-existing memory
|
||||
|
@ -613,11 +613,11 @@ void DSPEmitter::dmem_read(X64Reg address)
|
|||
// else if (saddr == 0xf)
|
||||
// return gdsp_ifx_read(addr);
|
||||
DSPJitRegCache c(gpr);
|
||||
X64Reg abisafereg = gpr.makeABICallSafe(address);
|
||||
gpr.pushRegs();
|
||||
X64Reg abisafereg = gpr.MakeABICallSafe(address);
|
||||
gpr.PushRegs();
|
||||
ABI_CallFunctionR((void *)gdsp_ifx_read, abisafereg);
|
||||
gpr.popRegs();
|
||||
gpr.flushRegs(c);
|
||||
gpr.PopRegs();
|
||||
gpr.FlushRegs(c);
|
||||
SetJumpTarget(end);
|
||||
SetJumpTarget(end2);
|
||||
}
|
||||
|
@ -638,9 +638,9 @@ void DSPEmitter::dmem_read_imm(u16 address)
|
|||
|
||||
case 0xf: // Fxxx HW regs
|
||||
{
|
||||
gpr.pushRegs();
|
||||
gpr.PushRegs();
|
||||
ABI_CallFunctionC16((void *)gdsp_ifx_read, address);
|
||||
gpr.popRegs();
|
||||
gpr.PopRegs();
|
||||
break;
|
||||
}
|
||||
default: // Unmapped/non-existing memory
|
||||
|
@ -654,19 +654,19 @@ void DSPEmitter::get_long_prod(X64Reg long_prod)
|
|||
{
|
||||
//s64 val = (s8)(u8)g_dsp.r[DSP_REG_PRODH];
|
||||
OpArg prod_reg;
|
||||
gpr.getReg(DSP_REG_PROD_64, prod_reg);
|
||||
gpr.GetReg(DSP_REG_PROD_64, prod_reg);
|
||||
MOV(64, R(long_prod), prod_reg);
|
||||
gpr.putReg(DSP_REG_PROD_64, false);
|
||||
gpr.PutReg(DSP_REG_PROD_64, false);
|
||||
//no use in keeping prod_reg any longer.
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
MOV(64, R(tmp), R(long_prod));
|
||||
SHL(64, R(long_prod), Imm8(64-40));//sign extend
|
||||
SAR(64, R(long_prod), Imm8(64-40));
|
||||
SHR(64, R(tmp), Imm8(48));
|
||||
SHL(64, R(tmp), Imm8(16));
|
||||
ADD(64, R(long_prod), R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
}
|
||||
|
||||
// Returns s64 in RAX
|
||||
|
@ -677,7 +677,7 @@ void DSPEmitter::get_long_prod_round_prodl(X64Reg long_prod)
|
|||
get_long_prod(long_prod);
|
||||
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
//if (prod & 0x10000) prod = (prod + 0x8000) & ~0xffff;
|
||||
TEST(32, R(long_prod), Imm32(0x10000));
|
||||
FixupBranch jump = J_CC(CC_Z);
|
||||
|
@ -692,7 +692,7 @@ void DSPEmitter::get_long_prod_round_prodl(X64Reg long_prod)
|
|||
AND(64, R(long_prod), R(tmp));
|
||||
SetJumpTarget(_ret);
|
||||
//return prod;
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
}
|
||||
|
||||
// For accurate emulation, this is wrong - but the real prod registers behave
|
||||
|
@ -701,17 +701,17 @@ void DSPEmitter::get_long_prod_round_prodl(X64Reg long_prod)
|
|||
void DSPEmitter::set_long_prod()
|
||||
{
|
||||
X64Reg tmp;
|
||||
gpr.getFreeXReg(tmp);
|
||||
gpr.GetFreeXReg(tmp);
|
||||
|
||||
MOV(64, R(tmp), Imm64(0x000000ffffffffffULL));
|
||||
AND(64, R(RAX), R(tmp));
|
||||
gpr.putXReg(tmp);
|
||||
gpr.PutXReg(tmp);
|
||||
OpArg prod_reg;
|
||||
gpr.getReg(DSP_REG_PROD_64, prod_reg, false);
|
||||
gpr.GetReg(DSP_REG_PROD_64, prod_reg, false);
|
||||
// g_dsp.r[DSP_REG_PRODL] = (u16)val;
|
||||
MOV(64, prod_reg, R(RAX));
|
||||
|
||||
gpr.putReg(DSP_REG_PROD_64, true);
|
||||
gpr.PutReg(DSP_REG_PROD_64, true);
|
||||
}
|
||||
|
||||
// Returns s64 in RAX
|
||||
|
@ -738,80 +738,80 @@ void DSPEmitter::round_long_acc(X64Reg long_acc)
|
|||
void DSPEmitter::get_long_acc(int _reg, X64Reg acc)
|
||||
{
|
||||
OpArg reg;
|
||||
gpr.getReg(DSP_REG_ACC0_64+_reg, reg);
|
||||
gpr.GetReg(DSP_REG_ACC0_64+_reg, reg);
|
||||
MOV(64, R(acc), reg);
|
||||
gpr.putReg(DSP_REG_ACC0_64+_reg, false);
|
||||
gpr.PutReg(DSP_REG_ACC0_64+_reg, false);
|
||||
}
|
||||
|
||||
// In: acc = s64 val
|
||||
void DSPEmitter::set_long_acc(int _reg, X64Reg acc)
|
||||
{
|
||||
OpArg reg;
|
||||
gpr.getReg(DSP_REG_ACC0_64+_reg, reg, false);
|
||||
gpr.GetReg(DSP_REG_ACC0_64+_reg, reg, false);
|
||||
MOV(64, reg, R(acc));
|
||||
gpr.putReg(DSP_REG_ACC0_64+_reg);
|
||||
gpr.PutReg(DSP_REG_ACC0_64+_reg);
|
||||
}
|
||||
|
||||
// Returns s16 in AX
|
||||
void DSPEmitter::get_acc_l(int _reg, X64Reg acl, bool sign)
|
||||
{
|
||||
// return g_dsp.r[DSP_REG_ACM0 + _reg];
|
||||
gpr.readReg(_reg+DSP_REG_ACL0, acl, sign?SIGN:ZERO);
|
||||
gpr.ReadReg(_reg+DSP_REG_ACL0, acl, sign?SIGN:ZERO);
|
||||
}
|
||||
|
||||
void DSPEmitter::set_acc_l(int _reg, const OpArg& arg)
|
||||
{
|
||||
// return g_dsp.r[DSP_REG_ACM0 + _reg];
|
||||
gpr.writeReg(_reg+DSP_REG_ACL0,arg);
|
||||
gpr.WriteReg(_reg+DSP_REG_ACL0,arg);
|
||||
}
|
||||
|
||||
// Returns s16 in AX
|
||||
void DSPEmitter::get_acc_m(int _reg, X64Reg acm, bool sign)
|
||||
{
|
||||
// return g_dsp.r[DSP_REG_ACM0 + _reg];
|
||||
gpr.readReg(_reg+DSP_REG_ACM0, acm, sign?SIGN:ZERO);
|
||||
gpr.ReadReg(_reg+DSP_REG_ACM0, acm, sign?SIGN:ZERO);
|
||||
}
|
||||
|
||||
// In: s16 in AX
|
||||
void DSPEmitter::set_acc_m(int _reg, const OpArg& arg)
|
||||
{
|
||||
// return g_dsp.r.ac[_reg].m;
|
||||
gpr.writeReg(_reg+DSP_REG_ACM0,arg);
|
||||
gpr.WriteReg(_reg+DSP_REG_ACM0,arg);
|
||||
}
|
||||
|
||||
// Returns s16 in AX
|
||||
void DSPEmitter::get_acc_h(int _reg, X64Reg ach, bool sign)
|
||||
{
|
||||
// return g_dsp.r.ac[_reg].h;
|
||||
gpr.readReg(_reg+DSP_REG_ACH0, ach, sign?SIGN:ZERO);
|
||||
gpr.ReadReg(_reg+DSP_REG_ACH0, ach, sign?SIGN:ZERO);
|
||||
}
|
||||
|
||||
// In: s16 in AX
|
||||
void DSPEmitter::set_acc_h(int _reg, const OpArg& arg)
|
||||
{
|
||||
// return g_dsp.r[DSP_REG_ACM0 + _reg];
|
||||
gpr.writeReg(_reg+DSP_REG_ACH0,arg);
|
||||
gpr.WriteReg(_reg+DSP_REG_ACH0,arg);
|
||||
}
|
||||
|
||||
// Returns u32 in EAX
|
||||
void DSPEmitter::get_long_acx(int _reg, X64Reg acx)
|
||||
{
|
||||
// return ((u32)g_dsp.r[DSP_REG_AXH0 + _reg] << 16) | g_dsp.r[DSP_REG_AXL0 + _reg];
|
||||
gpr.readReg(_reg+DSP_REG_AX0_32, acx, SIGN);
|
||||
gpr.ReadReg(_reg+DSP_REG_AX0_32, acx, SIGN);
|
||||
}
|
||||
|
||||
// Returns s16 in EAX
|
||||
void DSPEmitter::get_ax_l(int _reg, X64Reg axl)
|
||||
{
|
||||
// return (s16)g_dsp.r[DSP_REG_AXL0 + _reg];
|
||||
gpr.readReg(_reg+DSP_REG_AXL0, axl, SIGN);
|
||||
gpr.ReadReg(_reg+DSP_REG_AXL0, axl, SIGN);
|
||||
}
|
||||
|
||||
// Returns s16 in EAX
|
||||
void DSPEmitter::get_ax_h(int _reg, X64Reg axh)
|
||||
{
|
||||
// return (s16)g_dsp.r[DSP_REG_AXH0 + _reg];
|
||||
gpr.readReg(_reg+DSP_REG_AXH0, axh, SIGN);
|
||||
gpr.ReadReg(_reg+DSP_REG_AXH0, axh, SIGN);
|
||||
}
|
||||
|
||||
|
||||
|
|
Loading…
Reference in New Issue