Moves initialization of satp and mxl fields to a class initialization
function that checks target_riscv64().

Note: I'm aware the current iteration of this patch is rather hacky, I
don't like the introduction of runtime_misa_mxl_max, but I'm keeping
this in to get the series out there and collect feedback.

Signed-off-by: Anton Johansson <[email protected]>
---
 target/riscv/cpu.h |  1 +
 target/riscv/cpu.c | 90 +++++++++++++++++++++++++++++++++++-------------------
 2 files changed, 59 insertions(+), 32 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 3fa322a8a9..0b17fd3db1 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -590,6 +590,7 @@ typedef struct RISCVCPUDef {
     bool bare;
 #if !defined(CONFIG_USER_ONLY)
 #if defined(CONFIG_TCG)
+    bool runtime_misa_mxl_max; /* Skip max mxl base class validation */
     const RISCVCSR *custom_csrs;
 #endif
     uint8_t irq_local_guest_max;
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
index cfc80aaaf1..39501c6c9f 100644
--- a/target/riscv/cpu.c
+++ b/target/riscv/cpu.c
@@ -3062,6 +3062,27 @@ static void riscv_cpu_common_class_init(ObjectClass *c, 
const void *data)
     device_class_set_props(dc, riscv_cpu_properties);
 }
 
+static void riscv_cpu_max_class_init(ObjectClass *c, const void *data)
+{
+    RISCVCPUClass *mcc = RISCV_CPU_CLASS(c);
+    bool rv64 = target_riscv64();
+    mcc->def->misa_mxl_max = (rv64) ? MXL_RV64 : MXL_RV32;
+    mcc->def->cfg.max_satp_mode = (rv64) ? VM_1_10_SV57 : VM_1_10_SV32;
+    riscv_cpu_validate_misa_mxl(mcc);
+}
+
+static void riscv_cpu_bare_class_init(ObjectClass *c, const void *data)
+{
+    RISCVCPUClass *mcc = RISCV_CPU_CLASS(c);
+    bool rv64 = target_riscv64();
+    /*
+     * Support all available satp_mode settings. By default
+     * only MBARE will be available if the user doesn't enable
+     * a mode manually (see riscv_cpu_satp_mode_finalize()).
+     */
+    mcc->def->cfg.max_satp_mode = (rv64) ? VM_1_10_SV57 : VM_1_10_SV32;
+}
+
 static bool profile_extends(RISCVCPUProfile *trial, RISCVCPUProfile *parent)
 {
     RISCVCPUProfile *curr;
@@ -3113,6 +3134,9 @@ static void riscv_cpu_class_base_init(ObjectClass *c, 
const void *data)
     if (data) {
         const RISCVCPUDef *def = data;
         mcc->def->bare |= def->bare;
+#if defined(CONFIG_TCG) && !defined(CONFIG_USER_ONLY)
+        mcc->def->runtime_misa_mxl_max |= def->runtime_misa_mxl_max;
+#endif
         if (def->profile) {
             assert(profile_extends(def->profile, mcc->def->profile));
             assert(mcc->def->bare);
@@ -3157,9 +3181,11 @@ static void riscv_cpu_class_base_init(ObjectClass *c, 
const void *data)
 #endif
     }
 
-    if (!object_class_is_abstract(c)) {
+#if defined(CONFIG_TCG) && !defined(CONFIG_USER_ONLY)
+    if (!object_class_is_abstract(c) && !mcc->def->runtime_misa_mxl_max) {
         riscv_cpu_validate_misa_mxl(mcc);
     }
+#endif
 }
 
 static void riscv_isa_string_ext(RISCVCPU *cpu, char **isa_str,
@@ -3365,41 +3391,41 @@ static const TypeInfo riscv_cpu_type_infos[] = {
     ),
 
     DEFINE_ABSTRACT_RISCV_CPU(TYPE_RISCV_VENDOR_CPU, TYPE_RISCV_CPU),
-    DEFINE_ABSTRACT_RISCV_CPU(TYPE_RISCV_BARE_CPU, TYPE_RISCV_CPU,
-        /*
-         * Bare CPUs do not inherit the timer and performance
-         * counters from the parent class (see riscv_cpu_init()
-         * for info on why the parent enables them).
-         *
-         * Users have to explicitly enable these counters for
-         * bare CPUs.
-         */
-        .bare = true,
 
-        /* Set to QEMU's first supported priv version */
-        .priv_spec = PRIV_VERSION_1_10_0,
+    {
+        .name = TYPE_RISCV_BARE_CPU,
+        .parent = TYPE_RISCV_CPU,
+        .abstract = true,
+        .class_data = &(const RISCVCPUDef) {
+            /* Set to QEMU's first supported priv version */
+            .priv_spec = PRIV_VERSION_1_10_0,
+            .vext_spec = RISCV_PROFILE_ATTR_UNUSED,
 
-        /*
-         * Support all available satp_mode settings. By default
-         * only MBARE will be available if the user doesn't enable
-         * a mode manually (see riscv_cpu_satp_mode_finalize()).
-         */
-#ifdef TARGET_RISCV32
-        .cfg.max_satp_mode = VM_1_10_SV32,
-#else
-        .cfg.max_satp_mode = VM_1_10_SV57,
-#endif
-    ),
+            /*
+             * Bare CPUs do not inherit the timer and performance
+             * counters from the parent class (see riscv_cpu_init()
+             * for info on why the parent enables them).
+             *
+             * Users have to explicitly enable these counters for
+             * bare CPUs.
+             */
+            .bare = true,
+        },
+        .class_init = riscv_cpu_bare_class_init,
+    },
 
-    DEFINE_RISCV_CPU(TYPE_RISCV_CPU_MAX, TYPE_RISCV_DYNAMIC_CPU,
-#if defined(TARGET_RISCV32)
-        .misa_mxl_max = MXL_RV32,
-        .cfg.max_satp_mode = VM_1_10_SV32,
-#elif defined(TARGET_RISCV64)
-        .misa_mxl_max = MXL_RV64,
-        .cfg.max_satp_mode = VM_1_10_SV57,
+    {
+        .name = TYPE_RISCV_CPU_MAX,
+        .parent = TYPE_RISCV_DYNAMIC_CPU,
+        .class_data = &(const RISCVCPUDef) {
+            .priv_spec = RISCV_PROFILE_ATTR_UNUSED,
+            .vext_spec = RISCV_PROFILE_ATTR_UNUSED,
+#if defined(CONFIG_TCG) && !defined(CONFIG_USER_ONLY)
+            .runtime_misa_mxl_max = true,
 #endif
-    ),
+        },
+        .class_init = riscv_cpu_max_class_init,
+    },
 
     DEFINE_ABSTRACT_RISCV_CPU(TYPE_RISCV_CPU_SIFIVE_E, TYPE_RISCV_VENDOR_CPU,
         .misa_ext = RVI | RVM | RVA | RVC | RVU,

-- 
2.52.0


Reply via email to