mirror of
https://github.com/hrydgard/ppsspp.git
synced 2026-10-20 17:59:08 +02:00
ARM64Emitter: Implement instructions to move data to/from SP
This commit is contained in:
1 parent
f5cef88e14
commit
a1ec735f6c
6 files changed
+25
-2
No files matched your search
@@ -1464,6 +1464,15 @@ void ARM64XEmitter::MOV(ARM64Reg Rd, ARM64Reg Rm)
|
||||
_assert_msg_(JIT, false, "Non-GPRs not supported in MOV");
|
||||
}
|
||||
}
|
||||
|
||||
void ARM64XEmitter::MOVfromSP(ARM64Reg Rd) {
|
||||
ADD(Rd, ARM64Reg::SP, 0, false);
|
||||
}
|
||||
|
||||
void ARM64XEmitter::MOVtoSP(ARM64Reg Rn) {
|
||||
ADD(ARM64Reg::SP, Rn, 0, false);
|
||||
}
|
||||
|
||||
void ARM64XEmitter::MVN(ARM64Reg Rd, ARM64Reg Rm)
|
||||
{
|
||||
ORN(Rd, Is64Bit(Rd) ? ZR : WZR, Rm, ArithOption(Rm, ST_LSL, 0));
|
||||
|
||||
@@ -566,6 +566,10 @@ public:
|
||||
void MOV(ARM64Reg Rd, ARM64Reg Rm);
|
||||
void MVN(ARM64Reg Rd, ARM64Reg Rm);
|
||||
|
||||
// Wrapper around ADD reg, reg, imm.
|
||||
void MOVfromSP(ARM64Reg Rd);
|
||||
void MOVtoSP(ARM64Reg Rn);
|
||||
|
||||
// TODO: These are "slow" as they use arith+shift, should be replaced with UBFM/EXTR variants.
|
||||
void LSR(ARM64Reg Rd, ARM64Reg Rm, int shift);
|
||||
void LSL(ARM64Reg Rd, ARM64Reg Rm, int shift);
|
||||
|
||||
+1
-1
@@ -391,6 +391,7 @@ public:
|
||||
// INC and DEC are slow on Intel Core, but not on AMD. They create a
|
||||
// false flag dependency because they only update a subset of the flags.
|
||||
// XCHG is SLOW and should be avoided.
|
||||
// Actually, REP MOVSB has gotten fast again on recent CPU generations, though it's not all that useful anyway.
|
||||
|
||||
// Debug breakpoint
|
||||
void INT3();
|
||||
@@ -410,7 +411,6 @@ public:
|
||||
void LAHF(); // 3 cycle vector path
|
||||
void SAHF(); // direct path fast
|
||||
|
||||
|
||||
// Stack control
|
||||
void PUSH(X64Reg reg);
|
||||
void POP(X64Reg reg);
|
||||
|
||||
@@ -253,6 +253,7 @@ void MemoryMap_Shutdown(u32 flags) {
|
||||
|
||||
void Init() {
|
||||
// On some 32 bit platforms, you can only map < 32 megs at a time.
|
||||
// TODO: Wait, wtf? What platforms are those? This seems bad.
|
||||
const static int MAX_MMAP_SIZE = 31 * 1024 * 1024;
|
||||
_dbg_assert_msg_(MEMMAP, g_MemorySize < MAX_MMAP_SIZE * 3, "ACK - too much memory for three mmap views.");
|
||||
for (size_t i = 0; i < ARRAY_SIZE(views); i++) {
|
||||
|
||||
@@ -159,11 +159,15 @@ static void DataProcessingImmediate(uint32_t w, uint64_t addr, Instruction *inst
|
||||
// Add/subtract immediate value
|
||||
int op = (w >> 30) & 1;
|
||||
int imm = ((w >> 10) & 0xFFF);
|
||||
int shift = ((w >> 22) & 0x3) * 16;
|
||||
int shift = ((w >> 22) & 0x1) * 12;
|
||||
int s = ((w >> 29) & 1);
|
||||
imm <<= shift;
|
||||
if (s && Rd == 31) {
|
||||
snprintf(instr->text, sizeof(instr->text), "cmp %c%d, #%d", r, Rn, imm);
|
||||
} else if (!shift && Rn == 31 && imm == 0) {
|
||||
snprintf(instr->text, sizeof(instr->text), "mov %c%d, sp", r, Rd);
|
||||
} else if (!shift && Rd == 31 && imm == 0) {
|
||||
snprintf(instr->text, sizeof(instr->text), "mov sp, %c%d", r, Rn);
|
||||
} else {
|
||||
snprintf(instr->text, sizeof(instr->text), "%s%s %c%d, %c%d, #%d", op == 0 ? "add" : "sub", s ? "s" : "", r, Rd, r, Rn, imm);
|
||||
}
|
||||
|
||||
@@ -41,6 +41,11 @@ bool TestArm64Emitter() {
|
||||
ARM64XEmitter emitter((u8 *)code);
|
||||
ARM64FloatEmitter fp(&emitter);
|
||||
|
||||
emitter.MOVfromSP(X3);
|
||||
RET(CheckLast(emitter, "910003e3 mov x3, sp"));
|
||||
emitter.MOVtoSP(X11);
|
||||
RET(CheckLast(emitter, "9100017f mov sp, x11"));
|
||||
|
||||
fp.EOR(Q0, Q1, Q2);
|
||||
RET(CheckLast(emitter, "6e221c20 eor q0, q1, q2"));
|
||||
fp.EOR(D0, D1, D2);
|
||||
|
||||
Reference in new issue
Block a user