qemu-riscv
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[PATCH v3 20/21] target/riscv: adding 128-bit access functions for some


From: Frédéric Pétrot
Subject: [PATCH v3 20/21] target/riscv: adding 128-bit access functions for some csrs
Date: Tue, 19 Oct 2021 11:48:11 +0200

Access to mstatus, mtvec, mscratch and mepc is implemented.

Signed-off-by: Frédéric Pétrot <frederic.petrot@univ-grenoble-alpes.fr>
Co-authored-by: Fabien Portas <fabien.portas@grenoble-inp.org>
---
 target/riscv/cpu_bits.h |   1 +
 target/riscv/csr.c      | 111 ++++++++++++++++++++++++++++++++++++++--
 2 files changed, 108 insertions(+), 4 deletions(-)

diff --git a/target/riscv/cpu_bits.h b/target/riscv/cpu_bits.h
index e248c6bf6d..e4750afc78 100644
--- a/target/riscv/cpu_bits.h
+++ b/target/riscv/cpu_bits.h
@@ -360,6 +360,7 @@
 
 #define MSTATUS32_SD        0x80000000
 #define MSTATUS64_SD        0x8000000000000000ULL
+#define MSTATUSH128_SD      0x8000000000000000ULL
 
 #define MISA32_MXL          0xC0000000
 #define MISA64_MXL          0xC000000000000000ULL
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 3aac19e277..877cd2d63a 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -509,6 +509,61 @@ static uint64_t add_status_sd(RISCVMXL xl, uint64_t status)
     return status;
 }
 
