diff options
| author | ptitSeb <sebastien.chev@gmail.com> | 2021-03-20 10:48:15 +0100 |
|---|---|---|
| committer | ptitSeb <sebastien.chev@gmail.com> | 2021-03-20 10:48:15 +0100 |
| commit | e5b36d2997a44eb10adc1a17591a878200743f5f (patch) | |
| tree | 5cc012183572b78652ec4f00b21361422d896651 | |
| parent | cc2016bbc9b6a68c730db2982e1060df250c7a97 (diff) | |
| download | box64-e5b36d2997a44eb10adc1a17591a878200743f5f.tar.gz box64-e5b36d2997a44eb10adc1a17591a878200743f5f.zip | |
[DYNAREC] Added D0/D2 opcodes
| -rwxr-xr-x | src/dynarec/arm64_emitter.h | 3 | ||||
| -rwxr-xr-x | src/dynarec/dynarec_arm64_00.c | 100 | ||||
| -rwxr-xr-x | src/dynarec/dynarec_arm64_helper.h | 4 |
3 files changed, 104 insertions, 3 deletions
diff --git a/src/dynarec/arm64_emitter.h b/src/dynarec/arm64_emitter.h index 5e72e4d8..091544df 100755 --- a/src/dynarec/arm64_emitter.h +++ b/src/dynarec/arm64_emitter.h @@ -214,6 +214,9 @@ #define LDRSHx_U12(Rt, Rn, imm12) EMIT(LDRSH_gen(0b01, 0b01, 0b10, ((uint32_t)(imm12>>1))&0xfff, Rn, Rt)) #define LDRSHw_U12(Rt, Rn, imm12) EMIT(LDRSH_gen(0b01, 0b01, 0b11, ((uint32_t)(imm12>>1))&0xfff, Rn, Rt)) #define LDRSHxw_U12(Rt, Rn, imm12) EMIT(LDRSH_gen(0b01, 0b01, rex.w?0b10:0b11, ((uint32_t)(imm12>>1))&0xfff, Rn, Rt)) +#define LDRSBx_U12(Rt, Rn, imm12) EMIT(LDRSH_gen(0b00, 0b01, 0b10, ((uint32_t)(imm12>>1))&0xfff, Rn, Rt)) +#define LDRSBw_U12(Rt, Rn, imm12) EMIT(LDRSH_gen(0b00, 0b01, 0b11, ((uint32_t)(imm12>>1))&0xfff, Rn, Rt)) +#define LDRSBxw_U12(Rt, Rn, imm12) EMIT(LDRSH_gen(0b00, 0b01, rex.w?0b10:0b11, ((uint32_t)(imm12>>1))&0xfff, Rn, Rt)) #define LDR_PC_gen(opc, imm19, Rt) ((opc)<<30 | 0b011<<27 | (imm19)<<5 | (Rt)) #define LDRx_literal(Rt, imm19) EMIT(LDR_PC_gen(0b01, ((imm19)>>2)&0x7FFFF, Rt)) diff --git a/src/dynarec/dynarec_arm64_00.c b/src/dynarec/dynarec_arm64_00.c index fb1424de..ac3e470c 100755 --- a/src/dynarec/dynarec_arm64_00.c +++ b/src/dynarec/dynarec_arm64_00.c @@ -706,7 +706,105 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin #endif } break; - + case 0xD0: + case 0xD2: // TODO: Jump if CL is 0 + nextop = F8; + switch((nextop>>3)&7) { + case 0: + if(opcode==0xD0) { + INST_NAME("ROL Eb, 1"); + MOV32w(x2, 1); + } else { + INST_NAME("ROL Eb, CL"); + ANDSw_mask(x2, xRCX, 0, 0b00100); + } + SETFLAGS(X_OF|X_CF, SF_SUBSET); + GETEB(x1, 0); + CALL_(rol8, x1, x3); + EBBACK; + break; + case 1: + if(opcode==0xD0) { + INST_NAME("ROR Eb, 1"); + MOV32w(x2, 1); + } else { + INST_NAME("ROR Eb, CL"); + ANDSw_mask(x2, xRCX, 0, 0b00100); + } + SETFLAGS(X_OF|X_CF, SF_SUBSET); + GETEB(x1, 0); + CALL_(ror8, x1, x3); + EBBACK; + break; + case 2: + if(opcode==0xD0) {INST_NAME("RCL Eb, 1");} else {INST_NAME("RCL Eb, CL");} + READFLAGS(X_CF); + SETFLAGS(X_OF|X_CF, SF_SET); + if(opcode==0xD0) {MOV32w(x2, 1);} else {ANDSw_mask(x2, xRCX, 0, 0b00100);} + GETEB(x1, 0); + CALL_(rcl8, x1, x3); + EBBACK; + break; + case 3: + if(opcode==0xD0) {INST_NAME("RCR Eb, 1");} else {INST_NAME("RCR Eb, CL");} + READFLAGS(X_CF); + SETFLAGS(X_OF|X_CF, SF_SET); + if(opcode==0xD0) {MOV32w(x2, 1);} else {ANDSw_mask(x2, xRCX, 0, 0b00100);} + GETEB(x1, 0); + CALL_(rcr8, x1, x3); + EBBACK; + break; + case 4: + case 6: + if(opcode==0xD0) { + INST_NAME("SHL Eb, 1"); + MOV32w(x2, 1); + } else { + INST_NAME("SHL Eb, CL"); + ANDSw_mask(x2, xRCX, 0, 0b00100); + } + SETFLAGS(X_ALL, SF_PENDING); + GETEB(x1, 0); + UFLAG_OP12(ed, x2) + LSLw_REG(ed, ed, x2); + EBBACK; + UFLAG_RES(ed); + UFLAG_DF(x3, d_shl8); + break; + case 5: + if(opcode==0xD0) { + INST_NAME("SHR Eb, 1"); + MOV32w(x2, 1); + } else { + INST_NAME("SHR Eb, CL"); + ANDSw_mask(x2, xRCX, 0, 0b00100); + } + SETFLAGS(X_ALL, SF_PENDING); + GETEB(x1, 0); + UFLAG_OP12(ed, x2); + LSRw_REG(ed, ed, x2); + EBBACK; + UFLAG_RES(ed); + UFLAG_DF(x3, d_shr8); + break; + case 7: + if(opcode==0xD0) { + INST_NAME("SAR Eb, 1"); + MOV32w(x2, 1); + } else { + INST_NAME("SAR Eb, CL"); + ANDSw_mask(x2, xRCX, 0, 0b00100); + } + SETFLAGS(X_ALL, SF_PENDING); + GETSEB(x1, 0); + UFLAG_OP12(ed, x2) + ASRw_REG(ed, ed, x2); + EBBACK; + UFLAG_RES(ed); + UFLAG_DF(x3, d_sar8); + break; + } + break; case 0xD1: nextop = F8; switch((nextop>>3)&7) { diff --git a/src/dynarec/dynarec_arm64_helper.h b/src/dynarec/dynarec_arm64_helper.h index 6615598f..b3e08d7d 100755 --- a/src/dynarec/dynarec_arm64_helper.h +++ b/src/dynarec/dynarec_arm64_helper.h @@ -176,7 +176,7 @@ ed = i; \ } //GETSEB sign extend EB, will use i for ed, and can use r3 for wback. -#define GETSEB(i) if(MODREG) { \ +#define GETSEB(i, D) if(MODREG) { \ if(rex.rex) { \ wback = xRAX+(nextop&7)+(rex.b<<3); \ wb2 = 0; \ @@ -190,7 +190,7 @@ ed = i; \ } else { \ addr = geted(dyn, addr, ninst, nextop, &wback, x3, &fixedaddress, 0xfff, 0, rex, 0, D); \ - LDRSB_U12(i, wback, fixedaddress); \ + LDRSBx_U12(i, wback, fixedaddress); \ wb1 = 1; \ ed = i; \ } |