about summary refs log tree commit diff stats
path: root/src
diff options
context:
space:
mode:
authorYang Liu <numbksco@gmail.com>2024-05-23 05:00:13 +0800
committerGitHub <noreply@github.com>2024-05-22 23:00:13 +0200
commit48c47423a442086715b981fa44ba4996931d2fb5 (patch)
treef12a74b0daf42f5390d8069e0d70fdf4330398a6 /src
parent229cae16d1801b83bdee0a95c5515858df209876 (diff)
downloadbox64-48c47423a442086715b981fa44ba4996931d2fb5.tar.gz
box64-48c47423a442086715b981fa44ba4996931d2fb5.zip
[LA64_DYNAREC] Fixed more issues here and there (#1521)
* [LA64_DYNAREC] Fixed more issues here and there

* minor optim

* minor change
Diffstat (limited to 'src')
-rw-r--r--src/dynarec/la64/dynarec_la64_00.c2
-rw-r--r--src/dynarec/la64/dynarec_la64_660f.c12
-rw-r--r--src/dynarec/la64/dynarec_la64_emit_logic.c10
-rw-r--r--src/dynarec/la64/dynarec_la64_f0.c2
-rw-r--r--src/dynarec/la64/dynarec_la64_f30f.c14
5 files changed, 30 insertions, 10 deletions
diff --git a/src/dynarec/la64/dynarec_la64_00.c b/src/dynarec/la64/dynarec_la64_00.c
index 21936bb9..570db990 100644
--- a/src/dynarec/la64/dynarec_la64_00.c
+++ b/src/dynarec/la64/dynarec_la64_00.c
@@ -1446,7 +1446,7 @@ uintptr_t dynarec64_00(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                 MOV32w(x3, u8);
                 BSTRINS_D(eb1, x3, eb2 * 8 + 7, eb2 * 8);
             } else { // mem <= u8
-                addr = geted(dyn, addr, ninst, nextop, &wback, x2, x1, &fixedaddress, rex, &lock, 0, 1);
+                addr = geted(dyn, addr, ninst, nextop, &wback, x2, x1, &fixedaddress, rex, &lock, 1, 1);
                 u8 = F8;
                 if (u8) {
                     ADDI_D(x3, xZR, u8);
diff --git a/src/dynarec/la64/dynarec_la64_660f.c b/src/dynarec/la64/dynarec_la64_660f.c
index b25936bf..aea7b815 100644
--- a/src/dynarec/la64/dynarec_la64_660f.c
+++ b/src/dynarec/la64/dynarec_la64_660f.c
@@ -700,8 +700,16 @@ uintptr_t dynarec64_660F(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int
             GETGX(v0, 0);
             if (MODREG) {
                 v1 = sse_get_reg_empty(dyn, ninst, x1, (nextop & 7) + (rex.b << 3));
-                VXOR_V(v1, v1, v1);
-                VEXTRINS_D(v1, v0, 0);
+                if (v0 == v1) {
+                    // clear upper bits
+                    q0 = fpu_get_scratch(dyn);
+                    VXOR_V(q0, q0, q0);
+                    VEXTRINS_D(q0, v0, 0);
+                    VOR_V(v1, q0, q0);
+                } else {
+                    VXOR_V(v1, v1, v1);
+                    VEXTRINS_D(v1, v0, 0);
+                }
             } else {
                 addr = geted(dyn, addr, ninst, nextop, &ed, x2, x3, &fixedaddress, rex, NULL, 1, 0);
                 FST_D(v0, ed, fixedaddress);
diff --git a/src/dynarec/la64/dynarec_la64_emit_logic.c b/src/dynarec/la64/dynarec_la64_emit_logic.c
index 345dab9f..3d218cb3 100644
--- a/src/dynarec/la64/dynarec_la64_emit_logic.c
+++ b/src/dynarec/la64/dynarec_la64_emit_logic.c
@@ -509,13 +509,15 @@ void emit_or32(dynarec_la64_t* dyn, int ninst, rex_t rex, int s1, int s2, int s3
     }
 
     OR(s1, s1, s2);
-    if (!rex.w) ZEROUP(s1);
 
-    IFX(X_PEND) {
+    IFX (X_PEND) {
         SDxw(s1, xEmu, offsetof(x64emu_t, res));
     }
 
-    if(la64_lbt) return;
+    if (la64_lbt) {
+        if (!rex.w) ZEROUP(s1);
+        return;
+    }
 
     CLEAR_FLAGS(s3);
     // test sign bit before zeroup.
@@ -524,6 +526,8 @@ void emit_or32(dynarec_la64_t* dyn, int ninst, rex_t rex, int s1, int s2, int s3
         BGE(s1, xZR, 8);
         ORI(xFlags, xFlags, 1 << F_SF);
     }
+
+    if (!rex.w) ZEROUP(s1);
     IFX(X_ZF) {
         BNEZ(s1, 8);
         ORI(xFlags, xFlags, 1 << F_ZF);
diff --git a/src/dynarec/la64/dynarec_la64_f0.c b/src/dynarec/la64/dynarec_la64_f0.c
index afb27243..63aa187d 100644
--- a/src/dynarec/la64/dynarec_la64_f0.c
+++ b/src/dynarec/la64/dynarec_la64_f0.c
@@ -229,7 +229,7 @@ uintptr_t dynarec64_F0(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                             i64 = F32S;
                         else
                             i64 = F8S;
-                        ed = xRAX + (nextop & 7) + (rex.b << 3);
+                        ed = TO_LA64((nextop & 7) + (rex.b << 3));
                         emit_sub32c(dyn, ninst, rex, ed, i64, x3, x4, x5, x6);
                     } else {
                         addr = geted(dyn, addr, ninst, nextop, &wback, x2, x1, &fixedaddress, rex, LOCK_LOCK, 0, (opcode == 0x81) ? 4 : 1);
diff --git a/src/dynarec/la64/dynarec_la64_f30f.c b/src/dynarec/la64/dynarec_la64_f30f.c
index cd72ded4..c42310a7 100644
--- a/src/dynarec/la64/dynarec_la64_f30f.c
+++ b/src/dynarec/la64/dynarec_la64_f30f.c
@@ -229,8 +229,6 @@ uintptr_t dynarec64_F30F(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int
         case 0x7E:
             INST_NAME("MOVQ Gx, Ex");
             nextop = F8;
-            GETGX_empty(v0);
-            VXOR_V(v0, v0, v0);
             if (MODREG) {
                 v1 = sse_get_reg(dyn, ninst, x1, (nextop & 7) + (rex.b << 3), 0);
             } else {
@@ -239,7 +237,17 @@ uintptr_t dynarec64_F30F(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int
                 v1 = fpu_get_scratch(dyn);
                 FLD_D(v1, ed, fixedaddress);
             }
-            VEXTRINS_D(v0, v1, 0); // v0[63:0] = v1[63:0]
+            GETGX_empty(v0);
+            if (v0 == v1) {
+                // clear upper bits..
+                q1 = fpu_get_scratch(dyn);
+                VXOR_V(q1, q1, q1);
+                VEXTRINS_D(q1, v1, 0); // q1[63:0] = v1[63:0]
+                VOR_V(v0, q1, q1);
+            } else {
+                VXOR_V(v0, v0, v0);
+                VEXTRINS_D(v0, v1, 0); // v0[63:0] = v1[63:0]
+            }
             break;
         case 0x7F:
             INST_NAME("MOVDQU Ex,Gx");