+static RISCVException read_mstatus_i128(CPURISCVState *env, int csrno,
+                                   Int128 *val)
+{
+    *val = int128_make128(env->mstatus, env->mstatush);
+    return RISCV_EXCP_NONE;
+}
+
+static RISCVException write_mstatus_i128(CPURISCVState *env, int csrno,
+                                        Int128 val)
+{
+    Int128 mstatus = int128_make128(env->mstatus, env->mstatush);
+    Int128 mask = int128_zero();
+    int dirty;
+
+    /* flush tlb on mstatus fields that affect VM */
+    if (int128_getlo(int128_xor(mstatus, val))
+            & (MSTATUS_MXR | MSTATUS_MPP | MSTATUS_MPV |
+                           MSTATUS_MPRV | MSTATUS_SUM)) {
+        tlb_flush(env_cpu(env));
+    }
+    mask = int128_make64(MSTATUS_SIE | MSTATUS_SPIE |
+                         MSTATUS_MIE | MSTATUS_MPIE |
+                         MSTATUS_SPP | MSTATUS_FS | MSTATUS_MPRV | MSTATUS_SUM 
|
+                         MSTATUS_MPP | MSTATUS_MXR | MSTATUS_TVM | MSTATUS_TSR 
|
+                         MSTATUS_TW);
+
+    if (!riscv_cpu_is_32bit(env)) {
+        /*
+         * RV32: MPV and GVA are not in mstatus. The current plan is to
+         * add them to mstatush. For now, we just don't support it.
+         */
+        mask = int128_or(mask, int128_make64(MSTATUS_MPV | MSTATUS_GVA));
+    }
+
+    mstatus = int128_or(int128_and(mstatus, int128_not(mask)),
+                        int128_and(val, mask));
+
+    dirty = ((int128_getlo(mstatus) & MSTATUS_FS) == MSTATUS_FS) |
+            ((int128_getlo(mstatus) & MSTATUS_XS) == MSTATUS_XS);
+    if (dirty) {
+        if (riscv_cpu_is_32bit(env)) {
+            mstatus = int128_make64(int128_getlo(mstatus) | MSTATUS32_SD);
+        } else if (riscv_cpu_is_64bit(env)) {
+            mstatus = int128_make64(int128_getlo(mstatus) | MSTATUS64_SD);
+        } else {
+            mstatus = int128_or(mstatus, int128_make128(0, MSTATUSH128_SD));
+        }
+    }
+
+    env->mstatus = int128_getlo(mstatus);
+    env->mstatush = int128_gethi(mstatus);
+
+    return RISCV_EXCP_NONE;
+}
+
 static RISCVException read_mstatus(CPURISCVState *env, int csrno,
                                    target_ulong *val)
 {
@@ -713,6 +768,26 @@ static RISCVException write_mie(CPURISCVState *env, int 
csrno,
     return RISCV_EXCP_NONE;
 }
 
+static RISCVException read_mtvec_i128(CPURISCVState *env, int csrno,
+                                     Int128 *val)
+{
+    *val = int128_make128(env->mtvec, env->mtvech);
+    return RISCV_EXCP_NONE;
+}
+
+static RISCVException write_mtvec_i128(CPURISCVState *env, int csrno,
+                                      Int128 val)
+{
+    /* bits [1:0] encode mode; 0 = direct, 1 = vectored, 2 >= reserved */
+    if ((int128_getlo(val) & 3) < 2) {
+        env->mtvec = int128_getlo(val);
+        env->mtvech = int128_gethi(val);
+    } else {
+        qemu_log_mask(LOG_UNIMP, "CSR_MTVEC: reserved mode not supported\n");
+    }
+    return RISCV_EXCP_NONE;
+}
+
 static RISCVException read_mtvec(CPURISCVState *env, int csrno,
                                  target_ulong *val)
 {
@@ -747,6 +822,19 @@ static RISCVException write_mcounteren(CPURISCVState *env, 
int csrno,
 }
 
 /* Machine Trap Handling */
+static RISCVException read_mscratch_i128(CPURISCVState *env, int csrno,
+                                        Int128 *val)  {
+    *val = int128_make128(env->mscratch, env->mscratchh);
+    return RISCV_EXCP_NONE;
+}
+
+static RISCVException write_mscratch_i128(CPURISCVState *env, int csrno,
+                                         Int128 val) {
+    env->mscratch = int128_getlo(val);
+    env->mscratchh = int128_gethi(val);
+    return RISCV_EXCP_NONE;
+}
+
 static RISCVException read_mscratch(CPURISCVState *env, int csrno,
                                     target_ulong *val)
 {
@@ -761,6 +849,21 @@ static RISCVException write_mscratch(CPURISCVState *env, 
int csrno,
     return RISCV_EXCP_NONE;
 }
 
+static RISCVException read_mepc_i128(CPURISCVState *env, int csrno,
+                                    Int128 *val)
+{
+    *val = int128_make128(env->mepc, env->mepch);
+    return RISCV_EXCP_NONE;
+}
+
+static RISCVException write_mepc_i128(CPURISCVState *env, int csrno,
+                                     Int128 val)
+{
+    env->mepc = int128_getlo(val);
+    env->mepch = int128_gethi(val);
+    return RISCV_EXCP_NONE;
+}
+
 static RISCVException read_mepc(CPURISCVState *env, int csrno,
                                      target_ulong *val)
 {
@@ -1679,12 +1782,12 @@ riscv_csr_operations128 csr_ops_128[CSR_TABLE_SIZE] = {
     [CSR_MIMPID]     = { read_zero_i128    },
     [CSR_MHARTID]    = { read_mhartid_i128 },
 
-    [CSR_MSTATUS]    = { read_zero_i128    },
+    [CSR_MSTATUS]    = { read_mstatus_i128,  write_mstatus_i128  },
     [CSR_MISA]       = { read_misa_i128    },
-    [CSR_MTVEC]      = { read_zero_i128    },
+    [CSR_MTVEC]      = { read_mtvec_i128,    write_mtvec_i128    },
 
-    [CSR_MSCRATCH]   = { read_zero_i128    },
-    [CSR_MEPC]       = { read_zero_i128    },
+    [CSR_MSCRATCH]   = { read_mscratch_i128, write_mscratch_i128 },
+    [CSR_MEPC]       = { read_mepc_i128,     write_mepc_i128     },
 
     [CSR_SATP]       = { read_zero_i128    },
 #endif
-- 
2.33.0




reply via email to

[Prev in Thread] Current Thread [Next in Thread]