diff options
| author | Yang Liu <numbksco@gmail.com> | 2024-04-05 17:55:41 +0800 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2024-04-05 11:55:41 +0200 |
| commit | 2e9b8eff59cec7a0170f9dc2f1fb6212a4f3ab85 (patch) | |
| tree | 1a0acfaca339473cef6fc547abe7dcd06fa8972a /src | |
| parent | a4142f68ce3a6b5d5034966ff887a00160539917 (diff) | |
| download | box64-2e9b8eff59cec7a0170f9dc2f1fb6212a4f3ab85.tar.gz box64-2e9b8eff59cec7a0170f9dc2f1fb6212a4f3ab85.zip | |
[LA64_DYNAREC] Fixed SSE issues (#1415)
* [LA64_DYNAREC] Fixed SSE issues * Fixed MOVSD modreg
Diffstat (limited to 'src')
| -rw-r--r-- | src/dynarec/la64/dynarec_la64_f20f.c | 22 | ||||
| -rw-r--r-- | src/dynarec/la64/dynarec_la64_f30f.c | 11 |
2 files changed, 18 insertions, 15 deletions
diff --git a/src/dynarec/la64/dynarec_la64_f20f.c b/src/dynarec/la64/dynarec_la64_f20f.c index 54c8c746..d8b8cc17 100644 --- a/src/dynarec/la64/dynarec_la64_f20f.c +++ b/src/dynarec/la64/dynarec_la64_f20f.c @@ -49,18 +49,18 @@ uintptr_t dynarec64_F20F(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int nextop = F8; GETG; if(MODREG) { - ed = (nextop&7)+ (rex.b<<3); + ed = (nextop & 7) + (rex.b << 3); v0 = sse_get_reg(dyn, ninst, x1, gd, 1); - d0 = sse_get_reg(dyn, ninst, x1, ed, 0); - FMOV_D(v0, d0); + v1 = sse_get_reg(dyn, ninst, x1, ed, 0); } else { SMREAD(); v0 = sse_get_reg_empty(dyn, ninst, x1, gd); + v1 = fpu_get_scratch(dyn); + VXOR_V(v0, v0, v0); addr = geted(dyn, addr, ninst, nextop, &ed, x1, x2, &fixedaddress, rex, NULL, 8, 0); - FLD_D(v0, ed, fixedaddress); - // reset upper part - ST_D(xZR, xEmu, offsetof(x64emu_t, xmm[gd])+8); + FLD_D(v1, ed, fixedaddress); } + VEXTRINS_D(v0, v1, 0); // v0[63:0] = v1[63:0] break; case 0x58: INST_NAME("ADDSD Gx, Ex"); @@ -68,15 +68,19 @@ uintptr_t dynarec64_F20F(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int // TODO: fastnan handling GETGX(v0, 1); GETEXSD(v1, 0); - FADD_D(v0, v0, v1); + d0 = fpu_get_scratch(dyn); + FADD_D(d0, v0, v1); + VEXTRINS_D(v0, d0, 0); // v0[63:0] = v1[63:0] break; case 0x5C: INST_NAME("SUBSD Gx, Ex"); nextop = F8; - //TODO: fastnan handling + // TODO: fastnan handling GETGX(v0, 1); GETEXSD(v1, 0); - FSUB_D(v0, v0, v1); + d0 = fpu_get_scratch(dyn); + FSUB_D(d0, v0, v1); + VEXTRINS_D(v0, d0, 0); // v0[63:0] = v1[63:0] break; default: DEFAULT; diff --git a/src/dynarec/la64/dynarec_la64_f30f.c b/src/dynarec/la64/dynarec_la64_f30f.c index d36ea651..9c1da571 100644 --- a/src/dynarec/la64/dynarec_la64_f30f.c +++ b/src/dynarec/la64/dynarec_la64_f30f.c @@ -56,18 +56,17 @@ uintptr_t dynarec64_F30F(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int case 0x7E: INST_NAME("MOVQ Gx, Ex"); nextop = F8; - // Will load Gx as SD. Is that a good choice? + GETGX_empty(v0); + VXOR_V(v0, v0, v0); if (MODREG) { v1 = sse_get_reg(dyn, ninst, x1, (nextop & 7) + (rex.b << 3), 0); - GETGX_empty(v0); - FMOV_D(v0, v1); } else { - GETGX_empty(v0); SMREAD(); addr = geted(dyn, addr, ninst, nextop, &ed, x1, x2, &fixedaddress, rex, NULL, 1, 0); - FLD_D(v0, ed, fixedaddress); + v1 = fpu_get_scratch(dyn); + FLD_D(v1, ed, fixedaddress); } - ST_D(xZR, xEmu, offsetof(x64emu_t, xmm[gd]) + 8); + VEXTRINS_D(v0, v1, 0); // v0[63:0] = v1[63:0] break; default: DEFAULT; |