diff options
| author | ptitSeb <sebastien.chev@gmail.com> | 2021-04-02 14:41:19 +0200 |
|---|---|---|
| committer | ptitSeb <sebastien.chev@gmail.com> | 2021-04-02 14:41:19 +0200 |
| commit | 817c3d7058e9a7ee6b7c8edaccd880075d762271 (patch) | |
| tree | ef76949f9b5f1680f6a6b839e7570e21f1572cce /src | |
| parent | e2a7dd0f1760b0567067d20e55021746b57b2a37 (diff) | |
| download | box64-817c3d7058e9a7ee6b7c8edaccd880075d762271.tar.gz box64-817c3d7058e9a7ee6b7c8edaccd880075d762271.zip | |
Added 0F E0 opcode ([DYNAREC] too)
Diffstat (limited to 'src')
| -rwxr-xr-x | src/dynarec/arm64_emitter.h | 29 | ||||
| -rwxr-xr-x | src/dynarec/arm64_printer.c | 13 | ||||
| -rwxr-xr-x | src/dynarec/dynarec_arm64_0f.c | 8 | ||||
| -rw-r--r-- | src/emu/x64run0f.c | 8 |
4 files changed, 57 insertions, 1 deletions
diff --git a/src/dynarec/arm64_emitter.h b/src/dynarec/arm64_emitter.h index e4d130a1..bea887dc 100755 --- a/src/dynarec/arm64_emitter.h +++ b/src/dynarec/arm64_emitter.h @@ -1467,4 +1467,33 @@ #define UMINQ_32(Vd, Vn, Vm) EMIT(MINMAX_vector(1, 1, 0b10, Vm, 1, Vn, Vd)) #define UMINQ_64(Vd, Vn, Vm) EMIT(MINMAX_vector(1, 1, 0b11, Vm, 1, Vn, Vd)) +// HADD vector +#define HADD_vector(Q, U, size, Rm, Rn, Rd) ((Q)<<30 | (U)<<29 | 0b01110<<24 | (size)<<22 | 1<<21 | (Rm)<<16 | 1<<10 | (Rn)<<5 | (Rd)) +#define SHADD_8(Vd, Vn, Vm) EMIT(HADD_vector(0, 0, 0b00, Vm, Vn, Vd)) +#define SHADD_16(Vd, Vn, Vm) EMIT(HADD_vector(0, 0, 0b01, Vm, Vn, Vd)) +#define SHADD_32(Vd, Vn, Vm) EMIT(HADD_vector(0, 0, 0b10, Vm, Vn, Vd)) +#define SHADDQ_8(Vd, Vn, Vm) EMIT(HADD_vector(1, 0, 0b00, Vm, Vn, Vd)) +#define SHADDQ_16(Vd, Vn, Vm) EMIT(HADD_vector(1, 0, 0b01, Vm, Vn, Vd)) +#define SHADDQ_32(Vd, Vn, Vm) EMIT(HADD_vector(1, 0, 0b10, Vm, Vn, Vd)) +#define UHADD_8(Vd, Vn, Vm) EMIT(HADD_vector(0, 1, 0b00, Vm, Vn, Vd)) +#define UHADD_16(Vd, Vn, Vm) EMIT(HADD_vector(0, 1, 0b01, Vm, Vn, Vd)) +#define UHADD_32(Vd, Vn, Vm) EMIT(HADD_vector(0, 1, 0b10, Vm, Vn, Vd)) +#define UHADDQ_8(Vd, Vn, Vm) EMIT(HADD_vector(1, 1, 0b00, Vm, Vn, Vd)) +#define UHADDQ_16(Vd, Vn, Vm) EMIT(HADD_vector(1, 1, 0b01, Vm, Vn, Vd)) +#define UHADDQ_32(Vd, Vn, Vm) EMIT(HADD_vector(1, 1, 0b10, Vm, Vn, Vd)) + +#define RHADD_vector(Q, U, size, Rm, Rn, Rd) ((Q)<<30 | (U)<<29 | 0b01110<<24 | (size)<<22 | 1<<21 | (Rm)<<16 | 0b00010<<11 | 1<<10 | (Rn)<<5 | (Rd)) +#define SRHADD_8(Vd, Vn, Vm) EMIT(RHADD_vector(0, 0, 0b00, Vm, Vn, Vd)) +#define SRHADD_16(Vd, Vn, Vm) EMIT(RHADD_vector(0, 0, 0b01, Vm, Vn, Vd)) +#define SRHADD_32(Vd, Vn, Vm) EMIT(RHADD_vector(0, 0, 0b10, Vm, Vn, Vd)) +#define SRHADDQ_8(Vd, Vn, Vm) EMIT(RHADD_vector(1, 0, 0b00, Vm, Vn, Vd)) +#define SRHADDQ_16(Vd, Vn, Vm) EMIT(RHADD_vector(1, 0, 0b01, Vm, Vn, Vd)) +#define SRHADDQ_32(Vd, Vn, Vm) EMIT(RHADD_vector(1, 0, 0b10, Vm, Vn, Vd)) +#define URHADD_8(Vd, Vn, Vm) EMIT(RHADD_vector(0, 1, 0b00, Vm, Vn, Vd)) +#define URHADD_16(Vd, Vn, Vm) EMIT(RHADD_vector(0, 1, 0b01, Vm, Vn, Vd)) +#define URHADD_32(Vd, Vn, Vm) EMIT(RHADD_vector(0, 1, 0b10, Vm, Vn, Vd)) +#define URHADDQ_8(Vd, Vn, Vm) EMIT(RHADD_vector(1, 1, 0b00, Vm, Vn, Vd)) +#define URHADDQ_16(Vd, Vn, Vm) EMIT(RHADD_vector(1, 1, 0b01, Vm, Vn, Vd)) +#define URHADDQ_32(Vd, Vn, Vm) EMIT(RHADD_vector(1, 1, 0b10, Vm, Vn, Vd)) + #endif //__ARM64_EMITTER_H__ diff --git a/src/dynarec/arm64_printer.c b/src/dynarec/arm64_printer.c index bd2aaa65..556b2a2a 100755 --- a/src/dynarec/arm64_printer.c +++ b/src/dynarec/arm64_printer.c @@ -1176,6 +1176,19 @@ const char* arm64_print(uint32_t opcode, uintptr_t addr) snprintf(buff, sizeof(buff), "%cADDLV V%d.%s, V%d.%s", a.U?'U':'S', Rd, Z[sf], Rn, Vd); return buff; } + // HADD + if(isMask(opcode, "0QU01110ff1mmmmm000001nnnnnddddd", &a)) { + const char* Y[] = {"8B", "16B", "4H", "8H", "2S", "4S", "??", "???"}; + const char* Vd = Y[(sf<<1) | a.Q]; + snprintf(buff, sizeof(buff), "%cHADD V%d.%s, V%d.%s, V%d.%s", a.U?'U':'S', Rd, Vd, Rn, Vd, Rm, Vd); + return buff; + } + if(isMask(opcode, "0QU01110ff1mmmmm000101nnnnnddddd", &a)) { + const char* Y[] = {"8B", "16B", "4H", "8H", "2S", "4S", "??", "???"}; + const char* Vd = Y[(sf<<1) | a.Q]; + snprintf(buff, sizeof(buff), "%cRHADD V%d.%s, V%d.%s, V%d.%s", a.U?'U':'S', Rd, Vd, Rn, Vd, Rm, Vd); + return buff; + } // MOV immediate if(isMask(opcode, "0Q00111100000iii111001iiiiiddddd", &a)) { diff --git a/src/dynarec/dynarec_arm64_0f.c b/src/dynarec/dynarec_arm64_0f.c index 58380dfe..194f4f69 100755 --- a/src/dynarec/dynarec_arm64_0f.c +++ b/src/dynarec/dynarec_arm64_0f.c @@ -1275,6 +1275,14 @@ uintptr_t dynarec64_0F(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin VMUL_16(q0, q0, q1); break; + case 0xE0: + INST_NAME("PAVGB Gm, Em"); + nextop = F8; + GETGM(v0); + GETEM(v1, 0); + URHADD_8(v0, v0, v1); + break; + case 0xE7: INST_NAME("MOVNTQ Em, Gm"); // Non Temporal par not handled for now nextop = F8; diff --git a/src/emu/x64run0f.c b/src/emu/x64run0f.c index 3aeb8c9a..6037f073 100644 --- a/src/emu/x64run0f.c +++ b/src/emu/x64run0f.c @@ -1308,7 +1308,13 @@ int Run0F(x64emu_t *emu, rex_t rex) GETGM; GM->q = (~GM->q) & EM->q; break; - + case 0xE0: /* PAVGB Gm, Em */ + nextop = F8; + GETEM(0); + GETGM; + for(int i=0; i<8; ++i) + GM->ub[i] = ((uint32_t)GM->ub[i]+EM->ub[i]+1)>>1; + break; case 0xE1: /* PSRAW Gm, Em */ nextop = F8; GETEM(0); |