qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent
@ 2025-10-01  7:32 Anton Johansson via
  2025-10-01  7:32 ` [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions Anton Johansson via
                   ` (32 more replies)
  0 siblings, 33 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Hi,

this is a first patchset moving towards single-binary support for riscv.
Additional patchsets for hw/ and target/ are based on this one so it's
best to make sure the approach taken is ok.  Most patches in this set
concern fields in CPUArchState which are either widened (usually to
uint64_t) or fixed to a smaller size which handles all use cases.

General purpose registers and fields mapped to TCG are dealt with by
widening the type and applying an offset to tcg_global_mem_new() to
correctly handle 32-bit targets on big endian hosts.

Quick question to correct my understanding. AFAICT riscv64-softmmu is a
superset of riscv32-softmmu which handles 32-, 64, and 128-bit ISAs, so
concerning single-binary do we for the time being only need to support
riscv64-softmmu?

Let me know what you think of the direction taken here and if you would
prefer something else.

Changes in v2:
  - Use BIT() to define misa extension bits in "Use 32 bits for misa
    extensions";

  - Squash "Fix size of mcause" into "Fix size of trivial CPUArchState
    fields";

  - Bump VMSTATE version_id and minimum_version_id for "cpu/pmp/entry",
    "cpu/pmp", "cpu/hyper", "cpu/vector", "cpu/rv128", "cpu/debug",
    "cpu/envcfg", "cpu/pmu", "cpu/jvt", "cpu/ssp", and "cpu".  Migration
    from older versions is broken.

Anton Johansson (33):
  target/riscv: Use 32 bits for misa extensions
  target/riscv: Fix size of trivial CPUArchState fields
  target/riscv: Fix size of mhartid
  target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val()
  target/riscv: Combine mhpmevent and mhpmeventh
  target/riscv: Combine mcyclecfg and mcyclecfgh
  target/riscv: Combine minstretcfg and minstretcfgh
  target/riscv: Combine mhpmcounter and mhpmcounterh
  target/riscv: Fix size of gpr and gprh
  target/riscv: Fix size of vector CSRs
  target/riscv: Fix size of pc, load_[val|res]
  target/riscv: Fix size of frm and fflags
  target/riscv: Fix size of badaddr and bins
  target/riscv: Fix size of guest_phys_fault_addr
  target/riscv: Fix size of priv_ver and vext_ver
  target/riscv: Fix size of retxh
  target/riscv: Fix size of ssp
  target/riscv: Fix size of excp_uw2
  target/riscv: Fix size of sw_check_code
  target/riscv: Fix size of priv
  target/riscv: Fix size of gei fields
  target/riscv: Fix size of [m|s|vs]iselect fields
  target/riscv: Fix arguments to board IMSIC emulation callbacks
  target/riscv: Fix size of irq_overflow_left
  target/riscv: Indent PMUFixedCtrState correctly
  target/riscv: Replace target_ulong in riscv_cpu_get_trap_name()
  target/riscv: Replace target_ulong in riscv_ctr_add_entry()
  target/riscv: Fix size of trigger data
  target/riscv: Fix size of mseccfg
  target/riscv: Move debug.h include away from cpu.h
  target/riscv: Move CSR declarations to separate csr.h header
  target/riscv: Introduce externally facing CSR access functions
  target/riscv: Make pmp.h target_ulong agnostic

 target/riscv/cpu.h                            | 341 +++++++-----------
 target/riscv/csr.h                            |  93 +++++
 target/riscv/debug.h                          |   2 -
 target/riscv/pmp.h                            |  20 +-
 hw/intc/riscv_imsic.c                         |  34 +-
 hw/riscv/riscv_hart.c                         |   7 +-
 linux-user/riscv/signal.c                     |   5 +-
 target/riscv/cpu.c                            |  11 +-
 target/riscv/cpu_helper.c                     |  37 +-
 target/riscv/csr.c                            | 284 ++++++++-------
 target/riscv/debug.c                          |   1 +
 target/riscv/fpu_helper.c                     |   6 +-
 target/riscv/gdbstub.c                        |   1 +
 target/riscv/kvm/kvm-cpu.c                    |   1 +
 target/riscv/machine.c                        | 177 +++++----
 target/riscv/op_helper.c                      |   1 +
 target/riscv/pmp.c                            |  13 +-
 target/riscv/pmu.c                            | 150 ++------
 target/riscv/tcg/tcg-cpu.c                    |   3 +-
 target/riscv/th_csr.c                         |   1 +
 target/riscv/translate.c                      |  53 ++-
 target/riscv/vector_helper.c                  |  22 +-
 .../riscv/insn_trans/trans_privileged.c.inc   |   2 +-
 target/riscv/insn_trans/trans_rvi.c.inc       |  16 +-
 target/riscv/insn_trans/trans_rvm.c.inc       |  16 +-
 target/riscv/insn_trans/trans_rvv.c.inc       |  22 +-
 target/riscv/insn_trans/trans_rvzicfiss.c.inc |  22 +-
 27 files changed, 666 insertions(+), 675 deletions(-)
 create mode 100644 target/riscv/csr.h

-- 
2.51.0



^ permalink raw reply	[flat|nested] 99+ messages in thread

* [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-01  7:34   ` Philippe Mathieu-Daudé
                     ` (2 more replies)
  2025-10-01  7:32 ` [PATCH v2 02/33] target/riscv: Fix size of trivial CPUArchState fields Anton Johansson via
                   ` (31 subsequent siblings)
  32 siblings, 3 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

uint32_t is already in use in most places storing misa extensions such
as CPUArchState::misa_exts, RISCVCPUProfile::misa_exts,
RISCVImpliedExtsRule::implied_misa_exts.  Additionally. the field is
already migrated as uint32_t.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 4a862da615..f05e06bb70 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -50,7 +50,7 @@ typedef struct CPUArchState CPURISCVState;
  */
 #define RISCV_UW2_ALWAYS_STORE_AMO 1
 
-#define RV(x) ((target_ulong)1 << (x - 'A'))
+#define RV(x) BIT(x - 'A')
 
 /*
  * Update misa_bits[], misa_ext_info_arr[] and misa_ext_cfgs[]
@@ -582,7 +582,7 @@ struct RISCVCPUClass {
     RISCVCPUDef *def;
 };
 
-static inline int riscv_has_ext(CPURISCVState *env, target_ulong ext)
+static inline int riscv_has_ext(CPURISCVState *env, uint32_t ext)
 {
     return (env->misa_ext & ext) != 0;
 }
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 02/33] target/riscv: Fix size of trivial CPUArchState fields
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
  2025-10-01  7:32 ` [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02  1:57   ` Alistair Francis
  2025-10-02 18:31   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 03/33] target/riscv: Fix size of mhartid Anton Johansson via
                   ` (30 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

This commits groups together all CPUArchState fields whose behaviour can
be retained by simply changing the size of the field.

Note, senvcfg is defined to be SXLEN bits wide, but is widened to 64
bits to match henvcfg and menvcfg.  Next, [m|h]edeleg are changed to
64 bits as defined privileged specification, and hvictl is fixed to 32
bits which holds all relevant values, see HVICTL_VALID_MASK.  The
remaining fields touched in the commit are widened from [H|S|M]XLEN
to 64-bit.

Note, the cpu/hyper, cpu/envcfg, cpu/jvt, and cpu VMSTATE versions are
bumped, breaking migration from older versions.

References to the privileged/unprivileged RISCV specification refer to
version 20250508.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h     | 78 +++++++++++++++++++--------------------
 target/riscv/machine.c | 84 +++++++++++++++++++++---------------------
 2 files changed, 81 insertions(+), 81 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index f05e06bb70..736e4f6daa 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -254,7 +254,7 @@ struct CPUArchState {
     /* 128-bit helpers upper part return value */
     target_ulong retxh;
 
-    target_ulong jvt;
+    uint64_t jvt;
 
     /* elp state for zicfilp extension */
     bool      elp;
@@ -271,7 +271,7 @@ struct CPUArchState {
     target_ulong priv;
     /* CSRs for execution environment configuration */
     uint64_t menvcfg;
-    target_ulong senvcfg;
+    uint64_t senvcfg;
 
 #ifndef CONFIG_USER_ONLY
     /* This contains QEMU specific information about the virt state. */
@@ -313,18 +313,18 @@ struct CPUArchState {
      */
     uint64_t vsie;
 
-    target_ulong satp;   /* since: priv-1.10.0 */
-    target_ulong stval;
-    target_ulong medeleg;
+    uint64_t satp;   /* since: priv-1.10.0 */
+    uint64_t stval;
+    uint64_t medeleg;
 
-    target_ulong stvec;
-    target_ulong sepc;
-    target_ulong scause;
+    uint64_t stvec;
+    uint64_t sepc;
+    uint64_t scause;
 
-    target_ulong mtvec;
-    target_ulong mepc;
-    target_ulong mcause;
-    target_ulong mtval;  /* since: priv-1.10.0 */
+    uint64_t mtvec;
+    uint64_t mepc;
+    uint64_t mcause;
+    uint64_t mtval;  /* since: priv-1.10.0 */
 
     uint64_t mctrctl;
     uint32_t sctrdepth;
@@ -346,13 +346,13 @@ struct CPUArchState {
     uint64_t mvip;
 
     /* Hypervisor CSRs */
-    target_ulong hstatus;
-    target_ulong hedeleg;
+    uint64_t hstatus;
+    uint64_t hedeleg;
     uint64_t hideleg;
     uint32_t hcounteren;
-    target_ulong htval;
-    target_ulong htinst;
-    target_ulong hgatp;
+    uint64_t htval;
+    uint64_t htinst;
+    uint64_t hgatp;
     target_ulong hgeie;
     target_ulong hgeip;
     uint64_t htimedelta;
@@ -366,7 +366,7 @@ struct CPUArchState {
     uint64_t hvip;
 
     /* Hypervisor controlled virtual interrupt priorities */
-    target_ulong hvictl;
+    uint32_t hvictl;
     uint8_t hviprio[64];
 
     /* Upper 64-bits of 128-bit CSRs */
@@ -379,26 +379,26 @@ struct CPUArchState {
      * For RV64 this is a 64-bit vsstatus.
      */
     uint64_t vsstatus;
-    target_ulong vstvec;
-    target_ulong vsscratch;
-    target_ulong vsepc;
-    target_ulong vscause;
-    target_ulong vstval;
-    target_ulong vsatp;
+    uint64_t vstvec;
+    uint64_t vsscratch;
+    uint64_t vsepc;
+    uint64_t vscause;
+    uint64_t vstval;
+    uint64_t vsatp;
 
     /* AIA VS-mode CSRs */
     target_ulong vsiselect;
 
-    target_ulong mtval2;
-    target_ulong mtinst;
+    uint64_t mtval2;
+    uint64_t mtinst;
 
     /* HS Backup CSRs */
-    target_ulong stvec_hs;
-    target_ulong sscratch_hs;
-    target_ulong sepc_hs;
-    target_ulong scause_hs;
-    target_ulong stval_hs;
-    target_ulong satp_hs;
+    uint64_t stvec_hs;
+    uint64_t sscratch_hs;
+    uint64_t sepc_hs;
+    uint64_t scause_hs;
+    uint64_t stval_hs;
+    uint64_t satp_hs;
     uint64_t mstatus_hs;
 
     /*
@@ -435,8 +435,8 @@ struct CPUArchState {
 
     PMUFixedCtrState pmu_fixed_ctrs[2];
 
-    target_ulong sscratch;
-    target_ulong mscratch;
+    uint64_t sscratch;
+    uint64_t mscratch;
 
     /* Sstc CSRs */
     uint64_t stimecmp;
@@ -506,11 +506,11 @@ struct CPUArchState {
 #endif /* CONFIG_KVM */
 
     /* RNMI */
-    target_ulong mnscratch;
-    target_ulong mnepc;
-    target_ulong mncause; /* mncause without bit XLEN-1 set to 1 */
-    target_ulong mnstatus;
-    target_ulong rnmip;
+    uint64_t mnscratch;
+    uint64_t mnepc;
+    uint64_t mncause; /* mncause without bit XLEN-1 set to 1 */
+    uint64_t mnstatus;
+    uint64_t rnmip;
     uint64_t rnmi_irqvec;
     uint64_t rnmi_excpvec;
 };
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 1600ec44f0..99e46c3136 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -80,17 +80,17 @@ static bool hyper_needed(void *opaque)
 
 static const VMStateDescription vmstate_hyper = {
     .name = "cpu/hyper",
-    .version_id = 4,
-    .minimum_version_id = 4,
+    .version_id = 5,
+    .minimum_version_id = 5,
     .needed = hyper_needed,
     .fields = (const VMStateField[]) {
-        VMSTATE_UINTTL(env.hstatus, RISCVCPU),
-        VMSTATE_UINTTL(env.hedeleg, RISCVCPU),
+        VMSTATE_UINT64(env.hstatus, RISCVCPU),
+        VMSTATE_UINT64(env.hedeleg, RISCVCPU),
         VMSTATE_UINT64(env.hideleg, RISCVCPU),
         VMSTATE_UINT32(env.hcounteren, RISCVCPU),
-        VMSTATE_UINTTL(env.htval, RISCVCPU),
-        VMSTATE_UINTTL(env.htinst, RISCVCPU),
-        VMSTATE_UINTTL(env.hgatp, RISCVCPU),
+        VMSTATE_UINT64(env.htval, RISCVCPU),
+        VMSTATE_UINT64(env.htinst, RISCVCPU),
+        VMSTATE_UINT64(env.hgatp, RISCVCPU),
         VMSTATE_UINTTL(env.hgeie, RISCVCPU),
         VMSTATE_UINTTL(env.hgeip, RISCVCPU),
         VMSTATE_UINT64(env.hvien, RISCVCPU),
@@ -98,28 +98,28 @@ static const VMStateDescription vmstate_hyper = {
         VMSTATE_UINT64(env.htimedelta, RISCVCPU),
         VMSTATE_UINT64(env.vstimecmp, RISCVCPU),
 
-        VMSTATE_UINTTL(env.hvictl, RISCVCPU),
+        VMSTATE_UINT32(env.hvictl, RISCVCPU),
         VMSTATE_UINT8_ARRAY(env.hviprio, RISCVCPU, 64),
 
         VMSTATE_UINT64(env.vsstatus, RISCVCPU),
-        VMSTATE_UINTTL(env.vstvec, RISCVCPU),
-        VMSTATE_UINTTL(env.vsscratch, RISCVCPU),
-        VMSTATE_UINTTL(env.vsepc, RISCVCPU),
-        VMSTATE_UINTTL(env.vscause, RISCVCPU),
-        VMSTATE_UINTTL(env.vstval, RISCVCPU),
-        VMSTATE_UINTTL(env.vsatp, RISCVCPU),
+        VMSTATE_UINT64(env.vstvec, RISCVCPU),
+        VMSTATE_UINT64(env.vsscratch, RISCVCPU),
+        VMSTATE_UINT64(env.vsepc, RISCVCPU),
+        VMSTATE_UINT64(env.vscause, RISCVCPU),
+        VMSTATE_UINT64(env.vstval, RISCVCPU),
+        VMSTATE_UINT64(env.vsatp, RISCVCPU),
         VMSTATE_UINTTL(env.vsiselect, RISCVCPU),
         VMSTATE_UINT64(env.vsie, RISCVCPU),
 
-        VMSTATE_UINTTL(env.mtval2, RISCVCPU),
-        VMSTATE_UINTTL(env.mtinst, RISCVCPU),
+        VMSTATE_UINT64(env.mtval2, RISCVCPU),
+        VMSTATE_UINT64(env.mtinst, RISCVCPU),
 
-        VMSTATE_UINTTL(env.stvec_hs, RISCVCPU),
-        VMSTATE_UINTTL(env.sscratch_hs, RISCVCPU),
-        VMSTATE_UINTTL(env.sepc_hs, RISCVCPU),
-        VMSTATE_UINTTL(env.scause_hs, RISCVCPU),
-        VMSTATE_UINTTL(env.stval_hs, RISCVCPU),
-        VMSTATE_UINTTL(env.satp_hs, RISCVCPU),
+        VMSTATE_UINT64(env.stvec_hs, RISCVCPU),
+        VMSTATE_UINT64(env.sscratch_hs, RISCVCPU),
+        VMSTATE_UINT64(env.sepc_hs, RISCVCPU),
+        VMSTATE_UINT64(env.scause_hs, RISCVCPU),
+        VMSTATE_UINT64(env.stval_hs, RISCVCPU),
+        VMSTATE_UINT64(env.satp_hs, RISCVCPU),
         VMSTATE_UINT64(env.mstatus_hs, RISCVCPU),
 
         VMSTATE_END_OF_LIST()
@@ -290,12 +290,12 @@ static bool envcfg_needed(void *opaque)
 
 static const VMStateDescription vmstate_envcfg = {
     .name = "cpu/envcfg",
-    .version_id = 1,
-    .minimum_version_id = 1,
+    .version_id = 2,
+    .minimum_version_id = 2,
     .needed = envcfg_needed,
     .fields = (const VMStateField[]) {
         VMSTATE_UINT64(env.menvcfg, RISCVCPU),
-        VMSTATE_UINTTL(env.senvcfg, RISCVCPU),
+        VMSTATE_UINT64(env.senvcfg, RISCVCPU),
         VMSTATE_UINT64(env.henvcfg, RISCVCPU),
         VMSTATE_END_OF_LIST()
     }
@@ -355,11 +355,11 @@ static bool jvt_needed(void *opaque)
 
 static const VMStateDescription vmstate_jvt = {
     .name = "cpu/jvt",
-    .version_id = 1,
-    .minimum_version_id = 1,
+    .version_id = 2,
+    .minimum_version_id = 2,
     .needed = jvt_needed,
     .fields = (const VMStateField[]) {
-        VMSTATE_UINTTL(env.jvt, RISCVCPU),
+        VMSTATE_UINT64(env.jvt, RISCVCPU),
         VMSTATE_END_OF_LIST()
     }
 };
@@ -402,8 +402,8 @@ static const VMStateDescription vmstate_ssp = {
 
 const VMStateDescription vmstate_riscv_cpu = {
     .name = "cpu",
-    .version_id = 10,
-    .minimum_version_id = 10,
+    .version_id = 11,
+    .minimum_version_id = 11,
     .post_load = riscv_cpu_post_load,
     .fields = (const VMStateField[]) {
         VMSTATE_UINTTL_ARRAY(env.gpr, RISCVCPU, 32),
@@ -434,16 +434,16 @@ const VMStateDescription vmstate_riscv_cpu = {
         VMSTATE_UINT64(env.mvip, RISCVCPU),
         VMSTATE_UINT64(env.sie, RISCVCPU),
         VMSTATE_UINT64(env.mideleg, RISCVCPU),
-        VMSTATE_UINTTL(env.satp, RISCVCPU),
-        VMSTATE_UINTTL(env.stval, RISCVCPU),
-        VMSTATE_UINTTL(env.medeleg, RISCVCPU),
-        VMSTATE_UINTTL(env.stvec, RISCVCPU),
-        VMSTATE_UINTTL(env.sepc, RISCVCPU),
-        VMSTATE_UINTTL(env.scause, RISCVCPU),
-        VMSTATE_UINTTL(env.mtvec, RISCVCPU),
-        VMSTATE_UINTTL(env.mepc, RISCVCPU),
-        VMSTATE_UINTTL(env.mcause, RISCVCPU),
-        VMSTATE_UINTTL(env.mtval, RISCVCPU),
+        VMSTATE_UINT64(env.satp, RISCVCPU),
+        VMSTATE_UINT64(env.stval, RISCVCPU),
+        VMSTATE_UINT64(env.medeleg, RISCVCPU),
+        VMSTATE_UINT64(env.stvec, RISCVCPU),
+        VMSTATE_UINT64(env.sepc, RISCVCPU),
+        VMSTATE_UINT64(env.scause, RISCVCPU),
+        VMSTATE_UINT64(env.mtvec, RISCVCPU),
+        VMSTATE_UINT64(env.mepc, RISCVCPU),
+        VMSTATE_UINT64(env.mcause, RISCVCPU),
+        VMSTATE_UINT64(env.mtval, RISCVCPU),
         VMSTATE_UINTTL(env.miselect, RISCVCPU),
         VMSTATE_UINTTL(env.siselect, RISCVCPU),
         VMSTATE_UINT32(env.scounteren, RISCVCPU),
@@ -454,8 +454,8 @@ const VMStateDescription vmstate_riscv_cpu = {
                              vmstate_pmu_ctr_state, PMUCTRState),
         VMSTATE_UINTTL_ARRAY(env.mhpmevent_val, RISCVCPU, RV_MAX_MHPMEVENTS),
         VMSTATE_UINTTL_ARRAY(env.mhpmeventh_val, RISCVCPU, RV_MAX_MHPMEVENTS),
-        VMSTATE_UINTTL(env.sscratch, RISCVCPU),
-        VMSTATE_UINTTL(env.mscratch, RISCVCPU),
+        VMSTATE_UINT64(env.sscratch, RISCVCPU),
+        VMSTATE_UINT64(env.mscratch, RISCVCPU),
         VMSTATE_UINT64(env.stimecmp, RISCVCPU),
 
         VMSTATE_END_OF_LIST()
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 03/33] target/riscv: Fix size of mhartid
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
  2025-10-01  7:32 ` [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions Anton Johansson via
  2025-10-01  7:32 ` [PATCH v2 02/33] target/riscv: Fix size of trivial CPUArchState fields Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-01  7:38   ` Philippe Mathieu-Daudé
  2025-10-01  7:32 ` [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val() Anton Johansson via
                   ` (29 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

and update formatting in log.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h         | 2 +-
 target/riscv/cpu_helper.c  | 2 +-
 target/riscv/machine.c     | 2 +-
 target/riscv/tcg/tcg-cpu.c | 2 +-
 4 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 736e4f6daa..3235108112 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -279,7 +279,7 @@ struct CPUArchState {
     target_ulong geilen;
     uint64_t resetvec;
 
-    target_ulong mhartid;
+    uint64_t mhartid;
     /*
      * For RV32 this is 32-bit mstatus and 32-bit mstatush.
      * For RV64 this is a 64-bit mstatus.
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
index 3479a62cc7..9d0683f200 100644
--- a/target/riscv/cpu_helper.c
+++ b/target/riscv/cpu_helper.c
@@ -2278,7 +2278,7 @@ void riscv_cpu_do_interrupt(CPUState *cs)
                      riscv_cpu_get_trap_name(cause, async));
 
     qemu_log_mask(CPU_LOG_INT,
-                  "%s: hart:"TARGET_FMT_ld", async:%d, cause:"TARGET_FMT_lx", "
+                  "%s: hart:%"PRIu64", async:%d, cause:"TARGET_FMT_lx", "
                   "epc:0x"TARGET_FMT_lx", tval:0x"TARGET_FMT_lx", desc=%s\n",
                   __func__, env->mhartid, async, cause, env->pc, tval,
                   riscv_cpu_get_trap_name(cause, async));
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 99e46c3136..328fb674e1 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -425,7 +425,7 @@ const VMStateDescription vmstate_riscv_cpu = {
         VMSTATE_UINTTL(env.priv, RISCVCPU),
         VMSTATE_BOOL(env.virt_enabled, RISCVCPU),
         VMSTATE_UINT64(env.resetvec, RISCVCPU),
-        VMSTATE_UINTTL(env.mhartid, RISCVCPU),
+        VMSTATE_UINT64(env.mhartid, RISCVCPU),
         VMSTATE_UINT64(env.mstatus, RISCVCPU),
         VMSTATE_UINT64(env.mip, RISCVCPU),
         VMSTATE_UINT64(env.miclaim, RISCVCPU),
diff --git a/target/riscv/tcg/tcg-cpu.c b/target/riscv/tcg/tcg-cpu.c
index 143ab079d4..200759eaf0 100644
--- a/target/riscv/tcg/tcg-cpu.c
+++ b/target/riscv/tcg/tcg-cpu.c
@@ -472,7 +472,7 @@ static void riscv_cpu_disable_priv_spec_isa_exts(RISCVCPU *cpu)
                 continue;
             }
 #ifndef CONFIG_USER_ONLY
-            warn_report("disabling %s extension for hart 0x" TARGET_FMT_lx
+            warn_report("disabling %s extension for hart 0x%" PRIx64
                         " because privilege spec version does not match",
                         edata->name, env->mhartid);
 #else
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val()
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (2 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 03/33] target/riscv: Fix size of mhartid Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 18:50   ` Pierrick Bouvier
  2025-10-02 23:34   ` Alistair Francis
  2025-10-01  7:32 ` [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh Anton Johansson via
                   ` (28 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

From my understanding the upper_half argument only indicates whether the
upper or lower 32 bits should be returned, and upper_half will only ever
be set when MXLEN == 32.  However, the function also uses upper_half to
determine whether the inhibit flags are located in mcyclecfgh or
mcyclecfg, but this misses the case where MXLEN == 32, upper_half == false
for TARGET_RISCV32 where we would also need to read the upper half field.

Minor simplifications are also made along with some formatting fixes.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/csr.c | 22 ++++++++++------------
 1 file changed, 10 insertions(+), 12 deletions(-)

diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 3c8989f522..859f89aedd 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -17,6 +17,7 @@
  * this program.  If not, see <http://www.gnu.org/licenses/>.
  */
 
+#include "cpu_bits.h"
 #include "qemu/osdep.h"
 #include "qemu/log.h"
 #include "qemu/timer.h"
@@ -1241,18 +1242,21 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
     int inst = riscv_pmu_ctr_monitor_instructions(env, counter_idx);
     uint64_t *counter_arr_virt = env->pmu_fixed_ctrs[inst].counter_virt;
     uint64_t *counter_arr = env->pmu_fixed_ctrs[inst].counter;
-    target_ulong result = 0;
     uint64_t curr_val = 0;
     uint64_t cfg_val = 0;
+    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
+
+    /* Ensure upper_half is only set for MXL_RV32 */
+    g_assert(rv32 || !upper_half);
 
     if (counter_idx == 0) {
-        cfg_val = upper_half ? ((uint64_t)env->mcyclecfgh << 32) :
+        cfg_val = rv32 ? ((uint64_t)env->mcyclecfgh << 32) :
                   env->mcyclecfg;
     } else if (counter_idx == 2) {
-        cfg_val = upper_half ? ((uint64_t)env->minstretcfgh << 32) :
+        cfg_val = rv32 ? ((uint64_t)env->minstretcfgh << 32) :
                   env->minstretcfg;
     } else {
-        cfg_val = upper_half ?
+        cfg_val = rv32 ?
                   ((uint64_t)env->mhpmeventh_val[counter_idx] << 32) :
                   env->mhpmevent_val[counter_idx];
         cfg_val &= MHPMEVENT_FILTER_MASK;
@@ -1260,7 +1264,7 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
 
     if (!cfg_val) {
         if (icount_enabled()) {
-                curr_val = inst ? icount_get_raw() : icount_get();
+            curr_val = inst ? icount_get_raw() : icount_get();
         } else {
             curr_val = cpu_get_host_ticks();
         }
@@ -1292,13 +1296,7 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
     }
 
 done:
-    if (riscv_cpu_mxl(env) == MXL_RV32) {
-        result = upper_half ? curr_val >> 32 : curr_val;
-    } else {
-        result = curr_val;
-    }
-
-    return result;
+    return upper_half ? curr_val >> 32 : curr_val;
 }
 
 static RISCVException riscv_pmu_write_ctr(CPURISCVState *env, target_ulong val,
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (3 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val() Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-01  7:39   ` Philippe Mathieu-Daudé
  2025-10-02 19:08   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 06/33] target/riscv: Combine mcyclecfg and mcyclecfgh Anton Johansson via
                   ` (27 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

According to version 20250508 of the privileged specification,
mhpmeventn is 64 bits in size and mhpmeventnh is only ever used
when XLEN == 32 and accesses the top 32 bits of the 64-bit
mhpmeventn registers. Combine the two arrays of target_ulong
mhpmeventh[] and mhpmevent[] to a single array of uint64_t.

This also allows for some minor code simplification where branches
handling either mhpmeventh[] or mhpmevent[] could be combined.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h     | 10 +++----
 target/riscv/csr.c     | 67 +++++++++++++++---------------------------
 target/riscv/machine.c |  3 +-
 target/riscv/pmu.c     | 53 ++++++++-------------------------
 4 files changed, 42 insertions(+), 91 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 3235108112..64b9964028 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -427,11 +427,11 @@ struct CPUArchState {
     /* PMU counter state */
     PMUCTRState pmu_ctrs[RV_MAX_MHPMCOUNTERS];
 
-    /* PMU event selector configured values. First three are unused */
-    target_ulong mhpmevent_val[RV_MAX_MHPMEVENTS];
-
-    /* PMU event selector configured values for RV32 */
-    target_ulong mhpmeventh_val[RV_MAX_MHPMEVENTS];
+    /*
+     * PMU event selector configured values. First three are unused.
+     * For RV32 top 32 bits are accessed via the mhpmeventh CSR.
+     */
+    uint64_t mhpmevent_val[RV_MAX_MHPMEVENTS];
 
     PMUFixedCtrState pmu_fixed_ctrs[2];
 
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 859f89aedd..2d8916ee40 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -1166,8 +1166,9 @@ static RISCVException read_mhpmevent(CPURISCVState *env, int csrno,
                                      target_ulong *val)
 {
     int evt_index = csrno - CSR_MCOUNTINHIBIT;
+    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
 
-    *val = env->mhpmevent_val[evt_index];
+    *val = extract64(env->mhpmevent_val[evt_index], 0, rv32 ? 32 : 64);
 
     return RISCV_EXCP_NONE;
 }
@@ -1176,13 +1177,11 @@ static RISCVException write_mhpmevent(CPURISCVState *env, int csrno,
                                       target_ulong val, uintptr_t ra)
 {
     int evt_index = csrno - CSR_MCOUNTINHIBIT;
-    uint64_t mhpmevt_val = val;
+    uint64_t mhpmevt_val;
     uint64_t inh_avail_mask;
 
     if (riscv_cpu_mxl(env) == MXL_RV32) {
-        env->mhpmevent_val[evt_index] = val;
-        mhpmevt_val = mhpmevt_val |
-                      ((uint64_t)env->mhpmeventh_val[evt_index] << 32);
+        mhpmevt_val = deposit64(env->mhpmevent_val[evt_index], 0, 32, val);
     } else {
         inh_avail_mask = ~MHPMEVENT_FILTER_MASK | MHPMEVENT_BIT_MINH;
         inh_avail_mask |= riscv_has_ext(env, RVU) ? MHPMEVENT_BIT_UINH : 0;
@@ -1192,9 +1191,9 @@ static RISCVException write_mhpmevent(CPURISCVState *env, int csrno,
         inh_avail_mask |= (riscv_has_ext(env, RVH) &&
                            riscv_has_ext(env, RVS)) ? MHPMEVENT_BIT_VSINH : 0;
         mhpmevt_val = val & inh_avail_mask;
-        env->mhpmevent_val[evt_index] = mhpmevt_val;
     }
 
+    env->mhpmevent_val[evt_index] = mhpmevt_val;
     riscv_pmu_update_event_map(env, mhpmevt_val, evt_index);
 
     return RISCV_EXCP_NONE;
@@ -1205,7 +1204,7 @@ static RISCVException read_mhpmeventh(CPURISCVState *env, int csrno,
 {
     int evt_index = csrno - CSR_MHPMEVENT3H + 3;
 
-    *val = env->mhpmeventh_val[evt_index];
+    *val = extract64(env->mhpmevent_val[evt_index], 32, 32);
 
     return RISCV_EXCP_NONE;
 }
@@ -1214,8 +1213,6 @@ static RISCVException write_mhpmeventh(CPURISCVState *env, int csrno,
                                        target_ulong val, uintptr_t ra)
 {
     int evt_index = csrno - CSR_MHPMEVENT3H + 3;
-    uint64_t mhpmevth_val;
-    uint64_t mhpmevt_val = env->mhpmevent_val[evt_index];
     target_ulong inh_avail_mask = (target_ulong)(~MHPMEVENTH_FILTER_MASK |
                                                   MHPMEVENTH_BIT_MINH);
 
@@ -1226,11 +1223,10 @@ static RISCVException write_mhpmeventh(CPURISCVState *env, int csrno,
     inh_avail_mask |= (riscv_has_ext(env, RVH) &&
                        riscv_has_ext(env, RVS)) ? MHPMEVENTH_BIT_VSINH : 0;
 
-    mhpmevth_val = val & inh_avail_mask;
-    mhpmevt_val = mhpmevt_val | (mhpmevth_val << 32);
-    env->mhpmeventh_val[evt_index] = mhpmevth_val;
+    env->mhpmevent_val[evt_index] = deposit64(env->mhpmevent_val[evt_index],
+                                              32, 32, val & inh_avail_mask);
 
-    riscv_pmu_update_event_map(env, mhpmevt_val, evt_index);
+    riscv_pmu_update_event_map(env, env->mhpmevent_val[evt_index], evt_index);
 
     return RISCV_EXCP_NONE;
 }
@@ -1256,9 +1252,7 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
         cfg_val = rv32 ? ((uint64_t)env->minstretcfgh << 32) :
                   env->minstretcfg;
     } else {
-        cfg_val = rv32 ?
-                  ((uint64_t)env->mhpmeventh_val[counter_idx] << 32) :
-                  env->mhpmevent_val[counter_idx];
+        cfg_val = env->mhpmevent_val[counter_idx];
         cfg_val &= MHPMEVENT_FILTER_MASK;
     }
 
@@ -1471,27 +1465,23 @@ static int rmw_cd_mhpmcounterh(CPURISCVState *env, int ctr_idx,
 
 static int rmw_cd_mhpmevent(CPURISCVState *env, int evt_index,
                             target_ulong *val, target_ulong new_val,
-                            target_ulong wr_mask)
+                            uint64_t wr_mask)
 {
-    uint64_t mhpmevt_val = new_val;
+    uint64_t mhpmevt_val = env->mhpmevent_val[evt_index];
 
     if (wr_mask != 0 && wr_mask != -1) {
         return -EINVAL;
     }
 
     if (!wr_mask && val) {
-        *val = env->mhpmevent_val[evt_index];
+        *val = mhpmevt_val;
         if (riscv_cpu_cfg(env)->ext_sscofpmf) {
             *val &= ~MHPMEVENT_BIT_MINH;
         }
     } else if (wr_mask) {
         wr_mask &= ~MHPMEVENT_BIT_MINH;
-        mhpmevt_val = (new_val & wr_mask) |
-                      (env->mhpmevent_val[evt_index] & ~wr_mask);
-        if (riscv_cpu_mxl(env) == MXL_RV32) {
-            mhpmevt_val = mhpmevt_val |
-                          ((uint64_t)env->mhpmeventh_val[evt_index] << 32);
-        }
+        /* wr_mask is 64-bit so upper 32 bits of mhpmevt_val are retained */
+        mhpmevt_val = (new_val & wr_mask) | (mhpmevt_val & ~wr_mask);
         env->mhpmevent_val[evt_index] = mhpmevt_val;
         riscv_pmu_update_event_map(env, mhpmevt_val, evt_index);
     } else {
@@ -1505,24 +1495,23 @@ static int rmw_cd_mhpmeventh(CPURISCVState *env, int evt_index,
                              target_ulong *val, target_ulong new_val,
                              target_ulong wr_mask)
 {
-    uint64_t mhpmevth_val;
     uint64_t mhpmevt_val = env->mhpmevent_val[evt_index];
+    uint32_t mhpmevth_val = extract64(mhpmevt_val, 32, 32);
 
     if (wr_mask != 0 && wr_mask != -1) {
         return -EINVAL;
     }
 
     if (!wr_mask && val) {
-        *val = env->mhpmeventh_val[evt_index];
+        *val = mhpmevth_val;
         if (riscv_cpu_cfg(env)->ext_sscofpmf) {
             *val &= ~MHPMEVENTH_BIT_MINH;
         }
     } else if (wr_mask) {
         wr_mask &= ~MHPMEVENTH_BIT_MINH;
-        env->mhpmeventh_val[evt_index] =
-            (new_val & wr_mask) | (env->mhpmeventh_val[evt_index] & ~wr_mask);
-        mhpmevth_val = env->mhpmeventh_val[evt_index];
-        mhpmevt_val = mhpmevt_val | (mhpmevth_val << 32);
+        mhpmevth_val = (new_val & wr_mask) | (mhpmevth_val & ~wr_mask);
+        mhpmevt_val = deposit64(mhpmevt_val, 32, 32, mhpmevth_val);
+        env->mhpmevent_val[evt_index] = mhpmevt_val;
         riscv_pmu_update_event_map(env, mhpmevt_val, evt_index);
     } else {
         return -EINVAL;
@@ -1598,8 +1587,6 @@ static RISCVException read_scountovf(CPURISCVState *env, int csrno,
     int mhpmevt_start = CSR_MHPMEVENT3 - CSR_MCOUNTINHIBIT;
     int i;
     *val = 0;
-    target_ulong *mhpm_evt_val;
-    uint64_t of_bit_mask;
 
     /* Virtualize scountovf for counter delegation */
     if (riscv_cpu_cfg(env)->ext_sscofpmf &&
@@ -1609,19 +1596,11 @@ static RISCVException read_scountovf(CPURISCVState *env, int csrno,
         return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
     }
 
-    if (riscv_cpu_mxl(env) == MXL_RV32) {
-        mhpm_evt_val = env->mhpmeventh_val;
-        of_bit_mask = MHPMEVENTH_BIT_OF;
-    } else {
-        mhpm_evt_val = env->mhpmevent_val;
-        of_bit_mask = MHPMEVENT_BIT_OF;
-    }
-
     for (i = mhpmevt_start; i < RV_MAX_MHPMEVENTS; i++) {
         if ((get_field(env->mcounteren, BIT(i))) &&
-            (mhpm_evt_val[i] & of_bit_mask)) {
-                    *val |= BIT(i);
-            }
+            (env->mhpmevent_val[i] & MHPMEVENT_BIT_OF)) {
+            *val |= BIT(i);
+        }
     }
 
     return RISCV_EXCP_NONE;
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 328fb674e1..d9939489e1 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -452,8 +452,7 @@ const VMStateDescription vmstate_riscv_cpu = {
         VMSTATE_UINT32(env.mcountinhibit, RISCVCPU),
         VMSTATE_STRUCT_ARRAY(env.pmu_ctrs, RISCVCPU, RV_MAX_MHPMCOUNTERS, 0,
                              vmstate_pmu_ctr_state, PMUCTRState),
-        VMSTATE_UINTTL_ARRAY(env.mhpmevent_val, RISCVCPU, RV_MAX_MHPMEVENTS),
-        VMSTATE_UINTTL_ARRAY(env.mhpmeventh_val, RISCVCPU, RV_MAX_MHPMEVENTS),
+        VMSTATE_UINT64_ARRAY(env.mhpmevent_val, RISCVCPU, RV_MAX_MHPMEVENTS),
         VMSTATE_UINT64(env.sscratch, RISCVCPU),
         VMSTATE_UINT64(env.mscratch, RISCVCPU),
         VMSTATE_UINT64(env.stimecmp, RISCVCPU),
diff --git a/target/riscv/pmu.c b/target/riscv/pmu.c
index a68809eef3..273822e921 100644
--- a/target/riscv/pmu.c
+++ b/target/riscv/pmu.c
@@ -110,15 +110,15 @@ static int riscv_pmu_incr_ctr_rv32(RISCVCPU *cpu, uint32_t ctr_idx)
 
     /* Privilege mode filtering */
     if ((env->priv == PRV_M &&
-        (env->mhpmeventh_val[ctr_idx] & MHPMEVENTH_BIT_MINH)) ||
+        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_MINH)) ||
         (env->priv == PRV_S && virt_on &&
-        (env->mhpmeventh_val[ctr_idx] & MHPMEVENTH_BIT_VSINH)) ||
+        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_VSINH)) ||
         (env->priv == PRV_U && virt_on &&
-        (env->mhpmeventh_val[ctr_idx] & MHPMEVENTH_BIT_VUINH)) ||
+        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_VUINH)) ||
         (env->priv == PRV_S && !virt_on &&
-        (env->mhpmeventh_val[ctr_idx] & MHPMEVENTH_BIT_SINH)) ||
+        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_SINH)) ||
         (env->priv == PRV_U && !virt_on &&
-        (env->mhpmeventh_val[ctr_idx] & MHPMEVENTH_BIT_UINH))) {
+        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_UINH))) {
         return 0;
     }
 
@@ -128,8 +128,8 @@ static int riscv_pmu_incr_ctr_rv32(RISCVCPU *cpu, uint32_t ctr_idx)
             counter->mhpmcounter_val = 0;
             counter->mhpmcounterh_val = 0;
             /* Generate interrupt only if OF bit is clear */
-            if (!(env->mhpmeventh_val[ctr_idx] & MHPMEVENTH_BIT_OF)) {
-                env->mhpmeventh_val[ctr_idx] |= MHPMEVENTH_BIT_OF;
+            if (!(env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_OF)) {
+                env->mhpmevent_val[ctr_idx] |= MHPMEVENT_BIT_OF;
                 riscv_cpu_update_mip(env, MIP_LCOFIP, BOOL_TO_MASK(1));
             }
         } else {
@@ -420,41 +420,14 @@ int riscv_pmu_update_event_map(CPURISCVState *env, uint64_t value,
     return 0;
 }
 
-static bool pmu_hpmevent_is_of_set(CPURISCVState *env, uint32_t ctr_idx)
-{
-    target_ulong mhpmevent_val;
-    uint64_t of_bit_mask;
-
-    if (riscv_cpu_mxl(env) == MXL_RV32) {
-        mhpmevent_val = env->mhpmeventh_val[ctr_idx];
-        of_bit_mask = MHPMEVENTH_BIT_OF;
-     } else {
-        mhpmevent_val = env->mhpmevent_val[ctr_idx];
-        of_bit_mask = MHPMEVENT_BIT_OF;
-    }
-
-    return get_field(mhpmevent_val, of_bit_mask);
-}
-
 static bool pmu_hpmevent_set_of_if_clear(CPURISCVState *env, uint32_t ctr_idx)
 {
-    target_ulong *mhpmevent_val;
-    uint64_t of_bit_mask;
-
-    if (riscv_cpu_mxl(env) == MXL_RV32) {
-        mhpmevent_val = &env->mhpmeventh_val[ctr_idx];
-        of_bit_mask = MHPMEVENTH_BIT_OF;
-     } else {
-        mhpmevent_val = &env->mhpmevent_val[ctr_idx];
-        of_bit_mask = MHPMEVENT_BIT_OF;
-    }
-
-    if (!get_field(*mhpmevent_val, of_bit_mask)) {
-        *mhpmevent_val |= of_bit_mask;
+    if (!get_field(env->mhpmevent_val[ctr_idx], MHPMEVENT_BIT_OF)) {
+        env->mhpmevent_val[ctr_idx] |= MHPMEVENT_BIT_OF;
         return true;
+    } else {
+        return false;
     }
-
-    return false;
 }
 
 static void pmu_timer_trigger_irq(RISCVCPU *cpu,
@@ -479,7 +452,7 @@ static void pmu_timer_trigger_irq(RISCVCPU *cpu,
     }
 
     /* Generate interrupt only if OF bit is clear */
-    if (pmu_hpmevent_is_of_set(env, ctr_idx)) {
+    if (get_field(env->mhpmevent_val[ctr_idx], MHPMEVENT_BIT_OF)) {
         return;
     }
 
@@ -538,7 +511,7 @@ int riscv_pmu_setup_timer(CPURISCVState *env, uint64_t value, uint32_t ctr_idx)
 
     /* No need to setup a timer if LCOFI is disabled when OF is set */
     if (!riscv_pmu_counter_valid(cpu, ctr_idx) || !cpu->cfg.ext_sscofpmf ||
-        pmu_hpmevent_is_of_set(env, ctr_idx)) {
+        get_field(env->mhpmevent_val[ctr_idx], MHPMEVENT_BIT_OF)) {
         return -1;
     }
 
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 06/33] target/riscv: Combine mcyclecfg and mcyclecfgh
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (4 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 19:13   ` Pierrick Bouvier
  2025-10-03  0:05   ` Alistair Francis
  2025-10-01  7:32 ` [PATCH v2 07/33] target/riscv: Combine minstretcfg and minstretcfgh Anton Johansson via
                   ` (26 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

According to version 20250508 of the privileged specification, mcyclecfg
is a 64-bit register and mcyclecfgh refers to the top 32 bits of this
register when XLEN == 32.  No real advantage is gained by keeping
them separate, and combining them allows for slight simplification.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h |  3 +--
 target/riscv/csr.c | 28 +++++++++++++++++-----------
 2 files changed, 18 insertions(+), 13 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 64b9964028..60f7611c00 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -419,8 +419,7 @@ struct CPUArchState {
     uint32_t mcountinhibit;
 
     /* PMU cycle & instret privilege mode filtering */
-    target_ulong mcyclecfg;
-    target_ulong mcyclecfgh;
+    uint64_t mcyclecfg;
     target_ulong minstretcfg;
     target_ulong minstretcfgh;
 
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 2d8916ee40..77d0bd7bca 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -1060,7 +1060,8 @@ static RISCVException read_hpmcounterh(CPURISCVState *env, int csrno,
 static RISCVException read_mcyclecfg(CPURISCVState *env, int csrno,
                                      target_ulong *val)
 {
-    *val = env->mcyclecfg;
+    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
+    *val = extract64(env->mcyclecfg, 0, rv32 ? 32 : 64);
     return RISCV_EXCP_NONE;
 }
 
@@ -1070,7 +1071,7 @@ static RISCVException write_mcyclecfg(CPURISCVState *env, int csrno,
     uint64_t inh_avail_mask;
 
     if (riscv_cpu_mxl(env) == MXL_RV32) {
-        env->mcyclecfg = val;
+        env->mcyclecfg = deposit64(env->mcyclecfg, 0, 32, val);
     } else {
         /* Set xINH fields if priv mode supported */
         inh_avail_mask = ~MHPMEVENT_FILTER_MASK | MCYCLECFG_BIT_MINH;
@@ -1089,7 +1090,7 @@ static RISCVException write_mcyclecfg(CPURISCVState *env, int csrno,
 static RISCVException read_mcyclecfgh(CPURISCVState *env, int csrno,
                                       target_ulong *val)
 {
-    *val = env->mcyclecfgh;
+    *val = extract64(env->mcyclecfg, 32, 32);
     return RISCV_EXCP_NONE;
 }
 
@@ -1107,7 +1108,7 @@ static RISCVException write_mcyclecfgh(CPURISCVState *env, int csrno,
     inh_avail_mask |= (riscv_has_ext(env, RVH) &&
                        riscv_has_ext(env, RVS)) ? MCYCLECFGH_BIT_VSINH : 0;
 
-    env->mcyclecfgh = val & inh_avail_mask;
+    env->mcyclecfg = deposit64(env->mcyclecfg, 32, 32, val & inh_avail_mask);
     return RISCV_EXCP_NONE;
 }
 
@@ -1246,8 +1247,7 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
     g_assert(rv32 || !upper_half);
 
     if (counter_idx == 0) {
-        cfg_val = rv32 ? ((uint64_t)env->mcyclecfgh << 32) :
-                  env->mcyclecfg;
+        cfg_val = env->mcyclecfg;
     } else if (counter_idx == 2) {
         cfg_val = rv32 ? ((uint64_t)env->minstretcfgh << 32) :
                   env->minstretcfg;
@@ -1521,8 +1521,12 @@ static int rmw_cd_mhpmeventh(CPURISCVState *env, int evt_index,
 }
 
 static int rmw_cd_ctr_cfg(CPURISCVState *env, int cfg_index, target_ulong *val,
-                            target_ulong new_val, target_ulong wr_mask)
+                          target_ulong new_val, uint64_t wr_mask)
 {
+    /*
+     * wr_mask is 64-bit so upper 32 bits of mcyclecfg and minstretcfg
+     * are retained.
+     */
     switch (cfg_index) {
     case 0:             /* CYCLECFG */
         if (wr_mask) {
@@ -1548,8 +1552,9 @@ static int rmw_cd_ctr_cfg(CPURISCVState *env, int cfg_index, target_ulong *val,
 }
 
 static int rmw_cd_ctr_cfgh(CPURISCVState *env, int cfg_index, target_ulong *val,
-                            target_ulong new_val, target_ulong wr_mask)
+                           target_ulong new_val, target_ulong wr_mask)
 {
+    uint64_t cfgh;
 
     if (riscv_cpu_mxl(env) != MXL_RV32) {
         return RISCV_EXCP_ILLEGAL_INST;
@@ -1557,12 +1562,13 @@ static int rmw_cd_ctr_cfgh(CPURISCVState *env, int cfg_index, target_ulong *val,
 
     switch (cfg_index) {
     case 0:         /* CYCLECFGH */
+        cfgh = extract64(env->mcyclecfg, 32, 32);
         if (wr_mask) {
             wr_mask &= ~MCYCLECFGH_BIT_MINH;
-            env->mcyclecfgh = (new_val & wr_mask) |
-                              (env->mcyclecfgh & ~wr_mask);
+            cfgh = (new_val & wr_mask) | (cfgh & ~wr_mask);
+            env->mcyclecfg = deposit64(env->mcyclecfg, 32, 32, cfgh);
         } else {
-            *val = env->mcyclecfgh;
+            *val = cfgh;
         }
         break;
     case 2:          /* INSTRETCFGH */
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 07/33] target/riscv: Combine minstretcfg and minstretcfgh
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (5 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 06/33] target/riscv: Combine mcyclecfg and mcyclecfgh Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 19:14   ` Pierrick Bouvier
  2025-10-03  0:06   ` Alistair Francis
  2025-10-01  7:32 ` [PATCH v2 08/33] target/riscv: Combine mhpmcounter and mhpmcounterh Anton Johansson via
                   ` (25 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

According to version 20250508 of the privileged specification,
minstretcfg is a 64-bit register and minstretcfgh refers to the top
32 bits of this register when XLEN == 32.  No real advantage is
gained by keeping them separate, and combining them allows for slight
simplification.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h |  3 +--
 target/riscv/csr.c | 18 ++++++++++--------
 2 files changed, 11 insertions(+), 10 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 60f7611c00..d8f0818b08 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -420,8 +420,7 @@ struct CPUArchState {
 
     /* PMU cycle & instret privilege mode filtering */
     uint64_t mcyclecfg;
-    target_ulong minstretcfg;
-    target_ulong minstretcfgh;
+    uint64_t minstretcfg;
 
     /* PMU counter state */
     PMUCTRState pmu_ctrs[RV_MAX_MHPMCOUNTERS];
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 77d0bd7bca..83f6526723 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -1115,7 +1115,8 @@ static RISCVException write_mcyclecfgh(CPURISCVState *env, int csrno,
 static RISCVException read_minstretcfg(CPURISCVState *env, int csrno,
                                        target_ulong *val)
 {
-    *val = env->minstretcfg;
+    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
+    *val = extract64(env->minstretcfg, 0, rv32 ? 32 : 64);
     return RISCV_EXCP_NONE;
 }
 
@@ -1142,7 +1143,7 @@ static RISCVException write_minstretcfg(CPURISCVState *env, int csrno,
 static RISCVException read_minstretcfgh(CPURISCVState *env, int csrno,
                                         target_ulong *val)
 {
-    *val = env->minstretcfgh;
+    *val = extract64(env->minstretcfg, 32, 32);
     return RISCV_EXCP_NONE;
 }
 
@@ -1159,7 +1160,8 @@ static RISCVException write_minstretcfgh(CPURISCVState *env, int csrno,
     inh_avail_mask |= (riscv_has_ext(env, RVH) &&
                        riscv_has_ext(env, RVS)) ? MINSTRETCFGH_BIT_VSINH : 0;
 
-    env->minstretcfgh = val & inh_avail_mask;
+    env->minstretcfg = deposit64(env->minstretcfg, 32, 32,
+                                 val & inh_avail_mask);
     return RISCV_EXCP_NONE;
 }
 
@@ -1249,8 +1251,7 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
     if (counter_idx == 0) {
         cfg_val = env->mcyclecfg;
     } else if (counter_idx == 2) {
-        cfg_val = rv32 ? ((uint64_t)env->minstretcfgh << 32) :
-                  env->minstretcfg;
+        cfg_val = env->minstretcfg;
     } else {
         cfg_val = env->mhpmevent_val[counter_idx];
         cfg_val &= MHPMEVENT_FILTER_MASK;
@@ -1572,12 +1573,13 @@ static int rmw_cd_ctr_cfgh(CPURISCVState *env, int cfg_index, target_ulong *val,
         }
         break;
     case 2:          /* INSTRETCFGH */
+        cfgh = extract64(env->minstretcfg, 32, 32);
         if (wr_mask) {
             wr_mask &= ~MINSTRETCFGH_BIT_MINH;
-            env->minstretcfgh = (new_val & wr_mask) |
-                                (env->minstretcfgh & ~wr_mask);
+            cfgh = (new_val & wr_mask) | (cfgh & ~wr_mask);
+            env->minstretcfg = deposit64(env->minstretcfg, 32, 32, cfgh);
         } else {
-            *val = env->minstretcfgh;
+            *val = cfgh;
         }
         break;
     default:
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 08/33] target/riscv: Combine mhpmcounter and mhpmcounterh
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (6 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 07/33] target/riscv: Combine minstretcfg and minstretcfgh Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 19:24   ` Pierrick Bouvier
  2025-10-02 19:25   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 09/33] target/riscv: Fix size of gpr and gprh Anton Johansson via
                   ` (24 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

According to version 20250508 of the privileged specification,
mhpmconter is a 64-bit register and mhpmcounterh refers to the top
32 bits of this register when XLEN == 32.  No real advantage is
gained by keeping them separate, and combining allows for slight
simplification.

Note, the cpu/pmu VMSTATE version is bumped breaking migration from
older versions.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h     |   8 +--
 target/riscv/csr.c     |  74 +++++++++++++--------------
 target/riscv/machine.c |  10 ++--
 target/riscv/pmu.c     | 111 +++++++++++------------------------------
 4 files changed, 70 insertions(+), 133 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index d8f0818b08..d4a59692a1 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -195,13 +195,9 @@ FIELD(VTYPE, RESERVED, 10, sizeof(target_ulong) * 8 - 11)
 
 typedef struct PMUCTRState {
     /* Current value of a counter */
-    target_ulong mhpmcounter_val;
-    /* Current value of a counter in RV32 */
-    target_ulong mhpmcounterh_val;
+    uint64_t mhpmcounter_val;
     /* Snapshot values of counter */
-    target_ulong mhpmcounter_prev;
-    /* Snapshort value of a counter in RV32 */
-    target_ulong mhpmcounterh_prev;
+    uint64_t mhpmcounter_prev;
     /* Value beyond UINT32_MAX/UINT64_MAX before overflow interrupt trigger */
     target_ulong irq_overflow_left;
 } PMUCTRState;
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 83f6526723..d660635950 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -1298,24 +1298,27 @@ static RISCVException riscv_pmu_write_ctr(CPURISCVState *env, target_ulong val,
                                           uint32_t ctr_idx)
 {
     PMUCTRState *counter = &env->pmu_ctrs[ctr_idx];
-    uint64_t mhpmctr_val = val;
+    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
+    int deposit_size = rv32 ? 32 : 64;
+    uint64_t ctr;
+
+    counter->mhpmcounter_val = deposit64(counter->mhpmcounter_val,
+                                         0, deposit_size, val);
 
-    counter->mhpmcounter_val = val;
     if (!get_field(env->mcountinhibit, BIT(ctr_idx)) &&
         (riscv_pmu_ctr_monitor_cycles(env, ctr_idx) ||
          riscv_pmu_ctr_monitor_instructions(env, ctr_idx))) {
-        counter->mhpmcounter_prev = riscv_pmu_ctr_get_fixed_counters_val(env,
-                                                                ctr_idx, false);
+        ctr = riscv_pmu_ctr_get_fixed_counters_val(env, ctr_idx, false);
+        counter->mhpmcounter_prev = deposit64(counter->mhpmcounter_prev,
+                                              0, deposit_size, ctr);
         if (ctr_idx > 2) {
-            if (riscv_cpu_mxl(env) == MXL_RV32) {
-                mhpmctr_val = mhpmctr_val |
-                              ((uint64_t)counter->mhpmcounterh_val << 32);
-            }
-            riscv_pmu_setup_timer(env, mhpmctr_val, ctr_idx);
+            riscv_pmu_setup_timer(env, counter->mhpmcounter_val, ctr_idx);
         }
      } else {
         /* Other counters can keep incrementing from the given value */
-        counter->mhpmcounter_prev = val;
+        counter->mhpmcounter_prev = deposit64(counter->mhpmcounter_prev,
+                                              0, deposit_size, val);
+
     }
 
     return RISCV_EXCP_NONE;
@@ -1325,21 +1328,22 @@ static RISCVException riscv_pmu_write_ctrh(CPURISCVState *env, target_ulong val,
                                           uint32_t ctr_idx)
 {
     PMUCTRState *counter = &env->pmu_ctrs[ctr_idx];
-    uint64_t mhpmctr_val = counter->mhpmcounter_val;
-    uint64_t mhpmctrh_val = val;
+    uint64_t ctrh;
 
-    counter->mhpmcounterh_val = val;
-    mhpmctr_val = mhpmctr_val | (mhpmctrh_val << 32);
+    counter->mhpmcounter_val = deposit64(counter->mhpmcounter_val,
+                                         32, 32, val);
     if (!get_field(env->mcountinhibit, BIT(ctr_idx)) &&
         (riscv_pmu_ctr_monitor_cycles(env, ctr_idx) ||
          riscv_pmu_ctr_monitor_instructions(env, ctr_idx))) {
-        counter->mhpmcounterh_prev = riscv_pmu_ctr_get_fixed_counters_val(env,
-                                                                 ctr_idx, true);
+        ctrh = riscv_pmu_ctr_get_fixed_counters_val(env, ctr_idx, true);
+        counter->mhpmcounter_prev = deposit64(counter->mhpmcounter_prev,
+                                              32, 32, ctrh);
         if (ctr_idx > 2) {
-            riscv_pmu_setup_timer(env, mhpmctr_val, ctr_idx);
+            riscv_pmu_setup_timer(env, counter->mhpmcounter_val, ctr_idx);
         }
     } else {
-        counter->mhpmcounterh_prev = val;
+        counter->mhpmcounter_prev = deposit64(counter->mhpmcounter_prev,
+                                              32, 32, val);
     }
 
     return RISCV_EXCP_NONE;
@@ -1362,13 +1366,17 @@ static RISCVException write_mhpmcounterh(CPURISCVState *env, int csrno,
 }
 
 RISCVException riscv_pmu_read_ctr(CPURISCVState *env, target_ulong *val,
-                                         bool upper_half, uint32_t ctr_idx)
+                                  bool upper_half, uint32_t ctr_idx)
 {
     PMUCTRState *counter = &env->pmu_ctrs[ctr_idx];
-    target_ulong ctr_prev = upper_half ? counter->mhpmcounterh_prev :
-                                         counter->mhpmcounter_prev;
-    target_ulong ctr_val = upper_half ? counter->mhpmcounterh_val :
-                                        counter->mhpmcounter_val;
+    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
+    int start = upper_half ? 32 : 0;
+    int length = rv32 ? 32 : 64;
+    uint64_t ctr_prev = extract64(counter->mhpmcounter_prev, start, length);
+    uint64_t ctr_val  = extract64(counter->mhpmcounter_val, start, length);
+
+    /* Ensure upper_half is only set for XLEN == 32 */
+    g_assert(rv32 || !upper_half);
 
     if (get_field(env->mcountinhibit, BIT(ctr_idx))) {
         /*
@@ -2991,6 +2999,7 @@ static RISCVException write_mcountinhibit(CPURISCVState *env, int csrno,
     uint32_t present_ctrs = cpu->pmu_avail_ctrs | COUNTEREN_CY | COUNTEREN_IR;
     target_ulong updated_ctrs = (env->mcountinhibit ^ val) & present_ctrs;
     uint64_t mhpmctr_val, prev_count, curr_count;
+    uint64_t ctrh;
 
     /* WARL register - disable unavailable counters; TM bit is always 0 */
     env->mcountinhibit = val & present_ctrs;
@@ -3009,17 +3018,13 @@ static RISCVException write_mcountinhibit(CPURISCVState *env, int csrno,
             counter->mhpmcounter_prev =
                 riscv_pmu_ctr_get_fixed_counters_val(env, cidx, false);
             if (riscv_cpu_mxl(env) == MXL_RV32) {
-                counter->mhpmcounterh_prev =
-                    riscv_pmu_ctr_get_fixed_counters_val(env, cidx, true);
+                ctrh = riscv_pmu_ctr_get_fixed_counters_val(env, cidx, true);
+                counter->mhpmcounter_prev = deposit64(counter->mhpmcounter_prev,
+                                                      32, 32, ctrh);
             }
 
             if (cidx > 2) {
-                mhpmctr_val = counter->mhpmcounter_val;
-                if (riscv_cpu_mxl(env) == MXL_RV32) {
-                    mhpmctr_val = mhpmctr_val |
-                            ((uint64_t)counter->mhpmcounterh_val << 32);
-                }
-                riscv_pmu_setup_timer(env, mhpmctr_val, cidx);
+                riscv_pmu_setup_timer(env, counter->mhpmcounter_val, cidx);
             }
         } else {
             curr_count = riscv_pmu_ctr_get_fixed_counters_val(env, cidx, false);
@@ -3031,18 +3036,11 @@ static RISCVException write_mcountinhibit(CPURISCVState *env, int csrno,
                     riscv_pmu_ctr_get_fixed_counters_val(env, cidx, true);
 
                 curr_count = curr_count | (tmp << 32);
-                mhpmctr_val = mhpmctr_val |
-                    ((uint64_t)counter->mhpmcounterh_val << 32);
-                prev_count = prev_count |
-                    ((uint64_t)counter->mhpmcounterh_prev << 32);
             }
 
             /* Adjust the counter for later reads. */
             mhpmctr_val = curr_count - prev_count + mhpmctr_val;
             counter->mhpmcounter_val = mhpmctr_val;
-            if (riscv_cpu_mxl(env) == MXL_RV32) {
-                counter->mhpmcounterh_val = mhpmctr_val >> 32;
-            }
         }
     }
 
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index d9939489e1..10003a1fd9 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -334,14 +334,12 @@ static bool pmu_needed(void *opaque)
 
 static const VMStateDescription vmstate_pmu_ctr_state = {
     .name = "cpu/pmu",
-    .version_id = 2,
-    .minimum_version_id = 2,
+    .version_id = 3,
+    .minimum_version_id = 3,
     .needed = pmu_needed,
     .fields = (const VMStateField[]) {
-        VMSTATE_UINTTL(mhpmcounter_val, PMUCTRState),
-        VMSTATE_UINTTL(mhpmcounterh_val, PMUCTRState),
-        VMSTATE_UINTTL(mhpmcounter_prev, PMUCTRState),
-        VMSTATE_UINTTL(mhpmcounterh_prev, PMUCTRState),
+        VMSTATE_UINT64(mhpmcounter_val, PMUCTRState),
+        VMSTATE_UINT64(mhpmcounter_prev, PMUCTRState),
         VMSTATE_END_OF_LIST()
     }
 };
diff --git a/target/riscv/pmu.c b/target/riscv/pmu.c
index 273822e921..708f2ec7aa 100644
--- a/target/riscv/pmu.c
+++ b/target/riscv/pmu.c
@@ -101,82 +101,6 @@ static bool riscv_pmu_counter_enabled(RISCVCPU *cpu, uint32_t ctr_idx)
     }
 }
 
-static int riscv_pmu_incr_ctr_rv32(RISCVCPU *cpu, uint32_t ctr_idx)
-{
-    CPURISCVState *env = &cpu->env;
-    target_ulong max_val = UINT32_MAX;
-    PMUCTRState *counter = &env->pmu_ctrs[ctr_idx];
-    bool virt_on = env->virt_enabled;
-
-    /* Privilege mode filtering */
-    if ((env->priv == PRV_M &&
-        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_MINH)) ||
-        (env->priv == PRV_S && virt_on &&
-        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_VSINH)) ||
-        (env->priv == PRV_U && virt_on &&
-        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_VUINH)) ||
-        (env->priv == PRV_S && !virt_on &&
-        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_SINH)) ||
-        (env->priv == PRV_U && !virt_on &&
-        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_UINH))) {
-        return 0;
-    }
-
-    /* Handle the overflow scenario */
-    if (counter->mhpmcounter_val == max_val) {
-        if (counter->mhpmcounterh_val == max_val) {
-            counter->mhpmcounter_val = 0;
-            counter->mhpmcounterh_val = 0;
-            /* Generate interrupt only if OF bit is clear */
-            if (!(env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_OF)) {
-                env->mhpmevent_val[ctr_idx] |= MHPMEVENT_BIT_OF;
-                riscv_cpu_update_mip(env, MIP_LCOFIP, BOOL_TO_MASK(1));
-            }
-        } else {
-            counter->mhpmcounterh_val++;
-        }
-    } else {
-        counter->mhpmcounter_val++;
-    }
-
-    return 0;
-}
-
-static int riscv_pmu_incr_ctr_rv64(RISCVCPU *cpu, uint32_t ctr_idx)
-{
-    CPURISCVState *env = &cpu->env;
-    PMUCTRState *counter = &env->pmu_ctrs[ctr_idx];
-    uint64_t max_val = UINT64_MAX;
-    bool virt_on = env->virt_enabled;
-
-    /* Privilege mode filtering */
-    if ((env->priv == PRV_M &&
-        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_MINH)) ||
-        (env->priv == PRV_S && virt_on &&
-        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_VSINH)) ||
-        (env->priv == PRV_U && virt_on &&
-        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_VUINH)) ||
-        (env->priv == PRV_S && !virt_on &&
-        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_SINH)) ||
-        (env->priv == PRV_U && !virt_on &&
-        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_UINH))) {
-        return 0;
-    }
-
-    /* Handle the overflow scenario */
-    if (counter->mhpmcounter_val == max_val) {
-        counter->mhpmcounter_val = 0;
-        /* Generate interrupt only if OF bit is clear */
-        if (!(env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_OF)) {
-            env->mhpmevent_val[ctr_idx] |= MHPMEVENT_BIT_OF;
-            riscv_cpu_update_mip(env, MIP_LCOFIP, BOOL_TO_MASK(1));
-        }
-    } else {
-        counter->mhpmcounter_val++;
-    }
-    return 0;
-}
-
 /*
  * Information needed to update counters:
  *  new_priv, new_virt: To correctly save starting snapshot for the newly
@@ -275,8 +199,10 @@ void riscv_pmu_update_fixed_ctrs(CPURISCVState *env, target_ulong newpriv,
 int riscv_pmu_incr_ctr(RISCVCPU *cpu, enum riscv_pmu_event_idx event_idx)
 {
     uint32_t ctr_idx;
-    int ret;
     CPURISCVState *env = &cpu->env;
+    uint64_t max_val = UINT64_MAX;
+    bool virt_on = env->virt_enabled;
+    PMUCTRState *counter;
     gpointer value;
 
     if (!cpu->cfg.pmu_mask) {
@@ -293,13 +219,34 @@ int riscv_pmu_incr_ctr(RISCVCPU *cpu, enum riscv_pmu_event_idx event_idx)
         return -1;
     }
 
-    if (riscv_cpu_mxl(env) == MXL_RV32) {
-        ret = riscv_pmu_incr_ctr_rv32(cpu, ctr_idx);
+    /* Privilege mode filtering */
+    if ((env->priv == PRV_M &&
+        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_MINH)) ||
+        (env->priv == PRV_S && virt_on &&
+        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_VSINH)) ||
+        (env->priv == PRV_U && virt_on &&
+        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_VUINH)) ||
+        (env->priv == PRV_S && !virt_on &&
+        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_SINH)) ||
+        (env->priv == PRV_U && !virt_on &&
+        (env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_UINH))) {
+        return 0;
+    }
+
+    /* Handle the overflow scenario */
+    counter = &env->pmu_ctrs[ctr_idx];
+    if (counter->mhpmcounter_val == max_val) {
+        counter->mhpmcounter_val = 0;
+        /* Generate interrupt only if OF bit is clear */
+        if (!(env->mhpmevent_val[ctr_idx] & MHPMEVENT_BIT_OF)) {
+            env->mhpmevent_val[ctr_idx] |= MHPMEVENT_BIT_OF;
+            riscv_cpu_update_mip(env, MIP_LCOFIP, BOOL_TO_MASK(1));
+        }
     } else {
-        ret = riscv_pmu_incr_ctr_rv64(cpu, ctr_idx);
+        counter->mhpmcounter_val++;
     }
 
-    return ret;
+    return 0;
 }
 
 bool riscv_pmu_ctr_monitor_instructions(CPURISCVState *env,
@@ -470,8 +417,6 @@ static void pmu_timer_trigger_irq(RISCVCPU *cpu,
     if (riscv_cpu_mxl(env) == MXL_RV32) {
         riscv_pmu_read_ctr(env, (target_ulong *)&curr_ctrh_val, true, ctr_idx);
         curr_ctr_val = curr_ctr_val | (curr_ctrh_val << 32);
-        ctr_val = ctr_val |
-                ((uint64_t)counter->mhpmcounterh_val << 32);
     }
 
     /*
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 09/33] target/riscv: Fix size of gpr and gprh
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (7 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 08/33] target/riscv: Combine mhpmcounter and mhpmcounterh Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-01  7:42   ` Philippe Mathieu-Daudé
  2025-10-01  7:32 ` [PATCH v2 10/33] target/riscv: Fix size of vector CSRs Anton Johansson via
                   ` (23 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

gprh is only needed for TARGET_RISCV64 when modeling 128-bit registers,
fixing their size to 64 bits makes sense.

gpr is also fixed to 64 bits since all direct uses of env->gpr
correctly zero extend/truncate to/from target_ulong, meaning
!TARGET_RISCV64 will behave as expected.

We do however need to be a bit careful when mapping 64-bit fields to
32-bit TCGv globals on big endian hosts.

Note, the cpu/rv128 VMSTATE version is bumped, breaking migration from
older versions.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h       |  4 ++--
 target/riscv/cpu.c       |  2 +-
 target/riscv/machine.c   |  8 ++++----
 target/riscv/translate.c | 17 +++++++++++++++--
 4 files changed, 22 insertions(+), 9 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index d4a59692a1..fe774b00ef 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -212,8 +212,8 @@ typedef struct PMUFixedCtrState {
 } PMUFixedCtrState;
 
 struct CPUArchState {
-    target_ulong gpr[32];
-    target_ulong gprh[32]; /* 64 top bits of the 128-bit registers */
+    uint64_t gpr[32];
+    uint64_t gprh[32]; /* 64 top bits of the 128-bit registers */
 
     /* vector coprocessor state. */
     uint64_t vreg[32 * RV_VLEN_MAX / 64] QEMU_ALIGNED(16);
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
index d055ddf462..3c910e44cd 100644
--- a/target/riscv/cpu.c
+++ b/target/riscv/cpu.c
@@ -584,7 +584,7 @@ static void riscv_cpu_dump_state(CPUState *cs, FILE *f, int flags)
 
     for (i = 0; i < 32; i++) {
         qemu_fprintf(f, " %-8s " TARGET_FMT_lx,
-                     riscv_int_regnames[i], env->gpr[i]);
+                     riscv_int_regnames[i], (target_ulong) env->gpr[i]);
         if ((i & 3) == 3) {
             qemu_fprintf(f, "\n");
         }
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 10003a1fd9..6bc79cceaf 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -176,11 +176,11 @@ static bool rv128_needed(void *opaque)
 
 static const VMStateDescription vmstate_rv128 = {
     .name = "cpu/rv128",
-    .version_id = 1,
-    .minimum_version_id = 1,
+    .version_id = 2,
+    .minimum_version_id = 2,
     .needed = rv128_needed,
     .fields = (const VMStateField[]) {
-        VMSTATE_UINTTL_ARRAY(env.gprh, RISCVCPU, 32),
+        VMSTATE_UINT64_ARRAY(env.gprh, RISCVCPU, 32),
         VMSTATE_UINT64(env.mscratchh, RISCVCPU),
         VMSTATE_UINT64(env.sscratchh, RISCVCPU),
         VMSTATE_END_OF_LIST()
@@ -404,7 +404,7 @@ const VMStateDescription vmstate_riscv_cpu = {
     .minimum_version_id = 11,
     .post_load = riscv_cpu_post_load,
     .fields = (const VMStateField[]) {
-        VMSTATE_UINTTL_ARRAY(env.gpr, RISCVCPU, 32),
+        VMSTATE_UINT64_ARRAY(env.gpr, RISCVCPU, 32),
         VMSTATE_UINT64_ARRAY(env.fpr, RISCVCPU, 32),
         VMSTATE_UINT8_ARRAY(env.miprio, RISCVCPU, 64),
         VMSTATE_UINT8_ARRAY(env.siprio, RISCVCPU, 64),
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 9ddef2d6e2..2f8c7a6465 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -26,6 +26,7 @@
 #include "exec/translator.h"
 #include "exec/translation-block.h"
 #include "exec/log.h"
+#include "exec/tswap.h"
 #include "semihosting/semihost.h"
 
 #include "internals.h"
@@ -1427,12 +1428,24 @@ void riscv_translate_init(void)
      */
     cpu_gpr[0] = NULL;
     cpu_gprh[0] = NULL;
+    /*
+     * Be careful with big endian hosts when mapping 64-bit CPUArchState fields
+     * to 32-bit TCGv globals.  An offset of 4 bytes is applied so the least
+     * significant bytes are correctly written to.
+     */
+#if HOST_BIG_ENDIAN && !defined(TARGET_RISCV64)
+    size_t field_offset = 4;
+#else
+    size_t field_offset = 0;
+#endif
 
     for (i = 1; i < 32; i++) {
         cpu_gpr[i] = tcg_global_mem_new(tcg_env,
-            offsetof(CPURISCVState, gpr[i]), riscv_int_regnames[i]);
+            offsetof(CPURISCVState, gpr[i]) + field_offset,
+            riscv_int_regnames[i]);
         cpu_gprh[i] = tcg_global_mem_new(tcg_env,
-            offsetof(CPURISCVState, gprh[i]), riscv_int_regnamesh[i]);
+            offsetof(CPURISCVState, gprh[i]) + field_offset,
+            riscv_int_regnamesh[i]);
     }
 
     for (i = 0; i < 32; i++) {
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 10/33] target/riscv: Fix size of vector CSRs
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (8 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 09/33] target/riscv: Fix size of gpr and gprh Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 19:42   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 11/33] target/riscv: Fix size of pc, load_[val|res] Anton Johansson via
                   ` (22 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

According to version 20250508 of the unprivileged specification:
- vtype: bits 0..7 used, bit XLEN-1 illegal, rest reserved
  => fix to 64-bits.

- vxsat: bit 0 used, vxrm which would occupy bits 1..2 is stored
  separately, and bits 3..31 are set to 0
  => fix to 8-bits.

- vxrm: 2 lowest bits are used for rounding mode, rest set to 0
  => fix to 8-bits.

- vstart: maximum value of VLMAX-1, where VLMAX is at most 2^16
  => fix to 32-bits as vstart is mapped to a TCG global.

- vl: maximum value of VLEN which is at most 2^16
  => fix to 32-bits as vl is mapped to a TCG global.

Fields are shuffled for reduced padding.

Note, the cpu/vector VMSTATE version is bumped, breaking migration from
older versions.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h                      | 12 ++++++------
 target/riscv/machine.c                  | 14 +++++++-------
 target/riscv/translate.c                | 12 ++++++++----
 target/riscv/vector_helper.c            | 22 ++++++++++++++++++----
 target/riscv/insn_trans/trans_rvv.c.inc | 22 +++++++++++-----------
 5 files changed, 50 insertions(+), 32 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index fe774b00ef..c903b4f085 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -191,7 +191,7 @@ FIELD(VTYPE, VSEW, 3, 3)
 FIELD(VTYPE, VTA, 6, 1)
 FIELD(VTYPE, VMA, 7, 1)
 FIELD(VTYPE, VEDIV, 8, 2)
-FIELD(VTYPE, RESERVED, 10, sizeof(target_ulong) * 8 - 11)
+FIELD(VTYPE, RESERVED, 10, sizeof(uint64_t) * 8 - 11)
 
 typedef struct PMUCTRState {
     /* Current value of a counter */
@@ -217,11 +217,11 @@ struct CPUArchState {
 
     /* vector coprocessor state. */
     uint64_t vreg[32 * RV_VLEN_MAX / 64] QEMU_ALIGNED(16);
-    target_ulong vxrm;
-    target_ulong vxsat;
-    target_ulong vl;
-    target_ulong vstart;
-    target_ulong vtype;
+    uint64_t vtype;
+    uint32_t vl;
+    uint32_t vstart;
+    uint8_t vxrm;
+    uint8_t vxsat;
     bool vill;
 
     target_ulong pc;
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 6bc79cceaf..dcf18624bf 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -136,16 +136,16 @@ static bool vector_needed(void *opaque)
 
 static const VMStateDescription vmstate_vector = {
     .name = "cpu/vector",
-    .version_id = 2,
-    .minimum_version_id = 2,
+    .version_id = 3,
+    .minimum_version_id = 3,
     .needed = vector_needed,
     .fields = (const VMStateField[]) {
         VMSTATE_UINT64_ARRAY(env.vreg, RISCVCPU, 32 * RV_VLEN_MAX / 64),
-        VMSTATE_UINTTL(env.vxrm, RISCVCPU),
-        VMSTATE_UINTTL(env.vxsat, RISCVCPU),
-        VMSTATE_UINTTL(env.vl, RISCVCPU),
-        VMSTATE_UINTTL(env.vstart, RISCVCPU),
-        VMSTATE_UINTTL(env.vtype, RISCVCPU),
+        VMSTATE_UINT8(env.vxrm, RISCVCPU),
+        VMSTATE_UINT8(env.vxsat, RISCVCPU),
+        VMSTATE_UINT32(env.vl, RISCVCPU),
+        VMSTATE_UINT32(env.vstart, RISCVCPU),
+        VMSTATE_UINT64(env.vtype, RISCVCPU),
         VMSTATE_BOOL(env.vill, RISCVCPU),
         VMSTATE_END_OF_LIST()
     }
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 2f8c7a6465..5e8fc3e543 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -38,8 +38,9 @@
 #include "tcg/tcg-cpu.h"
 
 /* global register indices */
-static TCGv cpu_gpr[32], cpu_gprh[32], cpu_pc, cpu_vl, cpu_vstart;
+static TCGv cpu_gpr[32], cpu_gprh[32], cpu_pc;
 static TCGv_i64 cpu_fpr[32]; /* assume F and D extensions */
+static TCGv_i32 cpu_vl, cpu_vstart;
 static TCGv load_res;
 static TCGv load_val;
 
@@ -1439,6 +1440,10 @@ void riscv_translate_init(void)
     size_t field_offset = 0;
 #endif
 
+    /* 32 bits in size, no offset needed */
+    size_t vl_offset = offsetof(CPURISCVState, vl);
+    size_t vstart_offset = offsetof(CPURISCVState, vstart);
+
     for (i = 1; i < 32; i++) {
         cpu_gpr[i] = tcg_global_mem_new(tcg_env,
             offsetof(CPURISCVState, gpr[i]) + field_offset,
@@ -1454,9 +1459,8 @@ void riscv_translate_init(void)
     }
 
     cpu_pc = tcg_global_mem_new(tcg_env, offsetof(CPURISCVState, pc), "pc");
-    cpu_vl = tcg_global_mem_new(tcg_env, offsetof(CPURISCVState, vl), "vl");
-    cpu_vstart = tcg_global_mem_new(tcg_env, offsetof(CPURISCVState, vstart),
-                            "vstart");
+    cpu_vl = tcg_global_mem_new_i32(tcg_env, vl_offset, "vl");
+    cpu_vstart = tcg_global_mem_new_i32(tcg_env, vstart_offset, "vstart");
     load_res = tcg_global_mem_new(tcg_env, offsetof(CPURISCVState, load_res),
                              "load_res");
     load_val = tcg_global_mem_new(tcg_env, offsetof(CPURISCVState, load_val),
diff --git a/target/riscv/vector_helper.c b/target/riscv/vector_helper.c
index 7c67d67a13..2fc5348044 100644
--- a/target/riscv/vector_helper.c
+++ b/target/riscv/vector_helper.c
@@ -360,6 +360,12 @@ vext_page_ldst_us(CPURISCVState *env, void *vd, target_ulong addr,
     uint32_t evl = env->vstart + elems;
     MMUAccessType access_type = is_load ? MMU_DATA_LOAD : MMU_DATA_STORE;
 
+    /*
+     * Maximum vector length is VLMAX == 2^16 == LMUL * VL / SEW, and
+     * occurs for LMUL == 8, SEW == 8, VL == 2^16.
+     */
+    g_assert(env->vstart < UINT16_MAX && UINT16_MAX - env->vstart >= elems);
+
     /* Check page permission/pmp/watchpoint/etc. */
     probe_pages(env, addr, size, ra, access_type, mmu_index, &host, &flags,
                 true);
@@ -2594,19 +2600,27 @@ static inline uint8_t get_round(int vxrm, uint64_t v, uint8_t shift)
 
     d1 = extract64(v, shift - 1, 1);
     D1 = extract64(v, 0, shift);
-    if (vxrm == 0) { /* round-to-nearest-up (add +0.5 LSB) */
+    switch (vxrm) {
+    case 0:
+        /* round-to-nearest-up (add +0.5 LSB) */
         return d1;
-    } else if (vxrm == 1) { /* round-to-nearest-even */
+    case 1:
+        /* round-to-nearest-even */
         if (shift > 1) {
             D2 = extract64(v, 0, shift - 1);
             return d1 & ((D2 != 0) | d);
         } else {
             return d1 & d;
         }
-    } else if (vxrm == 3) { /* round-to-odd (OR bits into LSB, aka "jam") */
+    case 2:
+        /* round-down (truncate) */
+        return 0;
+    case 3:
+        /* round-to-odd (OR bits into LSB, aka "jam") */
         return !d & (D1 != 0);
+    default:
+        g_assert_not_reached();
     }
-    return 0; /* round-down (truncate) */
 }
 
 static inline int32_t aadd32(CPURISCVState *env, int vxrm, int32_t a,
diff --git a/target/riscv/insn_trans/trans_rvv.c.inc b/target/riscv/insn_trans/trans_rvv.c.inc
index 71f98fb350..f1b624922a 100644
--- a/target/riscv/insn_trans/trans_rvv.c.inc
+++ b/target/riscv/insn_trans/trans_rvv.c.inc
@@ -194,7 +194,7 @@ static bool do_vsetvl(DisasContext *s, int rd, int rs1, TCGv s2)
 
     if (rd == 0 && rs1 == 0) {
         s1 = tcg_temp_new();
-        tcg_gen_mov_tl(s1, cpu_vl);
+        tcg_gen_ext_i32_tl(s1, cpu_vl);
     } else if (rs1 == 0) {
         /* As the mask is at least one bit, RV_VLEN_MAX is >= VLMAX */
         s1 = tcg_constant_tl(RV_VLEN_MAX);
@@ -1213,9 +1213,9 @@ static bool ldst_whole_trans(uint32_t vd, uint32_t rs1, uint32_t nf,
                             MO_LE | MO_64 | atomicity);
                 }
                 if (i == size - 8) {
-                    tcg_gen_movi_tl(cpu_vstart, 0);
+                    tcg_gen_movi_i32(cpu_vstart, 0);
                 } else {
-                    tcg_gen_addi_tl(cpu_vstart, cpu_vstart, 8 >> log2_esz);
+                    tcg_gen_addi_i32(cpu_vstart, cpu_vstart, 8 >> log2_esz);
                 }
             }
         } else {
@@ -1231,9 +1231,9 @@ static bool ldst_whole_trans(uint32_t vd, uint32_t rs1, uint32_t nf,
                             MO_LE | MO_32 | atomicity);
                 }
                 if (i == size - 4) {
-                    tcg_gen_movi_tl(cpu_vstart, 0);
+                    tcg_gen_movi_i32(cpu_vstart, 0);
                 } else {
-                    tcg_gen_addi_tl(cpu_vstart, cpu_vstart, 4 >> log2_esz);
+                    tcg_gen_addi_i32(cpu_vstart, cpu_vstart, 4 >> log2_esz);
                 }
             }
         }
@@ -3459,7 +3459,7 @@ static bool trans_vmv_x_s(DisasContext *s, arg_vmv_x_s *a)
         vec_element_loadi(s, t1, a->rs2, 0, true);
         tcg_gen_trunc_i64_tl(dest, t1);
         gen_set_gpr(s, a->rd, dest);
-        tcg_gen_movi_tl(cpu_vstart, 0);
+        tcg_gen_movi_i32(cpu_vstart, 0);
         finalize_rvv_inst(s);
         return true;
     }
@@ -3476,7 +3476,7 @@ static bool trans_vmv_s_x(DisasContext *s, arg_vmv_s_x *a)
         TCGv s1;
         TCGLabel *over = gen_new_label();
 
-        tcg_gen_brcond_tl(TCG_COND_GEU, cpu_vstart, cpu_vl, over);
+        tcg_gen_brcond_i32(TCG_COND_GEU, cpu_vstart, cpu_vl, over);
 
         t1 = tcg_temp_new_i64();
 
@@ -3488,7 +3488,7 @@ static bool trans_vmv_s_x(DisasContext *s, arg_vmv_s_x *a)
         tcg_gen_ext_tl_i64(t1, s1);
         vec_element_storei(s, a->rd, 0, t1);
         gen_set_label(over);
-        tcg_gen_movi_tl(cpu_vstart, 0);
+        tcg_gen_movi_i32(cpu_vstart, 0);
         finalize_rvv_inst(s);
         return true;
     }
@@ -3516,7 +3516,7 @@ static bool trans_vfmv_f_s(DisasContext *s, arg_vfmv_f_s *a)
         }
 
         mark_fs_dirty(s);
-        tcg_gen_movi_tl(cpu_vstart, 0);
+        tcg_gen_movi_i32(cpu_vstart, 0);
         finalize_rvv_inst(s);
         return true;
     }
@@ -3536,7 +3536,7 @@ static bool trans_vfmv_s_f(DisasContext *s, arg_vfmv_s_f *a)
         TCGLabel *over = gen_new_label();
 
         /* if vstart >= vl, skip vector register write back */
-        tcg_gen_brcond_tl(TCG_COND_GEU, cpu_vstart, cpu_vl, over);
+        tcg_gen_brcond_i32(TCG_COND_GEU, cpu_vstart, cpu_vl, over);
 
         /* NaN-box f[rs1] */
         t1 = tcg_temp_new_i64();
@@ -3545,7 +3545,7 @@ static bool trans_vfmv_s_f(DisasContext *s, arg_vfmv_s_f *a)
         vec_element_storei(s, a->rd, 0, t1);
 
         gen_set_label(over);
-        tcg_gen_movi_tl(cpu_vstart, 0);
+        tcg_gen_movi_i32(cpu_vstart, 0);
         finalize_rvv_inst(s);
         return true;
     }
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 11/33] target/riscv: Fix size of pc, load_[val|res]
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (9 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 10/33] target/riscv: Fix size of vector CSRs Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 19:54   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 12/33] target/riscv: Fix size of frm and fflags Anton Johansson via
                   ` (21 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Fix to 64 bits in size and as these are mapped to TCG globals, be
careful with host endianness when allocating globals.  Casts are
added to logging expressions to retain the correct size for
TARGET_RISCV32.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h        |  6 +++---
 target/riscv/cpu.c        |  3 ++-
 target/riscv/cpu_helper.c |  4 ++--
 target/riscv/machine.c    |  6 +++---
 target/riscv/translate.c  | 12 +++++++-----
 5 files changed, 17 insertions(+), 14 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index c903b4f085..e29c12c5fb 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -224,9 +224,9 @@ struct CPUArchState {
     uint8_t vxsat;
     bool vill;
 
-    target_ulong pc;
-    target_ulong load_res;
-    target_ulong load_val;
+    uint64_t pc;
+    uint64_t load_res;
+    uint64_t load_val;
 
     /* Floating-Point state */
     uint64_t fpr[32]; /* assume both F and D extensions */
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
index 3c910e44cd..4e38487dca 100644
--- a/target/riscv/cpu.c
+++ b/target/riscv/cpu.c
@@ -528,7 +528,8 @@ static void riscv_cpu_dump_state(CPUState *cs, FILE *f, int flags)
         qemu_fprintf(f, " %s %d\n", "V      =  ", env->virt_enabled);
     }
 #endif
-    qemu_fprintf(f, " %s " TARGET_FMT_lx "\n", "pc      ", env->pc);
+    qemu_fprintf(f, " %s " TARGET_FMT_lx "\n", "pc      ",
+                 (target_ulong) env->pc);
 #ifndef CONFIG_USER_ONLY
     {
         static const int dump_csrs[] = {
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
index 9d0683f200..36f7baf690 100644
--- a/target/riscv/cpu_helper.c
+++ b/target/riscv/cpu_helper.c
@@ -2280,8 +2280,8 @@ void riscv_cpu_do_interrupt(CPUState *cs)
     qemu_log_mask(CPU_LOG_INT,
                   "%s: hart:%"PRIu64", async:%d, cause:"TARGET_FMT_lx", "
                   "epc:0x"TARGET_FMT_lx", tval:0x"TARGET_FMT_lx", desc=%s\n",
-                  __func__, env->mhartid, async, cause, env->pc, tval,
-                  riscv_cpu_get_trap_name(cause, async));
+                  __func__, env->mhartid, async, cause, (target_ulong) env->pc,
+                  tval, riscv_cpu_get_trap_name(cause, async));
 
     mode = env->priv <= PRV_S && cause < 64 &&
         (((deleg >> cause) & 1) || s_injected || vs_injected) ? PRV_S : PRV_M;
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index dcf18624bf..f9f00d83ba 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -408,9 +408,9 @@ const VMStateDescription vmstate_riscv_cpu = {
         VMSTATE_UINT64_ARRAY(env.fpr, RISCVCPU, 32),
         VMSTATE_UINT8_ARRAY(env.miprio, RISCVCPU, 64),
         VMSTATE_UINT8_ARRAY(env.siprio, RISCVCPU, 64),
-        VMSTATE_UINTTL(env.pc, RISCVCPU),
-        VMSTATE_UINTTL(env.load_res, RISCVCPU),
-        VMSTATE_UINTTL(env.load_val, RISCVCPU),
+        VMSTATE_UINT64(env.pc, RISCVCPU),
+        VMSTATE_UINT64(env.load_res, RISCVCPU),
+        VMSTATE_UINT64(env.load_val, RISCVCPU),
         VMSTATE_UINTTL(env.frm, RISCVCPU),
         VMSTATE_UINTTL(env.badaddr, RISCVCPU),
         VMSTATE_UINTTL(env.guest_phys_fault_addr, RISCVCPU),
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 5e8fc3e543..b856792d3b 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -1443,6 +1443,10 @@ void riscv_translate_init(void)
     /* 32 bits in size, no offset needed */
     size_t vl_offset = offsetof(CPURISCVState, vl);
     size_t vstart_offset = offsetof(CPURISCVState, vstart);
+    /* 64 bits in size mapped to TCGv, needs offset */
+    size_t pc_offset     = offsetof(CPURISCVState, pc) + field_offset;
+    size_t res_offset    = offsetof(CPURISCVState, load_res) + field_offset;
+    size_t val_offset    = offsetof(CPURISCVState, load_val) + field_offset;
 
     for (i = 1; i < 32; i++) {
         cpu_gpr[i] = tcg_global_mem_new(tcg_env,
@@ -1458,11 +1462,9 @@ void riscv_translate_init(void)
             offsetof(CPURISCVState, fpr[i]), riscv_fpr_regnames[i]);
     }
 
-    cpu_pc = tcg_global_mem_new(tcg_env, offsetof(CPURISCVState, pc), "pc");
+    cpu_pc = tcg_global_mem_new(tcg_env, pc_offset, "pc");
     cpu_vl = tcg_global_mem_new_i32(tcg_env, vl_offset, "vl");
     cpu_vstart = tcg_global_mem_new_i32(tcg_env, vstart_offset, "vstart");
-    load_res = tcg_global_mem_new(tcg_env, offsetof(CPURISCVState, load_res),
-                             "load_res");
-    load_val = tcg_global_mem_new(tcg_env, offsetof(CPURISCVState, load_val),
-                             "load_val");
+    load_res = tcg_global_mem_new(tcg_env, res_offset, "load_res");
+    load_val = tcg_global_mem_new(tcg_env, val_offset, "load_val");
 }
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 12/33] target/riscv: Fix size of frm and fflags
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (10 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 11/33] target/riscv: Fix size of pc, load_[val|res] Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 19:57   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 13/33] target/riscv: Fix size of badaddr and bins Anton Johansson via
                   ` (20 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

According to version 20250508 of the unprivileged specification the frm
field of fcsr is 3-bits in size, fix it to 8-bits.  Similarly fflags is
5 bits, fix to 8.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h        | 6 +++---
 target/riscv/csr.c        | 4 ++++
 target/riscv/fpu_helper.c | 6 +++---
 target/riscv/machine.c    | 2 +-
 4 files changed, 11 insertions(+), 7 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index e29c12c5fb..f1875c6d99 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -230,7 +230,7 @@ struct CPUArchState {
 
     /* Floating-Point state */
     uint64_t fpr[32]; /* assume both F and D extensions */
-    target_ulong frm;
+    uint8_t frm;
     float_status fp_status;
 
     target_ulong badaddr;
@@ -663,8 +663,8 @@ G_NORETURN void riscv_raise_exception(CPURISCVState *env,
                                       RISCVException exception,
                                       uintptr_t pc);
 
-target_ulong riscv_cpu_get_fflags(CPURISCVState *env);
-void riscv_cpu_set_fflags(CPURISCVState *env, target_ulong);
+uint8_t riscv_cpu_get_fflags(CPURISCVState *env);
+void riscv_cpu_set_fflags(CPURISCVState *env, uint8_t);
 
 FIELD(TB_FLAGS, MEM_IDX, 0, 3)
 FIELD(TB_FLAGS, FS, 3, 2)
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index d660635950..1210267427 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -894,6 +894,10 @@ static RISCVException write_frm(CPURISCVState *env, int csrno,
 static RISCVException read_fcsr(CPURISCVState *env, int csrno,
                                 target_ulong *val)
 {
+    /*
+     * This is an 8-bit operation, fflags make up the lower 5 bits and
+     * frm the upper 3 bits of fcsr.
+     */
     *val = (riscv_cpu_get_fflags(env) << FSR_AEXC_SHIFT)
         | (env->frm << FSR_RD_SHIFT);
     return RISCV_EXCP_NONE;
diff --git a/target/riscv/fpu_helper.c b/target/riscv/fpu_helper.c
index af40561b31..db64fca622 100644
--- a/target/riscv/fpu_helper.c
+++ b/target/riscv/fpu_helper.c
@@ -23,10 +23,10 @@
 #include "fpu/softfloat.h"
 #include "internals.h"
 
-target_ulong riscv_cpu_get_fflags(CPURISCVState *env)
+uint8_t riscv_cpu_get_fflags(CPURISCVState *env)
 {
     int soft = get_float_exception_flags(&env->fp_status);
-    target_ulong hard = 0;
+    uint8_t hard = 0;
 
     hard |= (soft & float_flag_inexact) ? FPEXC_NX : 0;
     hard |= (soft & float_flag_underflow) ? FPEXC_UF : 0;
@@ -37,7 +37,7 @@ target_ulong riscv_cpu_get_fflags(CPURISCVState *env)
     return hard;
 }
 
-void riscv_cpu_set_fflags(CPURISCVState *env, target_ulong hard)
+void riscv_cpu_set_fflags(CPURISCVState *env, uint8_t hard)
 {
     int soft = 0;
 
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index f9f00d83ba..62d103c09e 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -411,7 +411,7 @@ const VMStateDescription vmstate_riscv_cpu = {
         VMSTATE_UINT64(env.pc, RISCVCPU),
         VMSTATE_UINT64(env.load_res, RISCVCPU),
         VMSTATE_UINT64(env.load_val, RISCVCPU),
-        VMSTATE_UINTTL(env.frm, RISCVCPU),
+        VMSTATE_UINT8(env.frm, RISCVCPU),
         VMSTATE_UINTTL(env.badaddr, RISCVCPU),
         VMSTATE_UINTTL(env.guest_phys_fault_addr, RISCVCPU),
         VMSTATE_UINTTL(env.priv_ver, RISCVCPU),
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 13/33] target/riscv: Fix size of badaddr and bins
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (11 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 12/33] target/riscv: Fix size of frm and fflags Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:02   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 14/33] target/riscv: Fix size of guest_phys_fault_addr Anton Johansson via
                   ` (19 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Fix these fields to 64 bits as they cannot be made smaller. Also make
sure stores to these fields from TCG are 64 bits in size to avoid
incorrect values on big endian hosts.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h                             | 4 ++--
 target/riscv/machine.c                         | 2 +-
 target/riscv/translate.c                       | 6 ++++--
 target/riscv/insn_trans/trans_privileged.c.inc | 2 +-
 4 files changed, 8 insertions(+), 6 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index f1875c6d99..9e3b6b6879 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -233,8 +233,8 @@ struct CPUArchState {
     uint8_t frm;
     float_status fp_status;
 
-    target_ulong badaddr;
-    target_ulong bins;
+    uint64_t badaddr;
+    uint64_t bins;
 
     target_ulong guest_phys_fault_addr;
 
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 62d103c09e..7aafe5f5dd 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -412,7 +412,7 @@ const VMStateDescription vmstate_riscv_cpu = {
         VMSTATE_UINT64(env.load_res, RISCVCPU),
         VMSTATE_UINT64(env.load_val, RISCVCPU),
         VMSTATE_UINT8(env.frm, RISCVCPU),
-        VMSTATE_UINTTL(env.badaddr, RISCVCPU),
+        VMSTATE_UINT64(env.badaddr, RISCVCPU),
         VMSTATE_UINTTL(env.guest_phys_fault_addr, RISCVCPU),
         VMSTATE_UINTTL(env.priv_ver, RISCVCPU),
         VMSTATE_UINTTL(env.vext_ver, RISCVCPU),
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index b856792d3b..339ef91f6b 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -252,7 +252,7 @@ static void generate_exception(DisasContext *ctx, RISCVException excp)
 
 static void gen_exception_illegal(DisasContext *ctx)
 {
-    tcg_gen_st_i32(tcg_constant_i32(ctx->opcode), tcg_env,
+    tcg_gen_st_i64(tcg_constant_i64(ctx->opcode), tcg_env,
                    offsetof(CPURISCVState, bins));
     if (ctx->virt_inst_excp) {
         generate_exception(ctx, RISCV_EXCP_VIRT_INSTRUCTION_FAULT);
@@ -263,7 +263,9 @@ static void gen_exception_illegal(DisasContext *ctx)
 
 static void gen_exception_inst_addr_mis(DisasContext *ctx, TCGv target)
 {
-    tcg_gen_st_tl(target, tcg_env, offsetof(CPURISCVState, badaddr));
+    TCGv_i64 ext = tcg_temp_new_i64();
+    tcg_gen_extu_tl_i64(ext, target);
+    tcg_gen_st_i64(ext, tcg_env, offsetof(CPURISCVState, badaddr));
     generate_exception(ctx, RISCV_EXCP_INST_ADDR_MIS);
 }
 
diff --git a/target/riscv/insn_trans/trans_privileged.c.inc b/target/riscv/insn_trans/trans_privileged.c.inc
index 8a62b4cfcd..a8eaccef67 100644
--- a/target/riscv/insn_trans/trans_privileged.c.inc
+++ b/target/riscv/insn_trans/trans_privileged.c.inc
@@ -68,7 +68,7 @@ static bool trans_ebreak(DisasContext *ctx, arg_ebreak *a)
     if (pre == 0x01f01013 && ebreak == 0x00100073 && post == 0x40705013) {
         generate_exception(ctx, RISCV_EXCP_SEMIHOST);
     } else {
-        tcg_gen_st_tl(tcg_constant_tl(ebreak_addr), tcg_env,
+        tcg_gen_st_i64(tcg_constant_i64(ebreak_addr), tcg_env,
                       offsetof(CPURISCVState, badaddr));
         generate_exception(ctx, RISCV_EXCP_BREAKPOINT);
     }
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 14/33] target/riscv: Fix size of guest_phys_fault_addr
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (12 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 13/33] target/riscv: Fix size of badaddr and bins Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:03   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 15/33] target/riscv: Fix size of priv_ver and vext_ver Anton Johansson via
                   ` (18 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Widen to 64 bits, and use hwaddr as argument to get_physical_address().

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h        | 2 +-
 target/riscv/cpu_helper.c | 3 +--
 target/riscv/machine.c    | 2 +-
 3 files changed, 3 insertions(+), 4 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 9e3b6b6879..fcca4dfe49 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -236,7 +236,7 @@ struct CPUArchState {
     uint64_t badaddr;
     uint64_t bins;
 
-    target_ulong guest_phys_fault_addr;
+    uint64_t guest_phys_fault_addr;
 
     target_ulong priv_ver;
     target_ulong vext_ver;
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
index 36f7baf690..c9594b8719 100644
--- a/target/riscv/cpu_helper.c
+++ b/target/riscv/cpu_helper.c
@@ -1186,7 +1186,7 @@ static bool check_svukte_addr(CPURISCVState *env, vaddr addr)
  */
 static int get_physical_address(CPURISCVState *env, hwaddr *physical,
                                 int *ret_prot, vaddr addr,
-                                target_ulong *fault_pte_addr,
+                                hwaddr *fault_pte_addr,
                                 int access_type, int mmu_idx,
                                 bool first_stage, bool two_stage,
                                 bool is_debug, bool is_probe)
@@ -1787,7 +1787,6 @@ bool riscv_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
         ret = get_physical_address(env, &pa, &prot, address,
                                    &env->guest_phys_fault_addr, access_type,
                                    mmu_idx, true, true, false, probe);
-
         /*
          * A G-stage exception may be triggered during two state lookup.
          * And the env->guest_phys_fault_addr has already been set in
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 7aafe5f5dd..1bac57a60b 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -413,7 +413,7 @@ const VMStateDescription vmstate_riscv_cpu = {
         VMSTATE_UINT64(env.load_val, RISCVCPU),
         VMSTATE_UINT8(env.frm, RISCVCPU),
         VMSTATE_UINT64(env.badaddr, RISCVCPU),
-        VMSTATE_UINTTL(env.guest_phys_fault_addr, RISCVCPU),
+        VMSTATE_UINT64(env.guest_phys_fault_addr, RISCVCPU),
         VMSTATE_UINTTL(env.priv_ver, RISCVCPU),
         VMSTATE_UINTTL(env.vext_ver, RISCVCPU),
         VMSTATE_UINT32(env.misa_mxl, RISCVCPU),
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 15/33] target/riscv: Fix size of priv_ver and vext_ver
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (13 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 14/33] target/riscv: Fix size of guest_phys_fault_addr Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:03   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 16/33] target/riscv: Fix size of retxh Anton Johansson via
                   ` (17 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Fix these fields to 32 bits, also update corresponding priv_ver field
in DisasContext as well as function arguments. 32 bits was chosen
since it's large enough to fit all stored values and int/int32_t is
used in RISCVCPUDef and a few functions.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h       | 6 +++---
 target/riscv/machine.c   | 4 ++--
 target/riscv/translate.c | 2 +-
 3 files changed, 6 insertions(+), 6 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index fcca4dfe49..83d516e510 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -238,8 +238,8 @@ struct CPUArchState {
 
     uint64_t guest_phys_fault_addr;
 
-    target_ulong priv_ver;
-    target_ulong vext_ver;
+    uint32_t priv_ver;
+    uint32_t vext_ver;
 
     /* RISCVMXL, but uint32_t for vmstate migration */
     uint32_t misa_mxl;      /* current mxl */
@@ -798,7 +798,7 @@ static inline RISCVMXL riscv_cpu_sxl(CPURISCVState *env)
 #endif
 
 static inline bool riscv_cpu_allow_16bit_insn(const RISCVCPUConfig *cfg,
-                                              target_long priv_ver,
+                                              uint32_t priv_ver,
                                               uint32_t misa_ext)
 {
     /* In priv spec version 1.12 or newer, C always implies Zca */
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 1bac57a60b..f1a0d16fdd 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -414,8 +414,8 @@ const VMStateDescription vmstate_riscv_cpu = {
         VMSTATE_UINT8(env.frm, RISCVCPU),
         VMSTATE_UINT64(env.badaddr, RISCVCPU),
         VMSTATE_UINT64(env.guest_phys_fault_addr, RISCVCPU),
-        VMSTATE_UINTTL(env.priv_ver, RISCVCPU),
-        VMSTATE_UINTTL(env.vext_ver, RISCVCPU),
+        VMSTATE_UINT32(env.priv_ver, RISCVCPU),
+        VMSTATE_UINT32(env.vext_ver, RISCVCPU),
         VMSTATE_UINT32(env.misa_mxl, RISCVCPU),
         VMSTATE_UINT32(env.misa_ext, RISCVCPU),
         VMSTATE_UNUSED(4),
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 339ef91f6b..10d39fd42a 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -59,7 +59,7 @@ typedef struct DisasContext {
     DisasContextBase base;
     target_ulong cur_insn_len;
     target_ulong pc_save;
-    target_ulong priv_ver;
+    uint32_t priv_ver;
     RISCVMXL misa_mxl_max;
     RISCVMXL xl;
     RISCVMXL address_xl;
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 16/33] target/riscv: Fix size of retxh
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (14 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 15/33] target/riscv: Fix size of priv_ver and vext_ver Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:05   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 17/33] target/riscv: Fix size of ssp Anton Johansson via
                   ` (16 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

128-bit helpers only make sense for MXL_RV128, TARGET_RISCV64,
and TCGv == TCGv_i64, therefore fix retxh to 64 bits.

For the sake of being pedandic, update 128-bit instructions to access
retxh via 64 bit TCG ops, even if they only make sense when TCGv ==
TCGv_i64.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h                      |  2 +-
 target/riscv/insn_trans/trans_rvi.c.inc |  8 ++++++--
 target/riscv/insn_trans/trans_rvm.c.inc | 16 ++++++++++++----
 3 files changed, 19 insertions(+), 7 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 83d516e510..c2fd7368c4 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -248,7 +248,7 @@ struct CPUArchState {
     uint32_t xl;            /* current xlen */
 
     /* 128-bit helpers upper part return value */
-    target_ulong retxh;
+    uint64_t retxh;
 
     uint64_t jvt;
 
diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
index b9c7160468..9c8c04b2dc 100644
--- a/target/riscv/insn_trans/trans_rvi.c.inc
+++ b/target/riscv/insn_trans/trans_rvi.c.inc
@@ -1012,10 +1012,12 @@ static bool do_csrr_i128(DisasContext *ctx, int rd, int rc)
     TCGv destl = dest_gpr(ctx, rd);
     TCGv desth = dest_gprh(ctx, rd);
     TCGv_i32 csr = tcg_constant_i32(rc);
+    TCGv_i64 wide_desth = tcg_temp_new_i64();
 
     translator_io_start(&ctx->base);
     gen_helper_csrr_i128(destl, tcg_env, csr);
-    tcg_gen_ld_tl(desth, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_ld_i64(wide_desth, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_trunc_i64_tl(desth, wide_desth);
     gen_set_gpr128(ctx, rd, destl, desth);
     return do_csr_post(ctx);
 }
@@ -1035,10 +1037,12 @@ static bool do_csrrw_i128(DisasContext *ctx, int rd, int rc,
     TCGv destl = dest_gpr(ctx, rd);
     TCGv desth = dest_gprh(ctx, rd);
     TCGv_i32 csr = tcg_constant_i32(rc);
+    TCGv_i64 wide_desth = tcg_temp_new_i64();
 
     translator_io_start(&ctx->base);
     gen_helper_csrrw_i128(destl, tcg_env, csr, srcl, srch, maskl, maskh);
-    tcg_gen_ld_tl(desth, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_ld_i64(wide_desth, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_trunc_i64_tl(desth, wide_desth);
     gen_set_gpr128(ctx, rd, destl, desth);
     return do_csr_post(ctx);
 }
diff --git a/target/riscv/insn_trans/trans_rvm.c.inc b/target/riscv/insn_trans/trans_rvm.c.inc
index 795f0ccf14..0e2da5bed2 100644
--- a/target/riscv/insn_trans/trans_rvm.c.inc
+++ b/target/riscv/insn_trans/trans_rvm.c.inc
@@ -169,8 +169,10 @@ static bool trans_mulhu(DisasContext *ctx, arg_mulhu *a)
 static void gen_div_i128(TCGv rdl, TCGv rdh,
                          TCGv rs1l, TCGv rs1h, TCGv rs2l, TCGv rs2h)
 {
+    TCGv_i64 wide_rdh = tcg_temp_new_i64();
     gen_helper_divs_i128(rdl, tcg_env, rs1l, rs1h, rs2l, rs2h);
-    tcg_gen_ld_tl(rdh, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_ld_i64(wide_rdh, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_trunc_i64_tl(rdh, wide_rdh);
 }
 
 static void gen_div(TCGv ret, TCGv source1, TCGv source2)
@@ -212,8 +214,10 @@ static bool trans_div(DisasContext *ctx, arg_div *a)
 static void gen_divu_i128(TCGv rdl, TCGv rdh,
                           TCGv rs1l, TCGv rs1h, TCGv rs2l, TCGv rs2h)
 {
+    TCGv_i64 wide_rdh = tcg_temp_new_i64();
     gen_helper_divu_i128(rdl, tcg_env, rs1l, rs1h, rs2l, rs2h);
-    tcg_gen_ld_tl(rdh, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_ld_i64(wide_rdh, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_trunc_i64_tl(rdh, wide_rdh);
 }
 
 static void gen_divu(TCGv ret, TCGv source1, TCGv source2)
@@ -244,8 +248,10 @@ static bool trans_divu(DisasContext *ctx, arg_divu *a)
 static void gen_rem_i128(TCGv rdl, TCGv rdh,
                          TCGv rs1l, TCGv rs1h, TCGv rs2l, TCGv rs2h)
 {
+    TCGv_i64 wide_rdh = tcg_temp_new_i64();
     gen_helper_rems_i128(rdl, tcg_env, rs1l, rs1h, rs2l, rs2h);
-    tcg_gen_ld_tl(rdh, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_ld_i64(wide_rdh, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_trunc_i64_tl(rdh, wide_rdh);
 }
 
 static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
@@ -289,8 +295,10 @@ static bool trans_rem(DisasContext *ctx, arg_rem *a)
 static void gen_remu_i128(TCGv rdl, TCGv rdh,
                           TCGv rs1l, TCGv rs1h, TCGv rs2l, TCGv rs2h)
 {
+    TCGv_i64 wide_rdh = tcg_temp_new_i64();
     gen_helper_remu_i128(rdl, tcg_env, rs1l, rs1h, rs2l, rs2h);
-    tcg_gen_ld_tl(rdh, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_ld_i64(wide_rdh, tcg_env, offsetof(CPURISCVState, retxh));
+    tcg_gen_trunc_i64_tl(rdh, wide_rdh);
 }
 
 static void gen_remu(TCGv ret, TCGv source1, TCGv source2)
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 17/33] target/riscv: Fix size of ssp
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (15 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 16/33] target/riscv: Fix size of retxh Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:06   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 18/33] target/riscv: Fix size of excp_uw2 Anton Johansson via
                   ` (15 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

As ssp holds a pointer, fix to 64 bits in size and make sure stores from
TCG use the correct size to avoid problems on big endian hosts.

Note, the cpu/ssp VMSTATE version is bumped, breaking migration from
older versions.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h                            |  2 +-
 target/riscv/machine.c                        |  6 +++---
 target/riscv/insn_trans/trans_rvzicfiss.c.inc | 18 +++++++++++++-----
 3 files changed, 17 insertions(+), 9 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index c2fd7368c4..d78af5e053 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -255,7 +255,7 @@ struct CPUArchState {
     /* elp state for zicfilp extension */
     bool      elp;
     /* shadow stack register for zicfiss extension */
-    target_ulong ssp;
+    uint64_t ssp;
     /* env place holder for extra word 2 during unwind */
     target_ulong excp_uw2;
     /* sw check code for sw check exception */
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index f1a0d16fdd..aacd4f52b0 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -389,11 +389,11 @@ static bool ssp_needed(void *opaque)
 
 static const VMStateDescription vmstate_ssp = {
     .name = "cpu/ssp",
-    .version_id = 1,
-    .minimum_version_id = 1,
+    .version_id = 2,
+    .minimum_version_id = 2,
     .needed = ssp_needed,
     .fields = (const VMStateField[]) {
-        VMSTATE_UINTTL(env.ssp, RISCVCPU),
+        VMSTATE_UINT64(env.ssp, RISCVCPU),
         VMSTATE_END_OF_LIST()
     }
 };
diff --git a/target/riscv/insn_trans/trans_rvzicfiss.c.inc b/target/riscv/insn_trans/trans_rvzicfiss.c.inc
index b0096adcd0..4333854979 100644
--- a/target/riscv/insn_trans/trans_rvzicfiss.c.inc
+++ b/target/riscv/insn_trans/trans_rvzicfiss.c.inc
@@ -32,7 +32,9 @@ static bool trans_sspopchk(DisasContext *ctx, arg_sspopchk *a)
     TCGLabel *skip = gen_new_label();
     uint32_t tmp = (get_xl(ctx) == MXL_RV64) ? 8 : 4;
     TCGv data = tcg_temp_new();
-    tcg_gen_ld_tl(addr, tcg_env, offsetof(CPURISCVState, ssp));
+    TCGv_i64 wide_addr = tcg_temp_new_i64();
+    tcg_gen_ld_i64(wide_addr, tcg_env, offsetof(CPURISCVState, ssp));
+    tcg_gen_trunc_i64_tl(addr, wide_addr);
     decode_save_opc(ctx, RISCV_UW2_ALWAYS_STORE_AMO);
     tcg_gen_qemu_ld_tl(data, addr, SS_MMU_INDEX(ctx),
                        mxl_memop(ctx) | MO_ALIGN);
@@ -44,7 +46,8 @@ static bool trans_sspopchk(DisasContext *ctx, arg_sspopchk *a)
                   tcg_constant_i32(RISCV_EXCP_SW_CHECK));
     gen_set_label(skip);
     tcg_gen_addi_tl(addr, addr, tmp);
-    tcg_gen_st_tl(addr, tcg_env, offsetof(CPURISCVState, ssp));
+    tcg_gen_ext_tl_i64(wide_addr, addr);
+    tcg_gen_st_i64(wide_addr, tcg_env, offsetof(CPURISCVState, ssp));
 
     return true;
 }
@@ -58,12 +61,15 @@ static bool trans_sspush(DisasContext *ctx, arg_sspush *a)
     TCGv addr = tcg_temp_new();
     int tmp = (get_xl(ctx) == MXL_RV64) ? -8 : -4;
     TCGv data = get_gpr(ctx, a->rs2, EXT_NONE);
+    TCGv_i64 wide_addr = tcg_temp_new_i64();
     decode_save_opc(ctx, RISCV_UW2_ALWAYS_STORE_AMO);
-    tcg_gen_ld_tl(addr, tcg_env, offsetof(CPURISCVState, ssp));
+    tcg_gen_ld_i64(wide_addr, tcg_env, offsetof(CPURISCVState, ssp));
+    tcg_gen_trunc_i64_tl(addr, wide_addr);
     tcg_gen_addi_tl(addr, addr, tmp);
     tcg_gen_qemu_st_tl(data, addr, SS_MMU_INDEX(ctx),
                        mxl_memop(ctx) | MO_ALIGN);
-    tcg_gen_st_tl(addr, tcg_env, offsetof(CPURISCVState, ssp));
+    tcg_gen_ext_tl_i64(wide_addr, addr);
+    tcg_gen_st_i64(wide_addr, tcg_env, offsetof(CPURISCVState, ssp));
 
     return true;
 }
@@ -75,7 +81,9 @@ static bool trans_ssrdp(DisasContext *ctx, arg_ssrdp *a)
     }
 
     TCGv dest = dest_gpr(ctx, a->rd);
-    tcg_gen_ld_tl(dest, tcg_env, offsetof(CPURISCVState, ssp));
+    TCGv_i64 wide_addr = tcg_temp_new_i64();
+    tcg_gen_ld_i64(wide_addr, tcg_env, offsetof(CPURISCVState, ssp));
+    tcg_gen_trunc_i64_tl(dest, wide_addr);
     gen_set_gpr(ctx, a->rd, dest);
 
     return true;
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 18/33] target/riscv: Fix size of excp_uw2
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (16 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 17/33] target/riscv: Fix size of ssp Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:06   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 19/33] target/riscv: Fix size of sw_check_code Anton Johansson via
                   ` (14 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Fix to 64 bits to match size of instruction start words.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index d78af5e053..8c98e8c833 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -257,7 +257,7 @@ struct CPUArchState {
     /* shadow stack register for zicfiss extension */
     uint64_t ssp;
     /* env place holder for extra word 2 during unwind */
-    target_ulong excp_uw2;
+    uint64_t excp_uw2;
     /* sw check code for sw check exception */
     target_ulong sw_check_code;
 #ifdef CONFIG_USER_ONLY
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 19/33] target/riscv: Fix size of sw_check_code
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (17 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 18/33] target/riscv: Fix size of excp_uw2 Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:07   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 20/33] target/riscv: Fix size of priv Anton Johansson via
                   ` (13 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

The field only holds values of 2 and 3, fix its size to 8 bits and
update stores from TCG.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h                            | 2 +-
 target/riscv/translate.c                      | 4 ++--
 target/riscv/insn_trans/trans_rvi.c.inc       | 8 ++++----
 target/riscv/insn_trans/trans_rvzicfiss.c.inc | 4 ++--
 4 files changed, 9 insertions(+), 9 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 8c98e8c833..586b8731b2 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -259,7 +259,7 @@ struct CPUArchState {
     /* env place holder for extra word 2 during unwind */
     uint64_t excp_uw2;
     /* sw check code for sw check exception */
-    target_ulong sw_check_code;
+    uint8_t sw_check_code;
 #ifdef CONFIG_USER_ONLY
     uint32_t elf_flags;
 #endif
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 10d39fd42a..5c42271c30 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -1361,8 +1361,8 @@ static void riscv_tr_translate_insn(DisasContextBase *dcbase, CPUState *cpu)
     if (ctx->fcfi_lp_expected) {
         /* Emit after insn_start, i.e. before the op following insn_start. */
         tcg_ctx->emit_before_op = QTAILQ_NEXT(ctx->base.insn_start, link);
-        tcg_gen_st_tl(tcg_constant_tl(RISCV_EXCP_SW_CHECK_FCFI_TVAL),
-                      tcg_env, offsetof(CPURISCVState, sw_check_code));
+        tcg_gen_st8_i32(tcg_constant_i32(RISCV_EXCP_SW_CHECK_FCFI_TVAL),
+                        tcg_env, offsetof(CPURISCVState, sw_check_code));
         gen_helper_raise_exception(tcg_env,
                       tcg_constant_i32(RISCV_EXCP_SW_CHECK));
         tcg_ctx->emit_before_op = NULL;
diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
index 9c8c04b2dc..5efdd95f97 100644
--- a/target/riscv/insn_trans/trans_rvi.c.inc
+++ b/target/riscv/insn_trans/trans_rvi.c.inc
@@ -53,8 +53,8 @@ static bool trans_lpad(DisasContext *ctx, arg_lpad *a)
         /*
          * misaligned, according to spec we should raise sw check exception
          */
-        tcg_gen_st_tl(tcg_constant_tl(RISCV_EXCP_SW_CHECK_FCFI_TVAL),
-                      tcg_env, offsetof(CPURISCVState, sw_check_code));
+        tcg_gen_st8_i32(tcg_constant_i32(RISCV_EXCP_SW_CHECK_FCFI_TVAL),
+                        tcg_env, offsetof(CPURISCVState, sw_check_code));
         gen_helper_raise_exception(tcg_env,
                       tcg_constant_i32(RISCV_EXCP_SW_CHECK));
         return true;
@@ -66,8 +66,8 @@ static bool trans_lpad(DisasContext *ctx, arg_lpad *a)
         TCGv tmp = tcg_temp_new();
         tcg_gen_extract_tl(tmp, get_gpr(ctx, xT2, EXT_NONE), 12, 20);
         tcg_gen_brcondi_tl(TCG_COND_EQ, tmp, a->label, skip);
-        tcg_gen_st_tl(tcg_constant_tl(RISCV_EXCP_SW_CHECK_FCFI_TVAL),
-                      tcg_env, offsetof(CPURISCVState, sw_check_code));
+        tcg_gen_st8_i32(tcg_constant_i32(RISCV_EXCP_SW_CHECK_FCFI_TVAL),
+                        tcg_env, offsetof(CPURISCVState, sw_check_code));
         gen_helper_raise_exception(tcg_env,
                       tcg_constant_i32(RISCV_EXCP_SW_CHECK));
         gen_set_label(skip);
diff --git a/target/riscv/insn_trans/trans_rvzicfiss.c.inc b/target/riscv/insn_trans/trans_rvzicfiss.c.inc
index 4333854979..0827c97e31 100644
--- a/target/riscv/insn_trans/trans_rvzicfiss.c.inc
+++ b/target/riscv/insn_trans/trans_rvzicfiss.c.inc
@@ -40,8 +40,8 @@ static bool trans_sspopchk(DisasContext *ctx, arg_sspopchk *a)
                        mxl_memop(ctx) | MO_ALIGN);
     TCGv rs1 = get_gpr(ctx, a->rs1, EXT_NONE);
     tcg_gen_brcond_tl(TCG_COND_EQ, data, rs1, skip);
-    tcg_gen_st_tl(tcg_constant_tl(RISCV_EXCP_SW_CHECK_BCFI_TVAL),
-                  tcg_env, offsetof(CPURISCVState, sw_check_code));
+    tcg_gen_st8_i32(tcg_constant_i32(RISCV_EXCP_SW_CHECK_BCFI_TVAL),
+                    tcg_env, offsetof(CPURISCVState, sw_check_code));
     gen_helper_raise_exception(tcg_env,
                   tcg_constant_i32(RISCV_EXCP_SW_CHECK));
     gen_set_label(skip);
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 20/33] target/riscv: Fix size of priv
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (18 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 19/33] target/riscv: Fix size of sw_check_code Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:07   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 21/33] target/riscv: Fix size of gei fields Anton Johansson via
                   ` (12 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

The priv field of CPUArchState only stores values in the range [0,3],
fix to 8 bits in size and update relevant function arguments.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h        |  8 ++++----
 target/riscv/cpu_helper.c | 10 +++++-----
 target/riscv/machine.c    |  2 +-
 3 files changed, 10 insertions(+), 10 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 586b8731b2..0d2ea645e4 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -264,7 +264,7 @@ struct CPUArchState {
     uint32_t elf_flags;
 #endif
 
-    target_ulong priv;
+    uint8_t priv;
     /* CSRs for execution environment configuration */
     uint64_t menvcfg;
     uint64_t senvcfg;
@@ -649,10 +649,10 @@ void riscv_cpu_set_aia_ireg_rmw_fn(CPURISCVState *env, uint32_t priv,
 RISCVException smstateen_acc_ok(CPURISCVState *env, int index, uint64_t bit);
 #endif /* !CONFIG_USER_ONLY */
 
-void riscv_cpu_set_mode(CPURISCVState *env, target_ulong newpriv, bool virt_en);
+void riscv_cpu_set_mode(CPURISCVState *env, uint8_t newpriv, bool virt_en);
 
 void riscv_ctr_add_entry(CPURISCVState *env, target_long src, target_long dst,
-    enum CTRType type, target_ulong prev_priv, bool prev_virt);
+    enum CTRType type, uint8_t prev_priv, bool prev_virt);
 void riscv_ctr_clear(CPURISCVState *env);
 
 void riscv_translate_init(void);
@@ -723,7 +723,7 @@ static inline int cpu_address_mode(CPURISCVState *env)
     return mode;
 }
 
-static inline RISCVMXL cpu_get_xl(CPURISCVState *env, target_ulong mode)
+static inline RISCVMXL cpu_get_xl(CPURISCVState *env, uint8_t mode)
 {
     RISCVMXL xl = env->misa_mxl;
     /*
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
index c9594b8719..a57f33b3cb 100644
--- a/target/riscv/cpu_helper.c
+++ b/target/riscv/cpu_helper.c
@@ -799,7 +799,7 @@ void riscv_ctr_clear(CPURISCVState *env)
     memset(env->ctr_data, 0x0, sizeof(env->ctr_data));
 }
 
-static uint64_t riscv_ctr_priv_to_mask(target_ulong priv, bool virt)
+static uint64_t riscv_ctr_priv_to_mask(uint8_t priv, bool virt)
 {
     switch (priv) {
     case PRV_M:
@@ -819,7 +819,7 @@ static uint64_t riscv_ctr_priv_to_mask(target_ulong priv, bool virt)
     g_assert_not_reached();
 }
 
-static uint64_t riscv_ctr_get_control(CPURISCVState *env, target_long priv,
+static uint64_t riscv_ctr_get_control(CPURISCVState *env, uint8_t priv,
                                       bool virt)
 {
     switch (priv) {
@@ -841,7 +841,7 @@ static uint64_t riscv_ctr_get_control(CPURISCVState *env, target_long priv,
  * and src privilege is less than target privilege. This includes the virtual
  * state as well.
  */
-static bool riscv_ctr_check_xte(CPURISCVState *env, target_long src_prv,
+static bool riscv_ctr_check_xte(CPURISCVState *env, uint8_t src_prv,
                                 bool src_virt)
 {
     target_long tgt_prv = env->priv;
@@ -930,7 +930,7 @@ static bool riscv_ctr_check_xte(CPURISCVState *env, target_long src_prv,
  *    idx = (sctrstatus.WRPTR - entry - 1) & (depth - 1);
  */
 void riscv_ctr_add_entry(CPURISCVState *env, target_long src, target_long dst,
-    enum CTRType type, target_ulong src_priv, bool src_virt)
+    enum CTRType type, uint8_t src_priv, bool src_virt)
 {
     bool tgt_virt = env->virt_enabled;
     uint64_t src_mask = riscv_ctr_priv_to_mask(src_priv, src_virt);
@@ -1028,7 +1028,7 @@ void riscv_ctr_add_entry(CPURISCVState *env, target_long src, target_long dst,
     env->sctrstatus = set_field(env->sctrstatus, SCTRSTATUS_WRPTR_MASK, head);
 }
 
-void riscv_cpu_set_mode(CPURISCVState *env, target_ulong newpriv, bool virt_en)
+void riscv_cpu_set_mode(CPURISCVState *env, uint8_t newpriv, bool virt_en)
 {
     g_assert(newpriv <= PRV_M && newpriv != PRV_RESERVED);
 
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index aacd4f52b0..615e1dd94c 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -420,7 +420,7 @@ const VMStateDescription vmstate_riscv_cpu = {
         VMSTATE_UINT32(env.misa_ext, RISCVCPU),
         VMSTATE_UNUSED(4),
         VMSTATE_UINT32(env.misa_ext_mask, RISCVCPU),
-        VMSTATE_UINTTL(env.priv, RISCVCPU),
+        VMSTATE_UINT8(env.priv, RISCVCPU),
         VMSTATE_BOOL(env.virt_enabled, RISCVCPU),
         VMSTATE_UINT64(env.resetvec, RISCVCPU),
         VMSTATE_UINT64(env.mhartid, RISCVCPU),
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 21/33] target/riscv: Fix size of gei fields
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (19 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 20/33] target/riscv: Fix size of priv Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:08   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 22/33] target/riscv: Fix size of [m|s|vs]iselect fields Anton Johansson via
                   ` (11 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

geilen takes the values 31 or 63, fix it to 8 bits. hgeie and hgeip are
at most 64 bits in size, fix to 64.  Update relevant function arguments.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h        | 10 +++++-----
 target/riscv/cpu_helper.c |  4 ++--
 target/riscv/machine.c    |  4 ++--
 3 files changed, 9 insertions(+), 9 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 0d2ea645e4..2adeb3897a 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -272,7 +272,7 @@ struct CPUArchState {
 #ifndef CONFIG_USER_ONLY
     /* This contains QEMU specific information about the virt state. */
     bool virt_enabled;
-    target_ulong geilen;
+    uint8_t geilen;
     uint64_t resetvec;
 
     uint64_t mhartid;
@@ -349,8 +349,8 @@ struct CPUArchState {
     uint64_t htval;
     uint64_t htinst;
     uint64_t hgatp;
-    target_ulong hgeie;
-    target_ulong hgeip;
+    uint64_t hgeie;
+    uint64_t hgeip;
     uint64_t htimedelta;
     uint64_t hvien;
 
@@ -601,8 +601,8 @@ int riscv_cpu_mirq_pending(CPURISCVState *env);
 int riscv_cpu_sirq_pending(CPURISCVState *env);
 int riscv_cpu_vsirq_pending(CPURISCVState *env);
 bool riscv_cpu_fp_enabled(CPURISCVState *env);
-target_ulong riscv_cpu_get_geilen(CPURISCVState *env);
-void riscv_cpu_set_geilen(CPURISCVState *env, target_ulong geilen);
+uint8_t riscv_cpu_get_geilen(CPURISCVState *env);
+void riscv_cpu_set_geilen(CPURISCVState *env, uint8_t geilen);
 bool riscv_cpu_vector_enabled(CPURISCVState *env);
 void riscv_cpu_set_virt_enabled(CPURISCVState *env, bool enable);
 int riscv_env_mmu_index(CPURISCVState *env, bool ifetch);
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
index a57f33b3cb..c5e94359e4 100644
--- a/target/riscv/cpu_helper.c
+++ b/target/riscv/cpu_helper.c
@@ -662,7 +662,7 @@ void riscv_cpu_swap_hypervisor_regs(CPURISCVState *env)
     }
 }
 
-target_ulong riscv_cpu_get_geilen(CPURISCVState *env)
+uint8_t riscv_cpu_get_geilen(CPURISCVState *env)
 {
     if (!riscv_has_ext(env, RVH)) {
         return 0;
@@ -671,7 +671,7 @@ target_ulong riscv_cpu_get_geilen(CPURISCVState *env)
     return env->geilen;
 }
 
-void riscv_cpu_set_geilen(CPURISCVState *env, target_ulong geilen)
+void riscv_cpu_set_geilen(CPURISCVState *env, uint8_t geilen)
 {
     if (!riscv_has_ext(env, RVH)) {
         return;
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 615e1dd94c..08580c862d 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -91,8 +91,8 @@ static const VMStateDescription vmstate_hyper = {
         VMSTATE_UINT64(env.htval, RISCVCPU),
         VMSTATE_UINT64(env.htinst, RISCVCPU),
         VMSTATE_UINT64(env.hgatp, RISCVCPU),
-        VMSTATE_UINTTL(env.hgeie, RISCVCPU),
-        VMSTATE_UINTTL(env.hgeip, RISCVCPU),
+        VMSTATE_UINT64(env.hgeie, RISCVCPU),
+        VMSTATE_UINT64(env.hgeip, RISCVCPU),
         VMSTATE_UINT64(env.hvien, RISCVCPU),
         VMSTATE_UINT64(env.hvip, RISCVCPU),
         VMSTATE_UINT64(env.htimedelta, RISCVCPU),
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 22/33] target/riscv: Fix size of [m|s|vs]iselect fields
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (20 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 21/33] target/riscv: Fix size of gei fields Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:09   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 23/33] target/riscv: Fix arguments to board IMSIC emulation callbacks Anton Johansson via
                   ` (10 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

[m|s|vs]iselect are defined in version 20250508 of the privileged
specification to be XLEN in size, however QEMU only ever uses at most
16 bits of these fields, so fix them to 16.  Update relevant function
arguments.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h     |  6 +++---
 target/riscv/csr.c     | 32 ++++++++++++++++----------------
 target/riscv/machine.c |  6 +++---
 3 files changed, 22 insertions(+), 22 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 2adeb3897a..119392b4b0 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -336,8 +336,8 @@ struct CPUArchState {
     uint8_t siprio[64];
 
     /* AIA CSRs */
-    target_ulong miselect;
-    target_ulong siselect;
+    uint16_t miselect;
+    uint16_t siselect;
     uint64_t mvien;
     uint64_t mvip;
 
@@ -383,7 +383,7 @@ struct CPUArchState {
     uint64_t vsatp;
 
     /* AIA VS-mode CSRs */
-    target_ulong vsiselect;
+    uint16_t vsiselect;
 
     uint64_t mtval2;
     uint64_t mtinst;
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 1210267427..fed689fe30 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -2400,7 +2400,7 @@ static RISCVException rmw_xiselect(CPURISCVState *env, int csrno,
                                    target_ulong *val, target_ulong new_val,
                                    target_ulong wr_mask)
 {
-    target_ulong *iselect;
+    uint16_t *iselect;
     int ret;
 
     ret = smstateen_acc_ok(env, 0, SMSTATEEN0_SVSLCT);
@@ -2443,18 +2443,18 @@ static RISCVException rmw_xiselect(CPURISCVState *env, int csrno,
     return RISCV_EXCP_NONE;
 }
 
-static bool xiselect_aia_range(target_ulong isel)
+static bool xiselect_aia_range(uint16_t isel)
 {
     return (ISELECT_IPRIO0 <= isel && isel <= ISELECT_IPRIO15) ||
            (ISELECT_IMSIC_FIRST <= isel && isel <= ISELECT_IMSIC_LAST);
 }
 
-static bool xiselect_cd_range(target_ulong isel)
+static bool xiselect_cd_range(uint16_t isel)
 {
     return (ISELECT_CD_FIRST <= isel && isel <= ISELECT_CD_LAST);
 }
 
-static bool xiselect_ctr_range(int csrno, target_ulong isel)
+static bool xiselect_ctr_range(int csrno, uint16_t isel)
 {
     /* MIREG-MIREG6 for the range 0x200-0x2ff are not used by CTR. */
     return CTR_ENTRIES_FIRST <= isel && isel <= CTR_ENTRIES_LAST &&
@@ -2462,7 +2462,7 @@ static bool xiselect_ctr_range(int csrno, target_ulong isel)
 }
 
 static int rmw_iprio(target_ulong xlen,
-                     target_ulong iselect, uint8_t *iprio,
+                     uint16_t iselect, uint8_t *iprio,
                      target_ulong *val, target_ulong new_val,
                      target_ulong wr_mask, int ext_irq_no)
 {
@@ -2506,7 +2506,7 @@ static int rmw_iprio(target_ulong xlen,
     return 0;
 }
 
-static int rmw_ctrsource(CPURISCVState *env, int isel, target_ulong *val,
+static int rmw_ctrsource(CPURISCVState *env, uint16_t isel, target_ulong *val,
                           target_ulong new_val, target_ulong wr_mask)
 {
     /*
@@ -2545,7 +2545,7 @@ static int rmw_ctrsource(CPURISCVState *env, int isel, target_ulong *val,
     return 0;
 }
 
-static int rmw_ctrtarget(CPURISCVState *env, int isel, target_ulong *val,
+static int rmw_ctrtarget(CPURISCVState *env, uint16_t isel, target_ulong *val,
                           target_ulong new_val, target_ulong wr_mask)
 {
     /*
@@ -2584,7 +2584,7 @@ static int rmw_ctrtarget(CPURISCVState *env, int isel, target_ulong *val,
     return 0;
 }
 
-static int rmw_ctrdata(CPURISCVState *env, int isel, target_ulong *val,
+static int rmw_ctrdata(CPURISCVState *env, uint16_t isel, target_ulong *val,
                         target_ulong new_val, target_ulong wr_mask)
 {
     /*
@@ -2625,7 +2625,7 @@ static int rmw_ctrdata(CPURISCVState *env, int isel, target_ulong *val,
 }
 
 static RISCVException rmw_xireg_aia(CPURISCVState *env, int csrno,
-                         target_ulong isel, target_ulong *val,
+                         uint16_t isel, target_ulong *val,
                          target_ulong new_val, target_ulong wr_mask)
 {
     bool virt = false, isel_reserved = false;
@@ -2705,12 +2705,12 @@ done:
 }
 
 static int rmw_xireg_cd(CPURISCVState *env, int csrno,
-                        target_ulong isel, target_ulong *val,
+                        uint16_t isel, target_ulong *val,
                         target_ulong new_val, target_ulong wr_mask)
 {
     int ret = -EINVAL;
-    int ctr_index = isel - ISELECT_CD_FIRST;
-    int isel_hpm_start = ISELECT_CD_FIRST + 3;
+    uint16_t ctr_index = isel - ISELECT_CD_FIRST;
+    uint16_t isel_hpm_start = ISELECT_CD_FIRST + 3;
 
     if (!riscv_cpu_cfg(env)->ext_smcdeleg || !riscv_cpu_cfg(env)->ext_ssccfg) {
         ret = RISCV_EXCP_ILLEGAL_INST;
@@ -2777,7 +2777,7 @@ done:
 }
 
 static int rmw_xireg_ctr(CPURISCVState *env, int csrno,
-                        target_ulong isel, target_ulong *val,
+                        uint16_t isel, target_ulong *val,
                         target_ulong new_val, target_ulong wr_mask)
 {
     if (!riscv_cpu_cfg(env)->ext_smctr && !riscv_cpu_cfg(env)->ext_ssctr) {
@@ -2805,7 +2805,7 @@ static int rmw_xireg_ctr(CPURISCVState *env, int csrno,
  * extension using csrind should be implemented here.
  */
 static int rmw_xireg_csrind(CPURISCVState *env, int csrno,
-                              target_ulong isel, target_ulong *val,
+                              uint16_t isel, target_ulong *val,
                               target_ulong new_val, target_ulong wr_mask)
 {
     bool virt = csrno == CSR_VSIREG ? true : false;
@@ -2835,7 +2835,7 @@ static int rmw_xiregi(CPURISCVState *env, int csrno, target_ulong *val,
                       target_ulong new_val, target_ulong wr_mask)
 {
     int ret = -EINVAL;
-    target_ulong isel;
+    uint16_t isel;
 
     ret = smstateen_acc_ok(env, 0, SMSTATEEN0_SVSLCT);
     if (ret != RISCV_EXCP_NONE) {
@@ -2866,7 +2866,7 @@ static RISCVException rmw_xireg(CPURISCVState *env, int csrno,
                                 target_ulong wr_mask)
 {
     int ret = -EINVAL;
-    target_ulong isel;
+    uint16_t isel;
 
     ret = smstateen_acc_ok(env, 0, SMSTATEEN0_SVSLCT);
     if (ret != RISCV_EXCP_NONE) {
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 08580c862d..18dbc1bfa9 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -108,7 +108,7 @@ static const VMStateDescription vmstate_hyper = {
         VMSTATE_UINT64(env.vscause, RISCVCPU),
         VMSTATE_UINT64(env.vstval, RISCVCPU),
         VMSTATE_UINT64(env.vsatp, RISCVCPU),
-        VMSTATE_UINTTL(env.vsiselect, RISCVCPU),
+        VMSTATE_UINT16(env.vsiselect, RISCVCPU),
         VMSTATE_UINT64(env.vsie, RISCVCPU),
 
         VMSTATE_UINT64(env.mtval2, RISCVCPU),
@@ -442,8 +442,8 @@ const VMStateDescription vmstate_riscv_cpu = {
         VMSTATE_UINT64(env.mepc, RISCVCPU),
         VMSTATE_UINT64(env.mcause, RISCVCPU),
         VMSTATE_UINT64(env.mtval, RISCVCPU),
-        VMSTATE_UINTTL(env.miselect, RISCVCPU),
-        VMSTATE_UINTTL(env.siselect, RISCVCPU),
+        VMSTATE_UINT16(env.miselect, RISCVCPU),
+        VMSTATE_UINT16(env.siselect, RISCVCPU),
         VMSTATE_UINT32(env.scounteren, RISCVCPU),
         VMSTATE_UINT32(env.mcounteren, RISCVCPU),
         VMSTATE_UINT32(env.scountinhibit, RISCVCPU),
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 23/33] target/riscv: Fix arguments to board IMSIC emulation callbacks
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (21 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 22/33] target/riscv: Fix size of [m|s|vs]iselect fields Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:15   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 24/33] target/riscv: Fix size of irq_overflow_left Anton Johansson via
                   ` (9 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

In hw/ the relevant RISCVIMSICState fields
eidelivery, eithreshold, eistate are uint32_t.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h        | 42 ++++++++++++++++++++-------------------
 hw/intc/riscv_imsic.c     | 34 +++++++++++++++----------------
 target/riscv/cpu_helper.c | 12 ++++-------
 target/riscv/csr.c        | 24 ++++++++++++----------
 4 files changed, 57 insertions(+), 55 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 119392b4b0..5485d3e35f 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -193,6 +193,24 @@ FIELD(VTYPE, VMA, 7, 1)
 FIELD(VTYPE, VEDIV, 8, 2)
 FIELD(VTYPE, RESERVED, 10, sizeof(uint64_t) * 8 - 11)
 
+#ifndef CONFIG_USER_ONLY
+/* machine specific AIA ireg read-modify-write callback */
+#define AIA_MAKE_IREG(__isel, __priv, __virt, __vgein, __xlen)                 \
+    ((uint32_t)((((__xlen) & 0xff) << 24) |                                    \
+                (((__vgein) & 0x3f) << 20) |                                   \
+                (((__virt) & 0x1) << 18) |                                     \
+                (((__priv) & 0x3) << 16) |                                     \
+                  (__isel & 0xffff)))
+#define AIA_IREG_ISEL(__ireg) ((__ireg) & 0xffff)
+#define AIA_IREG_PRIV(__ireg) (((__ireg) >> 16) & 0x3)
+#define AIA_IREG_VIRT(__ireg) (((__ireg) >> 18) & 0x1)
+#define AIA_IREG_VGEIN(__ireg) (((__ireg) >> 20) & 0x3f)
+#define AIA_IREG_XLEN(__ireg) (((__ireg) >> 24) & 0xff)
+
+typedef int aia_ireg_rmw_fn(void *arg, uint32_t reg, uint64_t *val,
+                            uint64_t new_val, uint64_t write_mask);
+#endif
+
 typedef struct PMUCTRState {
     /* Current value of a counter */
     uint64_t mhpmcounter_val;
@@ -458,20 +476,8 @@ struct CPUArchState {
     void *rdtime_fn_arg;
 
     /* machine specific AIA ireg read-modify-write callback */
-#define AIA_MAKE_IREG(__isel, __priv, __virt, __vgein, __xlen) \
-    ((((__xlen) & 0xff) << 24) | \
-     (((__vgein) & 0x3f) << 20) | \
-     (((__virt) & 0x1) << 18) | \
-     (((__priv) & 0x3) << 16) | \
-     (__isel & 0xffff))
-#define AIA_IREG_ISEL(__ireg)                  ((__ireg) & 0xffff)
-#define AIA_IREG_PRIV(__ireg)                  (((__ireg) >> 16) & 0x3)
-#define AIA_IREG_VIRT(__ireg)                  (((__ireg) >> 18) & 0x1)
-#define AIA_IREG_VGEIN(__ireg)                 (((__ireg) >> 20) & 0x3f)
-#define AIA_IREG_XLEN(__ireg)                  (((__ireg) >> 24) & 0xff)
-    int (*aia_ireg_rmw_fn[4])(void *arg, target_ulong reg,
-        target_ulong *val, target_ulong new_val, target_ulong write_mask);
-    void *aia_ireg_rmw_fn_arg[4];
+    aia_ireg_rmw_fn *aia_ireg_rmw_cb[4];
+    void *aia_ireg_rmw_cb_arg[4];
 
     /* True if in debugger mode.  */
     bool debugger;
@@ -638,12 +644,8 @@ void riscv_cpu_interrupt(CPURISCVState *env);
 #define BOOL_TO_MASK(x) (-!!(x)) /* helper for riscv_cpu_update_mip value */
 void riscv_cpu_set_rdtime_fn(CPURISCVState *env, uint64_t (*fn)(void *),
                              void *arg);
-void riscv_cpu_set_aia_ireg_rmw_fn(CPURISCVState *env, uint32_t priv,
-                                   int (*rmw_fn)(void *arg,
-                                                 target_ulong reg,
-                                                 target_ulong *val,
-                                                 target_ulong new_val,
-                                                 target_ulong write_mask),
+void riscv_cpu_set_aia_ireg_rmw_cb(CPURISCVState *env, uint32_t priv,
+                                   aia_ireg_rmw_fn *rmw_fn,
                                    void *rmw_fn_arg);
 
 RISCVException smstateen_acc_ok(CPURISCVState *env, int index, uint64_t bit);
diff --git a/hw/intc/riscv_imsic.c b/hw/intc/riscv_imsic.c
index 6174e1a05d..9274a1e842 100644
--- a/hw/intc/riscv_imsic.c
+++ b/hw/intc/riscv_imsic.c
@@ -88,11 +88,11 @@ static void riscv_imsic_update(RISCVIMSICState *imsic, uint32_t page)
 }
 
 static int riscv_imsic_eidelivery_rmw(RISCVIMSICState *imsic, uint32_t page,
-                                      target_ulong *val,
-                                      target_ulong new_val,
-                                      target_ulong wr_mask)
+                                      uint64_t *val,
+                                      uint64_t new_val,
+                                      uint64_t wr_mask)
 {
-    target_ulong old_val = imsic->eidelivery[page];
+    uint32_t old_val = imsic->eidelivery[page];
 
     if (val) {
         *val = old_val;
@@ -106,11 +106,11 @@ static int riscv_imsic_eidelivery_rmw(RISCVIMSICState *imsic, uint32_t page,
 }
 
 static int riscv_imsic_eithreshold_rmw(RISCVIMSICState *imsic, uint32_t page,
-                                      target_ulong *val,
-                                      target_ulong new_val,
-                                      target_ulong wr_mask)
+                                      uint64_t *val,
+                                      uint64_t new_val,
+                                      uint64_t wr_mask)
 {
-    target_ulong old_val = imsic->eithreshold[page];
+    uint32_t old_val = imsic->eithreshold[page];
 
     if (val) {
         *val = old_val;
@@ -124,8 +124,8 @@ static int riscv_imsic_eithreshold_rmw(RISCVIMSICState *imsic, uint32_t page,
 }
 
 static int riscv_imsic_topei_rmw(RISCVIMSICState *imsic, uint32_t page,
-                                 target_ulong *val, target_ulong new_val,
-                                 target_ulong wr_mask)
+                                 uint64_t *val, uint64_t new_val,
+                                 uint64_t wr_mask)
 {
     uint32_t base, topei = riscv_imsic_topei(imsic, page);
 
@@ -149,11 +149,11 @@ static int riscv_imsic_topei_rmw(RISCVIMSICState *imsic, uint32_t page,
 
 static int riscv_imsic_eix_rmw(RISCVIMSICState *imsic,
                                uint32_t xlen, uint32_t page,
-                               uint32_t num, bool pend, target_ulong *val,
-                               target_ulong new_val, target_ulong wr_mask)
+                               uint32_t num, bool pend, uint64_t *val,
+                               uint64_t new_val, uint64_t wr_mask)
 {
     uint32_t i, base, prev;
-    target_ulong mask;
+    uint64_t mask;
     uint32_t state = (pend) ? IMSIC_EISTATE_PENDING : IMSIC_EISTATE_ENABLED;
 
     if (xlen != 32) {
@@ -178,7 +178,7 @@ static int riscv_imsic_eix_rmw(RISCVIMSICState *imsic,
             continue;
         }
 
-        mask = (target_ulong)1 << i;
+        mask = 1ull << i;
         if (wr_mask & mask) {
             if (new_val & mask) {
                 prev = qatomic_fetch_or(&imsic->eistate[base + i], state);
@@ -197,8 +197,8 @@ static int riscv_imsic_eix_rmw(RISCVIMSICState *imsic,
     return 0;
 }
 
-static int riscv_imsic_rmw(void *arg, target_ulong reg, target_ulong *val,
-                           target_ulong new_val, target_ulong wr_mask)
+static int riscv_imsic_rmw(void *arg, uint32_t reg, uint64_t *val,
+                           uint64_t new_val, uint64_t wr_mask)
 {
     RISCVIMSICState *imsic = arg;
     uint32_t isel, priv, virt, vgein, xlen, page;
@@ -383,7 +383,7 @@ static void riscv_imsic_realize(DeviceState *dev, Error **errp)
         }
 
         if (!kvm_irqchip_in_kernel()) {
-            riscv_cpu_set_aia_ireg_rmw_fn(env, (imsic->mmode) ? PRV_M : PRV_S,
+            riscv_cpu_set_aia_ireg_rmw_cb(env, (imsic->mmode) ? PRV_M : PRV_S,
                                           riscv_imsic_rmw, imsic);
         }
     }
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
index c5e94359e4..2945a89a9c 100644
--- a/target/riscv/cpu_helper.c
+++ b/target/riscv/cpu_helper.c
@@ -766,17 +766,13 @@ void riscv_cpu_set_rdtime_fn(CPURISCVState *env, uint64_t (*fn)(void *),
     env->rdtime_fn_arg = arg;
 }
 
-void riscv_cpu_set_aia_ireg_rmw_fn(CPURISCVState *env, uint32_t priv,
-                                   int (*rmw_fn)(void *arg,
-                                                 target_ulong reg,
-                                                 target_ulong *val,
-                                                 target_ulong new_val,
-                                                 target_ulong write_mask),
+void riscv_cpu_set_aia_ireg_rmw_cb(CPURISCVState *env, uint32_t priv,
+                                   aia_ireg_rmw_fn *rmw_fn,
                                    void *rmw_fn_arg)
 {
     if (priv <= PRV_M) {
-        env->aia_ireg_rmw_fn[priv] = rmw_fn;
-        env->aia_ireg_rmw_fn_arg[priv] = rmw_fn_arg;
+        env->aia_ireg_rmw_cb[priv] = rmw_fn;
+        env->aia_ireg_rmw_cb_arg[priv] = rmw_fn_arg;
     }
 }
 
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index fed689fe30..832f061711 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -2632,6 +2632,7 @@ static RISCVException rmw_xireg_aia(CPURISCVState *env, int csrno,
     int ret = -EINVAL;
     uint8_t *iprio;
     target_ulong priv, vgein;
+    uint64_t wide_val;
 
     /* VS-mode CSR number passed in has already been translated */
     switch (csrno) {
@@ -2676,16 +2677,17 @@ static RISCVException rmw_xireg_aia(CPURISCVState *env, int csrno,
         }
     } else if (ISELECT_IMSIC_FIRST <= isel && isel <= ISELECT_IMSIC_LAST) {
         /* IMSIC registers only available when machine implements it. */
-        if (env->aia_ireg_rmw_fn[priv]) {
+        if (env->aia_ireg_rmw_cb[priv]) {
             /* Selected guest interrupt file should not be zero */
             if (virt && (!vgein || env->geilen < vgein)) {
                 goto done;
             }
             /* Call machine specific IMSIC register emulation */
-            ret = env->aia_ireg_rmw_fn[priv](env->aia_ireg_rmw_fn_arg[priv],
+            ret = env->aia_ireg_rmw_cb[priv](env->aia_ireg_rmw_cb_arg[priv],
                                     AIA_MAKE_IREG(isel, priv, virt, vgein,
                                                   riscv_cpu_mxl_bits(env)),
-                                    val, new_val, wr_mask);
+                                    &wide_val, new_val, wr_mask);
+            *val = wide_val;
         }
     } else {
         isel_reserved = true;
@@ -2917,6 +2919,7 @@ static RISCVException rmw_xtopei(CPURISCVState *env, int csrno,
     bool virt;
     int ret = -EINVAL;
     target_ulong priv, vgein;
+    uint64_t wide_val;
 
     /* Translate CSR number for VS-mode */
     csrno = aia_xlate_vs_csrno(env, csrno);
@@ -2942,7 +2945,7 @@ static RISCVException rmw_xtopei(CPURISCVState *env, int csrno,
     };
 
     /* IMSIC CSRs only available when machine implements IMSIC. */
-    if (!env->aia_ireg_rmw_fn[priv]) {
+    if (!env->aia_ireg_rmw_cb[priv]) {
         goto done;
     }
 
@@ -2955,10 +2958,11 @@ static RISCVException rmw_xtopei(CPURISCVState *env, int csrno,
     }
 
     /* Call machine specific IMSIC register emulation for TOPEI */
-    ret = env->aia_ireg_rmw_fn[priv](env->aia_ireg_rmw_fn_arg[priv],
+    ret = env->aia_ireg_rmw_cb[priv](env->aia_ireg_rmw_cb_arg[priv],
                     AIA_MAKE_IREG(ISELECT_IMSIC_TOPEI, priv, virt, vgein,
                                   riscv_cpu_mxl_bits(env)),
-                    val, new_val, wr_mask);
+                    &wide_val, new_val, wr_mask);
+    *val = wide_val;
 
 done:
     if (ret) {
@@ -4423,7 +4427,7 @@ static RISCVException read_vstopi(CPURISCVState *env, int csrno,
                                   target_ulong *val)
 {
     int irq, ret;
-    target_ulong topei;
+    uint64_t topei = 0;
     uint64_t vseip, vsgein;
     uint32_t iid, iprio, hviid, hviprio, gein;
     uint32_t s, scount = 0, siid[VSTOPI_NUM_SRCS], siprio[VSTOPI_NUM_SRCS];
@@ -4438,13 +4442,13 @@ static RISCVException read_vstopi(CPURISCVState *env, int csrno,
         if (gein <= env->geilen && vseip) {
             siid[scount] = IRQ_S_EXT;
             siprio[scount] = IPRIO_MMAXIPRIO + 1;
-            if (env->aia_ireg_rmw_fn[PRV_S]) {
+            if (env->aia_ireg_rmw_cb[PRV_S]) {
                 /*
                  * Call machine specific IMSIC register emulation for
                  * reading TOPEI.
                  */
-                ret = env->aia_ireg_rmw_fn[PRV_S](
-                        env->aia_ireg_rmw_fn_arg[PRV_S],
+                ret = env->aia_ireg_rmw_cb[PRV_S](
+                        env->aia_ireg_rmw_cb_arg[PRV_S],
                         AIA_MAKE_IREG(ISELECT_IMSIC_TOPEI, PRV_S, true, gein,
                                       riscv_cpu_mxl_bits(env)),
                         &topei, 0, 0);
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 24/33] target/riscv: Fix size of irq_overflow_left
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (22 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 23/33] target/riscv: Fix arguments to board IMSIC emulation callbacks Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-02 20:15   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 25/33] target/riscv: Indent PMUFixedCtrState correctly Anton Johansson via
                   ` (8 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Fix to 64 bits to hold all relevant values.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 5485d3e35f..cf7710c695 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -217,7 +217,7 @@ typedef struct PMUCTRState {
     /* Snapshot values of counter */
     uint64_t mhpmcounter_prev;
     /* Value beyond UINT32_MAX/UINT64_MAX before overflow interrupt trigger */
-    target_ulong irq_overflow_left;
+    uint64_t irq_overflow_left;
 } PMUCTRState;
 
 typedef struct PMUFixedCtrState {
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 25/33] target/riscv: Indent PMUFixedCtrState correctly
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (23 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 24/33] target/riscv: Fix size of irq_overflow_left Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-01  7:43   ` Philippe Mathieu-Daudé
  2025-10-02 20:15   ` Pierrick Bouvier
  2025-10-01  7:32 ` [PATCH v2 26/33] target/riscv: Replace target_ulong in riscv_cpu_get_trap_name() Anton Johansson via
                   ` (7 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h | 12 ++++++------
 1 file changed, 6 insertions(+), 6 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index cf7710c695..d264c87e32 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -221,12 +221,12 @@ typedef struct PMUCTRState {
 } PMUCTRState;
 
 typedef struct PMUFixedCtrState {
-        /* Track cycle and icount for each privilege mode */
-        uint64_t counter[4];
-        uint64_t counter_prev[4];
-        /* Track cycle and icount for each privilege mode when V = 1*/
-        uint64_t counter_virt[2];
-        uint64_t counter_virt_prev[2];
+    /* Track cycle and icount for each privilege mode */
+    uint64_t counter[4];
+    uint64_t counter_prev[4];
+    /* Track cycle and icount for each privilege mode when V = 1*/
+    uint64_t counter_virt[2];
+    uint64_t counter_virt_prev[2];
 } PMUFixedCtrState;
 
 struct CPUArchState {
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 26/33] target/riscv: Replace target_ulong in riscv_cpu_get_trap_name()
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (24 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 25/33] target/riscv: Indent PMUFixedCtrState correctly Anton Johansson via
@ 2025-10-01  7:32 ` Anton Johansson via
  2025-10-01  7:43   ` Philippe Mathieu-Daudé
  2025-10-02 20:15   ` Pierrick Bouvier
  2025-10-01  7:33 ` [PATCH v2 27/33] target/riscv: Replace target_ulong in riscv_ctr_add_entry() Anton Johansson via
                   ` (6 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:32 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Fix cause argument to 64 bit to match env->mcause.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h | 2 +-
 target/riscv/cpu.c | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index d264c87e32..c1fbb67b08 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -593,7 +593,7 @@ extern const char * const riscv_int_regnames[];
 extern const char * const riscv_int_regnamesh[];
 extern const char * const riscv_fpr_regnames[];
 
-const char *riscv_cpu_get_trap_name(target_ulong cause, bool async);
+const char *riscv_cpu_get_trap_name(uint64_t cause, bool async);
 int riscv_cpu_write_elf64_note(WriteCoreDumpFunction f, CPUState *cs,
                                int cpuid, DumpState *s);
 int riscv_cpu_write_elf32_note(WriteCoreDumpFunction f, CPUState *cs,
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
index 4e38487dca..5206abe640 100644
--- a/target/riscv/cpu.c
+++ b/target/riscv/cpu.c
@@ -348,7 +348,7 @@ static const char * const riscv_intr_names[] = {
     "reserved"
 };
 
-const char *riscv_cpu_get_trap_name(target_ulong cause, bool async)
+const char *riscv_cpu_get_trap_name(uint64_t cause, bool async)
 {
     if (async) {
         return (cause < ARRAY_SIZE(riscv_intr_names)) ?
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 27/33] target/riscv: Replace target_ulong in riscv_ctr_add_entry()
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (25 preceding siblings ...)
  2025-10-01  7:32 ` [PATCH v2 26/33] target/riscv: Replace target_ulong in riscv_cpu_get_trap_name() Anton Johansson via
@ 2025-10-01  7:33 ` Anton Johansson via
  2025-10-01  7:44   ` Philippe Mathieu-Daudé
  2025-10-02 20:19   ` Pierrick Bouvier
  2025-10-01  7:33 ` [PATCH v2 28/33] target/riscv: Fix size of trigger data Anton Johansson via
                   ` (5 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:33 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Widen to 64 bits in size to hold all relevant values.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h        | 2 +-
 target/riscv/cpu_helper.c | 4 ++--
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index c1fbb67b08..b17aca0e02 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -653,7 +653,7 @@ RISCVException smstateen_acc_ok(CPURISCVState *env, int index, uint64_t bit);
 
 void riscv_cpu_set_mode(CPURISCVState *env, uint8_t newpriv, bool virt_en);
 
-void riscv_ctr_add_entry(CPURISCVState *env, target_long src, target_long dst,
+void riscv_ctr_add_entry(CPURISCVState *env, uint64_t src, uint64_t dst,
     enum CTRType type, uint8_t prev_priv, bool prev_virt);
 void riscv_ctr_clear(CPURISCVState *env);
 
diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
index 2945a89a9c..4acfccc9d8 100644
--- a/target/riscv/cpu_helper.c
+++ b/target/riscv/cpu_helper.c
@@ -925,8 +925,8 @@ static bool riscv_ctr_check_xte(CPURISCVState *env, uint8_t src_prv,
  *    entry = isel - CTR_ENTRIES_FIRST;
  *    idx = (sctrstatus.WRPTR - entry - 1) & (depth - 1);
  */
-void riscv_ctr_add_entry(CPURISCVState *env, target_long src, target_long dst,
-    enum CTRType type, uint8_t src_priv, bool src_virt)
+void riscv_ctr_add_entry(CPURISCVState *env, uint64_t src, uint64_t dst,
+                         enum CTRType type, uint8_t src_priv, bool src_virt)
 {
     bool tgt_virt = env->virt_enabled;
     uint64_t src_mask = riscv_ctr_priv_to_mask(src_priv, src_virt);
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 28/33] target/riscv: Fix size of trigger data
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (26 preceding siblings ...)
  2025-10-01  7:33 ` [PATCH v2 27/33] target/riscv: Replace target_ulong in riscv_ctr_add_entry() Anton Johansson via
@ 2025-10-01  7:33 ` Anton Johansson via
  2025-10-01  7:46   ` Philippe Mathieu-Daudé
  2025-10-02 20:19   ` Pierrick Bouvier
  2025-10-01  7:33 ` [PATCH v2 29/33] target/riscv: Fix size of mseccfg Anton Johansson via
                   ` (4 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:33 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

mcontext is at most 14 bits in size with the H extension, fix to 16
bits. trigger_cur indexes into tdata*[RV_MAX_TRIGGERS] which holds 2
elements, fix to 8 bits.

Note, the cpu/debug VMSTATE version is bumped, breaking migration from
older versions.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h     | 10 +++++-----
 target/riscv/machine.c | 12 ++++++------
 2 files changed, 11 insertions(+), 11 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index b17aca0e02..b718f6f3b1 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -460,11 +460,11 @@ struct CPUArchState {
     target_ulong mseccfg;
 
     /* trigger module */
-    target_ulong trigger_cur;
-    target_ulong tdata1[RV_MAX_TRIGGERS];
-    target_ulong tdata2[RV_MAX_TRIGGERS];
-    target_ulong tdata3[RV_MAX_TRIGGERS];
-    target_ulong mcontext;
+    uint16_t mcontext;
+    uint8_t trigger_cur;
+    uint64_t tdata1[RV_MAX_TRIGGERS];
+    uint64_t tdata2[RV_MAX_TRIGGERS];
+    uint64_t tdata3[RV_MAX_TRIGGERS];
     struct CPUBreakpoint *cpu_breakpoint[RV_MAX_TRIGGERS];
     struct CPUWatchpoint *cpu_watchpoint[RV_MAX_TRIGGERS];
     QEMUTimer *itrigger_timer[RV_MAX_TRIGGERS];
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index 18dbc1bfa9..aa71aa6eb1 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -238,15 +238,15 @@ static int debug_post_load(void *opaque, int version_id)
 
 static const VMStateDescription vmstate_debug = {
     .name = "cpu/debug",
-    .version_id = 2,
-    .minimum_version_id = 2,
+    .version_id = 3,
+    .minimum_version_id = 3,
     .needed = debug_needed,
     .post_load = debug_post_load,
     .fields = (const VMStateField[]) {
-        VMSTATE_UINTTL(env.trigger_cur, RISCVCPU),
-        VMSTATE_UINTTL_ARRAY(env.tdata1, RISCVCPU, RV_MAX_TRIGGERS),
-        VMSTATE_UINTTL_ARRAY(env.tdata2, RISCVCPU, RV_MAX_TRIGGERS),
-        VMSTATE_UINTTL_ARRAY(env.tdata3, RISCVCPU, RV_MAX_TRIGGERS),
+        VMSTATE_UINT8(env.trigger_cur, RISCVCPU),
+        VMSTATE_UINT64_ARRAY(env.tdata1, RISCVCPU, RV_MAX_TRIGGERS),
+        VMSTATE_UINT64_ARRAY(env.tdata2, RISCVCPU, RV_MAX_TRIGGERS),
+        VMSTATE_UINT64_ARRAY(env.tdata3, RISCVCPU, RV_MAX_TRIGGERS),
         VMSTATE_END_OF_LIST()
     }
 };
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 29/33] target/riscv: Fix size of mseccfg
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (27 preceding siblings ...)
  2025-10-01  7:33 ` [PATCH v2 28/33] target/riscv: Fix size of trigger data Anton Johansson via
@ 2025-10-01  7:33 ` Anton Johansson via
  2025-10-01  7:46   ` Philippe Mathieu-Daudé
  2025-10-02 20:20   ` Pierrick Bouvier
  2025-10-01  7:33 ` [PATCH v2 30/33] target/riscv: Move debug.h include away from cpu.h Anton Johansson via
                   ` (3 subsequent siblings)
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:33 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

mseccfg is defined in version 20250508 of the privileged specification
to be 64 bits in size.  Update relevant function arguments.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h | 2 +-
 target/riscv/pmp.h | 4 ++--
 target/riscv/pmp.c | 4 ++--
 3 files changed, 5 insertions(+), 5 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index b718f6f3b1..a53981a09b 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -457,7 +457,7 @@ struct CPUArchState {
 
     /* physical memory protection */
     pmp_table_t pmp_state;
-    target_ulong mseccfg;
+    uint64_t mseccfg;
 
     /* trigger module */
     uint16_t mcontext;
diff --git a/target/riscv/pmp.h b/target/riscv/pmp.h
index 271cf24169..e322904637 100644
--- a/target/riscv/pmp.h
+++ b/target/riscv/pmp.h
@@ -69,8 +69,8 @@ void pmpcfg_csr_write(CPURISCVState *env, uint32_t reg_index,
                       target_ulong val);
 target_ulong pmpcfg_csr_read(CPURISCVState *env, uint32_t reg_index);
 
-void mseccfg_csr_write(CPURISCVState *env, target_ulong val);
-target_ulong mseccfg_csr_read(CPURISCVState *env);
+void mseccfg_csr_write(CPURISCVState *env, uint64_t val);
+uint64_t mseccfg_csr_read(CPURISCVState *env);
 
 void pmpaddr_csr_write(CPURISCVState *env, uint32_t addr_index,
                        target_ulong val);
diff --git a/target/riscv/pmp.c b/target/riscv/pmp.c
index 72f1372a49..85199c7387 100644
--- a/target/riscv/pmp.c
+++ b/target/riscv/pmp.c
@@ -597,7 +597,7 @@ target_ulong pmpaddr_csr_read(CPURISCVState *env, uint32_t addr_index)
 /*
  * Handle a write to a mseccfg CSR
  */
-void mseccfg_csr_write(CPURISCVState *env, target_ulong val)
+void mseccfg_csr_write(CPURISCVState *env, uint64_t val)
 {
     int i;
     uint64_t mask = MSECCFG_MMWP | MSECCFG_MML;
@@ -643,7 +643,7 @@ void mseccfg_csr_write(CPURISCVState *env, target_ulong val)
 /*
  * Handle a read from a mseccfg CSR
  */
-target_ulong mseccfg_csr_read(CPURISCVState *env)
+uint64_t mseccfg_csr_read(CPURISCVState *env)
 {
     trace_mseccfg_csr_read(env->mhartid, env->mseccfg);
     return env->mseccfg;
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 30/33] target/riscv: Move debug.h include away from cpu.h
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (28 preceding siblings ...)
  2025-10-01  7:33 ` [PATCH v2 29/33] target/riscv: Fix size of mseccfg Anton Johansson via
@ 2025-10-01  7:33 ` Anton Johansson via
  2025-10-02 20:21   ` Pierrick Bouvier
  2025-10-01  7:33 ` [PATCH v2 31/33] target/riscv: Move CSR declarations to separate csr.h header Anton Johansson via
                   ` (2 subsequent siblings)
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:33 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

All debug.h definitions except for RV_MAX_TRIGGERS are internal to
target/riscv.  Move RV_MAX_TRIGGERS to cpu.h and include debug.h from
all translation units which relied on the cpu.h include.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h         | 4 ++--
 target/riscv/debug.h       | 2 --
 target/riscv/cpu.c         | 3 +++
 target/riscv/csr.c         | 3 +++
 target/riscv/debug.c       | 1 +
 target/riscv/tcg/tcg-cpu.c | 1 +
 6 files changed, 10 insertions(+), 4 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index a53981a09b..70e0f3718c 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -177,14 +177,14 @@ extern RISCVCPUImpliedExtsRule *riscv_multi_ext_implied_rules[];
 #define MAX_RISCV_PMPS (64)
 #define OLD_MAX_RISCV_PMPS (16)
 
-#if !defined(CONFIG_USER_ONLY)
+#if !defined(CONFIG_LINUX_USER)
 #include "pmp.h"
-#include "debug.h"
 #endif
 
 #define RV_VLEN_MAX 1024
 #define RV_MAX_MHPMEVENTS 32
 #define RV_MAX_MHPMCOUNTERS 32
+#define RV_MAX_TRIGGERS 2
 
 FIELD(VTYPE, VLMUL, 0, 3)
 FIELD(VTYPE, VSEW, 3, 3)
diff --git a/target/riscv/debug.h b/target/riscv/debug.h
index f76b8f944a..d3aae619db 100644
--- a/target/riscv/debug.h
+++ b/target/riscv/debug.h
@@ -24,8 +24,6 @@
 
 #include "exec/breakpoint.h"
 
-#define RV_MAX_TRIGGERS         2
-
 /* register index of tdata CSRs */
 enum {
     TDATA1 = 0,
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
index 5206abe640..246ec81beb 100644
--- a/target/riscv/cpu.c
+++ b/target/riscv/cpu.c
@@ -37,6 +37,9 @@
 #include "kvm/kvm_riscv.h"
 #include "tcg/tcg-cpu.h"
 #include "tcg/tcg.h"
+#if !defined(CONFIG_USER_ONLY)
+#include "debug.h"
+#endif
 
 /* RISC-V CPU definitions */
 static const char riscv_single_letter_exts[] = "IEMAFDQCBPVH";
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 832f061711..0e7236098b 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -32,6 +32,9 @@
 #include "qapi/error.h"
 #include "tcg/insn-start-words.h"
 #include "internals.h"
+#if !defined(CONFIG_USER_ONLY)
+#include "debug.h"
+#endif
 #include <stdbool.h>
 
 /* CSR function table public API */
diff --git a/target/riscv/debug.c b/target/riscv/debug.c
index 5664466749..f5b2043405 100644
--- a/target/riscv/debug.c
+++ b/target/riscv/debug.c
@@ -27,6 +27,7 @@
 #include "qemu/log.h"
 #include "qapi/error.h"
 #include "cpu.h"
+#include "debug.h"
 #include "trace.h"
 #include "exec/helper-proto.h"
 #include "exec/watchpoint.h"
diff --git a/target/riscv/tcg/tcg-cpu.c b/target/riscv/tcg/tcg-cpu.c
index 200759eaf0..08e9d2b554 100644
--- a/target/riscv/tcg/tcg-cpu.c
+++ b/target/riscv/tcg/tcg-cpu.c
@@ -37,6 +37,7 @@
 #include "hw/boards.h"
 #include "system/tcg.h"
 #include "exec/icount.h"
+#include "debug.h"
 #endif
 
 /* Hash that stores user set extensions */
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 31/33] target/riscv: Move CSR declarations to separate csr.h header
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (29 preceding siblings ...)
  2025-10-01  7:33 ` [PATCH v2 30/33] target/riscv: Move debug.h include away from cpu.h Anton Johansson via
@ 2025-10-01  7:33 ` Anton Johansson via
  2025-10-02 20:22   ` Pierrick Bouvier
  2025-10-01  7:33 ` [PATCH v2 32/33] target/riscv: Introduce externally facing CSR access functions Anton Johansson via
  2025-10-01  7:33 ` [PATCH v2 33/33] target/riscv: Make pmp.h target_ulong agnostic Anton Johansson via
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:33 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Most of these definitions save riscv_csrr, riscv_csrrw, riscv_csr_read,
riscv_csr_write are only used in target/.  Move declarations to a
separate headers which will soon be made internal to target/.

csr.h is temporarily included from cpu.h to not break includes from
outside target/, this include will be removed in the following commit.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h         | 82 +--------------------------------
 target/riscv/csr.h         | 94 ++++++++++++++++++++++++++++++++++++++
 target/riscv/cpu.c         |  1 +
 target/riscv/csr.c         |  1 +
 target/riscv/gdbstub.c     |  1 +
 target/riscv/kvm/kvm-cpu.c |  1 +
 target/riscv/op_helper.c   |  1 +
 target/riscv/th_csr.c      |  1 +
 8 files changed, 101 insertions(+), 81 deletions(-)
 create mode 100644 target/riscv/csr.h

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 70e0f3718c..61319575b0 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -849,75 +849,7 @@ RISCVPmPmm riscv_pm_get_pmm(CPURISCVState *env);
 RISCVPmPmm riscv_pm_get_virt_pmm(CPURISCVState *env);
 uint32_t riscv_pm_get_pmlen(RISCVPmPmm pmm);
 
-RISCVException riscv_csrr(CPURISCVState *env, int csrno,
-                          target_ulong *ret_value);
-
-RISCVException riscv_csrrw(CPURISCVState *env, int csrno,
-                           target_ulong *ret_value, target_ulong new_value,
-                           target_ulong write_mask, uintptr_t ra);
-RISCVException riscv_csrrw_debug(CPURISCVState *env, int csrno,
-                                 target_ulong *ret_value,
-                                 target_ulong new_value,
-                                 target_ulong write_mask);
-
-static inline void riscv_csr_write(CPURISCVState *env, int csrno,
-                                   target_ulong val)
-{
-    riscv_csrrw(env, csrno, NULL, val, MAKE_64BIT_MASK(0, TARGET_LONG_BITS), 0);
-}
-
-static inline target_ulong riscv_csr_read(CPURISCVState *env, int csrno)
-{
-    target_ulong val = 0;
-    riscv_csrrw(env, csrno, &val, 0, 0, 0);
-    return val;
-}
-
-typedef RISCVException (*riscv_csr_predicate_fn)(CPURISCVState *env,
-                                                 int csrno);
-typedef RISCVException (*riscv_csr_read_fn)(CPURISCVState *env, int csrno,
-                                            target_ulong *ret_value);
-typedef RISCVException (*riscv_csr_write_fn)(CPURISCVState *env, int csrno,
-                                             target_ulong new_value,
-                                             uintptr_t ra);
-typedef RISCVException (*riscv_csr_op_fn)(CPURISCVState *env, int csrno,
-                                          target_ulong *ret_value,
-                                          target_ulong new_value,
-                                          target_ulong write_mask);
-
-RISCVException riscv_csrr_i128(CPURISCVState *env, int csrno,
-                               Int128 *ret_value);
-RISCVException riscv_csrrw_i128(CPURISCVState *env, int csrno,
-                                Int128 *ret_value, Int128 new_value,
-                                Int128 write_mask, uintptr_t ra);
-
-typedef RISCVException (*riscv_csr_read128_fn)(CPURISCVState *env, int csrno,
-                                               Int128 *ret_value);
-typedef RISCVException (*riscv_csr_write128_fn)(CPURISCVState *env, int csrno,
-                                             Int128 new_value);
-
-typedef struct {
-    const char *name;
-    riscv_csr_predicate_fn predicate;
-    riscv_csr_read_fn read;
-    riscv_csr_write_fn write;
-    riscv_csr_op_fn op;
-    riscv_csr_read128_fn read128;
-    riscv_csr_write128_fn write128;
-    /* The default priv spec version should be PRIV_VERSION_1_10_0 (i.e 0) */
-    uint32_t min_priv_ver;
-} riscv_csr_operations;
-
-struct RISCVCSR {
-    int csrno;
-    bool (*insertion_test)(RISCVCPU *cpu);
-    riscv_csr_operations csr_ops;
-};
-
-/* CSR function table constants */
-enum {
-    CSR_TABLE_SIZE = 0x1000
-};
+#include "csr.h"
 
 /*
  * The event id are encoded based on the encoding specified in the
@@ -961,23 +893,11 @@ void riscv_cpu_finalize_features(RISCVCPU *cpu, Error **errp);
 void riscv_add_satp_mode_properties(Object *obj);
 bool riscv_cpu_accelerator_compatible(RISCVCPU *cpu);
 
-/* CSR function table */
-extern riscv_csr_operations csr_ops[CSR_TABLE_SIZE];
-
 extern const bool valid_vm_1_10_32[], valid_vm_1_10_64[];
 
-void riscv_get_csr_ops(int csrno, riscv_csr_operations *ops);
-void riscv_set_csr_ops(int csrno, const riscv_csr_operations *ops);
-
 void riscv_cpu_register_gdb_regs_for_features(CPUState *cs);
 
-target_ulong riscv_new_csr_seed(target_ulong new_value,
-                                target_ulong write_mask);
-
 const char *satp_mode_str(uint8_t satp_mode, bool is_32_bit);
 
-/* In th_csr.c */
-extern const RISCVCSR th_csr_list[];
-
 const char *priv_spec_to_str(int priv_version);
 #endif /* RISCV_CPU_H */
diff --git a/target/riscv/csr.h b/target/riscv/csr.h
new file mode 100644
index 0000000000..fab53992bb
--- /dev/null
+++ b/target/riscv/csr.h
@@ -0,0 +1,94 @@
+/*
+ * QEMU RISC-V CSRs
+ *
+ * Copyright (c) 2016-2017 Sagar Karandikar, sagark@eecs.berkeley.edu
+ * Copyright (c) 2017-2018 SiFive, Inc.
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ */
+
+#ifndef RISCV_CSR_H
+#define RISCV_CSR_H
+
+target_ulong riscv_new_csr_seed(target_ulong new_value,
+                                target_ulong write_mask);
+
+RISCVException riscv_csrr(CPURISCVState *env, int csrno,
+                          target_ulong *ret_value);
+
+RISCVException riscv_csrrw(CPURISCVState *env, int csrno,
+                           target_ulong *ret_value, target_ulong new_value,
+                           target_ulong write_mask, uintptr_t ra);
+RISCVException riscv_csrrw_debug(CPURISCVState *env, int csrno,
+                                 target_ulong *ret_value,
+                                 target_ulong new_value,
+                                 target_ulong write_mask);
+
+static inline void riscv_csr_write(CPURISCVState *env, int csrno,
+                                   target_ulong val)
+{
+    riscv_csrrw(env, csrno, NULL, val, MAKE_64BIT_MASK(0, TARGET_LONG_BITS), 0);
+}
+
+static inline target_ulong riscv_csr_read(CPURISCVState *env, int csrno)
+{
+    target_ulong val = 0;
+    riscv_csrrw(env, csrno, &val, 0, 0, 0);
+    return val;
+}
+
+typedef RISCVException (*riscv_csr_predicate_fn)(CPURISCVState *env,
+                                                 int csrno);
+typedef RISCVException (*riscv_csr_read_fn)(CPURISCVState *env, int csrno,
+                                            target_ulong *ret_value);
+typedef RISCVException (*riscv_csr_write_fn)(CPURISCVState *env, int csrno,
+                                             target_ulong new_value,
+                                             uintptr_t ra);
+typedef RISCVException (*riscv_csr_op_fn)(CPURISCVState *env, int csrno,
+                                          target_ulong *ret_value,
+                                          target_ulong new_value,
+                                          target_ulong write_mask);
+
+RISCVException riscv_csrr_i128(CPURISCVState *env, int csrno,
+                               Int128 *ret_value);
+RISCVException riscv_csrrw_i128(CPURISCVState *env, int csrno,
+                                Int128 *ret_value, Int128 new_value,
+                                Int128 write_mask, uintptr_t ra);
+
+typedef RISCVException (*riscv_csr_read128_fn)(CPURISCVState *env, int csrno,
+                                               Int128 *ret_value);
+typedef RISCVException (*riscv_csr_write128_fn)(CPURISCVState *env, int csrno,
+                                             Int128 new_value);
+
+typedef struct {
+    const char *name;
+    riscv_csr_predicate_fn predicate;
+    riscv_csr_read_fn read;
+    riscv_csr_write_fn write;
+    riscv_csr_op_fn op;
+    riscv_csr_read128_fn read128;
+    riscv_csr_write128_fn write128;
+    /* The default priv spec version should be PRIV_VERSION_1_10_0 (i.e 0) */
+    uint32_t min_priv_ver;
+} riscv_csr_operations;
+
+struct RISCVCSR {
+    int csrno;
+    bool (*insertion_test)(RISCVCPU *cpu);
+    riscv_csr_operations csr_ops;
+};
+
+/* CSR function table constants */
+enum {
+    CSR_TABLE_SIZE = 0x1000
+};
+
+/* CSR function table */
+extern riscv_csr_operations csr_ops[CSR_TABLE_SIZE];
+
+void riscv_get_csr_ops(int csrno, riscv_csr_operations *ops);
+void riscv_set_csr_ops(int csrno, const riscv_csr_operations *ops);
+
+/* In th_csr.c */
+extern const RISCVCSR th_csr_list[];
+
+#endif /* RISCV_CSR_H */
diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
index 246ec81beb..d8d06f92bc 100644
--- a/target/riscv/cpu.c
+++ b/target/riscv/cpu.c
@@ -23,6 +23,7 @@
 #include "qemu/log.h"
 #include "cpu.h"
 #include "cpu_vendorid.h"
+#include "csr.h"
 #include "internals.h"
 #include "qapi/error.h"
 #include "qapi/visitor.h"
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 0e7236098b..3ebfd19b07 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -22,6 +22,7 @@
 #include "qemu/log.h"
 #include "qemu/timer.h"
 #include "cpu.h"
+#include "csr.h"
 #include "tcg/tcg-cpu.h"
 #include "pmu.h"
 #include "time_helper.h"
diff --git a/target/riscv/gdbstub.c b/target/riscv/gdbstub.c
index 1934f919c0..f8d3bc0df1 100644
--- a/target/riscv/gdbstub.c
+++ b/target/riscv/gdbstub.c
@@ -20,6 +20,7 @@
 #include "exec/gdbstub.h"
 #include "gdbstub/helpers.h"
 #include "cpu.h"
+#include "csr.h"
 
 struct TypeSize {
     const char *gdb_type;
diff --git a/target/riscv/kvm/kvm-cpu.c b/target/riscv/kvm/kvm-cpu.c
index 5c19062c19..ad58e84158 100644
--- a/target/riscv/kvm/kvm-cpu.c
+++ b/target/riscv/kvm/kvm-cpu.c
@@ -31,6 +31,7 @@
 #include "system/kvm.h"
 #include "system/kvm_int.h"
 #include "cpu.h"
+#include "csr.h"
 #include "trace.h"
 #include "accel/accel-cpu-target.h"
 #include "hw/pci/pci.h"
diff --git a/target/riscv/op_helper.c b/target/riscv/op_helper.c
index 110292e84d..d2d9f2a47a 100644
--- a/target/riscv/op_helper.c
+++ b/target/riscv/op_helper.c
@@ -20,6 +20,7 @@
 
 #include "qemu/osdep.h"
 #include "cpu.h"
+#include "csr.h"
 #include "internals.h"
 #include "exec/cputlb.h"
 #include "accel/tcg/cpu-ldst.h"
diff --git a/target/riscv/th_csr.c b/target/riscv/th_csr.c
index 49eb7bbab5..bf6f8d62a3 100644
--- a/target/riscv/th_csr.c
+++ b/target/riscv/th_csr.c
@@ -19,6 +19,7 @@
 #include "qemu/osdep.h"
 #include "cpu.h"
 #include "cpu_vendorid.h"
+#include "csr.h"
 
 #define CSR_TH_SXSTATUS 0x5c0
 
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 32/33] target/riscv: Introduce externally facing CSR access functions
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (30 preceding siblings ...)
  2025-10-01  7:33 ` [PATCH v2 31/33] target/riscv: Move CSR declarations to separate csr.h header Anton Johansson via
@ 2025-10-01  7:33 ` Anton Johansson via
  2025-10-02 20:24   ` Pierrick Bouvier
  2025-10-01  7:33 ` [PATCH v2 33/33] target/riscv: Make pmp.h target_ulong agnostic Anton Johansson via
  32 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:33 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

Convert riscv_csr_[read|write]() into target_ulong angnostic CSR access
functions that can be safely used from outside of target/ without
knowledge of the target register size.  Replace the 4 existing CSR
accesses in hw/ and linux-user/.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/cpu.h        |  7 ++++++-
 target/riscv/csr.h        | 13 -------------
 hw/riscv/riscv_hart.c     |  7 +++----
 linux-user/riscv/signal.c |  5 +++--
 target/riscv/csr.c        | 17 +++++++++++++++++
 5 files changed, 29 insertions(+), 20 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 61319575b0..27f697f044 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -849,7 +849,12 @@ RISCVPmPmm riscv_pm_get_pmm(CPURISCVState *env);
 RISCVPmPmm riscv_pm_get_virt_pmm(CPURISCVState *env);
 uint32_t riscv_pm_get_pmlen(RISCVPmPmm pmm);
 
-#include "csr.h"
+/*
+ * Externally facing CSR access functions, asserts if access fails.
+ */
+
+int riscv_csr_write_i64(CPURISCVState *env, int csrno, uint64_t val);
+int riscv_csr_read_i64(CPURISCVState *env, int csrn, uint64_t *res);
 
 /*
  * The event id are encoded based on the encoding specified in the
diff --git a/target/riscv/csr.h b/target/riscv/csr.h
index fab53992bb..552e6c5de5 100644
--- a/target/riscv/csr.h
+++ b/target/riscv/csr.h
@@ -23,19 +23,6 @@ RISCVException riscv_csrrw_debug(CPURISCVState *env, int csrno,
                                  target_ulong new_value,
                                  target_ulong write_mask);
 
-static inline void riscv_csr_write(CPURISCVState *env, int csrno,
-                                   target_ulong val)
-{
-    riscv_csrrw(env, csrno, NULL, val, MAKE_64BIT_MASK(0, TARGET_LONG_BITS), 0);
-}
-
-static inline target_ulong riscv_csr_read(CPURISCVState *env, int csrno)
-{
-    target_ulong val = 0;
-    riscv_csrrw(env, csrno, &val, 0, 0, 0);
-    return val;
-}
-
 typedef RISCVException (*riscv_csr_predicate_fn)(CPURISCVState *env,
                                                  int csrno);
 typedef RISCVException (*riscv_csr_read_fn)(CPURISCVState *env, int csrno,
diff --git a/hw/riscv/riscv_hart.c b/hw/riscv/riscv_hart.c
index 7f2676008c..c7e98a4308 100644
--- a/hw/riscv/riscv_hart.c
+++ b/hw/riscv/riscv_hart.c
@@ -67,12 +67,11 @@ static void csr_call(char *cmd, uint64_t cpu_num, int csrno, uint64_t *val)
     RISCVCPU *cpu = RISCV_CPU(cpu_by_arch_id(cpu_num));
     CPURISCVState *env = &cpu->env;
 
-    int ret = RISCV_EXCP_NONE;
+    RISCVException ret = RISCV_EXCP_NONE;
     if (strcmp(cmd, "get_csr") == 0) {
-        ret = riscv_csrr(env, csrno, (target_ulong *)val);
+        ret = riscv_csr_read_i64(env, csrno, val);
     } else if (strcmp(cmd, "set_csr") == 0) {
-        ret = riscv_csrrw(env, csrno, NULL, *(target_ulong *)val,
-                          MAKE_64BIT_MASK(0, TARGET_LONG_BITS), 0);
+        ret = riscv_csr_write_i64(env, csrno, *val);
     }
 
     g_assert(ret == RISCV_EXCP_NONE);
diff --git a/linux-user/riscv/signal.c b/linux-user/riscv/signal.c
index 358fa1d82d..9d5ba300e4 100644
--- a/linux-user/riscv/signal.c
+++ b/linux-user/riscv/signal.c
@@ -90,7 +90,8 @@ static void setup_sigcontext(struct target_sigcontext *sc, CPURISCVState *env)
         __put_user(env->fpr[i], &sc->fpr[i]);
     }
 
-    uint32_t fcsr = riscv_csr_read(env, CSR_FCSR);
+    uint64_t fcsr;
+    riscv_csr_read_i64(env, CSR_FCSR, &fcsr);
     __put_user(fcsr, &sc->fcsr);
 }
 
@@ -159,7 +160,7 @@ static void restore_sigcontext(CPURISCVState *env, struct target_sigcontext *sc)
 
     uint32_t fcsr;
     __get_user(fcsr, &sc->fcsr);
-    riscv_csr_write(env, CSR_FCSR, fcsr);
+    riscv_csr_write_i64(env, CSR_FCSR, fcsr);
 }
 
 static void restore_ucontext(CPURISCVState *env, struct target_ucontext *uc)
diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 3ebfd19b07..83ef9fe707 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -5653,6 +5653,23 @@ RISCVException riscv_csrrw(CPURISCVState *env, int csrno,
     return riscv_csrrw_do64(env, csrno, ret_value, new_value, write_mask, ra);
 }
 
+int riscv_csr_write_i64(CPURISCVState *env, int csrno, uint64_t val)
+{
+    RISCVException ret;
+    ret = riscv_csrrw(env, csrno, NULL, val,
+                      MAKE_64BIT_MASK(0, TARGET_LONG_BITS), 0);
+    return ret;
+}
+
+int riscv_csr_read_i64(CPURISCVState *env, int csrno, uint64_t *res)
+{
+    RISCVException ret;
+    target_ulong val = 0;
+    ret = riscv_csrr(env, csrno, &val);
+    *res = val;
+    return ret;
+}
+
 static RISCVException riscv_csrrw_do128(CPURISCVState *env, int csrno,
                                         Int128 *ret_value,
                                         Int128 new_value,
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* [PATCH v2 33/33] target/riscv: Make pmp.h target_ulong agnostic
  2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
                   ` (31 preceding siblings ...)
  2025-10-01  7:33 ` [PATCH v2 32/33] target/riscv: Introduce externally facing CSR access functions Anton Johansson via
@ 2025-10-01  7:33 ` Anton Johansson via
  2025-10-01  7:49   ` Philippe Mathieu-Daudé
  2025-10-02 20:23   ` Pierrick Bouvier
  32 siblings, 2 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  7:33 UTC (permalink / raw)
  To: qemu-devel
  Cc: pierrick.bouvier, philmd, richard.henderson, alistair.francis,
	palmer

The pmp.h header is exposed through cpu.h.  pmp_table_t is also used in
CPUArchState.  CSR declaraions are only used in target/ and are moved to
csr.h.  In pmp.h, addr_reg is widened to 64 bits and the privilege mode
parameter is fixed to 8 bits, similar to previous commits.

Note, the cpu/pmp/entry and cpu/pmp VMSTATE versions are bumped, breaking
migration from older versions.

Signed-off-by: Anton Johansson <anjo@rev.ng>
---
 target/riscv/csr.h     | 12 ++++++++++++
 target/riscv/pmp.h     | 20 +++++---------------
 target/riscv/machine.c | 10 +++++-----
 target/riscv/pmp.c     |  9 +++++----
 4 files changed, 27 insertions(+), 24 deletions(-)

diff --git a/target/riscv/csr.h b/target/riscv/csr.h
index 552e6c5de5..3752a0ef43 100644
--- a/target/riscv/csr.h
+++ b/target/riscv/csr.h
@@ -78,4 +78,16 @@ void riscv_set_csr_ops(int csrno, const riscv_csr_operations *ops);
 /* In th_csr.c */
 extern const RISCVCSR th_csr_list[];
 
+/* PMP CSRs, defined in pmp.c */
+void pmpcfg_csr_write(CPURISCVState *env, uint32_t reg_index,
+                      target_ulong val);
+target_ulong pmpcfg_csr_read(CPURISCVState *env, uint32_t reg_index);
+
+void mseccfg_csr_write(CPURISCVState *env, uint64_t val);
+uint64_t mseccfg_csr_read(CPURISCVState *env);
+
+void pmpaddr_csr_write(CPURISCVState *env, uint32_t addr_index,
+                       target_ulong val);
+target_ulong pmpaddr_csr_read(CPURISCVState *env, uint32_t addr_index);
+
 #endif /* RISCV_CSR_H */
diff --git a/target/riscv/pmp.h b/target/riscv/pmp.h
index e322904637..c9b0ee6c58 100644
--- a/target/riscv/pmp.h
+++ b/target/riscv/pmp.h
@@ -22,8 +22,6 @@
 #ifndef RISCV_PMP_H
 #define RISCV_PMP_H
 
-#include "cpu.h"
-
 typedef enum {
     PMP_READ  = 1 << 0,
     PMP_WRITE = 1 << 1,
@@ -50,7 +48,7 @@ typedef enum {
 } mseccfg_field_t;
 
 typedef struct {
-    target_ulong addr_reg;
+    uint64_t addr_reg;
     uint8_t  cfg_reg;
 } pmp_entry_t;
 
@@ -65,21 +63,13 @@ typedef struct {
     uint32_t num_rules;
 } pmp_table_t;
 
-void pmpcfg_csr_write(CPURISCVState *env, uint32_t reg_index,
-                      target_ulong val);
-target_ulong pmpcfg_csr_read(CPURISCVState *env, uint32_t reg_index);
-
-void mseccfg_csr_write(CPURISCVState *env, uint64_t val);
-uint64_t mseccfg_csr_read(CPURISCVState *env);
+typedef struct CPUArchState CPURISCVState;
 
-void pmpaddr_csr_write(CPURISCVState *env, uint32_t addr_index,
-                       target_ulong val);
-target_ulong pmpaddr_csr_read(CPURISCVState *env, uint32_t addr_index);
 bool pmp_hart_has_privs(CPURISCVState *env, hwaddr addr,
-                        target_ulong size, pmp_priv_t privs,
+                        int size, pmp_priv_t privs,
                         pmp_priv_t *allowed_privs,
-                        target_ulong mode);
-target_ulong pmp_get_tlb_size(CPURISCVState *env, hwaddr addr);
+                        uint8_t mode);
+uint64_t pmp_get_tlb_size(CPURISCVState *env, hwaddr addr);
 void pmp_update_rule_addr(CPURISCVState *env, uint32_t pmp_index);
 void pmp_update_rule_nums(CPURISCVState *env);
 uint32_t pmp_get_num_rules(CPURISCVState *env);
diff --git a/target/riscv/machine.c b/target/riscv/machine.c
index aa71aa6eb1..6b92ac02b3 100644
--- a/target/riscv/machine.c
+++ b/target/riscv/machine.c
@@ -48,10 +48,10 @@ static int pmp_post_load(void *opaque, int version_id)
 
 static const VMStateDescription vmstate_pmp_entry = {
     .name = "cpu/pmp/entry",
-    .version_id = 1,
-    .minimum_version_id = 1,
+    .version_id = 2,
+    .minimum_version_id = 2,
     .fields = (const VMStateField[]) {
-        VMSTATE_UINTTL(addr_reg, pmp_entry_t),
+        VMSTATE_UINT64(addr_reg, pmp_entry_t),
         VMSTATE_UINT8(cfg_reg, pmp_entry_t),
         VMSTATE_END_OF_LIST()
     }
@@ -59,8 +59,8 @@ static const VMStateDescription vmstate_pmp_entry = {
 
 static const VMStateDescription vmstate_pmp = {
     .name = "cpu/pmp",
-    .version_id = 1,
-    .minimum_version_id = 1,
+    .version_id = 2,
+    .minimum_version_id = 2,
     .needed = pmp_needed,
     .post_load = pmp_post_load,
     .fields = (const VMStateField[]) {
diff --git a/target/riscv/pmp.c b/target/riscv/pmp.c
index 85199c7387..6089e2730e 100644
--- a/target/riscv/pmp.c
+++ b/target/riscv/pmp.c
@@ -23,6 +23,7 @@
 #include "qemu/log.h"
 #include "qapi/error.h"
 #include "cpu.h"
+#include "csr.h"
 #include "trace.h"
 #include "exec/cputlb.h"
 #include "exec/page-protection.h"
@@ -272,7 +273,7 @@ static int pmp_is_in_range(CPURISCVState *env, int pmp_index, hwaddr addr)
  */
 static bool pmp_hart_has_privs_default(CPURISCVState *env, pmp_priv_t privs,
                                        pmp_priv_t *allowed_privs,
-                                       target_ulong mode)
+                                       uint8_t mode)
 {
     bool ret;
 
@@ -331,8 +332,8 @@ static bool pmp_hart_has_privs_default(CPURISCVState *env, pmp_priv_t privs,
  * Return false if no match
  */
 bool pmp_hart_has_privs(CPURISCVState *env, hwaddr addr,
-                        target_ulong size, pmp_priv_t privs,
-                        pmp_priv_t *allowed_privs, target_ulong mode)
+                        int size, pmp_priv_t privs,
+                        pmp_priv_t *allowed_privs, uint8_t mode)
 {
     int i = 0;
     int pmp_size = 0;
@@ -662,7 +663,7 @@ uint64_t mseccfg_csr_read(CPURISCVState *env)
  * To avoid this we return a size of 1 (which means no caching) if the PMP
  * region only covers partial of the TLB page.
  */
-target_ulong pmp_get_tlb_size(CPURISCVState *env, hwaddr addr)
+uint64_t pmp_get_tlb_size(CPURISCVState *env, hwaddr addr)
 {
     hwaddr pmp_sa;
     hwaddr pmp_ea;
-- 
2.51.0



^ permalink raw reply related	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions
  2025-10-01  7:32 ` [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions Anton Johansson via
@ 2025-10-01  7:34   ` Philippe Mathieu-Daudé
  2025-10-02  1:56   ` Alistair Francis
  2025-10-02 18:31   ` Pierrick Bouvier
  2 siblings, 0 replies; 99+ messages in thread
From: Philippe Mathieu-Daudé @ 2025-10-01  7:34 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: pierrick.bouvier, richard.henderson, alistair.francis, palmer

On 1/10/25 09:32, Anton Johansson wrote:
> uint32_t is already in use in most places storing misa extensions such
> as CPUArchState::misa_exts, RISCVCPUProfile::misa_exts,
> RISCVImpliedExtsRule::implied_misa_exts.  Additionally. the field is
> already migrated as uint32_t.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h | 4 ++--
>   1 file changed, 2 insertions(+), 2 deletions(-)

Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 03/33] target/riscv: Fix size of mhartid
  2025-10-01  7:32 ` [PATCH v2 03/33] target/riscv: Fix size of mhartid Anton Johansson via
@ 2025-10-01  7:38   ` Philippe Mathieu-Daudé
  2025-10-01  8:28     ` Anton Johansson via
  0 siblings, 1 reply; 99+ messages in thread
From: Philippe Mathieu-Daudé @ 2025-10-01  7:38 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: pierrick.bouvier, richard.henderson, alistair.francis, palmer

On 1/10/25 09:32, Anton Johansson wrote:
> and update formatting in log.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h         | 2 +-
>   target/riscv/cpu_helper.c  | 2 +-
>   target/riscv/machine.c     | 2 +-
>   target/riscv/tcg/tcg-cpu.c | 2 +-
>   4 files changed, 4 insertions(+), 4 deletions(-)
> 
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index 736e4f6daa..3235108112 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -279,7 +279,7 @@ struct CPUArchState {
>       target_ulong geilen;
>       uint64_t resetvec;
>   
> -    target_ulong mhartid;
> +    uint64_t mhartid;
>       /*
>        * For RV32 this is 32-bit mstatus and 32-bit mstatush.
>        * For RV64 this is a 64-bit mstatus.


> diff --git a/target/riscv/machine.c b/target/riscv/machine.c
> index 99e46c3136..328fb674e1 100644
> --- a/target/riscv/machine.c
> +++ b/target/riscv/machine.c
> @@ -425,7 +425,7 @@ const VMStateDescription vmstate_riscv_cpu = {
>           VMSTATE_UINTTL(env.priv, RISCVCPU),
>           VMSTATE_BOOL(env.virt_enabled, RISCVCPU),
>           VMSTATE_UINT64(env.resetvec, RISCVCPU),
> -        VMSTATE_UINTTL(env.mhartid, RISCVCPU),
> +        VMSTATE_UINT64(env.mhartid, RISCVCPU),

The problem is you break the migration stream again. Maybe simpler to
just squash with previous patch?

Thay said, IIUC mhartid is only set once in riscv_hart_realize().
I suspect it is pointless to migrate it.


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh
  2025-10-01  7:32 ` [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh Anton Johansson via
@ 2025-10-01  7:39   ` Philippe Mathieu-Daudé
  2025-10-02 19:09     ` Pierrick Bouvier
  2025-10-02 19:08   ` Pierrick Bouvier
  1 sibling, 1 reply; 99+ messages in thread
From: Philippe Mathieu-Daudé @ 2025-10-01  7:39 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: pierrick.bouvier, richard.henderson, alistair.francis, palmer

On 1/10/25 09:32, Anton Johansson wrote:
> According to version 20250508 of the privileged specification,
> mhpmeventn is 64 bits in size and mhpmeventnh is only ever used
> when XLEN == 32 and accesses the top 32 bits of the 64-bit
> mhpmeventn registers. Combine the two arrays of target_ulong
> mhpmeventh[] and mhpmevent[] to a single array of uint64_t.
> 
> This also allows for some minor code simplification where branches
> handling either mhpmeventh[] or mhpmevent[] could be combined.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h     | 10 +++----
>   target/riscv/csr.c     | 67 +++++++++++++++---------------------------
>   target/riscv/machine.c |  3 +-
>   target/riscv/pmu.c     | 53 ++++++++-------------------------
>   4 files changed, 42 insertions(+), 91 deletions(-)


> diff --git a/target/riscv/machine.c b/target/riscv/machine.c
> index 328fb674e1..d9939489e1 100644
> --- a/target/riscv/machine.c
> +++ b/target/riscv/machine.c
> @@ -452,8 +452,7 @@ const VMStateDescription vmstate_riscv_cpu = {
>           VMSTATE_UINT32(env.mcountinhibit, RISCVCPU),
>           VMSTATE_STRUCT_ARRAY(env.pmu_ctrs, RISCVCPU, RV_MAX_MHPMCOUNTERS, 0,
>                                vmstate_pmu_ctr_state, PMUCTRState),
> -        VMSTATE_UINTTL_ARRAY(env.mhpmevent_val, RISCVCPU, RV_MAX_MHPMEVENTS),
> -        VMSTATE_UINTTL_ARRAY(env.mhpmeventh_val, RISCVCPU, RV_MAX_MHPMEVENTS),
> +        VMSTATE_UINT64_ARRAY(env.mhpmevent_val, RISCVCPU, RV_MAX_MHPMEVENTS),

Each time you change a VMStateDescription structure you need to bump its
version.


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 09/33] target/riscv: Fix size of gpr and gprh
  2025-10-01  7:32 ` [PATCH v2 09/33] target/riscv: Fix size of gpr and gprh Anton Johansson via
@ 2025-10-01  7:42   ` Philippe Mathieu-Daudé
  2025-10-03  9:00     ` Anton Johansson via
  0 siblings, 1 reply; 99+ messages in thread
From: Philippe Mathieu-Daudé @ 2025-10-01  7:42 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: pierrick.bouvier, richard.henderson, alistair.francis, palmer

On 1/10/25 09:32, Anton Johansson wrote:
> gprh is only needed for TARGET_RISCV64 when modeling 128-bit registers,
> fixing their size to 64 bits makes sense.
> 
> gpr is also fixed to 64 bits since all direct uses of env->gpr
> correctly zero extend/truncate to/from target_ulong, meaning
> !TARGET_RISCV64 will behave as expected.
> 
> We do however need to be a bit careful when mapping 64-bit fields to
> 32-bit TCGv globals on big endian hosts.
> 
> Note, the cpu/rv128 VMSTATE version is bumped, breaking migration from
> older versions.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h       |  4 ++--
>   target/riscv/cpu.c       |  2 +-
>   target/riscv/machine.c   |  8 ++++----
>   target/riscv/translate.c | 17 +++++++++++++++--
>   4 files changed, 22 insertions(+), 9 deletions(-)


> diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
> index d055ddf462..3c910e44cd 100644
> --- a/target/riscv/cpu.c
> +++ b/target/riscv/cpu.c
> @@ -584,7 +584,7 @@ static void riscv_cpu_dump_state(CPUState *cs, FILE *f, int flags)
>   
>       for (i = 0; i < 32; i++) {
>           qemu_fprintf(f, " %-8s " TARGET_FMT_lx,
> -                     riscv_int_regnames[i], env->gpr[i]);
> +                     riscv_int_regnames[i], (target_ulong) env->gpr[i]);

Rebase mistake?

>           if ((i & 3) == 3) {
>               qemu_fprintf(f, "\n");
>           }


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 25/33] target/riscv: Indent PMUFixedCtrState correctly
  2025-10-01  7:32 ` [PATCH v2 25/33] target/riscv: Indent PMUFixedCtrState correctly Anton Johansson via
@ 2025-10-01  7:43   ` Philippe Mathieu-Daudé
  2025-10-02 20:15   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Philippe Mathieu-Daudé @ 2025-10-01  7:43 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: pierrick.bouvier, richard.henderson, alistair.francis, palmer

On 1/10/25 09:32, Anton Johansson wrote:
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h | 12 ++++++------
>   1 file changed, 6 insertions(+), 6 deletions(-)

Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 26/33] target/riscv: Replace target_ulong in riscv_cpu_get_trap_name()
  2025-10-01  7:32 ` [PATCH v2 26/33] target/riscv: Replace target_ulong in riscv_cpu_get_trap_name() Anton Johansson via
@ 2025-10-01  7:43   ` Philippe Mathieu-Daudé
  2025-10-02 20:15   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Philippe Mathieu-Daudé @ 2025-10-01  7:43 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: pierrick.bouvier, richard.henderson, alistair.francis, palmer

On 1/10/25 09:32, Anton Johansson wrote:
> Fix cause argument to 64 bit to match env->mcause.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h | 2 +-
>   target/riscv/cpu.c | 2 +-
>   2 files changed, 2 insertions(+), 2 deletions(-)

Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 27/33] target/riscv: Replace target_ulong in riscv_ctr_add_entry()
  2025-10-01  7:33 ` [PATCH v2 27/33] target/riscv: Replace target_ulong in riscv_ctr_add_entry() Anton Johansson via
@ 2025-10-01  7:44   ` Philippe Mathieu-Daudé
  2025-10-02 20:19   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Philippe Mathieu-Daudé @ 2025-10-01  7:44 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: pierrick.bouvier, richard.henderson, alistair.francis, palmer

On 1/10/25 09:33, Anton Johansson wrote:
> Widen to 64 bits in size to hold all relevant values.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h        | 2 +-
>   target/riscv/cpu_helper.c | 4 ++--
>   2 files changed, 3 insertions(+), 3 deletions(-)

Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 28/33] target/riscv: Fix size of trigger data
  2025-10-01  7:33 ` [PATCH v2 28/33] target/riscv: Fix size of trigger data Anton Johansson via
@ 2025-10-01  7:46   ` Philippe Mathieu-Daudé
  2025-10-02 20:19   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Philippe Mathieu-Daudé @ 2025-10-01  7:46 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: pierrick.bouvier, richard.henderson, alistair.francis, palmer

On 1/10/25 09:33, Anton Johansson wrote:
> mcontext is at most 14 bits in size with the H extension, fix to 16
> bits. trigger_cur indexes into tdata*[RV_MAX_TRIGGERS] which holds 2
> elements, fix to 8 bits.
> 
> Note, the cpu/debug VMSTATE version is bumped, breaking migration from
> older versions.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h     | 10 +++++-----
>   target/riscv/machine.c | 12 ++++++------
>   2 files changed, 11 insertions(+), 11 deletions(-)
> 
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index b17aca0e02..b718f6f3b1 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -460,11 +460,11 @@ struct CPUArchState {
>       target_ulong mseccfg;
>   
>       /* trigger module */
> -    target_ulong trigger_cur;
> -    target_ulong tdata1[RV_MAX_TRIGGERS];
> -    target_ulong tdata2[RV_MAX_TRIGGERS];
> -    target_ulong tdata3[RV_MAX_TRIGGERS];
> -    target_ulong mcontext;
> +    uint16_t mcontext;
> +    uint8_t trigger_cur;
> +    uint64_t tdata1[RV_MAX_TRIGGERS];
> +    uint64_t tdata2[RV_MAX_TRIGGERS];
> +    uint64_t tdata3[RV_MAX_TRIGGERS];
>       struct CPUBreakpoint *cpu_breakpoint[RV_MAX_TRIGGERS];
>       struct CPUWatchpoint *cpu_watchpoint[RV_MAX_TRIGGERS];
>       QEMUTimer *itrigger_timer[RV_MAX_TRIGGERS];
> diff --git a/target/riscv/machine.c b/target/riscv/machine.c
> index 18dbc1bfa9..aa71aa6eb1 100644
> --- a/target/riscv/machine.c
> +++ b/target/riscv/machine.c
> @@ -238,15 +238,15 @@ static int debug_post_load(void *opaque, int version_id)
>   
>   static const VMStateDescription vmstate_debug = {
>       .name = "cpu/debug",
> -    .version_id = 2,
> -    .minimum_version_id = 2,
> +    .version_id = 3,
> +    .minimum_version_id = 3,
>       .needed = debug_needed,
>       .post_load = debug_post_load,
>       .fields = (const VMStateField[]) {
> -        VMSTATE_UINTTL(env.trigger_cur, RISCVCPU),
> -        VMSTATE_UINTTL_ARRAY(env.tdata1, RISCVCPU, RV_MAX_TRIGGERS),
> -        VMSTATE_UINTTL_ARRAY(env.tdata2, RISCVCPU, RV_MAX_TRIGGERS),
> -        VMSTATE_UINTTL_ARRAY(env.tdata3, RISCVCPU, RV_MAX_TRIGGERS),
> +        VMSTATE_UINT8(env.trigger_cur, RISCVCPU),
> +        VMSTATE_UINT64_ARRAY(env.tdata1, RISCVCPU, RV_MAX_TRIGGERS),
> +        VMSTATE_UINT64_ARRAY(env.tdata2, RISCVCPU, RV_MAX_TRIGGERS),
> +        VMSTATE_UINT64_ARRAY(env.tdata3, RISCVCPU, RV_MAX_TRIGGERS),

Should mcontext be migrated?

>           VMSTATE_END_OF_LIST()
>       }
>   };


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 29/33] target/riscv: Fix size of mseccfg
  2025-10-01  7:33 ` [PATCH v2 29/33] target/riscv: Fix size of mseccfg Anton Johansson via
@ 2025-10-01  7:46   ` Philippe Mathieu-Daudé
  2025-10-02 20:20   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Philippe Mathieu-Daudé @ 2025-10-01  7:46 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: pierrick.bouvier, richard.henderson, alistair.francis, palmer

On 1/10/25 09:33, Anton Johansson wrote:
> mseccfg is defined in version 20250508 of the privileged specification
> to be 64 bits in size.  Update relevant function arguments.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h | 2 +-
>   target/riscv/pmp.h | 4 ++--
>   target/riscv/pmp.c | 4 ++--
>   3 files changed, 5 insertions(+), 5 deletions(-)

Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 33/33] target/riscv: Make pmp.h target_ulong agnostic
  2025-10-01  7:33 ` [PATCH v2 33/33] target/riscv: Make pmp.h target_ulong agnostic Anton Johansson via
@ 2025-10-01  7:49   ` Philippe Mathieu-Daudé
  2025-10-03 12:57     ` Anton Johansson via
  2025-10-02 20:23   ` Pierrick Bouvier
  1 sibling, 1 reply; 99+ messages in thread
From: Philippe Mathieu-Daudé @ 2025-10-01  7:49 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: pierrick.bouvier, richard.henderson, alistair.francis, palmer

On 1/10/25 09:33, Anton Johansson wrote:
> The pmp.h header is exposed through cpu.h.  pmp_table_t is also used in
> CPUArchState.  CSR declaraions are only used in target/ and are moved to

Typo "declarations".

> csr.h.  In pmp.h, addr_reg is widened to 64 bits and the privilege mode
> parameter is fixed to 8 bits, similar to previous commits.

Worth a privilege_mode_t typedef?

> 
> Note, the cpu/pmp/entry and cpu/pmp VMSTATE versions are bumped, breaking
> migration from older versions.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/csr.h     | 12 ++++++++++++
>   target/riscv/pmp.h     | 20 +++++---------------
>   target/riscv/machine.c | 10 +++++-----
>   target/riscv/pmp.c     |  9 +++++----
>   4 files changed, 27 insertions(+), 24 deletions(-)

Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 03/33] target/riscv: Fix size of mhartid
  2025-10-01  7:38   ` Philippe Mathieu-Daudé
@ 2025-10-01  8:28     ` Anton Johansson via
  2025-10-02 18:34       ` Pierrick Bouvier
  0 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-01  8:28 UTC (permalink / raw)
  To: Philippe Mathieu-Daudé
  Cc: qemu-devel, pierrick.bouvier, richard.henderson, alistair.francis,
	palmer

On 01/10/25, Philippe Mathieu-Daudé wrote:
> On 1/10/25 09:32, Anton Johansson wrote:
> > and update formatting in log.
> > 
> > Signed-off-by: Anton Johansson <anjo@rev.ng>
> > ---
> >   target/riscv/cpu.h         | 2 +-
> >   target/riscv/cpu_helper.c  | 2 +-
> >   target/riscv/machine.c     | 2 +-
> >   target/riscv/tcg/tcg-cpu.c | 2 +-
> >   4 files changed, 4 insertions(+), 4 deletions(-)
> > 
> > diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> > index 736e4f6daa..3235108112 100644
> > --- a/target/riscv/cpu.h
> > +++ b/target/riscv/cpu.h
> > @@ -279,7 +279,7 @@ struct CPUArchState {
> >       target_ulong geilen;
> >       uint64_t resetvec;
> > -    target_ulong mhartid;
> > +    uint64_t mhartid;
> >       /*
> >        * For RV32 this is 32-bit mstatus and 32-bit mstatush.
> >        * For RV64 this is a 64-bit mstatus.
> 
> 
> > diff --git a/target/riscv/machine.c b/target/riscv/machine.c
> > index 99e46c3136..328fb674e1 100644
> > --- a/target/riscv/machine.c
> > +++ b/target/riscv/machine.c
> > @@ -425,7 +425,7 @@ const VMStateDescription vmstate_riscv_cpu = {
> >           VMSTATE_UINTTL(env.priv, RISCVCPU),
> >           VMSTATE_BOOL(env.virt_enabled, RISCVCPU),
> >           VMSTATE_UINT64(env.resetvec, RISCVCPU),
> > -        VMSTATE_UINTTL(env.mhartid, RISCVCPU),
> > +        VMSTATE_UINT64(env.mhartid, RISCVCPU),
> 
> The problem is you break the migration stream again. Maybe simpler to
> just squash with previous patch?
> 
> Thay said, IIUC mhartid is only set once in riscv_hart_realize().
> I suspect it is pointless to migrate it.

Right, wrt the other vmstate changes I only bumped the version on first
modification.  Maybe it makes more sense to group changes based on what
vmstate they touch?  If excessive version bumping is a problem that is.


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions
  2025-10-01  7:32 ` [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions Anton Johansson via
  2025-10-01  7:34   ` Philippe Mathieu-Daudé
@ 2025-10-02  1:56   ` Alistair Francis
  2025-10-02 18:31   ` Pierrick Bouvier
  2 siblings, 0 replies; 99+ messages in thread
From: Alistair Francis @ 2025-10-02  1:56 UTC (permalink / raw)
  To: Anton Johansson
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On Wed, Oct 1, 2025 at 5:33 PM Anton Johansson via
<qemu-devel@nongnu.org> wrote:
>
> uint32_t is already in use in most places storing misa extensions such
> as CPUArchState::misa_exts, RISCVCPUProfile::misa_exts,
> RISCVImpliedExtsRule::implied_misa_exts.  Additionally. the field is
> already migrated as uint32_t.
>
> Signed-off-by: Anton Johansson <anjo@rev.ng>

Reviewed-by: Alistair Francis <alistair.francis@wdc.com>

Alistair

> ---
>  target/riscv/cpu.h | 4 ++--
>  1 file changed, 2 insertions(+), 2 deletions(-)
>
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index 4a862da615..f05e06bb70 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -50,7 +50,7 @@ typedef struct CPUArchState CPURISCVState;
>   */
>  #define RISCV_UW2_ALWAYS_STORE_AMO 1
>
> -#define RV(x) ((target_ulong)1 << (x - 'A'))
> +#define RV(x) BIT(x - 'A')
>
>  /*
>   * Update misa_bits[], misa_ext_info_arr[] and misa_ext_cfgs[]
> @@ -582,7 +582,7 @@ struct RISCVCPUClass {
>      RISCVCPUDef *def;
>  };
>
> -static inline int riscv_has_ext(CPURISCVState *env, target_ulong ext)
> +static inline int riscv_has_ext(CPURISCVState *env, uint32_t ext)
>  {
>      return (env->misa_ext & ext) != 0;
>  }
> --
> 2.51.0
>
>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 02/33] target/riscv: Fix size of trivial CPUArchState fields
  2025-10-01  7:32 ` [PATCH v2 02/33] target/riscv: Fix size of trivial CPUArchState fields Anton Johansson via
@ 2025-10-02  1:57   ` Alistair Francis
  2025-10-02 18:31   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Alistair Francis @ 2025-10-02  1:57 UTC (permalink / raw)
  To: Anton Johansson
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On Wed, Oct 1, 2025 at 5:45 PM Anton Johansson via
<qemu-devel@nongnu.org> wrote:
>
> This commits groups together all CPUArchState fields whose behaviour can
> be retained by simply changing the size of the field.
>
> Note, senvcfg is defined to be SXLEN bits wide, but is widened to 64
> bits to match henvcfg and menvcfg.  Next, [m|h]edeleg are changed to
> 64 bits as defined privileged specification, and hvictl is fixed to 32
> bits which holds all relevant values, see HVICTL_VALID_MASK.  The
> remaining fields touched in the commit are widened from [H|S|M]XLEN
> to 64-bit.
>
> Note, the cpu/hyper, cpu/envcfg, cpu/jvt, and cpu VMSTATE versions are
> bumped, breaking migration from older versions.
>
> References to the privileged/unprivileged RISCV specification refer to
> version 20250508.
>
> Signed-off-by: Anton Johansson <anjo@rev.ng>

Reviewed-by: Alistair Francis <alistair.francis@wdc.com>

Alistair

> ---
>  target/riscv/cpu.h     | 78 +++++++++++++++++++--------------------
>  target/riscv/machine.c | 84 +++++++++++++++++++++---------------------
>  2 files changed, 81 insertions(+), 81 deletions(-)
>
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index f05e06bb70..736e4f6daa 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -254,7 +254,7 @@ struct CPUArchState {
>      /* 128-bit helpers upper part return value */
>      target_ulong retxh;
>
> -    target_ulong jvt;
> +    uint64_t jvt;
>
>      /* elp state for zicfilp extension */
>      bool      elp;
> @@ -271,7 +271,7 @@ struct CPUArchState {
>      target_ulong priv;
>      /* CSRs for execution environment configuration */
>      uint64_t menvcfg;
> -    target_ulong senvcfg;
> +    uint64_t senvcfg;
>
>  #ifndef CONFIG_USER_ONLY
>      /* This contains QEMU specific information about the virt state. */
> @@ -313,18 +313,18 @@ struct CPUArchState {
>       */
>      uint64_t vsie;
>
> -    target_ulong satp;   /* since: priv-1.10.0 */
> -    target_ulong stval;
> -    target_ulong medeleg;
> +    uint64_t satp;   /* since: priv-1.10.0 */
> +    uint64_t stval;
> +    uint64_t medeleg;
>
> -    target_ulong stvec;
> -    target_ulong sepc;
> -    target_ulong scause;
> +    uint64_t stvec;
> +    uint64_t sepc;
> +    uint64_t scause;
>
> -    target_ulong mtvec;
> -    target_ulong mepc;
> -    target_ulong mcause;
> -    target_ulong mtval;  /* since: priv-1.10.0 */
> +    uint64_t mtvec;
> +    uint64_t mepc;
> +    uint64_t mcause;
> +    uint64_t mtval;  /* since: priv-1.10.0 */
>
>      uint64_t mctrctl;
>      uint32_t sctrdepth;
> @@ -346,13 +346,13 @@ struct CPUArchState {
>      uint64_t mvip;
>
>      /* Hypervisor CSRs */
> -    target_ulong hstatus;
> -    target_ulong hedeleg;
> +    uint64_t hstatus;
> +    uint64_t hedeleg;
>      uint64_t hideleg;
>      uint32_t hcounteren;
> -    target_ulong htval;
> -    target_ulong htinst;
> -    target_ulong hgatp;
> +    uint64_t htval;
> +    uint64_t htinst;
> +    uint64_t hgatp;
>      target_ulong hgeie;
>      target_ulong hgeip;
>      uint64_t htimedelta;
> @@ -366,7 +366,7 @@ struct CPUArchState {
>      uint64_t hvip;
>
>      /* Hypervisor controlled virtual interrupt priorities */
> -    target_ulong hvictl;
> +    uint32_t hvictl;
>      uint8_t hviprio[64];
>
>      /* Upper 64-bits of 128-bit CSRs */
> @@ -379,26 +379,26 @@ struct CPUArchState {
>       * For RV64 this is a 64-bit vsstatus.
>       */
>      uint64_t vsstatus;
> -    target_ulong vstvec;
> -    target_ulong vsscratch;
> -    target_ulong vsepc;
> -    target_ulong vscause;
> -    target_ulong vstval;
> -    target_ulong vsatp;
> +    uint64_t vstvec;
> +    uint64_t vsscratch;
> +    uint64_t vsepc;
> +    uint64_t vscause;
> +    uint64_t vstval;
> +    uint64_t vsatp;
>
>      /* AIA VS-mode CSRs */
>      target_ulong vsiselect;
>
> -    target_ulong mtval2;
> -    target_ulong mtinst;
> +    uint64_t mtval2;
> +    uint64_t mtinst;
>
>      /* HS Backup CSRs */
> -    target_ulong stvec_hs;
> -    target_ulong sscratch_hs;
> -    target_ulong sepc_hs;
> -    target_ulong scause_hs;
> -    target_ulong stval_hs;
> -    target_ulong satp_hs;
> +    uint64_t stvec_hs;
> +    uint64_t sscratch_hs;
> +    uint64_t sepc_hs;
> +    uint64_t scause_hs;
> +    uint64_t stval_hs;
> +    uint64_t satp_hs;
>      uint64_t mstatus_hs;
>
>      /*
> @@ -435,8 +435,8 @@ struct CPUArchState {
>
>      PMUFixedCtrState pmu_fixed_ctrs[2];
>
> -    target_ulong sscratch;
> -    target_ulong mscratch;
> +    uint64_t sscratch;
> +    uint64_t mscratch;
>
>      /* Sstc CSRs */
>      uint64_t stimecmp;
> @@ -506,11 +506,11 @@ struct CPUArchState {
>  #endif /* CONFIG_KVM */
>
>      /* RNMI */
> -    target_ulong mnscratch;
> -    target_ulong mnepc;
> -    target_ulong mncause; /* mncause without bit XLEN-1 set to 1 */
> -    target_ulong mnstatus;
> -    target_ulong rnmip;
> +    uint64_t mnscratch;
> +    uint64_t mnepc;
> +    uint64_t mncause; /* mncause without bit XLEN-1 set to 1 */
> +    uint64_t mnstatus;
> +    uint64_t rnmip;
>      uint64_t rnmi_irqvec;
>      uint64_t rnmi_excpvec;
>  };
> diff --git a/target/riscv/machine.c b/target/riscv/machine.c
> index 1600ec44f0..99e46c3136 100644
> --- a/target/riscv/machine.c
> +++ b/target/riscv/machine.c
> @@ -80,17 +80,17 @@ static bool hyper_needed(void *opaque)
>
>  static const VMStateDescription vmstate_hyper = {
>      .name = "cpu/hyper",
> -    .version_id = 4,
> -    .minimum_version_id = 4,
> +    .version_id = 5,
> +    .minimum_version_id = 5,
>      .needed = hyper_needed,
>      .fields = (const VMStateField[]) {
> -        VMSTATE_UINTTL(env.hstatus, RISCVCPU),
> -        VMSTATE_UINTTL(env.hedeleg, RISCVCPU),
> +        VMSTATE_UINT64(env.hstatus, RISCVCPU),
> +        VMSTATE_UINT64(env.hedeleg, RISCVCPU),
>          VMSTATE_UINT64(env.hideleg, RISCVCPU),
>          VMSTATE_UINT32(env.hcounteren, RISCVCPU),
> -        VMSTATE_UINTTL(env.htval, RISCVCPU),
> -        VMSTATE_UINTTL(env.htinst, RISCVCPU),
> -        VMSTATE_UINTTL(env.hgatp, RISCVCPU),
> +        VMSTATE_UINT64(env.htval, RISCVCPU),
> +        VMSTATE_UINT64(env.htinst, RISCVCPU),
> +        VMSTATE_UINT64(env.hgatp, RISCVCPU),
>          VMSTATE_UINTTL(env.hgeie, RISCVCPU),
>          VMSTATE_UINTTL(env.hgeip, RISCVCPU),
>          VMSTATE_UINT64(env.hvien, RISCVCPU),
> @@ -98,28 +98,28 @@ static const VMStateDescription vmstate_hyper = {
>          VMSTATE_UINT64(env.htimedelta, RISCVCPU),
>          VMSTATE_UINT64(env.vstimecmp, RISCVCPU),
>
> -        VMSTATE_UINTTL(env.hvictl, RISCVCPU),
> +        VMSTATE_UINT32(env.hvictl, RISCVCPU),
>          VMSTATE_UINT8_ARRAY(env.hviprio, RISCVCPU, 64),
>
>          VMSTATE_UINT64(env.vsstatus, RISCVCPU),
> -        VMSTATE_UINTTL(env.vstvec, RISCVCPU),
> -        VMSTATE_UINTTL(env.vsscratch, RISCVCPU),
> -        VMSTATE_UINTTL(env.vsepc, RISCVCPU),
> -        VMSTATE_UINTTL(env.vscause, RISCVCPU),
> -        VMSTATE_UINTTL(env.vstval, RISCVCPU),
> -        VMSTATE_UINTTL(env.vsatp, RISCVCPU),
> +        VMSTATE_UINT64(env.vstvec, RISCVCPU),
> +        VMSTATE_UINT64(env.vsscratch, RISCVCPU),
> +        VMSTATE_UINT64(env.vsepc, RISCVCPU),
> +        VMSTATE_UINT64(env.vscause, RISCVCPU),
> +        VMSTATE_UINT64(env.vstval, RISCVCPU),
> +        VMSTATE_UINT64(env.vsatp, RISCVCPU),
>          VMSTATE_UINTTL(env.vsiselect, RISCVCPU),
>          VMSTATE_UINT64(env.vsie, RISCVCPU),
>
> -        VMSTATE_UINTTL(env.mtval2, RISCVCPU),
> -        VMSTATE_UINTTL(env.mtinst, RISCVCPU),
> +        VMSTATE_UINT64(env.mtval2, RISCVCPU),
> +        VMSTATE_UINT64(env.mtinst, RISCVCPU),
>
> -        VMSTATE_UINTTL(env.stvec_hs, RISCVCPU),
> -        VMSTATE_UINTTL(env.sscratch_hs, RISCVCPU),
> -        VMSTATE_UINTTL(env.sepc_hs, RISCVCPU),
> -        VMSTATE_UINTTL(env.scause_hs, RISCVCPU),
> -        VMSTATE_UINTTL(env.stval_hs, RISCVCPU),
> -        VMSTATE_UINTTL(env.satp_hs, RISCVCPU),
> +        VMSTATE_UINT64(env.stvec_hs, RISCVCPU),
> +        VMSTATE_UINT64(env.sscratch_hs, RISCVCPU),
> +        VMSTATE_UINT64(env.sepc_hs, RISCVCPU),
> +        VMSTATE_UINT64(env.scause_hs, RISCVCPU),
> +        VMSTATE_UINT64(env.stval_hs, RISCVCPU),
> +        VMSTATE_UINT64(env.satp_hs, RISCVCPU),
>          VMSTATE_UINT64(env.mstatus_hs, RISCVCPU),
>
>          VMSTATE_END_OF_LIST()
> @@ -290,12 +290,12 @@ static bool envcfg_needed(void *opaque)
>
>  static const VMStateDescription vmstate_envcfg = {
>      .name = "cpu/envcfg",
> -    .version_id = 1,
> -    .minimum_version_id = 1,
> +    .version_id = 2,
> +    .minimum_version_id = 2,
>      .needed = envcfg_needed,
>      .fields = (const VMStateField[]) {
>          VMSTATE_UINT64(env.menvcfg, RISCVCPU),
> -        VMSTATE_UINTTL(env.senvcfg, RISCVCPU),
> +        VMSTATE_UINT64(env.senvcfg, RISCVCPU),
>          VMSTATE_UINT64(env.henvcfg, RISCVCPU),
>          VMSTATE_END_OF_LIST()
>      }
> @@ -355,11 +355,11 @@ static bool jvt_needed(void *opaque)
>
>  static const VMStateDescription vmstate_jvt = {
>      .name = "cpu/jvt",
> -    .version_id = 1,
> -    .minimum_version_id = 1,
> +    .version_id = 2,
> +    .minimum_version_id = 2,
>      .needed = jvt_needed,
>      .fields = (const VMStateField[]) {
> -        VMSTATE_UINTTL(env.jvt, RISCVCPU),
> +        VMSTATE_UINT64(env.jvt, RISCVCPU),
>          VMSTATE_END_OF_LIST()
>      }
>  };
> @@ -402,8 +402,8 @@ static const VMStateDescription vmstate_ssp = {
>
>  const VMStateDescription vmstate_riscv_cpu = {
>      .name = "cpu",
> -    .version_id = 10,
> -    .minimum_version_id = 10,
> +    .version_id = 11,
> +    .minimum_version_id = 11,
>      .post_load = riscv_cpu_post_load,
>      .fields = (const VMStateField[]) {
>          VMSTATE_UINTTL_ARRAY(env.gpr, RISCVCPU, 32),
> @@ -434,16 +434,16 @@ const VMStateDescription vmstate_riscv_cpu = {
>          VMSTATE_UINT64(env.mvip, RISCVCPU),
>          VMSTATE_UINT64(env.sie, RISCVCPU),
>          VMSTATE_UINT64(env.mideleg, RISCVCPU),
> -        VMSTATE_UINTTL(env.satp, RISCVCPU),
> -        VMSTATE_UINTTL(env.stval, RISCVCPU),
> -        VMSTATE_UINTTL(env.medeleg, RISCVCPU),
> -        VMSTATE_UINTTL(env.stvec, RISCVCPU),
> -        VMSTATE_UINTTL(env.sepc, RISCVCPU),
> -        VMSTATE_UINTTL(env.scause, RISCVCPU),
> -        VMSTATE_UINTTL(env.mtvec, RISCVCPU),
> -        VMSTATE_UINTTL(env.mepc, RISCVCPU),
> -        VMSTATE_UINTTL(env.mcause, RISCVCPU),
> -        VMSTATE_UINTTL(env.mtval, RISCVCPU),
> +        VMSTATE_UINT64(env.satp, RISCVCPU),
> +        VMSTATE_UINT64(env.stval, RISCVCPU),
> +        VMSTATE_UINT64(env.medeleg, RISCVCPU),
> +        VMSTATE_UINT64(env.stvec, RISCVCPU),
> +        VMSTATE_UINT64(env.sepc, RISCVCPU),
> +        VMSTATE_UINT64(env.scause, RISCVCPU),
> +        VMSTATE_UINT64(env.mtvec, RISCVCPU),
> +        VMSTATE_UINT64(env.mepc, RISCVCPU),
> +        VMSTATE_UINT64(env.mcause, RISCVCPU),
> +        VMSTATE_UINT64(env.mtval, RISCVCPU),
>          VMSTATE_UINTTL(env.miselect, RISCVCPU),
>          VMSTATE_UINTTL(env.siselect, RISCVCPU),
>          VMSTATE_UINT32(env.scounteren, RISCVCPU),
> @@ -454,8 +454,8 @@ const VMStateDescription vmstate_riscv_cpu = {
>                               vmstate_pmu_ctr_state, PMUCTRState),
>          VMSTATE_UINTTL_ARRAY(env.mhpmevent_val, RISCVCPU, RV_MAX_MHPMEVENTS),
>          VMSTATE_UINTTL_ARRAY(env.mhpmeventh_val, RISCVCPU, RV_MAX_MHPMEVENTS),
> -        VMSTATE_UINTTL(env.sscratch, RISCVCPU),
> -        VMSTATE_UINTTL(env.mscratch, RISCVCPU),
> +        VMSTATE_UINT64(env.sscratch, RISCVCPU),
> +        VMSTATE_UINT64(env.mscratch, RISCVCPU),
>          VMSTATE_UINT64(env.stimecmp, RISCVCPU),
>
>          VMSTATE_END_OF_LIST()
> --
> 2.51.0
>
>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions
  2025-10-01  7:32 ` [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions Anton Johansson via
  2025-10-01  7:34   ` Philippe Mathieu-Daudé
  2025-10-02  1:56   ` Alistair Francis
@ 2025-10-02 18:31   ` Pierrick Bouvier
  2 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 18:31 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> uint32_t is already in use in most places storing misa extensions such
> as CPUArchState::misa_exts, RISCVCPUProfile::misa_exts,
> RISCVImpliedExtsRule::implied_misa_exts.  Additionally. the field is
> already migrated as uint32_t.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h | 4 ++--
>   1 file changed, 2 insertions(+), 2 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 02/33] target/riscv: Fix size of trivial CPUArchState fields
  2025-10-01  7:32 ` [PATCH v2 02/33] target/riscv: Fix size of trivial CPUArchState fields Anton Johansson via
  2025-10-02  1:57   ` Alistair Francis
@ 2025-10-02 18:31   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 18:31 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> This commits groups together all CPUArchState fields whose behaviour can
> be retained by simply changing the size of the field.
> 
> Note, senvcfg is defined to be SXLEN bits wide, but is widened to 64
> bits to match henvcfg and menvcfg.  Next, [m|h]edeleg are changed to
> 64 bits as defined privileged specification, and hvictl is fixed to 32
> bits which holds all relevant values, see HVICTL_VALID_MASK.  The
> remaining fields touched in the commit are widened from [H|S|M]XLEN
> to 64-bit.
> 
> Note, the cpu/hyper, cpu/envcfg, cpu/jvt, and cpu VMSTATE versions are
> bumped, breaking migration from older versions.
> 
> References to the privileged/unprivileged RISCV specification refer to
> version 20250508.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h     | 78 +++++++++++++++++++--------------------
>   target/riscv/machine.c | 84 +++++++++++++++++++++---------------------
>   2 files changed, 81 insertions(+), 81 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 03/33] target/riscv: Fix size of mhartid
  2025-10-01  8:28     ` Anton Johansson via
@ 2025-10-02 18:34       ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 18:34 UTC (permalink / raw)
  To: Anton Johansson, Philippe Mathieu-Daudé
  Cc: qemu-devel, richard.henderson, alistair.francis, palmer

On 10/1/25 1:28 AM, Anton Johansson wrote:
> On 01/10/25, Philippe Mathieu-Daudé wrote:
>> On 1/10/25 09:32, Anton Johansson wrote:
>>> and update formatting in log.
>>>
>>> Signed-off-by: Anton Johansson <anjo@rev.ng>
>>> ---
>>>    target/riscv/cpu.h         | 2 +-
>>>    target/riscv/cpu_helper.c  | 2 +-
>>>    target/riscv/machine.c     | 2 +-
>>>    target/riscv/tcg/tcg-cpu.c | 2 +-
>>>    4 files changed, 4 insertions(+), 4 deletions(-)
>>>
>>> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
>>> index 736e4f6daa..3235108112 100644
>>> --- a/target/riscv/cpu.h
>>> +++ b/target/riscv/cpu.h
>>> @@ -279,7 +279,7 @@ struct CPUArchState {
>>>        target_ulong geilen;
>>>        uint64_t resetvec;
>>> -    target_ulong mhartid;
>>> +    uint64_t mhartid;
>>>        /*
>>>         * For RV32 this is 32-bit mstatus and 32-bit mstatush.
>>>         * For RV64 this is a 64-bit mstatus.
>>
>>
>>> diff --git a/target/riscv/machine.c b/target/riscv/machine.c
>>> index 99e46c3136..328fb674e1 100644
>>> --- a/target/riscv/machine.c
>>> +++ b/target/riscv/machine.c
>>> @@ -425,7 +425,7 @@ const VMStateDescription vmstate_riscv_cpu = {
>>>            VMSTATE_UINTTL(env.priv, RISCVCPU),
>>>            VMSTATE_BOOL(env.virt_enabled, RISCVCPU),
>>>            VMSTATE_UINT64(env.resetvec, RISCVCPU),
>>> -        VMSTATE_UINTTL(env.mhartid, RISCVCPU),
>>> +        VMSTATE_UINT64(env.mhartid, RISCVCPU),
>>
>> The problem is you break the migration stream again. Maybe simpler to
>> just squash with previous patch?
>>
>> Thay said, IIUC mhartid is only set once in riscv_hart_realize().
>> I suspect it is pointless to migrate it.
> 
> Right, wrt the other vmstate changes I only bumped the version on first
> modification.  Maybe it makes more sense to group changes based on what
> vmstate they touch?  If excessive version bumping is a problem that is.

As long as it's bumped once in the series, I think it's acceptable.
No one will try to bisect that for migration.

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val()
  2025-10-01  7:32 ` [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val() Anton Johansson via
@ 2025-10-02 18:50   ` Pierrick Bouvier
  2025-10-02 23:34   ` Alistair Francis
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 18:50 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
>  From my understanding the upper_half argument only indicates whether the
> upper or lower 32 bits should be returned, and upper_half will only ever
> be set when MXLEN == 32.  However, the function also uses upper_half to
> determine whether the inhibit flags are located in mcyclecfgh or
> mcyclecfg, but this misses the case where MXLEN == 32, upper_half == false
> for TARGET_RISCV32 where we would also need to read the upper half field.
> 
> Minor simplifications are also made along with some formatting fixes.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/csr.c | 22 ++++++++++------------
>   1 file changed, 10 insertions(+), 12 deletions(-)

Looks good.
write_mhpmcounterh is indeed available only for riscv32.

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh
  2025-10-01  7:32 ` [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh Anton Johansson via
  2025-10-01  7:39   ` Philippe Mathieu-Daudé
@ 2025-10-02 19:08   ` Pierrick Bouvier
  2025-10-02 19:33     ` Pierrick Bouvier
  1 sibling, 1 reply; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 19:08 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> According to version 20250508 of the privileged specification,
> mhpmeventn is 64 bits in size and mhpmeventnh is only ever used
> when XLEN == 32 and accesses the top 32 bits of the 64-bit
> mhpmeventn registers. Combine the two arrays of target_ulong
> mhpmeventh[] and mhpmevent[] to a single array of uint64_t.
> 
> This also allows for some minor code simplification where branches
> handling either mhpmeventh[] or mhpmevent[] could be combined.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h     | 10 +++----
>   target/riscv/csr.c     | 67 +++++++++++++++---------------------------
>   target/riscv/machine.c |  3 +-
>   target/riscv/pmu.c     | 53 ++++++++-------------------------
>   4 files changed, 42 insertions(+), 91 deletions(-)
> 
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index 3235108112..64b9964028 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -427,11 +427,11 @@ struct CPUArchState {
>       /* PMU counter state */
>       PMUCTRState pmu_ctrs[RV_MAX_MHPMCOUNTERS];
>   
> -    /* PMU event selector configured values. First three are unused */
> -    target_ulong mhpmevent_val[RV_MAX_MHPMEVENTS];
> -
> -    /* PMU event selector configured values for RV32 */
> -    target_ulong mhpmeventh_val[RV_MAX_MHPMEVENTS];
> +    /*
> +     * PMU event selector configured values. First three are unused.
> +     * For RV32 top 32 bits are accessed via the mhpmeventh CSR.
> +     */
> +    uint64_t mhpmevent_val[RV_MAX_MHPMEVENTS];
>   
>       PMUFixedCtrState pmu_fixed_ctrs[2];
>   
> diff --git a/target/riscv/csr.c b/target/riscv/csr.c
> index 859f89aedd..2d8916ee40 100644
> --- a/target/riscv/csr.c
> +++ b/target/riscv/csr.c
> @@ -1166,8 +1166,9 @@ static RISCVException read_mhpmevent(CPURISCVState *env, int csrno,
>                                        target_ulong *val)
>   {
>       int evt_index = csrno - CSR_MCOUNTINHIBIT;
> +    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
>   
> -    *val = env->mhpmevent_val[evt_index];
> +    *val = extract64(env->mhpmevent_val[evt_index], 0, rv32 ? 32 : 64);
>   
>       return RISCV_EXCP_NONE;
>   }
> @@ -1176,13 +1177,11 @@ static RISCVException write_mhpmevent(CPURISCVState *env, int csrno,
>                                         target_ulong val, uintptr_t ra)
>   {
>       int evt_index = csrno - CSR_MCOUNTINHIBIT;
> -    uint64_t mhpmevt_val = val;
> +    uint64_t mhpmevt_val;
>       uint64_t inh_avail_mask;
>   
>       if (riscv_cpu_mxl(env) == MXL_RV32) {
> -        env->mhpmevent_val[evt_index] = val;
> -        mhpmevt_val = mhpmevt_val |
> -                      ((uint64_t)env->mhpmeventh_val[evt_index] << 32);
> +        mhpmevt_val = deposit64(env->mhpmevent_val[evt_index], 0, 32, val);

Maybe I missed something, but should it be:
deposit64(env->mhpmevent_val[evt_index], 32, 32, val)
instead?

Reading the rest of the patch, I'm a bit confused about which bits are 
supposed to be used in 32/64 mode.


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh
  2025-10-01  7:39   ` Philippe Mathieu-Daudé
@ 2025-10-02 19:09     ` Pierrick Bouvier
  2025-10-02 23:52       ` Alistair Francis
  0 siblings, 1 reply; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 19:09 UTC (permalink / raw)
  To: Philippe Mathieu-Daudé, Anton Johansson, qemu-devel
  Cc: richard.henderson, alistair.francis, palmer

On 10/1/25 12:39 AM, Philippe Mathieu-Daudé wrote:
> On 1/10/25 09:32, Anton Johansson wrote:
>> According to version 20250508 of the privileged specification,
>> mhpmeventn is 64 bits in size and mhpmeventnh is only ever used
>> when XLEN == 32 and accesses the top 32 bits of the 64-bit
>> mhpmeventn registers. Combine the two arrays of target_ulong
>> mhpmeventh[] and mhpmevent[] to a single array of uint64_t.
>>
>> This also allows for some minor code simplification where branches
>> handling either mhpmeventh[] or mhpmevent[] could be combined.
>>
>> Signed-off-by: Anton Johansson <anjo@rev.ng>
>> ---
>>    target/riscv/cpu.h     | 10 +++----
>>    target/riscv/csr.c     | 67 +++++++++++++++---------------------------
>>    target/riscv/machine.c |  3 +-
>>    target/riscv/pmu.c     | 53 ++++++++-------------------------
>>    4 files changed, 42 insertions(+), 91 deletions(-)
> 
> 
>> diff --git a/target/riscv/machine.c b/target/riscv/machine.c
>> index 328fb674e1..d9939489e1 100644
>> --- a/target/riscv/machine.c
>> +++ b/target/riscv/machine.c
>> @@ -452,8 +452,7 @@ const VMStateDescription vmstate_riscv_cpu = {
>>            VMSTATE_UINT32(env.mcountinhibit, RISCVCPU),
>>            VMSTATE_STRUCT_ARRAY(env.pmu_ctrs, RISCVCPU, RV_MAX_MHPMCOUNTERS, 0,
>>                                 vmstate_pmu_ctr_state, PMUCTRState),
>> -        VMSTATE_UINTTL_ARRAY(env.mhpmevent_val, RISCVCPU, RV_MAX_MHPMEVENTS),
>> -        VMSTATE_UINTTL_ARRAY(env.mhpmeventh_val, RISCVCPU, RV_MAX_MHPMEVENTS),
>> +        VMSTATE_UINT64_ARRAY(env.mhpmevent_val, RISCVCPU, RV_MAX_MHPMEVENTS),
> 
> Each time you change a VMStateDescription structure you need to bump its
> version.

Maybe we could agree with Alistair if we prefer a single bump for whole 
series, or bump on any change within this series.


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 06/33] target/riscv: Combine mcyclecfg and mcyclecfgh
  2025-10-01  7:32 ` [PATCH v2 06/33] target/riscv: Combine mcyclecfg and mcyclecfgh Anton Johansson via
@ 2025-10-02 19:13   ` Pierrick Bouvier
  2025-10-03  0:05   ` Alistair Francis
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 19:13 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> According to version 20250508 of the privileged specification, mcyclecfg
> is a 64-bit register and mcyclecfgh refers to the top 32 bits of this
> register when XLEN == 32.  No real advantage is gained by keeping
> them separate, and combining them allows for slight simplification.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h |  3 +--
>   target/riscv/csr.c | 28 +++++++++++++++++-----------
>   2 files changed, 18 insertions(+), 13 deletions(-)

Clearer on this patch.
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 07/33] target/riscv: Combine minstretcfg and minstretcfgh
  2025-10-01  7:32 ` [PATCH v2 07/33] target/riscv: Combine minstretcfg and minstretcfgh Anton Johansson via
@ 2025-10-02 19:14   ` Pierrick Bouvier
  2025-10-03  0:06   ` Alistair Francis
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 19:14 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> According to version 20250508 of the privileged specification,
> minstretcfg is a 64-bit register and minstretcfgh refers to the top
> 32 bits of this register when XLEN == 32.  No real advantage is
> gained by keeping them separate, and combining them allows for slight
> simplification.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h |  3 +--
>   target/riscv/csr.c | 18 ++++++++++--------
>   2 files changed, 11 insertions(+), 10 deletions(-)
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 08/33] target/riscv: Combine mhpmcounter and mhpmcounterh
  2025-10-01  7:32 ` [PATCH v2 08/33] target/riscv: Combine mhpmcounter and mhpmcounterh Anton Johansson via
@ 2025-10-02 19:24   ` Pierrick Bouvier
  2025-10-02 19:25   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 19:24 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> According to version 20250508 of the privileged specification,
> mhpmconter is a 64-bit register and mhpmcounterh refers to the top
> 32 bits of this register when XLEN == 32.  No real advantage is
> gained by keeping them separate, and combining allows for slight
> simplification.
> 
> Note, the cpu/pmu VMSTATE version is bumped breaking migration from
> older versions.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h     |   8 +--
>   target/riscv/csr.c     |  74 +++++++++++++--------------
>   target/riscv/machine.c |  10 ++--
>   target/riscv/pmu.c     | 111 +++++++++++------------------------------
>   4 files changed, 70 insertions(+), 133 deletions(-)
> 

...

>   RISCVException riscv_pmu_read_ctr(CPURISCVState *env, target_ulong *val,
> -                                         bool upper_half, uint32_t ctr_idx)
> +                                  bool upper_half, uint32_t ctr_idx)
>   {
>       PMUCTRState *counter = &env->pmu_ctrs[ctr_idx];
> -    target_ulong ctr_prev = upper_half ? counter->mhpmcounterh_prev :
> -                                         counter->mhpmcounter_prev;
> -    target_ulong ctr_val = upper_half ? counter->mhpmcounterh_val :
> -                                        counter->mhpmcounter_val;
> +    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
> +    int start = upper_half ? 32 : 0;
> +    int length = rv32 ? 32 : 64;
> +    uint64_t ctr_prev = extract64(counter->mhpmcounter_prev, start, length);
> +    uint64_t ctr_val  = extract64(counter->mhpmcounter_val, start, length);
> +
> +    /* Ensure upper_half is only set for XLEN == 32 */
> +    g_assert(rv32 || !upper_half);

An assert will be triggered by extract64 first if this happens.
static inline uint64_t extract64(uint64_t value, int start, int length)
{
     assert(start >= 0 && length > 0 && length <= 64 - start);

Thus, you can move the assert before extract64 calls.


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 08/33] target/riscv: Combine mhpmcounter and mhpmcounterh
  2025-10-01  7:32 ` [PATCH v2 08/33] target/riscv: Combine mhpmcounter and mhpmcounterh Anton Johansson via
  2025-10-02 19:24   ` Pierrick Bouvier
@ 2025-10-02 19:25   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 19:25 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> According to version 20250508 of the privileged specification,
> mhpmconter is a 64-bit register and mhpmcounterh refers to the top
> 32 bits of this register when XLEN == 32.  No real advantage is
> gained by keeping them separate, and combining allows for slight
> simplification.
> 
> Note, the cpu/pmu VMSTATE version is bumped breaking migration from
> older versions.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h     |   8 +--
>   target/riscv/csr.c     |  74 +++++++++++++--------------
>   target/riscv/machine.c |  10 ++--
>   target/riscv/pmu.c     | 111 +++++++++++------------------------------
>   4 files changed, 70 insertions(+), 133 deletions(-)
With assert being fixed,
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh
  2025-10-02 19:08   ` Pierrick Bouvier
@ 2025-10-02 19:33     ` Pierrick Bouvier
  2025-10-02 23:55       ` Alistair Francis
  0 siblings, 1 reply; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 19:33 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/2/25 12:08 PM, Pierrick Bouvier wrote:
> On 10/1/25 12:32 AM, Anton Johansson wrote:
>> According to version 20250508 of the privileged specification,
>> mhpmeventn is 64 bits in size and mhpmeventnh is only ever used
>> when XLEN == 32 and accesses the top 32 bits of the 64-bit
>> mhpmeventn registers. Combine the two arrays of target_ulong
>> mhpmeventh[] and mhpmevent[] to a single array of uint64_t.
>>
>> This also allows for some minor code simplification where branches
>> handling either mhpmeventh[] or mhpmevent[] could be combined.
>>
>> Signed-off-by: Anton Johansson <anjo@rev.ng>
>> ---
>>    target/riscv/cpu.h     | 10 +++----
>>    target/riscv/csr.c     | 67 +++++++++++++++---------------------------
>>    target/riscv/machine.c |  3 +-
>>    target/riscv/pmu.c     | 53 ++++++++-------------------------
>>    4 files changed, 42 insertions(+), 91 deletions(-)
>>
>> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
>> index 3235108112..64b9964028 100644
>> --- a/target/riscv/cpu.h
>> +++ b/target/riscv/cpu.h
>> @@ -427,11 +427,11 @@ struct CPUArchState {
>>        /* PMU counter state */
>>        PMUCTRState pmu_ctrs[RV_MAX_MHPMCOUNTERS];
>>    
>> -    /* PMU event selector configured values. First three are unused */
>> -    target_ulong mhpmevent_val[RV_MAX_MHPMEVENTS];
>> -
>> -    /* PMU event selector configured values for RV32 */
>> -    target_ulong mhpmeventh_val[RV_MAX_MHPMEVENTS];
>> +    /*
>> +     * PMU event selector configured values. First three are unused.
>> +     * For RV32 top 32 bits are accessed via the mhpmeventh CSR.
>> +     */
>> +    uint64_t mhpmevent_val[RV_MAX_MHPMEVENTS];
>>    
>>        PMUFixedCtrState pmu_fixed_ctrs[2];
>>    
>> diff --git a/target/riscv/csr.c b/target/riscv/csr.c
>> index 859f89aedd..2d8916ee40 100644
>> --- a/target/riscv/csr.c
>> +++ b/target/riscv/csr.c
>> @@ -1166,8 +1166,9 @@ static RISCVException read_mhpmevent(CPURISCVState *env, int csrno,
>>                                         target_ulong *val)
>>    {
>>        int evt_index = csrno - CSR_MCOUNTINHIBIT;
>> +    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
>>    
>> -    *val = env->mhpmevent_val[evt_index];
>> +    *val = extract64(env->mhpmevent_val[evt_index], 0, rv32 ? 32 : 64);
>>    
>>        return RISCV_EXCP_NONE;
>>    }
>> @@ -1176,13 +1177,11 @@ static RISCVException write_mhpmevent(CPURISCVState *env, int csrno,
>>                                          target_ulong val, uintptr_t ra)
>>    {
>>        int evt_index = csrno - CSR_MCOUNTINHIBIT;
>> -    uint64_t mhpmevt_val = val;
>> +    uint64_t mhpmevt_val;
>>        uint64_t inh_avail_mask;
>>    
>>        if (riscv_cpu_mxl(env) == MXL_RV32) {
>> -        env->mhpmevent_val[evt_index] = val;
>> -        mhpmevt_val = mhpmevt_val |
>> -                      ((uint64_t)env->mhpmeventh_val[evt_index] << 32);
>> +        mhpmevt_val = deposit64(env->mhpmevent_val[evt_index], 0, 32, val);
> 
> Maybe I missed something, but should it be:
> deposit64(env->mhpmevent_val[evt_index], 32, 32, val)
> instead?
> 
> Reading the rest of the patch, I'm a bit confused about which bits are
> supposed to be used in 32/64 mode.

Indeed I missed something, it's more clear with next patchs combining 
low/high parts.
The concern I have that is left is regarding the definition of 
MHPMEVENT_BIT_OF. It seems to be out of sync with what we have now given 
that we now keep lower part in lower bits.
Existing implementation is quite confusing to be honest.


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 10/33] target/riscv: Fix size of vector CSRs
  2025-10-01  7:32 ` [PATCH v2 10/33] target/riscv: Fix size of vector CSRs Anton Johansson via
@ 2025-10-02 19:42   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 19:42 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> According to version 20250508 of the unprivileged specification:
> - vtype: bits 0..7 used, bit XLEN-1 illegal, rest reserved
>    => fix to 64-bits.
> 
> - vxsat: bit 0 used, vxrm which would occupy bits 1..2 is stored
>    separately, and bits 3..31 are set to 0
>    => fix to 8-bits.
> 
> - vxrm: 2 lowest bits are used for rounding mode, rest set to 0
>    => fix to 8-bits.
> 
> - vstart: maximum value of VLMAX-1, where VLMAX is at most 2^16
>    => fix to 32-bits as vstart is mapped to a TCG global.
> 
> - vl: maximum value of VLEN which is at most 2^16
>    => fix to 32-bits as vl is mapped to a TCG global.
> 
> Fields are shuffled for reduced padding.
> 
> Note, the cpu/vector VMSTATE version is bumped, breaking migration from
> older versions.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h                      | 12 ++++++------
>   target/riscv/machine.c                  | 14 +++++++-------
>   target/riscv/translate.c                | 12 ++++++++----
>   target/riscv/vector_helper.c            | 22 ++++++++++++++++++----
>   target/riscv/insn_trans/trans_rvv.c.inc | 22 +++++++++++-----------
>   5 files changed, 50 insertions(+), 32 deletions(-)
> 

...

>   typedef struct PMUCTRState {
>       /* Current value of a counter */
> @@ -217,11 +217,11 @@ struct CPUArchState {
>   
>       /* vector coprocessor state. */
>       uint64_t vreg[32 * RV_VLEN_MAX / 64] QEMU_ALIGNED(16);
> -    target_ulong vxrm;
> -    target_ulong vxsat;
> -    target_ulong vl;
> -    target_ulong vstart;
> -    target_ulong vtype;
> +    uint64_t vtype;
> +    uint32_t vl;
> +    uint32_t vstart;
> +    uint8_t vxrm;
> +    uint8_t vxsat;
>       bool vill;
>   
>       target_ulong pc;
> diff --git a/target/riscv/machine.c b/target/riscv/machine.c
> index 6bc79cceaf..dcf18624bf 100644
> --- a/target/riscv/machine.c
> +++ b/target/riscv/machine.c
> @@ -136,16 +136,16 @@ static bool vector_needed(void *opaque)
>   
>   static const VMStateDescription vmstate_vector = {
>       .name = "cpu/vector",
> -    .version_id = 2,
> -    .minimum_version_id = 2,
> +    .version_id = 3,
> +    .minimum_version_id = 3,
>       .needed = vector_needed,
>       .fields = (const VMStateField[]) {
>           VMSTATE_UINT64_ARRAY(env.vreg, RISCVCPU, 32 * RV_VLEN_MAX / 64),
> -        VMSTATE_UINTTL(env.vxrm, RISCVCPU),
> -        VMSTATE_UINTTL(env.vxsat, RISCVCPU),
> -        VMSTATE_UINTTL(env.vl, RISCVCPU),
> -        VMSTATE_UINTTL(env.vstart, RISCVCPU),
> -        VMSTATE_UINTTL(env.vtype, RISCVCPU),
> +        VMSTATE_UINT8(env.vxrm, RISCVCPU),
> +        VMSTATE_UINT8(env.vxsat, RISCVCPU),
> +        VMSTATE_UINT32(env.vl, RISCVCPU),
> +        VMSTATE_UINT32(env.vstart, RISCVCPU),
> +        VMSTATE_UINT64(env.vtype, RISCVCPU),


Just a nit, but might be more maintainable to keep in sync with fields
declaration order, given you changed that to optimize struct Cpu size.

>           VMSTATE_BOOL(env.vill, RISCVCPU),
>           VMSTATE_END_OF_LIST()
>       }

...

The rest is pretty straightforward,
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 11/33] target/riscv: Fix size of pc, load_[val|res]
  2025-10-01  7:32 ` [PATCH v2 11/33] target/riscv: Fix size of pc, load_[val|res] Anton Johansson via
@ 2025-10-02 19:54   ` Pierrick Bouvier
  2025-10-03 12:43     ` Anton Johansson via
  0 siblings, 1 reply; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 19:54 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> Fix to 64 bits in size and as these are mapped to TCG globals, be
> careful with host endianness when allocating globals.  Casts are
> added to logging expressions to retain the correct size for
> TARGET_RISCV32.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h        |  6 +++---
>   target/riscv/cpu.c        |  3 ++-
>   target/riscv/cpu_helper.c |  4 ++--
>   target/riscv/machine.c    |  6 +++---
>   target/riscv/translate.c  | 12 +++++++-----
>   5 files changed, 17 insertions(+), 14 deletions(-)
I guess you'll update string formats later when really getting rid of 
target_ulong. For now it's good.

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 12/33] target/riscv: Fix size of frm and fflags
  2025-10-01  7:32 ` [PATCH v2 12/33] target/riscv: Fix size of frm and fflags Anton Johansson via
@ 2025-10-02 19:57   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 19:57 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> According to version 20250508 of the unprivileged specification the frm
> field of fcsr is 3-bits in size, fix it to 8-bits.  Similarly fflags is
> 5 bits, fix to 8.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h        | 6 +++---
>   target/riscv/csr.c        | 4 ++++
>   target/riscv/fpu_helper.c | 6 +++---
>   target/riscv/machine.c    | 2 +-
>   4 files changed, 11 insertions(+), 7 deletions(-)
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 13/33] target/riscv: Fix size of badaddr and bins
  2025-10-01  7:32 ` [PATCH v2 13/33] target/riscv: Fix size of badaddr and bins Anton Johansson via
@ 2025-10-02 20:02   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:02 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> Fix these fields to 64 bits as they cannot be made smaller. Also make
> sure stores to these fields from TCG are 64 bits in size to avoid
> incorrect values on big endian hosts.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h                             | 4 ++--
>   target/riscv/machine.c                         | 2 +-
>   target/riscv/translate.c                       | 6 ++++--
>   target/riscv/insn_trans/trans_privileged.c.inc | 2 +-
>   4 files changed, 8 insertions(+), 6 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 14/33] target/riscv: Fix size of guest_phys_fault_addr
  2025-10-01  7:32 ` [PATCH v2 14/33] target/riscv: Fix size of guest_phys_fault_addr Anton Johansson via
@ 2025-10-02 20:03   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:03 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> Widen to 64 bits, and use hwaddr as argument to get_physical_address().
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h        | 2 +-
>   target/riscv/cpu_helper.c | 3 +--
>   target/riscv/machine.c    | 2 +-
>   3 files changed, 3 insertions(+), 4 deletions(-)
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 15/33] target/riscv: Fix size of priv_ver and vext_ver
  2025-10-01  7:32 ` [PATCH v2 15/33] target/riscv: Fix size of priv_ver and vext_ver Anton Johansson via
@ 2025-10-02 20:03   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:03 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> Fix these fields to 32 bits, also update corresponding priv_ver field
> in DisasContext as well as function arguments. 32 bits was chosen
> since it's large enough to fit all stored values and int/int32_t is
> used in RISCVCPUDef and a few functions.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h       | 6 +++---
>   target/riscv/machine.c   | 4 ++--
>   target/riscv/translate.c | 2 +-
>   3 files changed, 6 insertions(+), 6 deletions(-)
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 16/33] target/riscv: Fix size of retxh
  2025-10-01  7:32 ` [PATCH v2 16/33] target/riscv: Fix size of retxh Anton Johansson via
@ 2025-10-02 20:05   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:05 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> 128-bit helpers only make sense for MXL_RV128, TARGET_RISCV64,
> and TCGv == TCGv_i64, therefore fix retxh to 64 bits.
> 
> For the sake of being pedandic, update 128-bit instructions to access
> retxh via 64 bit TCG ops, even if they only make sense when TCGv ==
> TCGv_i64.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h                      |  2 +-
>   target/riscv/insn_trans/trans_rvi.c.inc |  8 ++++++--
>   target/riscv/insn_trans/trans_rvm.c.inc | 16 ++++++++++++----
>   3 files changed, 19 insertions(+), 7 deletions(-)
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 17/33] target/riscv: Fix size of ssp
  2025-10-01  7:32 ` [PATCH v2 17/33] target/riscv: Fix size of ssp Anton Johansson via
@ 2025-10-02 20:06   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:06 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> As ssp holds a pointer, fix to 64 bits in size and make sure stores from
> TCG use the correct size to avoid problems on big endian hosts.
> 
> Note, the cpu/ssp VMSTATE version is bumped, breaking migration from
> older versions.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h                            |  2 +-
>   target/riscv/machine.c                        |  6 +++---
>   target/riscv/insn_trans/trans_rvzicfiss.c.inc | 18 +++++++++++++-----
>   3 files changed, 17 insertions(+), 9 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 18/33] target/riscv: Fix size of excp_uw2
  2025-10-01  7:32 ` [PATCH v2 18/33] target/riscv: Fix size of excp_uw2 Anton Johansson via
@ 2025-10-02 20:06   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:06 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> Fix to 64 bits to match size of instruction start words.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h | 2 +-
>   1 file changed, 1 insertion(+), 1 deletion(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 19/33] target/riscv: Fix size of sw_check_code
  2025-10-01  7:32 ` [PATCH v2 19/33] target/riscv: Fix size of sw_check_code Anton Johansson via
@ 2025-10-02 20:07   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:07 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> The field only holds values of 2 and 3, fix its size to 8 bits and
> update stores from TCG.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h                            | 2 +-
>   target/riscv/translate.c                      | 4 ++--
>   target/riscv/insn_trans/trans_rvi.c.inc       | 8 ++++----
>   target/riscv/insn_trans/trans_rvzicfiss.c.inc | 4 ++--
>   4 files changed, 9 insertions(+), 9 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 20/33] target/riscv: Fix size of priv
  2025-10-01  7:32 ` [PATCH v2 20/33] target/riscv: Fix size of priv Anton Johansson via
@ 2025-10-02 20:07   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:07 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> The priv field of CPUArchState only stores values in the range [0,3],
> fix to 8 bits in size and update relevant function arguments.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h        |  8 ++++----
>   target/riscv/cpu_helper.c | 10 +++++-----
>   target/riscv/machine.c    |  2 +-
>   3 files changed, 10 insertions(+), 10 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 21/33] target/riscv: Fix size of gei fields
  2025-10-01  7:32 ` [PATCH v2 21/33] target/riscv: Fix size of gei fields Anton Johansson via
@ 2025-10-02 20:08   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:08 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> geilen takes the values 31 or 63, fix it to 8 bits. hgeie and hgeip are
> at most 64 bits in size, fix to 64.  Update relevant function arguments.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h        | 10 +++++-----
>   target/riscv/cpu_helper.c |  4 ++--
>   target/riscv/machine.c    |  4 ++--
>   3 files changed, 9 insertions(+), 9 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 22/33] target/riscv: Fix size of [m|s|vs]iselect fields
  2025-10-01  7:32 ` [PATCH v2 22/33] target/riscv: Fix size of [m|s|vs]iselect fields Anton Johansson via
@ 2025-10-02 20:09   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:09 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> [m|s|vs]iselect are defined in version 20250508 of the privileged
> specification to be XLEN in size, however QEMU only ever uses at most
> 16 bits of these fields, so fix them to 16.  Update relevant function
> arguments.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h     |  6 +++---
>   target/riscv/csr.c     | 32 ++++++++++++++++----------------
>   target/riscv/machine.c |  6 +++---
>   3 files changed, 22 insertions(+), 22 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 23/33] target/riscv: Fix arguments to board IMSIC emulation callbacks
  2025-10-01  7:32 ` [PATCH v2 23/33] target/riscv: Fix arguments to board IMSIC emulation callbacks Anton Johansson via
@ 2025-10-02 20:15   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:15 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> In hw/ the relevant RISCVIMSICState fields
> eidelivery, eithreshold, eistate are uint32_t.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h        | 42 ++++++++++++++++++++-------------------
>   hw/intc/riscv_imsic.c     | 34 +++++++++++++++----------------
>   target/riscv/cpu_helper.c | 12 ++++-------
>   target/riscv/csr.c        | 24 ++++++++++++----------
>   4 files changed, 57 insertions(+), 55 deletions(-)

Fix + refactor, but it's ok to read.
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 24/33] target/riscv: Fix size of irq_overflow_left
  2025-10-01  7:32 ` [PATCH v2 24/33] target/riscv: Fix size of irq_overflow_left Anton Johansson via
@ 2025-10-02 20:15   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:15 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> Fix to 64 bits to hold all relevant values.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h | 2 +-
>   1 file changed, 1 insertion(+), 1 deletion(-)
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 25/33] target/riscv: Indent PMUFixedCtrState correctly
  2025-10-01  7:32 ` [PATCH v2 25/33] target/riscv: Indent PMUFixedCtrState correctly Anton Johansson via
  2025-10-01  7:43   ` Philippe Mathieu-Daudé
@ 2025-10-02 20:15   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:15 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h | 12 ++++++------
>   1 file changed, 6 insertions(+), 6 deletions(-)
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 26/33] target/riscv: Replace target_ulong in riscv_cpu_get_trap_name()
  2025-10-01  7:32 ` [PATCH v2 26/33] target/riscv: Replace target_ulong in riscv_cpu_get_trap_name() Anton Johansson via
  2025-10-01  7:43   ` Philippe Mathieu-Daudé
@ 2025-10-02 20:15   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:15 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:32 AM, Anton Johansson wrote:
> Fix cause argument to 64 bit to match env->mcause.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h | 2 +-
>   target/riscv/cpu.c | 2 +-
>   2 files changed, 2 insertions(+), 2 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 27/33] target/riscv: Replace target_ulong in riscv_ctr_add_entry()
  2025-10-01  7:33 ` [PATCH v2 27/33] target/riscv: Replace target_ulong in riscv_ctr_add_entry() Anton Johansson via
  2025-10-01  7:44   ` Philippe Mathieu-Daudé
@ 2025-10-02 20:19   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:19 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:33 AM, Anton Johansson wrote:
> Widen to 64 bits in size to hold all relevant values.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h        | 2 +-
>   target/riscv/cpu_helper.c | 4 ++--
>   2 files changed, 3 insertions(+), 3 deletions(-)
> 
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index c1fbb67b08..b17aca0e02 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -653,7 +653,7 @@ RISCVException smstateen_acc_ok(CPURISCVState *env, int index, uint64_t bit);
>   
>   void riscv_cpu_set_mode(CPURISCVState *env, uint8_t newpriv, bool virt_en);
>   
> -void riscv_ctr_add_entry(CPURISCVState *env, target_long src, target_long dst,
> +void riscv_ctr_add_entry(CPURISCVState *env, uint64_t src, uint64_t dst,
>       enum CTRType type, uint8_t prev_priv, bool prev_virt);
>   void riscv_ctr_clear(CPURISCVState *env);
>   
> diff --git a/target/riscv/cpu_helper.c b/target/riscv/cpu_helper.c
> index 2945a89a9c..4acfccc9d8 100644
> --- a/target/riscv/cpu_helper.c
> +++ b/target/riscv/cpu_helper.c
> @@ -925,8 +925,8 @@ static bool riscv_ctr_check_xte(CPURISCVState *env, uint8_t src_prv,
>    *    entry = isel - CTR_ENTRIES_FIRST;
>    *    idx = (sctrstatus.WRPTR - entry - 1) & (depth - 1);
>    */
> -void riscv_ctr_add_entry(CPURISCVState *env, target_long src, target_long dst,
> -    enum CTRType type, uint8_t src_priv, bool src_virt)
> +void riscv_ctr_add_entry(CPURISCVState *env, uint64_t src, uint64_t dst,
> +                         enum CTRType type, uint8_t src_priv, bool src_virt)
>   {
>       bool tgt_virt = env->virt_enabled;
>       uint64_t src_mask = riscv_ctr_priv_to_mask(src_priv, src_virt);

Watchout, here we have signed values.

However, checking call sites call sites, since we deal with pc, it seems 
safe to have uint64_t. Maybe it's worth saying this in commit description.

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 28/33] target/riscv: Fix size of trigger data
  2025-10-01  7:33 ` [PATCH v2 28/33] target/riscv: Fix size of trigger data Anton Johansson via
  2025-10-01  7:46   ` Philippe Mathieu-Daudé
@ 2025-10-02 20:19   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:19 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:33 AM, Anton Johansson wrote:
> mcontext is at most 14 bits in size with the H extension, fix to 16
> bits. trigger_cur indexes into tdata*[RV_MAX_TRIGGERS] which holds 2
> elements, fix to 8 bits.
> 
> Note, the cpu/debug VMSTATE version is bumped, breaking migration from
> older versions.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h     | 10 +++++-----
>   target/riscv/machine.c | 12 ++++++------
>   2 files changed, 11 insertions(+), 11 deletions(-)
Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 29/33] target/riscv: Fix size of mseccfg
  2025-10-01  7:33 ` [PATCH v2 29/33] target/riscv: Fix size of mseccfg Anton Johansson via
  2025-10-01  7:46   ` Philippe Mathieu-Daudé
@ 2025-10-02 20:20   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:20 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:33 AM, Anton Johansson wrote:
> mseccfg is defined in version 20250508 of the privileged specification
> to be 64 bits in size.  Update relevant function arguments.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h | 2 +-
>   target/riscv/pmp.h | 4 ++--
>   target/riscv/pmp.c | 4 ++--
>   3 files changed, 5 insertions(+), 5 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 30/33] target/riscv: Move debug.h include away from cpu.h
  2025-10-01  7:33 ` [PATCH v2 30/33] target/riscv: Move debug.h include away from cpu.h Anton Johansson via
@ 2025-10-02 20:21   ` Pierrick Bouvier
  2025-10-03 12:52     ` Anton Johansson via
  0 siblings, 1 reply; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:21 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:33 AM, Anton Johansson wrote:
> All debug.h definitions except for RV_MAX_TRIGGERS are internal to
> target/riscv.  Move RV_MAX_TRIGGERS to cpu.h and include debug.h from
> all translation units which relied on the cpu.h include.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h         | 4 ++--
>   target/riscv/debug.h       | 2 --
>   target/riscv/cpu.c         | 3 +++
>   target/riscv/csr.c         | 3 +++
>   target/riscv/debug.c       | 1 +
>   target/riscv/tcg/tcg-cpu.c | 1 +
>   6 files changed, 10 insertions(+), 4 deletions(-)
> 
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index a53981a09b..70e0f3718c 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -177,14 +177,14 @@ extern RISCVCPUImpliedExtsRule *riscv_multi_ext_implied_rules[];
>   #define MAX_RISCV_PMPS (64)
>   #define OLD_MAX_RISCV_PMPS (16)
>   
> -#if !defined(CONFIG_USER_ONLY)
> +#if !defined(CONFIG_LINUX_USER)

Squashed from another change?

...

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 31/33] target/riscv: Move CSR declarations to separate csr.h header
  2025-10-01  7:33 ` [PATCH v2 31/33] target/riscv: Move CSR declarations to separate csr.h header Anton Johansson via
@ 2025-10-02 20:22   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:22 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:33 AM, Anton Johansson wrote:
> Most of these definitions save riscv_csrr, riscv_csrrw, riscv_csr_read,
> riscv_csr_write are only used in target/.  Move declarations to a
> separate headers which will soon be made internal to target/.
> 
> csr.h is temporarily included from cpu.h to not break includes from
> outside target/, this include will be removed in the following commit.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h         | 82 +--------------------------------
>   target/riscv/csr.h         | 94 ++++++++++++++++++++++++++++++++++++++
>   target/riscv/cpu.c         |  1 +
>   target/riscv/csr.c         |  1 +
>   target/riscv/gdbstub.c     |  1 +
>   target/riscv/kvm/kvm-cpu.c |  1 +
>   target/riscv/op_helper.c   |  1 +
>   target/riscv/th_csr.c      |  1 +
>   8 files changed, 101 insertions(+), 81 deletions(-)
>   create mode 100644 target/riscv/csr.h

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 33/33] target/riscv: Make pmp.h target_ulong agnostic
  2025-10-01  7:33 ` [PATCH v2 33/33] target/riscv: Make pmp.h target_ulong agnostic Anton Johansson via
  2025-10-01  7:49   ` Philippe Mathieu-Daudé
@ 2025-10-02 20:23   ` Pierrick Bouvier
  1 sibling, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:23 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:33 AM, Anton Johansson wrote:
> The pmp.h header is exposed through cpu.h.  pmp_table_t is also used in
> CPUArchState.  CSR declaraions are only used in target/ and are moved to
> csr.h.  In pmp.h, addr_reg is widened to 64 bits and the privilege mode
> parameter is fixed to 8 bits, similar to previous commits.
> 
> Note, the cpu/pmp/entry and cpu/pmp VMSTATE versions are bumped, breaking
> migration from older versions.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/csr.h     | 12 ++++++++++++
>   target/riscv/pmp.h     | 20 +++++---------------
>   target/riscv/machine.c | 10 +++++-----
>   target/riscv/pmp.c     |  9 +++++----
>   4 files changed, 27 insertions(+), 24 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>



^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 32/33] target/riscv: Introduce externally facing CSR access functions
  2025-10-01  7:33 ` [PATCH v2 32/33] target/riscv: Introduce externally facing CSR access functions Anton Johansson via
@ 2025-10-02 20:24   ` Pierrick Bouvier
  0 siblings, 0 replies; 99+ messages in thread
From: Pierrick Bouvier @ 2025-10-02 20:24 UTC (permalink / raw)
  To: Anton Johansson, qemu-devel
  Cc: philmd, richard.henderson, alistair.francis, palmer

On 10/1/25 12:33 AM, Anton Johansson wrote:
> Convert riscv_csr_[read|write]() into target_ulong angnostic CSR access
> functions that can be safely used from outside of target/ without
> knowledge of the target register size.  Replace the 4 existing CSR
> accesses in hw/ and linux-user/.
> 
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>   target/riscv/cpu.h        |  7 ++++++-
>   target/riscv/csr.h        | 13 -------------
>   hw/riscv/riscv_hart.c     |  7 +++----
>   linux-user/riscv/signal.c |  5 +++--
>   target/riscv/csr.c        | 17 +++++++++++++++++
>   5 files changed, 29 insertions(+), 20 deletions(-)

Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val()
  2025-10-01  7:32 ` [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val() Anton Johansson via
  2025-10-02 18:50   ` Pierrick Bouvier
@ 2025-10-02 23:34   ` Alistair Francis
  2025-10-07 11:08     ` Anton Johansson via
  1 sibling, 1 reply; 99+ messages in thread
From: Alistair Francis @ 2025-10-02 23:34 UTC (permalink / raw)
  To: Anton Johansson
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On Wed, Oct 1, 2025 at 5:43 PM Anton Johansson via
<qemu-devel@nongnu.org> wrote:
>
> From my understanding the upper_half argument only indicates whether the
> upper or lower 32 bits should be returned, and upper_half will only ever
> be set when MXLEN == 32.  However, the function also uses upper_half to
> determine whether the inhibit flags are located in mcyclecfgh or
> mcyclecfg, but this misses the case where MXLEN == 32, upper_half == false
> for TARGET_RISCV32 where we would also need to read the upper half field.

If MXLEN == 32, upper_half == false then we want to read mcyclecfg,
which the code today seems to be doing correctly.

>
> Minor simplifications are also made along with some formatting fixes.
>
> Signed-off-by: Anton Johansson <anjo@rev.ng>
> ---
>  target/riscv/csr.c | 22 ++++++++++------------
>  1 file changed, 10 insertions(+), 12 deletions(-)
>
> diff --git a/target/riscv/csr.c b/target/riscv/csr.c
> index 3c8989f522..859f89aedd 100644
> --- a/target/riscv/csr.c
> +++ b/target/riscv/csr.c
> @@ -17,6 +17,7 @@
>   * this program.  If not, see <http://www.gnu.org/licenses/>.
>   */
>
> +#include "cpu_bits.h"
>  #include "qemu/osdep.h"
>  #include "qemu/log.h"
>  #include "qemu/timer.h"
> @@ -1241,18 +1242,21 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
>      int inst = riscv_pmu_ctr_monitor_instructions(env, counter_idx);
>      uint64_t *counter_arr_virt = env->pmu_fixed_ctrs[inst].counter_virt;
>      uint64_t *counter_arr = env->pmu_fixed_ctrs[inst].counter;
> -    target_ulong result = 0;
>      uint64_t curr_val = 0;
>      uint64_t cfg_val = 0;
> +    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
> +
> +    /* Ensure upper_half is only set for MXL_RV32 */
> +    g_assert(rv32 || !upper_half);
>
>      if (counter_idx == 0) {
> -        cfg_val = upper_half ? ((uint64_t)env->mcyclecfgh << 32) :
> +        cfg_val = rv32 ? ((uint64_t)env->mcyclecfgh << 32) :

This doesn't look right.

RV32 will want to access both mcyclecfgh and mcyclecfg, but this
change restricts access to mcyclecfg as rv32 will always be true.

I don't think there is anything wrong with the current code.

Alistair

>                    env->mcyclecfg;
>      } else if (counter_idx == 2) {
> -        cfg_val = upper_half ? ((uint64_t)env->minstretcfgh << 32) :
> +        cfg_val = rv32 ? ((uint64_t)env->minstretcfgh << 32) :
>                    env->minstretcfg;
>      } else {
> -        cfg_val = upper_half ?
> +        cfg_val = rv32 ?
>                    ((uint64_t)env->mhpmeventh_val[counter_idx] << 32) :
>                    env->mhpmevent_val[counter_idx];
>          cfg_val &= MHPMEVENT_FILTER_MASK;
> @@ -1260,7 +1264,7 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
>
>      if (!cfg_val) {
>          if (icount_enabled()) {
> -                curr_val = inst ? icount_get_raw() : icount_get();
> +            curr_val = inst ? icount_get_raw() : icount_get();
>          } else {
>              curr_val = cpu_get_host_ticks();
>          }
> @@ -1292,13 +1296,7 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
>      }
>
>  done:
> -    if (riscv_cpu_mxl(env) == MXL_RV32) {
> -        result = upper_half ? curr_val >> 32 : curr_val;
> -    } else {
> -        result = curr_val;
> -    }
> -
> -    return result;
> +    return upper_half ? curr_val >> 32 : curr_val;
>  }
>
>  static RISCVException riscv_pmu_write_ctr(CPURISCVState *env, target_ulong val,
> --
> 2.51.0
>
>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh
  2025-10-02 19:09     ` Pierrick Bouvier
@ 2025-10-02 23:52       ` Alistair Francis
  0 siblings, 0 replies; 99+ messages in thread
From: Alistair Francis @ 2025-10-02 23:52 UTC (permalink / raw)
  To: Pierrick Bouvier
  Cc: Philippe Mathieu-Daudé, Anton Johansson, qemu-devel,
	richard.henderson, alistair.francis, palmer

On Fri, Oct 3, 2025 at 5:11 AM Pierrick Bouvier
<pierrick.bouvier@linaro.org> wrote:
>
> On 10/1/25 12:39 AM, Philippe Mathieu-Daudé wrote:
> > On 1/10/25 09:32, Anton Johansson wrote:
> >> According to version 20250508 of the privileged specification,
> >> mhpmeventn is 64 bits in size and mhpmeventnh is only ever used
> >> when XLEN == 32 and accesses the top 32 bits of the 64-bit
> >> mhpmeventn registers. Combine the two arrays of target_ulong
> >> mhpmeventh[] and mhpmevent[] to a single array of uint64_t.
> >>
> >> This also allows for some minor code simplification where branches
> >> handling either mhpmeventh[] or mhpmevent[] could be combined.
> >>
> >> Signed-off-by: Anton Johansson <anjo@rev.ng>
> >> ---
> >>    target/riscv/cpu.h     | 10 +++----
> >>    target/riscv/csr.c     | 67 +++++++++++++++---------------------------
> >>    target/riscv/machine.c |  3 +-
> >>    target/riscv/pmu.c     | 53 ++++++++-------------------------
> >>    4 files changed, 42 insertions(+), 91 deletions(-)
> >
> >
> >> diff --git a/target/riscv/machine.c b/target/riscv/machine.c
> >> index 328fb674e1..d9939489e1 100644
> >> --- a/target/riscv/machine.c
> >> +++ b/target/riscv/machine.c
> >> @@ -452,8 +452,7 @@ const VMStateDescription vmstate_riscv_cpu = {
> >>            VMSTATE_UINT32(env.mcountinhibit, RISCVCPU),
> >>            VMSTATE_STRUCT_ARRAY(env.pmu_ctrs, RISCVCPU, RV_MAX_MHPMCOUNTERS, 0,
> >>                                 vmstate_pmu_ctr_state, PMUCTRState),
> >> -        VMSTATE_UINTTL_ARRAY(env.mhpmevent_val, RISCVCPU, RV_MAX_MHPMEVENTS),
> >> -        VMSTATE_UINTTL_ARRAY(env.mhpmeventh_val, RISCVCPU, RV_MAX_MHPMEVENTS),
> >> +        VMSTATE_UINT64_ARRAY(env.mhpmevent_val, RISCVCPU, RV_MAX_MHPMEVENTS),
> >
> > Each time you change a VMStateDescription structure you need to bump its
> > version.
>
> Maybe we could agree with Alistair if we prefer a single bump for whole
> series, or bump on any change within this series.

I'm fine with one bump in the series. Otherwise we end up with a huge
number of bumps

Alistair

>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh
  2025-10-02 19:33     ` Pierrick Bouvier
@ 2025-10-02 23:55       ` Alistair Francis
  2025-10-07 11:29         ` Anton Johansson via
  2025-10-14 11:25         ` Anton Johansson via
  0 siblings, 2 replies; 99+ messages in thread
From: Alistair Francis @ 2025-10-02 23:55 UTC (permalink / raw)
  To: Pierrick Bouvier
  Cc: Anton Johansson, qemu-devel, philmd, richard.henderson,
	alistair.francis, palmer

On Fri, Oct 3, 2025 at 5:37 AM Pierrick Bouvier
<pierrick.bouvier@linaro.org> wrote:
>
> On 10/2/25 12:08 PM, Pierrick Bouvier wrote:
> > On 10/1/25 12:32 AM, Anton Johansson wrote:
> >> According to version 20250508 of the privileged specification,
> >> mhpmeventn is 64 bits in size and mhpmeventnh is only ever used
> >> when XLEN == 32 and accesses the top 32 bits of the 64-bit
> >> mhpmeventn registers. Combine the two arrays of target_ulong
> >> mhpmeventh[] and mhpmevent[] to a single array of uint64_t.
> >>
> >> This also allows for some minor code simplification where branches
> >> handling either mhpmeventh[] or mhpmevent[] could be combined.
> >>
> >> Signed-off-by: Anton Johansson <anjo@rev.ng>
> >> ---
> >>    target/riscv/cpu.h     | 10 +++----
> >>    target/riscv/csr.c     | 67 +++++++++++++++---------------------------
> >>    target/riscv/machine.c |  3 +-
> >>    target/riscv/pmu.c     | 53 ++++++++-------------------------
> >>    4 files changed, 42 insertions(+), 91 deletions(-)
> >>
> >> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> >> index 3235108112..64b9964028 100644
> >> --- a/target/riscv/cpu.h
> >> +++ b/target/riscv/cpu.h
> >> @@ -427,11 +427,11 @@ struct CPUArchState {
> >>        /* PMU counter state */
> >>        PMUCTRState pmu_ctrs[RV_MAX_MHPMCOUNTERS];
> >>
> >> -    /* PMU event selector configured values. First three are unused */
> >> -    target_ulong mhpmevent_val[RV_MAX_MHPMEVENTS];
> >> -
> >> -    /* PMU event selector configured values for RV32 */
> >> -    target_ulong mhpmeventh_val[RV_MAX_MHPMEVENTS];
> >> +    /*
> >> +     * PMU event selector configured values. First three are unused.
> >> +     * For RV32 top 32 bits are accessed via the mhpmeventh CSR.
> >> +     */
> >> +    uint64_t mhpmevent_val[RV_MAX_MHPMEVENTS];
> >>
> >>        PMUFixedCtrState pmu_fixed_ctrs[2];
> >>
> >> diff --git a/target/riscv/csr.c b/target/riscv/csr.c
> >> index 859f89aedd..2d8916ee40 100644
> >> --- a/target/riscv/csr.c
> >> +++ b/target/riscv/csr.c
> >> @@ -1166,8 +1166,9 @@ static RISCVException read_mhpmevent(CPURISCVState *env, int csrno,
> >>                                         target_ulong *val)
> >>    {
> >>        int evt_index = csrno - CSR_MCOUNTINHIBIT;
> >> +    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
> >>
> >> -    *val = env->mhpmevent_val[evt_index];
> >> +    *val = extract64(env->mhpmevent_val[evt_index], 0, rv32 ? 32 : 64);
> >>
> >>        return RISCV_EXCP_NONE;
> >>    }
> >> @@ -1176,13 +1177,11 @@ static RISCVException write_mhpmevent(CPURISCVState *env, int csrno,
> >>                                          target_ulong val, uintptr_t ra)
> >>    {
> >>        int evt_index = csrno - CSR_MCOUNTINHIBIT;
> >> -    uint64_t mhpmevt_val = val;
> >> +    uint64_t mhpmevt_val;
> >>        uint64_t inh_avail_mask;
> >>
> >>        if (riscv_cpu_mxl(env) == MXL_RV32) {
> >> -        env->mhpmevent_val[evt_index] = val;
> >> -        mhpmevt_val = mhpmevt_val |
> >> -                      ((uint64_t)env->mhpmeventh_val[evt_index] << 32);
> >> +        mhpmevt_val = deposit64(env->mhpmevent_val[evt_index], 0, 32, val);
> >
> > Maybe I missed something, but should it be:
> > deposit64(env->mhpmevent_val[evt_index], 32, 32, val)
> > instead?
> >
> > Reading the rest of the patch, I'm a bit confused about which bits are
> > supposed to be used in 32/64 mode.
>
> Indeed I missed something, it's more clear with next patchs combining
> low/high parts.

Besides this missed part the patch looks good.

Reviewed-by: Alistair Francis <alistair.francis@wdc.com>

> The concern I have that is left is regarding the definition of
> MHPMEVENT_BIT_OF. It seems to be out of sync with what we have now given
> that we now keep lower part in lower bits.

That might be a bug, it should be using MHPMEVENTH_BIT_OF with mhpmeventh_val


Alistair

> Existing implementation is quite confusing to be honest.
>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 06/33] target/riscv: Combine mcyclecfg and mcyclecfgh
  2025-10-01  7:32 ` [PATCH v2 06/33] target/riscv: Combine mcyclecfg and mcyclecfgh Anton Johansson via
  2025-10-02 19:13   ` Pierrick Bouvier
@ 2025-10-03  0:05   ` Alistair Francis
  1 sibling, 0 replies; 99+ messages in thread
From: Alistair Francis @ 2025-10-03  0:05 UTC (permalink / raw)
  To: Anton Johansson
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On Wed, Oct 1, 2025 at 5:36 PM Anton Johansson via
<qemu-devel@nongnu.org> wrote:
>
> According to version 20250508 of the privileged specification, mcyclecfg
> is a 64-bit register and mcyclecfgh refers to the top 32 bits of this
> register when XLEN == 32.  No real advantage is gained by keeping
> them separate, and combining them allows for slight simplification.
>
> Signed-off-by: Anton Johansson <anjo@rev.ng>

Reviewed-by: Alistair Francis <alistair.francis@wdc.com>

Alistair

> ---
>  target/riscv/cpu.h |  3 +--
>  target/riscv/csr.c | 28 +++++++++++++++++-----------
>  2 files changed, 18 insertions(+), 13 deletions(-)
>
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index 64b9964028..60f7611c00 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -419,8 +419,7 @@ struct CPUArchState {
>      uint32_t mcountinhibit;
>
>      /* PMU cycle & instret privilege mode filtering */
> -    target_ulong mcyclecfg;
> -    target_ulong mcyclecfgh;
> +    uint64_t mcyclecfg;
>      target_ulong minstretcfg;
>      target_ulong minstretcfgh;
>
> diff --git a/target/riscv/csr.c b/target/riscv/csr.c
> index 2d8916ee40..77d0bd7bca 100644
> --- a/target/riscv/csr.c
> +++ b/target/riscv/csr.c
> @@ -1060,7 +1060,8 @@ static RISCVException read_hpmcounterh(CPURISCVState *env, int csrno,
>  static RISCVException read_mcyclecfg(CPURISCVState *env, int csrno,
>                                       target_ulong *val)
>  {
> -    *val = env->mcyclecfg;
> +    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
> +    *val = extract64(env->mcyclecfg, 0, rv32 ? 32 : 64);
>      return RISCV_EXCP_NONE;
>  }
>
> @@ -1070,7 +1071,7 @@ static RISCVException write_mcyclecfg(CPURISCVState *env, int csrno,
>      uint64_t inh_avail_mask;
>
>      if (riscv_cpu_mxl(env) == MXL_RV32) {
> -        env->mcyclecfg = val;
> +        env->mcyclecfg = deposit64(env->mcyclecfg, 0, 32, val);
>      } else {
>          /* Set xINH fields if priv mode supported */
>          inh_avail_mask = ~MHPMEVENT_FILTER_MASK | MCYCLECFG_BIT_MINH;
> @@ -1089,7 +1090,7 @@ static RISCVException write_mcyclecfg(CPURISCVState *env, int csrno,
>  static RISCVException read_mcyclecfgh(CPURISCVState *env, int csrno,
>                                        target_ulong *val)
>  {
> -    *val = env->mcyclecfgh;
> +    *val = extract64(env->mcyclecfg, 32, 32);
>      return RISCV_EXCP_NONE;
>  }
>
> @@ -1107,7 +1108,7 @@ static RISCVException write_mcyclecfgh(CPURISCVState *env, int csrno,
>      inh_avail_mask |= (riscv_has_ext(env, RVH) &&
>                         riscv_has_ext(env, RVS)) ? MCYCLECFGH_BIT_VSINH : 0;
>
> -    env->mcyclecfgh = val & inh_avail_mask;
> +    env->mcyclecfg = deposit64(env->mcyclecfg, 32, 32, val & inh_avail_mask);
>      return RISCV_EXCP_NONE;
>  }
>
> @@ -1246,8 +1247,7 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
>      g_assert(rv32 || !upper_half);
>
>      if (counter_idx == 0) {
> -        cfg_val = rv32 ? ((uint64_t)env->mcyclecfgh << 32) :
> -                  env->mcyclecfg;
> +        cfg_val = env->mcyclecfg;
>      } else if (counter_idx == 2) {
>          cfg_val = rv32 ? ((uint64_t)env->minstretcfgh << 32) :
>                    env->minstretcfg;
> @@ -1521,8 +1521,12 @@ static int rmw_cd_mhpmeventh(CPURISCVState *env, int evt_index,
>  }
>
>  static int rmw_cd_ctr_cfg(CPURISCVState *env, int cfg_index, target_ulong *val,
> -                            target_ulong new_val, target_ulong wr_mask)
> +                          target_ulong new_val, uint64_t wr_mask)
>  {
> +    /*
> +     * wr_mask is 64-bit so upper 32 bits of mcyclecfg and minstretcfg
> +     * are retained.
> +     */
>      switch (cfg_index) {
>      case 0:             /* CYCLECFG */
>          if (wr_mask) {
> @@ -1548,8 +1552,9 @@ static int rmw_cd_ctr_cfg(CPURISCVState *env, int cfg_index, target_ulong *val,
>  }
>
>  static int rmw_cd_ctr_cfgh(CPURISCVState *env, int cfg_index, target_ulong *val,
> -                            target_ulong new_val, target_ulong wr_mask)
> +                           target_ulong new_val, target_ulong wr_mask)
>  {
> +    uint64_t cfgh;
>
>      if (riscv_cpu_mxl(env) != MXL_RV32) {
>          return RISCV_EXCP_ILLEGAL_INST;
> @@ -1557,12 +1562,13 @@ static int rmw_cd_ctr_cfgh(CPURISCVState *env, int cfg_index, target_ulong *val,
>
>      switch (cfg_index) {
>      case 0:         /* CYCLECFGH */
> +        cfgh = extract64(env->mcyclecfg, 32, 32);
>          if (wr_mask) {
>              wr_mask &= ~MCYCLECFGH_BIT_MINH;
> -            env->mcyclecfgh = (new_val & wr_mask) |
> -                              (env->mcyclecfgh & ~wr_mask);
> +            cfgh = (new_val & wr_mask) | (cfgh & ~wr_mask);
> +            env->mcyclecfg = deposit64(env->mcyclecfg, 32, 32, cfgh);
>          } else {
> -            *val = env->mcyclecfgh;
> +            *val = cfgh;
>          }
>          break;
>      case 2:          /* INSTRETCFGH */
> --
> 2.51.0
>
>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 07/33] target/riscv: Combine minstretcfg and minstretcfgh
  2025-10-01  7:32 ` [PATCH v2 07/33] target/riscv: Combine minstretcfg and minstretcfgh Anton Johansson via
  2025-10-02 19:14   ` Pierrick Bouvier
@ 2025-10-03  0:06   ` Alistair Francis
  1 sibling, 0 replies; 99+ messages in thread
From: Alistair Francis @ 2025-10-03  0:06 UTC (permalink / raw)
  To: Anton Johansson
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On Wed, Oct 1, 2025 at 5:31 PM Anton Johansson via
<qemu-devel@nongnu.org> wrote:
>
> According to version 20250508 of the privileged specification,
> minstretcfg is a 64-bit register and minstretcfgh refers to the top
> 32 bits of this register when XLEN == 32.  No real advantage is
> gained by keeping them separate, and combining them allows for slight
> simplification.
>
> Signed-off-by: Anton Johansson <anjo@rev.ng>

Reviewed-by: Alistair Francis <alistair.francis@wdc.com>

Alistair

> ---
>  target/riscv/cpu.h |  3 +--
>  target/riscv/csr.c | 18 ++++++++++--------
>  2 files changed, 11 insertions(+), 10 deletions(-)
>
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index 60f7611c00..d8f0818b08 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -420,8 +420,7 @@ struct CPUArchState {
>
>      /* PMU cycle & instret privilege mode filtering */
>      uint64_t mcyclecfg;
> -    target_ulong minstretcfg;
> -    target_ulong minstretcfgh;
> +    uint64_t minstretcfg;
>
>      /* PMU counter state */
>      PMUCTRState pmu_ctrs[RV_MAX_MHPMCOUNTERS];
> diff --git a/target/riscv/csr.c b/target/riscv/csr.c
> index 77d0bd7bca..83f6526723 100644
> --- a/target/riscv/csr.c
> +++ b/target/riscv/csr.c
> @@ -1115,7 +1115,8 @@ static RISCVException write_mcyclecfgh(CPURISCVState *env, int csrno,
>  static RISCVException read_minstretcfg(CPURISCVState *env, int csrno,
>                                         target_ulong *val)
>  {
> -    *val = env->minstretcfg;
> +    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
> +    *val = extract64(env->minstretcfg, 0, rv32 ? 32 : 64);
>      return RISCV_EXCP_NONE;
>  }
>
> @@ -1142,7 +1143,7 @@ static RISCVException write_minstretcfg(CPURISCVState *env, int csrno,
>  static RISCVException read_minstretcfgh(CPURISCVState *env, int csrno,
>                                          target_ulong *val)
>  {
> -    *val = env->minstretcfgh;
> +    *val = extract64(env->minstretcfg, 32, 32);
>      return RISCV_EXCP_NONE;
>  }
>
> @@ -1159,7 +1160,8 @@ static RISCVException write_minstretcfgh(CPURISCVState *env, int csrno,
>      inh_avail_mask |= (riscv_has_ext(env, RVH) &&
>                         riscv_has_ext(env, RVS)) ? MINSTRETCFGH_BIT_VSINH : 0;
>
> -    env->minstretcfgh = val & inh_avail_mask;
> +    env->minstretcfg = deposit64(env->minstretcfg, 32, 32,
> +                                 val & inh_avail_mask);
>      return RISCV_EXCP_NONE;
>  }
>
> @@ -1249,8 +1251,7 @@ static target_ulong riscv_pmu_ctr_get_fixed_counters_val(CPURISCVState *env,
>      if (counter_idx == 0) {
>          cfg_val = env->mcyclecfg;
>      } else if (counter_idx == 2) {
> -        cfg_val = rv32 ? ((uint64_t)env->minstretcfgh << 32) :
> -                  env->minstretcfg;
> +        cfg_val = env->minstretcfg;
>      } else {
>          cfg_val = env->mhpmevent_val[counter_idx];
>          cfg_val &= MHPMEVENT_FILTER_MASK;
> @@ -1572,12 +1573,13 @@ static int rmw_cd_ctr_cfgh(CPURISCVState *env, int cfg_index, target_ulong *val,
>          }
>          break;
>      case 2:          /* INSTRETCFGH */
> +        cfgh = extract64(env->minstretcfg, 32, 32);
>          if (wr_mask) {
>              wr_mask &= ~MINSTRETCFGH_BIT_MINH;
> -            env->minstretcfgh = (new_val & wr_mask) |
> -                                (env->minstretcfgh & ~wr_mask);
> +            cfgh = (new_val & wr_mask) | (cfgh & ~wr_mask);
> +            env->minstretcfg = deposit64(env->minstretcfg, 32, 32, cfgh);
>          } else {
> -            *val = env->minstretcfgh;
> +            *val = cfgh;
>          }
>          break;
>      default:
> --
> 2.51.0
>
>


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 09/33] target/riscv: Fix size of gpr and gprh
  2025-10-01  7:42   ` Philippe Mathieu-Daudé
@ 2025-10-03  9:00     ` Anton Johansson via
  0 siblings, 0 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-03  9:00 UTC (permalink / raw)
  To: Philippe Mathieu-Daudé
  Cc: qemu-devel, pierrick.bouvier, richard.henderson, alistair.francis,
	palmer

On 01/10/25, Philippe Mathieu-Daudé wrote:
> On 1/10/25 09:32, Anton Johansson wrote:
> > gprh is only needed for TARGET_RISCV64 when modeling 128-bit registers,
> > fixing their size to 64 bits makes sense.
> > 
> > gpr is also fixed to 64 bits since all direct uses of env->gpr
> > correctly zero extend/truncate to/from target_ulong, meaning
> > !TARGET_RISCV64 will behave as expected.
> > 
> > We do however need to be a bit careful when mapping 64-bit fields to
> > 32-bit TCGv globals on big endian hosts.
> > 
> > Note, the cpu/rv128 VMSTATE version is bumped, breaking migration from
> > older versions.
> > 
> > Signed-off-by: Anton Johansson <anjo@rev.ng>
> > ---
> >   target/riscv/cpu.h       |  4 ++--
> >   target/riscv/cpu.c       |  2 +-
> >   target/riscv/machine.c   |  8 ++++----
> >   target/riscv/translate.c | 17 +++++++++++++++--
> >   4 files changed, 22 insertions(+), 9 deletions(-)
> 
> 
> > diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
> > index d055ddf462..3c910e44cd 100644
> > --- a/target/riscv/cpu.c
> > +++ b/target/riscv/cpu.c
> > @@ -584,7 +584,7 @@ static void riscv_cpu_dump_state(CPUState *cs, FILE *f, int flags)
> >       for (i = 0; i < 32; i++) {
> >           qemu_fprintf(f, " %-8s " TARGET_FMT_lx,
> > -                     riscv_int_regnames[i], env->gpr[i]);
> > +                     riscv_int_regnames[i], (target_ulong) env->gpr[i]);
> 
> Rebase mistake?

Yup, I'll print as u64 instead! Thanks:)


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 11/33] target/riscv: Fix size of pc, load_[val|res]
  2025-10-02 19:54   ` Pierrick Bouvier
@ 2025-10-03 12:43     ` Anton Johansson via
  0 siblings, 0 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-03 12:43 UTC (permalink / raw)
  To: Pierrick Bouvier
  Cc: qemu-devel, philmd, richard.henderson, alistair.francis, palmer

On 02/10/25, Pierrick Bouvier wrote:
> On 10/1/25 12:32 AM, Anton Johansson wrote:
> > Fix to 64 bits in size and as these are mapped to TCG globals, be
> > careful with host endianness when allocating globals.  Casts are
> > added to logging expressions to retain the correct size for
> > TARGET_RISCV32.
> > 
> > Signed-off-by: Anton Johansson <anjo@rev.ng>
> > ---
> >   target/riscv/cpu.h        |  6 +++---
> >   target/riscv/cpu.c        |  3 ++-
> >   target/riscv/cpu_helper.c |  4 ++--
> >   target/riscv/machine.c    |  6 +++---
> >   target/riscv/translate.c  | 12 +++++++-----
> >   5 files changed, 17 insertions(+), 14 deletions(-)
> I guess you'll update string formats later when really getting rid of
> target_ulong. For now it's good.
> 
> Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>

Thanks!:) Yes exactly follow up patchsets will get rid of target_ulong,
the goal of this one is to simply fix the size of CPUArchState and
retain all behaviour.


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 30/33] target/riscv: Move debug.h include away from cpu.h
  2025-10-02 20:21   ` Pierrick Bouvier
@ 2025-10-03 12:52     ` Anton Johansson via
  0 siblings, 0 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-03 12:52 UTC (permalink / raw)
  To: Pierrick Bouvier
  Cc: qemu-devel, philmd, richard.henderson, alistair.francis, palmer

On 02/10/25, Pierrick Bouvier wrote:
> On 10/1/25 12:33 AM, Anton Johansson wrote:
> > All debug.h definitions except for RV_MAX_TRIGGERS are internal to
> > target/riscv.  Move RV_MAX_TRIGGERS to cpu.h and include debug.h from
> > all translation units which relied on the cpu.h include.
> > 
> > Signed-off-by: Anton Johansson <anjo@rev.ng>
> > ---
> >   target/riscv/cpu.h         | 4 ++--
> >   target/riscv/debug.h       | 2 --
> >   target/riscv/cpu.c         | 3 +++
> >   target/riscv/csr.c         | 3 +++
> >   target/riscv/debug.c       | 1 +
> >   target/riscv/tcg/tcg-cpu.c | 1 +
> >   6 files changed, 10 insertions(+), 4 deletions(-)
> > 
> > diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> > index a53981a09b..70e0f3718c 100644
> > --- a/target/riscv/cpu.h
> > +++ b/target/riscv/cpu.h
> > @@ -177,14 +177,14 @@ extern RISCVCPUImpliedExtsRule *riscv_multi_ext_implied_rules[];
> >   #define MAX_RISCV_PMPS (64)
> >   #define OLD_MAX_RISCV_PMPS (16)
> > -#if !defined(CONFIG_USER_ONLY)
> > +#if !defined(CONFIG_LINUX_USER)
> 
> Squashed from another change?
> 
> ...
> 
> Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>

Yup, nice catch!


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 33/33] target/riscv: Make pmp.h target_ulong agnostic
  2025-10-01  7:49   ` Philippe Mathieu-Daudé
@ 2025-10-03 12:57     ` Anton Johansson via
  0 siblings, 0 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-03 12:57 UTC (permalink / raw)
  To: Philippe Mathieu-Daudé
  Cc: qemu-devel, pierrick.bouvier, richard.henderson, alistair.francis,
	palmer

On 01/10/25, Philippe Mathieu-Daudé wrote:
> On 1/10/25 09:33, Anton Johansson wrote:
> > The pmp.h header is exposed through cpu.h.  pmp_table_t is also used in
> > CPUArchState.  CSR declaraions are only used in target/ and are moved to
> 
> Typo "declarations".
> 
> > csr.h.  In pmp.h, addr_reg is widened to 64 bits and the privilege mode
> > parameter is fixed to 8 bits, similar to previous commits.
> 
> Worth a privilege_mode_t typedef?

I think this makes sense, will add in v3!


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val()
  2025-10-02 23:34   ` Alistair Francis
@ 2025-10-07 11:08     ` Anton Johansson via
  2025-10-15  2:55       ` Alistair Francis
  0 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-07 11:08 UTC (permalink / raw)
  To: Alistair Francis
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On 03/10/25, Alistair Francis wrote:
> On Wed, Oct 1, 2025 at 5:43 PM Anton Johansson via
> <qemu-devel@nongnu.org> wrote:
> >
> > From my understanding the upper_half argument only indicates whether the
> > upper or lower 32 bits should be returned, and upper_half will only ever
> > be set when MXLEN == 32.  However, the function also uses upper_half to
> > determine whether the inhibit flags are located in mcyclecfgh or
> > mcyclecfg, but this misses the case where MXLEN == 32, upper_half == false
> > for TARGET_RISCV32 where we would also need to read the upper half field.
> 
> If MXLEN == 32, upper_half == false then we want to read mcyclecfg,
> which the code today seems to be doing correctly.

Hi again, I might be missing something then, when would this function need
to access mcyclecfg for MXLEN == 32?  AFAIU mcyclecfg and mcyclecfgh are
modeled separately for MXLEN == 32, even when sizeof(target_ulong) == 8.
Since this function only checks inhibit flags wouldn't we always want to
access mcyclecfgh for MXLEN == 32?

//Anton


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh
  2025-10-02 23:55       ` Alistair Francis
@ 2025-10-07 11:29         ` Anton Johansson via
  2025-10-14 11:25         ` Anton Johansson via
  1 sibling, 0 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-07 11:29 UTC (permalink / raw)
  To: Alistair Francis
  Cc: Pierrick Bouvier, qemu-devel, philmd, richard.henderson,
	alistair.francis, palmer

On 03/10/25, Alistair Francis wrote:
> On Fri, Oct 3, 2025 at 5:37 AM Pierrick Bouvier
> <pierrick.bouvier@linaro.org> wrote:
> >
> > On 10/2/25 12:08 PM, Pierrick Bouvier wrote:
> > > On 10/1/25 12:32 AM, Anton Johansson wrote:
> > >> According to version 20250508 of the privileged specification,
> > >> mhpmeventn is 64 bits in size and mhpmeventnh is only ever used
> > >> when XLEN == 32 and accesses the top 32 bits of the 64-bit
> > >> mhpmeventn registers. Combine the two arrays of target_ulong
> > >> mhpmeventh[] and mhpmevent[] to a single array of uint64_t.
> > >>
> > >> This also allows for some minor code simplification where branches
> > >> handling either mhpmeventh[] or mhpmevent[] could be combined.
> > >>
> > >> Signed-off-by: Anton Johansson <anjo@rev.ng>
> > >> ---
> > >>    target/riscv/cpu.h     | 10 +++----
> > >>    target/riscv/csr.c     | 67 +++++++++++++++---------------------------
> > >>    target/riscv/machine.c |  3 +-
> > >>    target/riscv/pmu.c     | 53 ++++++++-------------------------
> > >>    4 files changed, 42 insertions(+), 91 deletions(-)
> > >>
> > >> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> > >> index 3235108112..64b9964028 100644
> > >> --- a/target/riscv/cpu.h
> > >> +++ b/target/riscv/cpu.h
> > >> @@ -427,11 +427,11 @@ struct CPUArchState {
> > >>        /* PMU counter state */
> > >>        PMUCTRState pmu_ctrs[RV_MAX_MHPMCOUNTERS];
> > >>
> > >> -    /* PMU event selector configured values. First three are unused */
> > >> -    target_ulong mhpmevent_val[RV_MAX_MHPMEVENTS];
> > >> -
> > >> -    /* PMU event selector configured values for RV32 */
> > >> -    target_ulong mhpmeventh_val[RV_MAX_MHPMEVENTS];
> > >> +    /*
> > >> +     * PMU event selector configured values. First three are unused.
> > >> +     * For RV32 top 32 bits are accessed via the mhpmeventh CSR.
> > >> +     */
> > >> +    uint64_t mhpmevent_val[RV_MAX_MHPMEVENTS];
> > >>
> > >>        PMUFixedCtrState pmu_fixed_ctrs[2];
> > >>
> > >> diff --git a/target/riscv/csr.c b/target/riscv/csr.c
> > >> index 859f89aedd..2d8916ee40 100644
> > >> --- a/target/riscv/csr.c
> > >> +++ b/target/riscv/csr.c
> > >> @@ -1166,8 +1166,9 @@ static RISCVException read_mhpmevent(CPURISCVState *env, int csrno,
> > >>                                         target_ulong *val)
> > >>    {
> > >>        int evt_index = csrno - CSR_MCOUNTINHIBIT;
> > >> +    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
> > >>
> > >> -    *val = env->mhpmevent_val[evt_index];
> > >> +    *val = extract64(env->mhpmevent_val[evt_index], 0, rv32 ? 32 : 64);
> > >>
> > >>        return RISCV_EXCP_NONE;
> > >>    }
> > >> @@ -1176,13 +1177,11 @@ static RISCVException write_mhpmevent(CPURISCVState *env, int csrno,
> > >>                                          target_ulong val, uintptr_t ra)
> > >>    {
> > >>        int evt_index = csrno - CSR_MCOUNTINHIBIT;
> > >> -    uint64_t mhpmevt_val = val;
> > >> +    uint64_t mhpmevt_val;
> > >>        uint64_t inh_avail_mask;
> > >>
> > >>        if (riscv_cpu_mxl(env) == MXL_RV32) {
> > >> -        env->mhpmevent_val[evt_index] = val;
> > >> -        mhpmevt_val = mhpmevt_val |
> > >> -                      ((uint64_t)env->mhpmeventh_val[evt_index] << 32);
> > >> +        mhpmevt_val = deposit64(env->mhpmevent_val[evt_index], 0, 32, val);
> > >
> > > Maybe I missed something, but should it be:
> > > deposit64(env->mhpmevent_val[evt_index], 32, 32, val)
> > > instead?
> > >
> > > Reading the rest of the patch, I'm a bit confused about which bits are
> > > supposed to be used in 32/64 mode.
> >
> > Indeed I missed something, it's more clear with next patchs combining
> > low/high parts.
> 
> Besides this missed part the patch looks good.
> 
> Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
> 

Did I miss something here? Isn't writing the lower 32 bits correct?

> > The concern I have that is left is regarding the definition of
> > MHPMEVENT_BIT_OF. It seems to be out of sync with what we have now given
> > that we now keep lower part in lower bits.
> 
> That might be a bug, it should be using MHPMEVENTH_BIT_OF with mhpmeventh_val
> 
> 
> Alistair

I'll take a look at the flags, thanks!:)


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh
  2025-10-02 23:55       ` Alistair Francis
  2025-10-07 11:29         ` Anton Johansson via
@ 2025-10-14 11:25         ` Anton Johansson via
  1 sibling, 0 replies; 99+ messages in thread
From: Anton Johansson via @ 2025-10-14 11:25 UTC (permalink / raw)
  To: Alistair Francis
  Cc: Pierrick Bouvier, qemu-devel, philmd, richard.henderson,
	alistair.francis, palmer

On 03/10/25, Alistair Francis wrote:
> On Fri, Oct 3, 2025 at 5:37 AM Pierrick Bouvier
> <pierrick.bouvier@linaro.org> wrote:
> >
> > On 10/2/25 12:08 PM, Pierrick Bouvier wrote:
> > > On 10/1/25 12:32 AM, Anton Johansson wrote:
> > >> According to version 20250508 of the privileged specification,
> > >> mhpmeventn is 64 bits in size and mhpmeventnh is only ever used
> > >> when XLEN == 32 and accesses the top 32 bits of the 64-bit
> > >> mhpmeventn registers. Combine the two arrays of target_ulong
> > >> mhpmeventh[] and mhpmevent[] to a single array of uint64_t.
> > >>
> > >> This also allows for some minor code simplification where branches
> > >> handling either mhpmeventh[] or mhpmevent[] could be combined.
> > >>
> > >> Signed-off-by: Anton Johansson <anjo@rev.ng>
> > >> ---
> > >>    target/riscv/cpu.h     | 10 +++----
> > >>    target/riscv/csr.c     | 67 +++++++++++++++---------------------------
> > >>    target/riscv/machine.c |  3 +-
> > >>    target/riscv/pmu.c     | 53 ++++++++-------------------------
> > >>    4 files changed, 42 insertions(+), 91 deletions(-)
> > >>
> > >> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> > >> index 3235108112..64b9964028 100644
> > >> --- a/target/riscv/cpu.h
> > >> +++ b/target/riscv/cpu.h
> > >> @@ -427,11 +427,11 @@ struct CPUArchState {
> > >>        /* PMU counter state */
> > >>        PMUCTRState pmu_ctrs[RV_MAX_MHPMCOUNTERS];
> > >>
> > >> -    /* PMU event selector configured values. First three are unused */
> > >> -    target_ulong mhpmevent_val[RV_MAX_MHPMEVENTS];
> > >> -
> > >> -    /* PMU event selector configured values for RV32 */
> > >> -    target_ulong mhpmeventh_val[RV_MAX_MHPMEVENTS];
> > >> +    /*
> > >> +     * PMU event selector configured values. First three are unused.
> > >> +     * For RV32 top 32 bits are accessed via the mhpmeventh CSR.
> > >> +     */
> > >> +    uint64_t mhpmevent_val[RV_MAX_MHPMEVENTS];
> > >>
> > >>        PMUFixedCtrState pmu_fixed_ctrs[2];
> > >>
> > >> diff --git a/target/riscv/csr.c b/target/riscv/csr.c
> > >> index 859f89aedd..2d8916ee40 100644
> > >> --- a/target/riscv/csr.c
> > >> +++ b/target/riscv/csr.c
> > >> @@ -1166,8 +1166,9 @@ static RISCVException read_mhpmevent(CPURISCVState *env, int csrno,
> > >>                                         target_ulong *val)
> > >>    {
> > >>        int evt_index = csrno - CSR_MCOUNTINHIBIT;
> > >> +    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32;
> > >>
> > >> -    *val = env->mhpmevent_val[evt_index];
> > >> +    *val = extract64(env->mhpmevent_val[evt_index], 0, rv32 ? 32 : 64);
> > >>
> > >>        return RISCV_EXCP_NONE;
> > >>    }
> > >> @@ -1176,13 +1177,11 @@ static RISCVException write_mhpmevent(CPURISCVState *env, int csrno,
> > >>                                          target_ulong val, uintptr_t ra)
> > >>    {
> > >>        int evt_index = csrno - CSR_MCOUNTINHIBIT;
> > >> -    uint64_t mhpmevt_val = val;
> > >> +    uint64_t mhpmevt_val;
> > >>        uint64_t inh_avail_mask;
> > >>
> > >>        if (riscv_cpu_mxl(env) == MXL_RV32) {
> > >> -        env->mhpmevent_val[evt_index] = val;
> > >> -        mhpmevt_val = mhpmevt_val |
> > >> -                      ((uint64_t)env->mhpmeventh_val[evt_index] << 32);
> > >> +        mhpmevt_val = deposit64(env->mhpmevent_val[evt_index], 0, 32, val);
> > >
> > > Maybe I missed something, but should it be:
> > > deposit64(env->mhpmevent_val[evt_index], 32, 32, val)
> > > instead?
> > >
> > > Reading the rest of the patch, I'm a bit confused about which bits are
> > > supposed to be used in 32/64 mode.
> >
> > Indeed I missed something, it's more clear with next patchs combining
> > low/high parts.
> 
> Besides this missed part the patch looks good.
> 
> Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
> 
> > The concern I have that is left is regarding the definition of
> > MHPMEVENT_BIT_OF. It seems to be out of sync with what we have now given
> > that we now keep lower part in lower bits.
> 
> That might be a bug, it should be using MHPMEVENTH_BIT_OF with mhpmeventh_val

Looked over usage of M*H_BIT* and everything seems correct AFAICT.  I
did however find a bug in upstream rmw_cd_ctr_cfg() where bit 30 is made
read-only 0 instead of bit 62, I'll attach a separate patch to fix this
in v3.

//Anton


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val()
  2025-10-07 11:08     ` Anton Johansson via
@ 2025-10-15  2:55       ` Alistair Francis
  2025-10-15  9:58         ` Anton Johansson via
  0 siblings, 1 reply; 99+ messages in thread
From: Alistair Francis @ 2025-10-15  2:55 UTC (permalink / raw)
  To: Anton Johansson
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On Tue, Oct 7, 2025 at 9:06 PM Anton Johansson <anjo@rev.ng> wrote:
>
> On 03/10/25, Alistair Francis wrote:
> > On Wed, Oct 1, 2025 at 5:43 PM Anton Johansson via
> > <qemu-devel@nongnu.org> wrote:
> > >
> > > From my understanding the upper_half argument only indicates whether the
> > > upper or lower 32 bits should be returned, and upper_half will only ever
> > > be set when MXLEN == 32.  However, the function also uses upper_half to
> > > determine whether the inhibit flags are located in mcyclecfgh or
> > > mcyclecfg, but this misses the case where MXLEN == 32, upper_half == false
> > > for TARGET_RISCV32 where we would also need to read the upper half field.
> >
> > If MXLEN == 32, upper_half == false then we want to read mcyclecfg,
> > which the code today seems to be doing correctly.
>
> Hi again, I might be missing something then, when would this function need
> to access mcyclecfg for MXLEN == 32?  AFAIU mcyclecfg and mcyclecfgh are
> modeled separately for MXLEN == 32, even when sizeof(target_ulong) == 8.
> Since this function only checks inhibit flags wouldn't we always want to
> access mcyclecfgh for MXLEN == 32?

When MXLEN == 32 mcyclecfg is the bottom 32-bits of the mcyclecfg CSR
and mcyclecfgh is the top 32-bits of the CSR. The idea is that
target_ulong will be 32-bits (sizeof(target_ulong) == 4). It doesn't
really matter if target_ulong is 64-bits though, as the registers
should just be treated as 32-bit registers anyway.

Combining mcyclecfg and mcyclecfgh into one 64-bit register for MXLEN
== 32 makes sense though. For MXLEN == 64 there is no mcyclecfgh and
mcyclecfg it always 64-bit.

Alistair

>
> //Anton


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val()
  2025-10-15  2:55       ` Alistair Francis
@ 2025-10-15  9:58         ` Anton Johansson via
  2025-10-16  4:01           ` Alistair Francis
  0 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-15  9:58 UTC (permalink / raw)
  To: Alistair Francis
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On 15/10/25, Alistair Francis wrote:
> On Tue, Oct 7, 2025 at 9:06 PM Anton Johansson <anjo@rev.ng> wrote:
> >
> > On 03/10/25, Alistair Francis wrote:
> > > On Wed, Oct 1, 2025 at 5:43 PM Anton Johansson via
> > > <qemu-devel@nongnu.org> wrote:
> > > >
> > > > From my understanding the upper_half argument only indicates whether the
> > > > upper or lower 32 bits should be returned, and upper_half will only ever
> > > > be set when MXLEN == 32.  However, the function also uses upper_half to
> > > > determine whether the inhibit flags are located in mcyclecfgh or
> > > > mcyclecfg, but this misses the case where MXLEN == 32, upper_half == false
> > > > for TARGET_RISCV32 where we would also need to read the upper half field.
> > >
> > > If MXLEN == 32, upper_half == false then we want to read mcyclecfg,
> > > which the code today seems to be doing correctly.
> >
> > Hi again, I might be missing something then, when would this function need
> > to access mcyclecfg for MXLEN == 32?  AFAIU mcyclecfg and mcyclecfgh are
> > modeled separately for MXLEN == 32, even when sizeof(target_ulong) == 8.
> > Since this function only checks inhibit flags wouldn't we always want to
> > access mcyclecfgh for MXLEN == 32?
> 
> When MXLEN == 32 mcyclecfg is the bottom 32-bits of the mcyclecfg CSR
> and mcyclecfgh is the top 32-bits of the CSR. The idea is that
> target_ulong will be 32-bits (sizeof(target_ulong) == 4). It doesn't
> really matter if target_ulong is 64-bits though, as the registers
> should just be treated as 32-bit registers anyway.

Appreciate the explanation, this makes sense to me.  But the function
only uses cfg_val to check inhibit flags in the top 32 bits, so accessing the
lower 32 bits when upper_half == false and MXLEN == 32 would be incorrect
then?  

Your comment below is what's tripping me up, since the behaviour of
accesing the lower 32 bits for MXLEN == 32 is not retained when
mcyclecfgh and mcyclecfg are merged to a single 64 bit field

> >      if (counter_idx == 0) {
> > -        cfg_val = upper_half ? ((uint64_t)env->mcyclecfgh << 32) :
> > +        cfg_val = rv32 ? ((uint64_t)env->mcyclecfgh << 32) :
> 
> This doesn't look right.
> 
> RV32 will want to access both mcyclecfgh and mcyclecfg, but this
> change restricts access to mcyclecfg as rv32 will always be true.
> 
> I don't think there is anything wrong with the current code.

//Anton


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val()
  2025-10-15  9:58         ` Anton Johansson via
@ 2025-10-16  4:01           ` Alistair Francis
  2025-10-17 14:24             ` Anton Johansson via
  0 siblings, 1 reply; 99+ messages in thread
From: Alistair Francis @ 2025-10-16  4:01 UTC (permalink / raw)
  To: Anton Johansson
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On Wed, Oct 15, 2025 at 7:55 PM Anton Johansson <anjo@rev.ng> wrote:
>
> On 15/10/25, Alistair Francis wrote:
> > On Tue, Oct 7, 2025 at 9:06 PM Anton Johansson <anjo@rev.ng> wrote:
> > >
> > > On 03/10/25, Alistair Francis wrote:
> > > > On Wed, Oct 1, 2025 at 5:43 PM Anton Johansson via
> > > > <qemu-devel@nongnu.org> wrote:
> > > > >
> > > > > From my understanding the upper_half argument only indicates whether the
> > > > > upper or lower 32 bits should be returned, and upper_half will only ever
> > > > > be set when MXLEN == 32.  However, the function also uses upper_half to
> > > > > determine whether the inhibit flags are located in mcyclecfgh or
> > > > > mcyclecfg, but this misses the case where MXLEN == 32, upper_half == false
> > > > > for TARGET_RISCV32 where we would also need to read the upper half field.
> > > >
> > > > If MXLEN == 32, upper_half == false then we want to read mcyclecfg,
> > > > which the code today seems to be doing correctly.
> > >
> > > Hi again, I might be missing something then, when would this function need
> > > to access mcyclecfg for MXLEN == 32?  AFAIU mcyclecfg and mcyclecfgh are
> > > modeled separately for MXLEN == 32, even when sizeof(target_ulong) == 8.
> > > Since this function only checks inhibit flags wouldn't we always want to
> > > access mcyclecfgh for MXLEN == 32?
> >
> > When MXLEN == 32 mcyclecfg is the bottom 32-bits of the mcyclecfg CSR
> > and mcyclecfgh is the top 32-bits of the CSR. The idea is that
> > target_ulong will be 32-bits (sizeof(target_ulong) == 4). It doesn't
> > really matter if target_ulong is 64-bits though, as the registers
> > should just be treated as 32-bit registers anyway.
>
> Appreciate the explanation, this makes sense to me.  But the function
> only uses cfg_val to check inhibit flags in the top 32 bits, so accessing the
> lower 32 bits when upper_half == false and MXLEN == 32 would be incorrect
> then?

Well a guest can still access the lower 32-bits and although there is
nothing there now there might be in the future.

>
> Your comment below is what's tripping me up, since the behaviour of
> accesing the lower 32 bits for MXLEN == 32 is not retained when
> mcyclecfgh and mcyclecfg are merged to a single 64 bit field

I don't follow what you mean here

Alistair

>
> > >      if (counter_idx == 0) {
> > > -        cfg_val = upper_half ? ((uint64_t)env->mcyclecfgh << 32) :
> > > +        cfg_val = rv32 ? ((uint64_t)env->mcyclecfgh << 32) :
> >
> > This doesn't look right.
> >
> > RV32 will want to access both mcyclecfgh and mcyclecfg, but this
> > change restricts access to mcyclecfg as rv32 will always be true.
> >
> > I don't think there is anything wrong with the current code.
>
> //Anton


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val()
  2025-10-16  4:01           ` Alistair Francis
@ 2025-10-17 14:24             ` Anton Johansson via
  2025-10-23  1:54               ` Alistair Francis
  0 siblings, 1 reply; 99+ messages in thread
From: Anton Johansson via @ 2025-10-17 14:24 UTC (permalink / raw)
  To: Alistair Francis
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On 16/10/25, Alistair Francis wrote:
> On Wed, Oct 15, 2025 at 7:55 PM Anton Johansson <anjo@rev.ng> wrote:
> >
> > On 15/10/25, Alistair Francis wrote:
> > > On Tue, Oct 7, 2025 at 9:06 PM Anton Johansson <anjo@rev.ng> wrote:
> > > >
> > > > On 03/10/25, Alistair Francis wrote:
> > > > > On Wed, Oct 1, 2025 at 5:43 PM Anton Johansson via
> > > > > <qemu-devel@nongnu.org> wrote:
> > > > > >
> > > > > > From my understanding the upper_half argument only indicates whether the
> > > > > > upper or lower 32 bits should be returned, and upper_half will only ever
> > > > > > be set when MXLEN == 32.  However, the function also uses upper_half to
> > > > > > determine whether the inhibit flags are located in mcyclecfgh or
> > > > > > mcyclecfg, but this misses the case where MXLEN == 32, upper_half == false
> > > > > > for TARGET_RISCV32 where we would also need to read the upper half field.
> > > > >
> > > > > If MXLEN == 32, upper_half == false then we want to read mcyclecfg,
> > > > > which the code today seems to be doing correctly.
> > > >
> > > > Hi again, I might be missing something then, when would this function need
> > > > to access mcyclecfg for MXLEN == 32?  AFAIU mcyclecfg and mcyclecfgh are
> > > > modeled separately for MXLEN == 32, even when sizeof(target_ulong) == 8.
> > > > Since this function only checks inhibit flags wouldn't we always want to
> > > > access mcyclecfgh for MXLEN == 32?
> > >
> > > When MXLEN == 32 mcyclecfg is the bottom 32-bits of the mcyclecfg CSR
> > > and mcyclecfgh is the top 32-bits of the CSR. The idea is that
> > > target_ulong will be 32-bits (sizeof(target_ulong) == 4). It doesn't
> > > really matter if target_ulong is 64-bits though, as the registers
> > > should just be treated as 32-bit registers anyway.
> >
> > Appreciate the explanation, this makes sense to me.  But the function
> > only uses cfg_val to check inhibit flags in the top 32 bits, so accessing the
> > lower 32 bits when upper_half == false and MXLEN == 32 would be incorrect
> > then?
> 
> Well a guest can still access the lower 32-bits and although there is
> nothing there now there might be in the future.
> 
> >
> > Your comment below is what's tripping me up, since the behaviour of
> > accesing the lower 32 bits for MXLEN == 32 is not retained when
> > mcyclecfgh and mcyclecfg are merged to a single 64 bit field
> 
> I don't follow what you mean here

On upstream when riscv_pmu_ctr_get_fixed_counters_val() is called with
MXLEN == 32 and upper_half == false, we read the inhibit flags from the
lower 32 bits (mcyclecfg) and check against bit 62 (MINH) etc. thus
always returning false

  if (counter_idx == 0) {
      cfg_val = upper_half ? ((uint64_t)env->mcyclecfgh << 32) :
                             env->mcyclecfg;
  }
  [...]
  if (!(cfg_val & MCYCLECFG_BIT_MINH)) {
      curr_val += counter_arr[PRV_M];
  }

if this behaviour is intended, we do not retain it with this patch as
we always access the higher cfg bits to check for MINH.  Similarly when
merging mcyclecfgh and mcyclecfg

  if (counter_idx == 0) {
      cfg_val = env->mcyclecfg;
  }
  [...]
  if (!(cfg_val & MCYCLECFG_BIT_MINH)) {
      curr_val += counter_arr[PRV_M];
  }

we only check for MINH in the higher bits.

//Anton


^ permalink raw reply	[flat|nested] 99+ messages in thread

* Re: [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val()
  2025-10-17 14:24             ` Anton Johansson via
@ 2025-10-23  1:54               ` Alistair Francis
  0 siblings, 0 replies; 99+ messages in thread
From: Alistair Francis @ 2025-10-23  1:54 UTC (permalink / raw)
  To: Anton Johansson
  Cc: qemu-devel, pierrick.bouvier, philmd, richard.henderson,
	alistair.francis, palmer

On Sat, Oct 18, 2025 at 12:22 AM Anton Johansson <anjo@rev.ng> wrote:
>
> On 16/10/25, Alistair Francis wrote:
> > On Wed, Oct 15, 2025 at 7:55 PM Anton Johansson <anjo@rev.ng> wrote:
> > >
> > > On 15/10/25, Alistair Francis wrote:
> > > > On Tue, Oct 7, 2025 at 9:06 PM Anton Johansson <anjo@rev.ng> wrote:
> > > > >
> > > > > On 03/10/25, Alistair Francis wrote:
> > > > > > On Wed, Oct 1, 2025 at 5:43 PM Anton Johansson via
> > > > > > <qemu-devel@nongnu.org> wrote:
> > > > > > >
> > > > > > > From my understanding the upper_half argument only indicates whether the
> > > > > > > upper or lower 32 bits should be returned, and upper_half will only ever
> > > > > > > be set when MXLEN == 32.  However, the function also uses upper_half to
> > > > > > > determine whether the inhibit flags are located in mcyclecfgh or
> > > > > > > mcyclecfg, but this misses the case where MXLEN == 32, upper_half == false
> > > > > > > for TARGET_RISCV32 where we would also need to read the upper half field.
> > > > > >
> > > > > > If MXLEN == 32, upper_half == false then we want to read mcyclecfg,
> > > > > > which the code today seems to be doing correctly.
> > > > >
> > > > > Hi again, I might be missing something then, when would this function need
> > > > > to access mcyclecfg for MXLEN == 32?  AFAIU mcyclecfg and mcyclecfgh are
> > > > > modeled separately for MXLEN == 32, even when sizeof(target_ulong) == 8.
> > > > > Since this function only checks inhibit flags wouldn't we always want to
> > > > > access mcyclecfgh for MXLEN == 32?
> > > >
> > > > When MXLEN == 32 mcyclecfg is the bottom 32-bits of the mcyclecfg CSR
> > > > and mcyclecfgh is the top 32-bits of the CSR. The idea is that
> > > > target_ulong will be 32-bits (sizeof(target_ulong) == 4). It doesn't
> > > > really matter if target_ulong is 64-bits though, as the registers
> > > > should just be treated as 32-bit registers anyway.
> > >
> > > Appreciate the explanation, this makes sense to me.  But the function
> > > only uses cfg_val to check inhibit flags in the top 32 bits, so accessing the
> > > lower 32 bits when upper_half == false and MXLEN == 32 would be incorrect
> > > then?
> >
> > Well a guest can still access the lower 32-bits and although there is
> > nothing there now there might be in the future.
> >
> > >
> > > Your comment below is what's tripping me up, since the behaviour of
> > > accesing the lower 32 bits for MXLEN == 32 is not retained when
> > > mcyclecfgh and mcyclecfg are merged to a single 64 bit field
> >
> > I don't follow what you mean here
>
> On upstream when riscv_pmu_ctr_get_fixed_counters_val() is called with
> MXLEN == 32 and upper_half == false, we read the inhibit flags from the
> lower 32 bits (mcyclecfg) and check against bit 62 (MINH) etc. thus
> always returning false

That's correct.

If MXLEN == 32 and the guest accesses mcyclecfg (lower 32-bits) then
we expect riscv_pmu_ctr_get_fixed_counters_val() to return 0.

I agree it's clunky, we should combine the two halves into a single
64-bit value for both 32-bit and 64-bit. But the current approach of
separate registers although confusing, doesn't look wrong.

>
>   if (counter_idx == 0) {
>       cfg_val = upper_half ? ((uint64_t)env->mcyclecfgh << 32) :
>                              env->mcyclecfg;
>   }
>   [...]
>   if (!(cfg_val & MCYCLECFG_BIT_MINH)) {
>       curr_val += counter_arr[PRV_M];
>   }
>
> if this behaviour is intended, we do not retain it with this patch as
> we always access the higher cfg bits to check for MINH.  Similarly when
> merging mcyclecfgh and mcyclecfg

Once merged it's fine to always check the higher bits

Alistair

>
>   if (counter_idx == 0) {
>       cfg_val = env->mcyclecfg;
>   }
>   [...]
>   if (!(cfg_val & MCYCLECFG_BIT_MINH)) {
>       curr_val += counter_arr[PRV_M];
>   }
>
> we only check for MINH in the higher bits.
>
> //Anton


^ permalink raw reply	[flat|nested] 99+ messages in thread

end of thread, other threads:[~2025-10-23  1:55 UTC | newest]

Thread overview: 99+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-10-01  7:32 [PATCH v2 00/33] single-binary: Make riscv cpu.h target independent Anton Johansson via
2025-10-01  7:32 ` [PATCH v2 01/33] target/riscv: Use 32 bits for misa extensions Anton Johansson via
2025-10-01  7:34   ` Philippe Mathieu-Daudé
2025-10-02  1:56   ` Alistair Francis
2025-10-02 18:31   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 02/33] target/riscv: Fix size of trivial CPUArchState fields Anton Johansson via
2025-10-02  1:57   ` Alistair Francis
2025-10-02 18:31   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 03/33] target/riscv: Fix size of mhartid Anton Johansson via
2025-10-01  7:38   ` Philippe Mathieu-Daudé
2025-10-01  8:28     ` Anton Johansson via
2025-10-02 18:34       ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 04/33] target/riscv: Bugfix riscv_pmu_ctr_get_fixed_counters_val() Anton Johansson via
2025-10-02 18:50   ` Pierrick Bouvier
2025-10-02 23:34   ` Alistair Francis
2025-10-07 11:08     ` Anton Johansson via
2025-10-15  2:55       ` Alistair Francis
2025-10-15  9:58         ` Anton Johansson via
2025-10-16  4:01           ` Alistair Francis
2025-10-17 14:24             ` Anton Johansson via
2025-10-23  1:54               ` Alistair Francis
2025-10-01  7:32 ` [PATCH v2 05/33] target/riscv: Combine mhpmevent and mhpmeventh Anton Johansson via
2025-10-01  7:39   ` Philippe Mathieu-Daudé
2025-10-02 19:09     ` Pierrick Bouvier
2025-10-02 23:52       ` Alistair Francis
2025-10-02 19:08   ` Pierrick Bouvier
2025-10-02 19:33     ` Pierrick Bouvier
2025-10-02 23:55       ` Alistair Francis
2025-10-07 11:29         ` Anton Johansson via
2025-10-14 11:25         ` Anton Johansson via
2025-10-01  7:32 ` [PATCH v2 06/33] target/riscv: Combine mcyclecfg and mcyclecfgh Anton Johansson via
2025-10-02 19:13   ` Pierrick Bouvier
2025-10-03  0:05   ` Alistair Francis
2025-10-01  7:32 ` [PATCH v2 07/33] target/riscv: Combine minstretcfg and minstretcfgh Anton Johansson via
2025-10-02 19:14   ` Pierrick Bouvier
2025-10-03  0:06   ` Alistair Francis
2025-10-01  7:32 ` [PATCH v2 08/33] target/riscv: Combine mhpmcounter and mhpmcounterh Anton Johansson via
2025-10-02 19:24   ` Pierrick Bouvier
2025-10-02 19:25   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 09/33] target/riscv: Fix size of gpr and gprh Anton Johansson via
2025-10-01  7:42   ` Philippe Mathieu-Daudé
2025-10-03  9:00     ` Anton Johansson via
2025-10-01  7:32 ` [PATCH v2 10/33] target/riscv: Fix size of vector CSRs Anton Johansson via
2025-10-02 19:42   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 11/33] target/riscv: Fix size of pc, load_[val|res] Anton Johansson via
2025-10-02 19:54   ` Pierrick Bouvier
2025-10-03 12:43     ` Anton Johansson via
2025-10-01  7:32 ` [PATCH v2 12/33] target/riscv: Fix size of frm and fflags Anton Johansson via
2025-10-02 19:57   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 13/33] target/riscv: Fix size of badaddr and bins Anton Johansson via
2025-10-02 20:02   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 14/33] target/riscv: Fix size of guest_phys_fault_addr Anton Johansson via
2025-10-02 20:03   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 15/33] target/riscv: Fix size of priv_ver and vext_ver Anton Johansson via
2025-10-02 20:03   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 16/33] target/riscv: Fix size of retxh Anton Johansson via
2025-10-02 20:05   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 17/33] target/riscv: Fix size of ssp Anton Johansson via
2025-10-02 20:06   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 18/33] target/riscv: Fix size of excp_uw2 Anton Johansson via
2025-10-02 20:06   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 19/33] target/riscv: Fix size of sw_check_code Anton Johansson via
2025-10-02 20:07   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 20/33] target/riscv: Fix size of priv Anton Johansson via
2025-10-02 20:07   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 21/33] target/riscv: Fix size of gei fields Anton Johansson via
2025-10-02 20:08   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 22/33] target/riscv: Fix size of [m|s|vs]iselect fields Anton Johansson via
2025-10-02 20:09   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 23/33] target/riscv: Fix arguments to board IMSIC emulation callbacks Anton Johansson via
2025-10-02 20:15   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 24/33] target/riscv: Fix size of irq_overflow_left Anton Johansson via
2025-10-02 20:15   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 25/33] target/riscv: Indent PMUFixedCtrState correctly Anton Johansson via
2025-10-01  7:43   ` Philippe Mathieu-Daudé
2025-10-02 20:15   ` Pierrick Bouvier
2025-10-01  7:32 ` [PATCH v2 26/33] target/riscv: Replace target_ulong in riscv_cpu_get_trap_name() Anton Johansson via
2025-10-01  7:43   ` Philippe Mathieu-Daudé
2025-10-02 20:15   ` Pierrick Bouvier
2025-10-01  7:33 ` [PATCH v2 27/33] target/riscv: Replace target_ulong in riscv_ctr_add_entry() Anton Johansson via
2025-10-01  7:44   ` Philippe Mathieu-Daudé
2025-10-02 20:19   ` Pierrick Bouvier
2025-10-01  7:33 ` [PATCH v2 28/33] target/riscv: Fix size of trigger data Anton Johansson via
2025-10-01  7:46   ` Philippe Mathieu-Daudé
2025-10-02 20:19   ` Pierrick Bouvier
2025-10-01  7:33 ` [PATCH v2 29/33] target/riscv: Fix size of mseccfg Anton Johansson via
2025-10-01  7:46   ` Philippe Mathieu-Daudé
2025-10-02 20:20   ` Pierrick Bouvier
2025-10-01  7:33 ` [PATCH v2 30/33] target/riscv: Move debug.h include away from cpu.h Anton Johansson via
2025-10-02 20:21   ` Pierrick Bouvier
2025-10-03 12:52     ` Anton Johansson via
2025-10-01  7:33 ` [PATCH v2 31/33] target/riscv: Move CSR declarations to separate csr.h header Anton Johansson via
2025-10-02 20:22   ` Pierrick Bouvier
2025-10-01  7:33 ` [PATCH v2 32/33] target/riscv: Introduce externally facing CSR access functions Anton Johansson via
2025-10-02 20:24   ` Pierrick Bouvier
2025-10-01  7:33 ` [PATCH v2 33/33] target/riscv: Make pmp.h target_ulong agnostic Anton Johansson via
2025-10-01  7:49   ` Philippe Mathieu-Daudé
2025-10-03 12:57     ` Anton Johansson via
2025-10-02 20:23   ` Pierrick Bouvier

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).