mirror of
https://github.com/ptitSeb/box64.git
synced 2025-02-20 06:22:59 +00:00
[ARM64_DYNAREC] Some small improvments to ROR/ROL/RCR/RCL opcodes
This commit is contained in:
parent
3760be946f
commit
730eb1f472
@ -1933,7 +1933,7 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
INST_NAME("ROL Eb, Ib");
|
||||
u8 = geted_ib(dyn, addr, ninst, nextop)&0x1f;
|
||||
if(u8) {
|
||||
SETFLAGS(X_CF|X_OF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEB(x1, 1);
|
||||
u8 = F8&0x1f;
|
||||
emit_rol8c(dyn, ninst, x1, u8, x4, x5);
|
||||
@ -1947,7 +1947,7 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
INST_NAME("ROR Eb, Ib");
|
||||
u8 = geted_ib(dyn, addr, ninst, nextop)&0x1f;
|
||||
if(u8) {
|
||||
SETFLAGS(X_CF|X_OF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEB(x1, 1);
|
||||
u8 = F8&0x1f;
|
||||
emit_ror8c(dyn, ninst, x1, u8, x4, x5);
|
||||
@ -1962,7 +1962,7 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
u8 = geted_ib(dyn, addr, ninst, nextop)&0x1f;
|
||||
if(u8) {
|
||||
READFLAGS(X_CF);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEB(x1, 1);
|
||||
u8 = F8&0x1f;
|
||||
emit_rcl8c(dyn, ninst, x1, u8, x4, x5);
|
||||
@ -1977,7 +1977,7 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
u8 = geted_ib(dyn, addr, ninst, nextop)&0x1f;
|
||||
if(u8) {
|
||||
READFLAGS(X_CF);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEB(x1, 1);
|
||||
u8 = F8&0x1f;
|
||||
emit_rcr8c(dyn, ninst, x1, u8, x4, x5);
|
||||
@ -2039,7 +2039,7 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
INST_NAME("ROL Ed, Ib");
|
||||
u8 = geted_ib(dyn, addr, ninst, nextop)&(0x1f+(rex.w*0x20));
|
||||
if(u8) {
|
||||
SETFLAGS(X_CF|X_OF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETED(1);
|
||||
u8 = (F8)&(rex.w?0x3f:0x1f);
|
||||
emit_rol32c(dyn, ninst, rex, ed, u8, x3, x4);
|
||||
@ -2058,7 +2058,7 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
INST_NAME("ROR Ed, Ib");
|
||||
u8 = geted_ib(dyn, addr, ninst, nextop)&(0x1f+(rex.w*0x20));
|
||||
if(u8) {
|
||||
SETFLAGS(X_CF|X_OF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETED(1);
|
||||
u8 = (F8)&(rex.w?0x3f:0x1f);
|
||||
emit_ror32c(dyn, ninst, rex, ed, u8, x3, x4);
|
||||
@ -2470,14 +2470,14 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
switch((nextop>>3)&7) {
|
||||
case 0:
|
||||
INST_NAME("ROL Eb, 1");
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEB(x1, 0);
|
||||
emit_rol8c(dyn, ninst, ed, 1, x4, x5);
|
||||
EBBACK;
|
||||
break;
|
||||
case 1:
|
||||
INST_NAME("ROR Eb, 1");
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEB(x1, 0);
|
||||
emit_ror8c(dyn, ninst, ed, 1, x4, x5);
|
||||
EBBACK;
|
||||
@ -2527,14 +2527,14 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
switch((nextop>>3)&7) {
|
||||
case 0:
|
||||
INST_NAME("ROL Ed, 1");
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETED(0);
|
||||
emit_rol32c(dyn, ninst, rex, ed, 1, x3, x4);
|
||||
WBACK;
|
||||
break;
|
||||
case 1:
|
||||
INST_NAME("ROR Ed, 1");
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETED(0);
|
||||
emit_ror32c(dyn, ninst, rex, ed, 1, x3, x4);
|
||||
WBACK;
|
||||
|
@ -797,14 +797,14 @@ uintptr_t dynarec64_64(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
switch((nextop>>3)&7) {
|
||||
case 0:
|
||||
INST_NAME("ROL Ed, 1");
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEDO(x6, 0);
|
||||
emit_rol32c(dyn, ninst, rex, ed, 1, x3, x4);
|
||||
WBACKO(x6);
|
||||
break;
|
||||
case 1:
|
||||
INST_NAME("ROR Ed, 1");
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEDO(x6, 0);
|
||||
emit_ror32c(dyn, ninst, rex, ed, 1, x3, x4);
|
||||
WBACKO(x6);
|
||||
|
@ -977,7 +977,7 @@ uintptr_t dynarec64_66(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
INST_NAME("ROL Ew, Ib");
|
||||
u8 = geted_ib(dyn, addr, ninst, nextop) & 15;
|
||||
if (u8) {
|
||||
SETFLAGS(X_CF | X_OF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEW(x1, 1);
|
||||
u8 = (F8)&0x1f;
|
||||
emit_rol16c(dyn, ninst, x1, u8, x4, x5);
|
||||
@ -990,7 +990,7 @@ uintptr_t dynarec64_66(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
case 1:
|
||||
INST_NAME("ROR Ew, Ib");
|
||||
if (geted_ib(dyn, addr, ninst, nextop) & 15) {
|
||||
SETFLAGS(X_CF | X_OF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEW(x1, 1);
|
||||
u8 = (F8)&0x1f;
|
||||
emit_ror16c(dyn, ninst, x1, u8, x4, x5);
|
||||
@ -1006,7 +1006,7 @@ uintptr_t dynarec64_66(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
READFLAGS(X_CF);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEW(x1, 1);
|
||||
u8 = F8;
|
||||
u8 = (F8)&0x1f;
|
||||
emit_rcl16c(dyn, ninst, ed, u8, x4, x5);
|
||||
EWBACK;
|
||||
} else {
|
||||
@ -1020,7 +1020,7 @@ uintptr_t dynarec64_66(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
READFLAGS(X_CF);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEW(x1, 1);
|
||||
u8 = F8;
|
||||
u8 = (F8)&0x1f;
|
||||
emit_rcr16c(dyn, ninst, ed, u8, x4, x5);
|
||||
EWBACK;
|
||||
} else {
|
||||
@ -1093,14 +1093,14 @@ uintptr_t dynarec64_66(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
switch((nextop>>3)&7) {
|
||||
case 0:
|
||||
INST_NAME("ROL Ew, 1");
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEW(x1, 0);
|
||||
emit_rol16c(dyn, ninst, x1, 1, x5, x4);
|
||||
EWBACK;
|
||||
break;
|
||||
case 1:
|
||||
INST_NAME("ROR Ew, 1");
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETEW(x1, 0);
|
||||
emit_ror16c(dyn, ninst, x1, 1, x5, x4);
|
||||
EWBACK;
|
||||
|
@ -1050,7 +1050,7 @@ uintptr_t dynarec64_67(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
switch((nextop>>3)&7) {
|
||||
case 0:
|
||||
INST_NAME("ROL Ed, Ib");
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETED32(1);
|
||||
u8 = (F8)&(rex.w?0x3f:0x1f);
|
||||
emit_rol32c(dyn, ninst, rex, ed, u8, x3, x4);
|
||||
@ -1058,7 +1058,7 @@ uintptr_t dynarec64_67(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
break;
|
||||
case 1:
|
||||
INST_NAME("ROR Ed, Ib");
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET_PENDING);
|
||||
SETFLAGS(X_OF|X_CF, SF_SUBSET); // removed PENDING on purpose
|
||||
GETED32(1);
|
||||
u8 = (F8)&(rex.w?0x3f:0x1f);
|
||||
emit_ror32c(dyn, ninst, rex, ed, u8, x3, x4);
|
||||
|
@ -804,23 +804,9 @@ void emit_rol32c(dynarec_arm_t* dyn, int ninst, rex_t rex, int s1, uint32_t c, i
|
||||
|
||||
if (!c) return;
|
||||
|
||||
IFX(X_PEND) {
|
||||
MOV32w(s3, c);
|
||||
STRxw_U12(s3, xEmu, offsetof(x64emu_t, op2));
|
||||
SET_DF(s4, rex.w?d_rol64:d_rol32);
|
||||
} else IFX(X_ALL) {
|
||||
SET_DFNONE(s4);
|
||||
}
|
||||
if(!c) {
|
||||
IFX(X_PEND) {
|
||||
STRxw_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
return;
|
||||
}
|
||||
SET_DFNONE(s4);
|
||||
|
||||
RORxw(s1, s1, (rex.w?64:32)-c);
|
||||
IFX(X_PEND) {
|
||||
STRxw_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
IFX(X_CF) {
|
||||
BFIw(xFlags, s1, F_CF, 1);
|
||||
}
|
||||
@ -839,23 +825,9 @@ void emit_ror32c(dynarec_arm_t* dyn, int ninst, rex_t rex, int s1, uint32_t c, i
|
||||
|
||||
if (!c) return;
|
||||
|
||||
IFX(X_PEND) {
|
||||
MOV32w(s3, c);
|
||||
STRxw_U12(s3, xEmu, offsetof(x64emu_t, op2));
|
||||
SET_DF(s4, rex.w?d_ror64:d_ror32);
|
||||
} else IFX(X_ALL) {
|
||||
SET_DFNONE(s4);
|
||||
}
|
||||
if(!c) {
|
||||
IFX(X_PEND) {
|
||||
STRxw_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
return;
|
||||
}
|
||||
SET_DFNONE(s4);
|
||||
|
||||
RORxw(s1, s1, c);
|
||||
IFX(X_PEND) {
|
||||
STRxw_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
IFX(X_CF) {
|
||||
BFXILxw(xFlags, s1, rex.w?63:31, 1);
|
||||
}
|
||||
@ -875,21 +847,13 @@ void emit_rol8c(dynarec_arm_t* dyn, int ninst, int s1, uint32_t c, int s3, int s
|
||||
|
||||
if (!c) return;
|
||||
|
||||
IFX(X_PEND) {
|
||||
MOV32w(s3, c);
|
||||
STRB_U12(s3, xEmu, offsetof(x64emu_t, op2));
|
||||
SET_DF(s4, d_rol8);
|
||||
} else IFX(X_ALL) {
|
||||
SET_DFNONE(s4);
|
||||
}
|
||||
SET_DFNONE(s4);
|
||||
|
||||
if(c&7) {
|
||||
int rc = 8-(c&7);
|
||||
ORRw_REG_LSL(s1, s1, s1, 8);
|
||||
LSRw(s1, s1, rc);
|
||||
}
|
||||
IFX(X_PEND) {
|
||||
STRB_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
IFX(X_CF) {
|
||||
BFIw(xFlags, s1, F_CF, 1);
|
||||
}
|
||||
@ -908,20 +872,12 @@ void emit_ror8c(dynarec_arm_t* dyn, int ninst, int s1, uint32_t c, int s3, int s
|
||||
|
||||
if (!c) return;
|
||||
|
||||
IFX(X_PEND) {
|
||||
MOV32w(s3, c);
|
||||
STRB_U12(s3, xEmu, offsetof(x64emu_t, op2));
|
||||
SET_DF(s4, d_ror8);
|
||||
} else IFX(X_ALL) {
|
||||
SET_DFNONE(s4);
|
||||
}
|
||||
SET_DFNONE(s4);
|
||||
|
||||
if(c&7) {
|
||||
ORRw_REG_LSL(s1, s1, s1, 8);
|
||||
LSRw(s1, s1, c&7);
|
||||
}
|
||||
IFX(X_PEND) {
|
||||
STRB_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
IFX(X_CF) {
|
||||
BFXILw(xFlags, s1, 7, 1);
|
||||
}
|
||||
@ -941,21 +897,13 @@ void emit_rol16c(dynarec_arm_t* dyn, int ninst, int s1, uint32_t c, int s3, int
|
||||
|
||||
if (!c) return;
|
||||
|
||||
IFX(X_PEND) {
|
||||
MOV32w(s3, c);
|
||||
STRH_U12(s3, xEmu, offsetof(x64emu_t, op2));
|
||||
SET_DF(s4, d_rol16);
|
||||
} else IFX(X_ALL) {
|
||||
SET_DFNONE(s4);
|
||||
}
|
||||
SET_DFNONE(s4);
|
||||
|
||||
if(c&15) {
|
||||
int rc = 16-(c&15);
|
||||
ORRw_REG_LSL(s1, s1, s1, 16);
|
||||
LSRw(s1, s1, rc);
|
||||
}
|
||||
IFX(X_PEND) {
|
||||
STRH_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
IFX(X_CF) {
|
||||
BFIw(xFlags, s1, F_CF, 1);
|
||||
}
|
||||
@ -974,20 +922,12 @@ void emit_ror16c(dynarec_arm_t* dyn, int ninst, int s1, uint32_t c, int s3, int
|
||||
|
||||
if (!c) return;
|
||||
|
||||
IFX(X_PEND) {
|
||||
MOV32w(s3, c);
|
||||
STRH_U12(s3, xEmu, offsetof(x64emu_t, op2));
|
||||
SET_DF(s4, d_ror16);
|
||||
} else IFX(X_ALL) {
|
||||
SET_DFNONE(s4);
|
||||
}
|
||||
SET_DFNONE(s4);
|
||||
|
||||
if(c&15) {
|
||||
ORRw_REG_LSL(s1, s1, s1, 16);
|
||||
LSRw(s1, s1, c&15);
|
||||
}
|
||||
IFX(X_PEND) {
|
||||
STRH_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
IFX(X_CF) {
|
||||
BFXILw(xFlags, s1, 15, 1);
|
||||
}
|
||||
@ -1020,9 +960,6 @@ void emit_rcl8c(dynarec_arm_t* dyn, int ninst, int s1, uint32_t c, int s3, int s
|
||||
}
|
||||
ORRw_REG_LSL(s1, s1, s1, 9); // insert s1 again
|
||||
LSRw_IMM(s1, s1, 9-c); // do the rcl
|
||||
IFX(X_PEND) {
|
||||
STRB_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
IFX(X_OF|X_CF) {
|
||||
IFX(X_CF) {
|
||||
BFIw(xFlags, s3, F_CF, 1);
|
||||
@ -1063,9 +1000,6 @@ void emit_rcr8c(dynarec_arm_t* dyn, int ninst, int s1, uint32_t c, int s3, int s
|
||||
BFIw(xFlags, s3, F_OF, 1);
|
||||
}
|
||||
}
|
||||
IFX(X_PEND) {
|
||||
STRB_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
}
|
||||
|
||||
// emit RCL16 instruction, from s1 , constant c, store result in s1 using s3 and s4 as scratch
|
||||
@ -1088,9 +1022,6 @@ void emit_rcl16c(dynarec_arm_t* dyn, int ninst, int s1, uint32_t c, int s3, int
|
||||
}
|
||||
ORRx_REG_LSL(s1, s1, s1, 17); // insert s1 again
|
||||
LSRx_IMM(s1, s1, 17-c); // do the rcl
|
||||
IFX(X_PEND) {
|
||||
STRH_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
IFX(X_CF) {
|
||||
BFIw(xFlags, s3, F_CF, 1);
|
||||
}
|
||||
@ -1129,9 +1060,6 @@ void emit_rcr16c(dynarec_arm_t* dyn, int ninst, int s1, uint32_t c, int s3, int
|
||||
BFIw(xFlags, s3, F_OF, 1);
|
||||
}
|
||||
}
|
||||
IFX(X_PEND) {
|
||||
STRH_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
}
|
||||
|
||||
// emit RCL32/RCL64 instruction, from s1 , constant c, store result in s1 using s3 and s4 as scratch
|
||||
@ -1139,6 +1067,8 @@ void emit_rcl32c(dynarec_arm_t* dyn, int ninst, rex_t rex, int s1, uint32_t c, i
|
||||
{
|
||||
MAYUSE(s1); MAYUSE(s3); MAYUSE(s4);
|
||||
|
||||
if(!c) return;
|
||||
|
||||
SET_DFNONE(s4);
|
||||
|
||||
IFX(X_OF|X_CF) {
|
||||
@ -1152,9 +1082,6 @@ void emit_rcl32c(dynarec_arm_t* dyn, int ninst, rex_t rex, int s1, uint32_t c, i
|
||||
BFIxw(s4, xFlags, c-1, 1);
|
||||
ORRxw_REG_LSR(s1, s4, s1, (rex.w?65:33)-c);
|
||||
}
|
||||
IFX(X_PEND) {
|
||||
STRxw_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
IFX(X_CF) {
|
||||
BFIw(xFlags, s3, F_CF, 1);
|
||||
}
|
||||
@ -1170,6 +1097,8 @@ void emit_rcr32c(dynarec_arm_t* dyn, int ninst, rex_t rex, int s1, uint32_t c, i
|
||||
{
|
||||
MAYUSE(s1); MAYUSE(s3); MAYUSE(s4);
|
||||
|
||||
if(!c) return;
|
||||
|
||||
SET_DFNONE(s4);
|
||||
|
||||
IFX(X_OF) {
|
||||
@ -1192,9 +1121,6 @@ void emit_rcr32c(dynarec_arm_t* dyn, int ninst, rex_t rex, int s1, uint32_t c, i
|
||||
IFX(X_CF) {
|
||||
BFIw(wFlags, s3, 0, 1);
|
||||
}
|
||||
IFX(X_PEND) {
|
||||
STRxw_U12(s1, xEmu, offsetof(x64emu_t, res));
|
||||
}
|
||||
}
|
||||
|
||||
// emit SHRD32 instruction, from s1, fill s2 , constant c, store result in s1 using s3 and s4 as scratch
|
||||
|
Loading…
x
Reference in New Issue
Block a user