diff options
| author | phorcys <phorcys@126.com> | 2025-07-14 14:08:16 +0800 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2025-07-14 08:08:16 +0200 |
| commit | c558bdcb6977b3892157207d720dede89a9fb7b0 (patch) | |
| tree | eb0d4125485cfdfca0438a6ba6256dfd9fa29d55 /src | |
| parent | 0674e546e1743e2fd47c8477abe685de462f9744 (diff) | |
| download | box64-c558bdcb6977b3892157207d720dede89a9fb7b0.tar.gz box64-c558bdcb6977b3892157207d720dede89a9fb7b0.zip | |
[LA64_DYNAREC] Add la64 avx BMI2 shift ops. (#2807)
* VEX.66.0f.38 SHLX * VEX.f2.0f.38 SHRX * VEX.f3.0f.38 SARX
Diffstat (limited to 'src')
| -rw-r--r-- | src/dynarec/la64/dynarec_la64_avx.c | 8 | ||||
| -rw-r--r-- | src/dynarec/la64/dynarec_la64_avx_66_0f38.c | 11 | ||||
| -rw-r--r-- | src/dynarec/la64/dynarec_la64_avx_f2_0f38.c | 73 | ||||
| -rw-r--r-- | src/dynarec/la64/dynarec_la64_avx_f3_0f38.c | 73 | ||||
| -rw-r--r-- | src/dynarec/la64/dynarec_la64_helper.h | 4 |
5 files changed, 164 insertions, 5 deletions
diff --git a/src/dynarec/la64/dynarec_la64_avx.c b/src/dynarec/la64/dynarec_la64_avx.c index 12e00db2..f395c80e 100644 --- a/src/dynarec/la64/dynarec_la64_avx.c +++ b/src/dynarec/la64/dynarec_la64_avx.c @@ -63,12 +63,12 @@ uintptr_t dynarec64_AVX(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int n addr = dynarec64_AVX_66_0F38(dyn, addr, ip, ninst, vex, ok, need_epilog); else if ((vex.m == VEX_M_0F3A) && (vex.p == VEX_P_66)) addr = dynarec64_AVX_66_0F3A(dyn, addr, ip, ninst, vex, ok, need_epilog); - // else if( (vex.m==VEX_M_0F38) && (vex.p==VEX_P_F2)) - // addr = dynarec64_AVX_F2_0F38(dyn, addr, ip, ninst, vex, ok, need_epilog); + else if( (vex.m == VEX_M_0F38) && (vex.p == VEX_P_F2)) + addr = dynarec64_AVX_F2_0F38(dyn, addr, ip, ninst, vex, ok, need_epilog); else if ((vex.m == VEX_M_0F3A) && (vex.p == VEX_P_F2)) addr = dynarec64_AVX_F2_0F3A(dyn, addr, ip, ninst, vex, ok, need_epilog); - // else if( (vex.m==VEX_M_0F38) && (vex.p==VEX_P_F3)) - // addr = dynarec64_AVX_F3_0F38(dyn, addr, ip, ninst, vex, ok, need_epilog); + else if( (vex.m==VEX_M_0F38) && (vex.p==VEX_P_F3)) + addr = dynarec64_AVX_F3_0F38(dyn, addr, ip, ninst, vex, ok, need_epilog); else { DEFAULT; } diff --git a/src/dynarec/la64/dynarec_la64_avx_66_0f38.c b/src/dynarec/la64/dynarec_la64_avx_66_0f38.c index 48d4e4e1..e8f82715 100644 --- a/src/dynarec/la64/dynarec_la64_avx_66_0f38.c +++ b/src/dynarec/la64/dynarec_la64_avx_66_0f38.c @@ -27,7 +27,7 @@ uintptr_t dynarec64_AVX_66_0F38(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t i uint8_t opcode = F8; uint8_t nextop, u8; - uint8_t gd, ed; + uint8_t gd, ed, vd; uint8_t wback, wb1, wb2; uint8_t eb1, eb2, gb1, gb2; int32_t i32, i32_; @@ -354,6 +354,15 @@ uintptr_t dynarec64_AVX_66_0F38(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t i PUTEYx(v0); } break; + case 0xF7: + INST_NAME("SHLX Gd, Ed, Vd"); + nextop = F8; + GETGD; + GETED(0); + GETVD; + ANDI(x5, vd, rex.w ? 0x3f : 0x1f); + SLLxw(gd, ed, x5); + break; default: DEFAULT; } diff --git a/src/dynarec/la64/dynarec_la64_avx_f2_0f38.c b/src/dynarec/la64/dynarec_la64_avx_f2_0f38.c new file mode 100644 index 00000000..f8a29542 --- /dev/null +++ b/src/dynarec/la64/dynarec_la64_avx_f2_0f38.c @@ -0,0 +1,73 @@ +#include <stdio.h> +#include <stdlib.h> +#include <stddef.h> +#include <errno.h> + +#include "debug.h" +#include "env.h" +#include "box64context.h" +#include "box64cpu.h" +#include "emu/x64emu_private.h" +#include "x64emu.h" +#include "box64stack.h" +#include "callback.h" +#include "emu/x64run_private.h" +#include "x64trace.h" +#include "dynarec_native.h" + +#include "la64_printer.h" +#include "dynarec_la64_private.h" +#include "dynarec_la64_functions.h" +#include "../dynarec_helper.h" + +uintptr_t dynarec64_AVX_F2_0F38(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ninst, vex_t vex, int* ok, int* need_epilog) +{ + (void)ip; + (void)need_epilog; + + uint8_t opcode = F8; + uint8_t nextop, u8; + uint8_t gd, ed, vd; + uint8_t wback, wb1, wb2; + uint8_t eb1, eb2, gb1, gb2; + int32_t i32, i32_; + int cacheupd = 0; + int v0, v1, v2; + int q0, q1, q2; + int d0, d1, d2; + int s0; + uint64_t tmp64u; + int64_t j64; + int64_t fixedaddress; + int unscaled; + MAYUSE(wb1); + MAYUSE(wb2); + MAYUSE(eb1); + MAYUSE(eb2); + MAYUSE(gb1); + MAYUSE(gb2); + MAYUSE(q0); + MAYUSE(q1); + MAYUSE(d0); + MAYUSE(d1); + MAYUSE(s0); + MAYUSE(j64); + MAYUSE(cacheupd); + + rex_t rex = vex.rex; + + switch (opcode) { + case 0xF7: + INST_NAME("SHRX Gd, Ed, Vd"); + nextop = F8; + GETGD; + GETED(0); + GETVD; + ANDI(x5, vd, rex.w ? 0x3f : 0x1f); + SRLxw(gd, ed, x5); + break; + default: + DEFAULT; + } + return addr; +} diff --git a/src/dynarec/la64/dynarec_la64_avx_f3_0f38.c b/src/dynarec/la64/dynarec_la64_avx_f3_0f38.c new file mode 100644 index 00000000..8e8e6781 --- /dev/null +++ b/src/dynarec/la64/dynarec_la64_avx_f3_0f38.c @@ -0,0 +1,73 @@ +#include <stdio.h> +#include <stdlib.h> +#include <stddef.h> +#include <errno.h> + +#include "debug.h" +#include "env.h" +#include "box64context.h" +#include "box64cpu.h" +#include "emu/x64emu_private.h" +#include "x64emu.h" +#include "box64stack.h" +#include "callback.h" +#include "emu/x64run_private.h" +#include "x64trace.h" +#include "dynarec_native.h" + +#include "la64_printer.h" +#include "dynarec_la64_private.h" +#include "dynarec_la64_functions.h" +#include "../dynarec_helper.h" + +uintptr_t dynarec64_AVX_F3_0F38(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ninst, vex_t vex, int* ok, int* need_epilog) +{ + (void)ip; + (void)need_epilog; + + uint8_t opcode = F8; + uint8_t nextop, u8; + uint8_t gd, ed, vd; + uint8_t wback, wb1, wb2; + uint8_t eb1, eb2, gb1, gb2; + int32_t i32, i32_; + int cacheupd = 0; + int v0, v1, v2; + int q0, q1, q2; + int d0, d1, d2; + int s0; + uint64_t tmp64u; + int64_t j64; + int64_t fixedaddress; + int unscaled; + MAYUSE(wb1); + MAYUSE(wb2); + MAYUSE(eb1); + MAYUSE(eb2); + MAYUSE(gb1); + MAYUSE(gb2); + MAYUSE(q0); + MAYUSE(q1); + MAYUSE(d0); + MAYUSE(d1); + MAYUSE(s0); + MAYUSE(j64); + MAYUSE(cacheupd); + + rex_t rex = vex.rex; + + switch (opcode) { + case 0xF7: + INST_NAME("SARX Gd, Ed, Vd"); + nextop = F8; + GETGD; + GETED(0); + GETVD; + ANDI(x5, vd, rex.w ? 0x3f : 0x1f); + SRAxw(gd, ed, x5); + break; + default: + DEFAULT; + } + return addr; +} diff --git a/src/dynarec/la64/dynarec_la64_helper.h b/src/dynarec/la64/dynarec_la64_helper.h index b6b646a8..acd22031 100644 --- a/src/dynarec/la64/dynarec_la64_helper.h +++ b/src/dynarec/la64/dynarec_la64_helper.h @@ -1100,8 +1100,10 @@ #define dynarec64_AVX_66_0F38 STEPNAME(dynarec64_AVX_66_0F38) #define dynarec64_AVX_66_0F3A STEPNAME(dynarec64_AVX_66_0F3A) #define dynarec64_AVX_F2_0F STEPNAME(dynarec64_AVX_F2_0F) +#define dynarec64_AVX_F2_0F38 STEPNAME(dynarec64_AVX_F2_0F38) #define dynarec64_AVX_F2_0F3A STEPNAME(dynarec64_AVX_F2_0F3A) #define dynarec64_AVX_F3_0F STEPNAME(dynarec64_AVX_F3_0F) +#define dynarec64_AVX_F3_0F38 STEPNAME(dynarec64_AVX_F3_0F38) #define geted STEPNAME(geted) #define geted32 STEPNAME(geted32) @@ -1392,8 +1394,10 @@ uintptr_t dynarec64_AVX_66_0F(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, uintptr_t dynarec64_AVX_66_0F38(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ninst, vex_t vex, int* ok, int* need_epilog); uintptr_t dynarec64_AVX_66_0F3A(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ninst, vex_t vex, int* ok, int* need_epilog); uintptr_t dynarec64_AVX_F2_0F(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ninst, vex_t vex, int* ok, int* need_epilog); +uintptr_t dynarec64_AVX_F2_0F38(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ninst, vex_t vex, int* ok, int* need_epilog); uintptr_t dynarec64_AVX_F2_0F3A(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ninst, vex_t vex, int* ok, int* need_epilog); uintptr_t dynarec64_AVX_F3_0F(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ninst, vex_t vex, int* ok, int* need_epilog); +uintptr_t dynarec64_AVX_F3_0F38(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ninst, vex_t vex, int* ok, int* need_epilog); #if STEP < 3 |