mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-02-14 00:09:24 +01:00
Add a new WriteNewStoreOp emitter function for beginning of rewrite of the Arm Emitter LoadStores. Will finish when I have the hardware in front of me to test on.
This commit is contained in:
parent
c23a6505ad
commit
202e2fa5c8
@ -659,6 +659,103 @@ void ARMXEmitter::SVC(Operand2 op)
|
|||||||
Write32(condition | (0x0F << 24) | op.Imm24());
|
Write32(condition | (0x0F << 24) | op.Imm24());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// IMM, REG, IMMSREG, RSR
|
||||||
|
// -1 for invalid if the instruction doesn't support that
|
||||||
|
const s32 LoadStoreOps[][4] = { {0x40, 0x60, 0x60, -1}, // STR
|
||||||
|
{0x41, 0x61, 0x61, -1}, // LDR
|
||||||
|
{0x44, 0x64, 0x64, -1}, // STRB
|
||||||
|
{0x45, 0x65, 0x65, -1}, // LDRB
|
||||||
|
// Special encodings
|
||||||
|
{ 0x4, 0x0, -1, -1}, // STRH
|
||||||
|
{ 0x5, 0x1, -1, -1}, // LDRH
|
||||||
|
{ 0x5, 0x1, -1, -1}, // LDRSB
|
||||||
|
{ 0x5, 0x1, -1, -1}, // LDRSH
|
||||||
|
};
|
||||||
|
const char *LoadStoreNames[] = { "STR",
|
||||||
|
"LDR",
|
||||||
|
"STRB",
|
||||||
|
"LDRB",
|
||||||
|
"STRH",
|
||||||
|
"LDRH",
|
||||||
|
"LDRSB",
|
||||||
|
"LDRSH",
|
||||||
|
};
|
||||||
|
|
||||||
|
void ARMXEmitter::WriteNewStoreOp(u32 Op, ARMReg Rt, ARMReg Rn, Operand2 op2, bool RegAdd)
|
||||||
|
{
|
||||||
|
s32 op = LoadStoreOps[Op][Rm.GetType()]; // Type always decided by last operand
|
||||||
|
u32 Data;
|
||||||
|
|
||||||
|
// Qualcomm chipsets get /really/ angry if you don't use index, even if the offset is zero.
|
||||||
|
// Some of these encodings require Index at all times anyway. Doesn't really matter.
|
||||||
|
// bool Index = op2 != 0 ? true : false;
|
||||||
|
bool Index = true;
|
||||||
|
bool Add = false;
|
||||||
|
|
||||||
|
// Special Encoding
|
||||||
|
bool SpecialOp = false;
|
||||||
|
bool Half = false;
|
||||||
|
bool SignedLoad = false;
|
||||||
|
|
||||||
|
if (op == -1)
|
||||||
|
_assert_msg_(DYNA_REC, false, "%s does not support %d", LoadStoreNames[Op], Rm.GetType());
|
||||||
|
|
||||||
|
switch (Op)
|
||||||
|
{
|
||||||
|
case 4: // STRH
|
||||||
|
SpecialOp = true;
|
||||||
|
Half = true;
|
||||||
|
SignedLoad = false;
|
||||||
|
break;
|
||||||
|
case 5: // LDRH
|
||||||
|
SpecialOp = true;
|
||||||
|
Half = true;
|
||||||
|
SignedLoad = false;
|
||||||
|
break;
|
||||||
|
case 6: // LDRSB
|
||||||
|
SpecialOp = true;
|
||||||
|
Half = false;
|
||||||
|
SignedLoad = true;
|
||||||
|
break;
|
||||||
|
case 7: // LDRSH
|
||||||
|
SpecialOp = true;
|
||||||
|
Half = true;
|
||||||
|
SignedLoad = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
switch (Rm.GetType())
|
||||||
|
{
|
||||||
|
case TYPE_IMM:
|
||||||
|
s32 Temp = (s32)Rm.Value;
|
||||||
|
Data = abs(Temp);
|
||||||
|
// The offset is encoded differently on this one.
|
||||||
|
if (SpecialOp)
|
||||||
|
Data = (Data & 0xF0 << 4) | (Data & 0xF);
|
||||||
|
if (Temp >= 0) ImmAdd = true;
|
||||||
|
break;
|
||||||
|
case TYPE_REG:
|
||||||
|
case TYPE_IMMSREG:
|
||||||
|
if (!SpecialOp)
|
||||||
|
{
|
||||||
|
Data = Rm.GetData();
|
||||||
|
Add = RegAdd;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
// RSR not supported for any of these
|
||||||
|
// We already have the warning above
|
||||||
|
BKPT(0x2);
|
||||||
|
return;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (SpecialOp)
|
||||||
|
{
|
||||||
|
// Add SpecialOp things
|
||||||
|
Data = (0x5 << 4) | (SignedLoad << 6) | (Half << 5) | Data;
|
||||||
|
}
|
||||||
|
Write32(condition | (op << 20) | (Index << 24) | (Add << 23) | (Rn << 16) | (Rt << 12) | Data);
|
||||||
|
}
|
||||||
|
|
||||||
void ARMXEmitter::LDR (ARMReg dest, ARMReg src, s16 op) { WriteStoreOp(0x41, src, dest, op);}
|
void ARMXEmitter::LDR (ARMReg dest, ARMReg src, s16 op) { WriteStoreOp(0x41, src, dest, op);}
|
||||||
void ARMXEmitter::LDRH(ARMReg dest, ARMReg src, Operand2 op)
|
void ARMXEmitter::LDRH(ARMReg dest, ARMReg src, Operand2 op)
|
||||||
{
|
{
|
||||||
|
@ -353,6 +353,8 @@ private:
|
|||||||
std::vector<LiteralPool> currentLitPool;
|
std::vector<LiteralPool> currentLitPool;
|
||||||
|
|
||||||
void WriteStoreOp(u32 op, ARMReg src, ARMReg dest, s16 op2);
|
void WriteStoreOp(u32 op, ARMReg src, ARMReg dest, s16 op2);
|
||||||
|
void WriteNewStoreOp(u32 Op, ARMReg Rt, ARMReg Rn, Operand2 op2, bool RegAdd);
|
||||||
|
|
||||||
void WriteRegStoreOp(u32 op, ARMReg dest, bool WriteBack, u16 RegList);
|
void WriteRegStoreOp(u32 op, ARMReg dest, bool WriteBack, u16 RegList);
|
||||||
void WriteShiftedDataOp(u32 op, bool SetFlags, ARMReg dest, ARMReg src, ARMReg op2);
|
void WriteShiftedDataOp(u32 op, bool SetFlags, ARMReg dest, ARMReg src, ARMReg op2);
|
||||||
void WriteShiftedDataOp(u32 op, bool SetFlags, ARMReg dest, ARMReg src, Operand2 op2);
|
void WriteShiftedDataOp(u32 op, bool SetFlags, ARMReg dest, ARMReg src, Operand2 op2);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user