about summary refs log tree commit diff stats
diff options
context:
space:
mode:
authorYang Liu <numbksco@gmail.com>2024-03-01 00:48:23 +0800
committerGitHub <noreply@github.com>2024-02-29 17:48:23 +0100
commit92532b0fd1c14aefbd82aed93a04ce5b11e5abf7 (patch)
tree7f1fe6773e3636fb067a800f5c8eacc0563f7331
parent8cba5d55cef4c9a0f047b6cd81e440144fb12e8f (diff)
downloadbox64-92532b0fd1c14aefbd82aed93a04ce5b11e5abf7.tar.gz
box64-92532b0fd1c14aefbd82aed93a04ce5b11e5abf7.zip
[LA64_DYNAREC] Added more opcodes and fixed more things (#1304)
* [LA64_DYNAREC] Fixed GETED macro

* [LA64_DYNAREC] Added 81/83 /5 SUB opcode

* Use xMASK when possible

* Added 8B MOV opcode

* Fix
-rw-r--r--src/dynarec/la64/dynarec_la64_00.c28
-rw-r--r--src/dynarec/la64/dynarec_la64_emit_math.c10
-rw-r--r--src/dynarec/la64/dynarec_la64_helper.c3
-rw-r--r--src/dynarec/la64/dynarec_la64_helper.h7
-rw-r--r--src/dynarec/la64/la64_emitter.h16
5 files changed, 45 insertions, 19 deletions
diff --git a/src/dynarec/la64/dynarec_la64_00.c b/src/dynarec/la64/dynarec_la64_00.c
index 5eeba868..bcfd9e7b 100644
--- a/src/dynarec/la64/dynarec_la64_00.c
+++ b/src/dynarec/la64/dynarec_la64_00.c
@@ -177,6 +177,22 @@ uintptr_t dynarec64_00(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
             gd = TO_LA64((opcode & 0x07) + (rex.b << 3));
             POP1z(gd);
             break;
+        case 0x81:
+        case 0x83:
+            nextop = F8;
+            switch ((nextop >> 3) & 7) {
+                case 5: // SUB
+                    if(opcode==0x81) {INST_NAME("SUB Ed, Id");} else {INST_NAME("SUB Ed, Ib");}
+                    SETFLAGS(X_ALL, SF_SET_PENDING);
+                    GETED((opcode==0x81)?4:1);
+                    if(opcode==0x81) i64 = F32S; else i64 = F8S;
+                    emit_sub32c(dyn, ninst, rex, ed, i64, x3, x4, x5, x6);
+                    WBACK;
+                    break;
+                default:
+                    DEFAULT;
+            }
+            break;
         case 0x89:
             INST_NAME("MOV Ed, Gd");
             nextop = F8;
@@ -193,6 +209,18 @@ uintptr_t dynarec64_00(dynarec_la64_t* dyn, uintptr_t addr, uintptr_t ip, int ni
                 SMWRITELOCK(lock);
             }
             break;
+        case 0x8B:
+            INST_NAME("MOV Gd, Ed");
+            nextop=F8;
+            GETGD;
+            if(MODREG) {
+                MVxw(gd, xRAX + TO_LA64((nextop&7) + (rex.b<<3)));
+            } else {
+                addr = geted(dyn, addr, ninst, nextop, &ed, x2, x1, &fixedaddress, rex, &lock, 1, 0);
+                SMREADLOCK(lock);
+                LDxw(gd, ed, fixedaddress);
+            }
+            break;
         case 0x8D:
             INST_NAME("LEA Gd, Ed");
             nextop = F8;
diff --git a/src/dynarec/la64/dynarec_la64_emit_math.c b/src/dynarec/la64/dynarec_la64_emit_math.c
index e5efec62..b3db124c 100644
--- a/src/dynarec/la64/dynarec_la64_emit_math.c
+++ b/src/dynarec/la64/dynarec_la64_emit_math.c
@@ -55,9 +55,8 @@ void emit_add32(dynarec_la64_t* dyn, int ninst, rex_t rex, int s1, int s2, int s
     IFX(X_CF)
     {
         if (rex.w) {
-            MOV32w(x2, 0xffffffff);
-            AND(s5, x2, s1);
-            AND(s4, x2, s2);
+            AND(s5, xMASK, s1);
+            AND(s4, xMASK, s2);
             ADD_D(s5, s5, s4);
             SRLI_D(s3, s1, 0x20);
             SRLI_D(s4, s2, 0x20);
@@ -171,9 +170,8 @@ void emit_add32c(dynarec_la64_t* dyn, int ninst, rex_t rex, int s1, int64_t c, i
     IFX(X_CF)
     {
         if (rex.w) {
-            MOV32w(x2, 0xffffffff);
-            AND(s5, x2, s1);
-            AND(s4, x2, s2);
+            AND(s5, xMASK, s1);
+            AND(s4, xMASK, s2);
             ADD_D(s5, s5, s4);
             SRLI_D(s3, s1, 0x20);
             SRLI_D(s4, s2, 0x20);
diff --git a/src/dynarec/la64/dynarec_la64_helper.c b/src/dynarec/la64/dynarec_la64_helper.c
index 5ab4e320..6de2422b 100644
--- a/src/dynarec/la64/dynarec_la64_helper.c
+++ b/src/dynarec/la64/dynarec_la64_helper.c
@@ -246,8 +246,7 @@ static uintptr_t geted_32(dynarec_la64_t* dyn, uintptr_t addr, int ninst, uint8_
         } else {
             ret = TO_LA64((nextop & 7));
             if (ret == hint) {
-                MOV32w(x2, 0xffffffff);
-                AND(hint, ret, x2); // to clear upper part
+                AND(hint, ret, xMASK); // to clear upper part
             }
         }
     } else {
diff --git a/src/dynarec/la64/dynarec_la64_helper.h b/src/dynarec/la64/dynarec_la64_helper.h
index 33291b3a..5306814d 100644
--- a/src/dynarec/la64/dynarec_la64_helper.h
+++ b/src/dynarec/la64/dynarec_la64_helper.h
@@ -87,15 +87,12 @@
 // GETED can use r1 for ed, and r2 for wback. wback is 0 if ed is xEAX..xEDI
 #define GETED(D)                                                                                \
     if (MODREG) {                                                                               \
-        ed = TO_LA64((nextop & 7) + (rex.b << 3));                                             \
+        ed = TO_LA64((nextop & 7) + (rex.b << 3));                                              \
         wback = 0;                                                                              \
     } else {                                                                                    \
         SMREAD();                                                                               \
         addr = geted(dyn, addr, ninst, nextop, &wback, x2, x1, &fixedaddress, rex, NULL, 1, D); \
-        if (rex.w)                                                                              \
-            LD_D(x1, wback, fixedaddress);                                                      \
-        else                                                                                    \
-            LD_W(x1, wback, fixedaddress);                                                      \
+        LDxw(x1, wback, fixedaddress);                                                          \
         ed = x1;                                                                                \
     }
 
diff --git a/src/dynarec/la64/la64_emitter.h b/src/dynarec/la64/la64_emitter.h
index 5e826734..6adcdf7f 100644
--- a/src/dynarec/la64/la64_emitter.h
+++ b/src/dynarec/la64/la64_emitter.h
@@ -52,9 +52,9 @@ f24-f31  fs0-fs7   Static registers                Callee
 #define xFlags  31
 #define xRIP    20
 // function to move from x86 regs number to LA64 reg number
-#define TO_LA64(A) ((A)>7)?((A)+15):((A)+12)
+#define TO_LA64(A) (((A)>7)?((A)+15):((A)+12))
 // function to move from LA64 regs number to x86 reg number
-#define FROM_LA64(A) ((A)>22)?((A)-15):((A)-12)
+#define FROM_LA64(A) (((A)>22)?((A)-15):((A)-12))
 // 32bits version
 #define wEAX    xRAX
 #define wECX    xRCX
@@ -528,14 +528,12 @@ f24-f31  fs0-fs7   Static registers                Callee
     if (rex.w) {                \
         MV(rd, rj);             \
     } else {                    \
-        MOV32w(x2, 0xffffffff); \
-        AND(rd, rj, x2);        \
+        AND(rd, rj, xMASK);     \
     }
 // rd = rj (pseudo instruction)
 #define MVz(rd, rj)             \
     if (rex.is32bits) {         \
-        MOV32w(x2, 0xffffffff); \
-        AND(rd, rj, x2);        \
+        AND(rd, rj, xMASK);     \
     } else {                    \
         MV(rd, rj);             \
     }
@@ -565,6 +563,12 @@ f24-f31  fs0-fs7   Static registers                Callee
     else                   \
         ADD_D(rd, rj, rk);
 
+#define LDxw(rd, rj, imm12)   \
+    if (rex.w)                \
+        LD_D(rd, rj, imm12);  \
+    else                      \
+        LD_WU(rd, rj, imm12);
+
 #define SDxw(rd, rj, imm12)  \
     if (rex.w)               \
         ST_D(rd, rj, imm12); \