about summary refs log tree commit diff stats
diff options
context:
space:
mode:
authorYang Liu <liuyang22@iscas.ac.cn>2024-09-19 18:06:07 +0800
committerGitHub <noreply@github.com>2024-09-19 12:06:07 +0200
commit7263a2e7ab703db5e22753e43803f34cdd4928ba (patch)
tree82a940a9fde98f100077204c5f319b1979175843
parentef7f25481cb2e85da51b2da107a1b88f2434bf2d (diff)
downloadbox64-7263a2e7ab703db5e22753e43803f34cdd4928ba.tar.gz
box64-7263a2e7ab703db5e22753e43803f34cdd4928ba.zip
[RV64_DYNAREC] Added more opcodes for vector (#1837)
-rw-r--r--src/dynarec/rv64/dynarec_rv64_660f_vector.c75
-rw-r--r--src/dynarec/rv64/dynarec_rv64_helper.h7
2 files changed, 78 insertions, 4 deletions
diff --git a/src/dynarec/rv64/dynarec_rv64_660f_vector.c b/src/dynarec/rv64/dynarec_rv64_660f_vector.c
index b421a053..460abf23 100644
--- a/src/dynarec/rv64/dynarec_rv64_660f_vector.c
+++ b/src/dynarec/rv64/dynarec_rv64_660f_vector.c
@@ -884,6 +884,26 @@ uintptr_t dynarec64_660F_vector(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t i
                 default: DEFAULT_VECTOR;
             }
             break;
+        case 0x74 ... 0x76:
+            if (opcode == 0x74) {
+                INST_NAME("PCMPEQB Gx,Ex");
+                u8 = VECTOR_SEW8;
+            } else if (opcode == 0x75) {
+                INST_NAME("PCMPEQW Gx,Ex");
+                u8 = VECTOR_SEW16;
+            } else {
+                INST_NAME("PCMPEQD Gx, Ex");
+                u8 = VECTOR_SEW32;
+            }
+            nextop = F8;
+            SET_ELEMENT_WIDTH(x1, u8, 1);
+            GETGX_vector(q0, 1, dyn->vector_eew);
+            GETEX_vector(q1, 0, 0, dyn->vector_eew);
+            VMSEQ_VV(VMASK, q0, q1, VECTOR_UNMASKED);
+            VXOR_VV(q0, q0, q0, VECTOR_UNMASKED);
+            VMERGE_VIM(q0, 1, q0); // implies vmask and widened it
+            VRSUB_VX(q0, xZR, q0, VECTOR_UNMASKED);
+            break;
         case 0x7E:
             return 0;
         case 0xEF:
@@ -935,6 +955,36 @@ uintptr_t dynarec64_660F_vector(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t i
             GETEX_vector(q1, 0, 0, dyn->vector_eew);
             VAND_VV(q0, q0, q1, VECTOR_UNMASKED);
             break;
+        case 0xDF:
+            INST_NAME("PANDN Gx, Ex");
+            nextop = F8;
+            SET_ELEMENT_WIDTH(x1, VECTOR_SEWANY, 1);
+            GETGX_vector(q0, 1, dyn->vector_eew);
+            GETEX_vector(q1, 0, 0, dyn->vector_eew);
+            VXOR_VI(q0, 0x1F, q0, VECTOR_UNMASKED);
+            VAND_VV(q0, q0, q1, VECTOR_UNMASKED);
+            break;
+        case 0xE2:
+            INST_NAME("PSRAD Gx, Ex");
+            nextop = F8;
+            SET_ELEMENT_WIDTH(x1, VECTOR_SEW64, 1);
+            GETGX_vector(q0, 1, VECTOR_SEW64);
+            VMV_V_I(VMASK, 0b01);
+            if (MODREG) {
+                q1 = sse_get_reg_vector(dyn, ninst, x1, (nextop & 7) + (rex.b << 3), 0, VECTOR_SEW64);
+            } else {
+                SMREAD();
+                addr = geted(dyn, addr, ninst, nextop, &ed, x3, x2, &fixedaddress, rex, NULL, 0, 0);
+                q1 = fpu_get_scratch(dyn);
+                VLE_V(q1, ed, VECTOR_SEW64, VECTOR_MASKED, VECTOR_NFIELD1);
+            }
+            v1 = fpu_get_scratch(dyn);
+            ADDI(x4, xZR, 31);
+            VMINU_VX(v1, x4, q1, VECTOR_MASKED);
+            VMV_X_S(x4, v1);
+            SET_ELEMENT_WIDTH(x1, VECTOR_SEW32, 1);
+            VSRA_VX(q0, x4, q0, VECTOR_UNMASKED);
+            break;
         case 0xEB:
             INST_NAME("POR Gx, Ex");
             nextop = F8;
@@ -943,6 +993,31 @@ uintptr_t dynarec64_660F_vector(dynarec_rv64_t* dyn, uintptr_t addr, uintptr_t i
             GETEX_vector(q1, 0, 0, dyn->vector_eew);
             VOR_VV(q0, q0, q1, VECTOR_UNMASKED);
             break;
+        case 0xEE:
+            INST_NAME("PMAXSW Gx,Ex");
+            nextop = F8;
+            SET_ELEMENT_WIDTH(x1, VECTOR_SEW16, 1);
+            GETGX_vector(q0, 1, VECTOR_SEW16);
+            GETEX_vector(q1, 0, 0, VECTOR_SEW16);
+            VMAX_VV(q0, q0, q1, VECTOR_UNMASKED);
+            break;
+        case 0xFC ... 0xFE:
+            nextop = F8;
+            if (opcode == 0xFC) {
+                INST_NAME("PADDB Gx, Ex");
+                u8 = VECTOR_SEW8;
+            } else if (opcode == 0xFD) {
+                INST_NAME("PADDW Gx, Ex");
+                u8 = VECTOR_SEW16;
+            } else {
+                INST_NAME("PADDD Gx, Ex");
+                u8 = VECTOR_SEW32;
+            }
+            SET_ELEMENT_WIDTH(x1, u8, 1);
+            GETGX_vector(q0, 1, dyn->vector_eew);
+            GETEX_vector(q1, 0, 0, dyn->vector_eew);
+            VADD_VV(q0, q0, q1, VECTOR_UNMASKED);
+            break;
         default:
             DEFAULT_VECTOR;
     }
diff --git a/src/dynarec/rv64/dynarec_rv64_helper.h b/src/dynarec/rv64/dynarec_rv64_helper.h
index a04af639..eedd4a61 100644
--- a/src/dynarec/rv64/dynarec_rv64_helper.h
+++ b/src/dynarec/rv64/dynarec_rv64_helper.h
@@ -504,16 +504,15 @@
         a = sse_get_reg_vector(dyn, ninst, x1, (nextop & 7) + (rex.b << 3), w, sew);         \
     } else {                                                                                 \
         SMREAD();                                                                            \
-        addr = geted(dyn, addr, ninst, nextop, &ed, x3, x2, &fixedaddress, rex, NULL, 1, D); \
+        addr = geted(dyn, addr, ninst, nextop, &ed, x3, x2, &fixedaddress, rex, NULL, 0, D); \
         a = fpu_get_scratch(dyn);                                                            \
-        ADDI(x2, ed, fixedaddress);                                                          \
-        VLE_V(a, x2, sew, VECTOR_UNMASKED, VECTOR_NFIELD1);                                  \
+        VLE_V(a, ed, sew, VECTOR_UNMASKED, VECTOR_NFIELD1);                                  \
     }
 
 // Put Back EX if it was a memory and not an emm register
 #define PUTEX_vector(a, sew)                                \
     if (!MODREG) {                                          \
-        VSE_V(a, x2, sew, VECTOR_UNMASKED, VECTOR_NFIELD1); \
+        VSE_V(a, ed, sew, VECTOR_UNMASKED, VECTOR_NFIELD1); \
         SMWRITE2();                                         \
     }