@samitouri / QOSamiQemu / commits / f359e46301

target/riscv: Add a helper to return the current effective priv mode

This helper returns the current effective privilege mode. Signed-off-by: Frank Chang <frank.chang@sifive.com> Reviewed-by: Alistair Francis <alistair.francis@wdc.com> Message-ID: <20260421093715.2995067-3-frank.chang@sifive.com> Signed-off-by: Alistair Francis <alistair.francis@wdc.com>

Frank Chang committed Apr 21, 2026 at 17:37 UTC f359e463015c2f22388eeb4743e93e1176f93abe
2 files changed +42 -10
target/riscv/cpu.h
+37
@@ -806,6 +806,43 @@ static inline RISCVMXL riscv_cpu_sxl(CPURISCVState *env)
806 }
807 #endif
808
809 +/*
810 + * Returns the current effective privilege mode.
811 + *
812 + * @env: CPURISCVState
813 + * @priv: The returned effective privilege mode.
814 + * @virt: The returned effective virtualization mode.
815 + *
816 + * Returns true if the effective privilege mode is modified.
817 + */
818 +static inline QEMU_ALWAYS_INLINE
819 +bool riscv_cpu_eff_priv(CPURISCVState *env, int *priv, bool *virt)
820 +{
821 + int mode = env->priv;
822 + bool virt_enabled = false;
823 + bool mode_modified = false;
824 +
825 +#ifndef CONFIG_USER_ONLY
826 + if (mode == PRV_M && get_field(env->mstatus, MSTATUS_MPRV)) {
827 + mode = get_field(env->mstatus, MSTATUS_MPP);
828 + virt_enabled = get_field(env->mstatus, MSTATUS_MPV) && (mode != PRV_M);
829 + mode_modified = true;
830 + } else {
831 + virt_enabled = env->virt_enabled;
832 + }
833 +#endif
834 +
835 + if (priv) {
836 + *priv = mode;
837 + }
838 +
839 + if (virt) {
840 + *virt = virt_enabled;
841 + }
842 +
843 + return mode_modified;
844 +}
845 +
846 static inline bool riscv_cpu_allow_16bit_insn(const RISCVCPUConfig *cfg,
847 target_long priv_ver,
848 uint32_t misa_ext)
target/riscv/cpu_helper.c
+5 -10
@@ -45,19 +45,14 @@ int riscv_env_mmu_index(CPURISCVState *env, bool ifetch)
45 #else
46 bool virt = env->virt_enabled;
47 int mode = env->priv;
48 + bool mode_modified = false;
49
50 /* All priv -> mmu_idx mapping are here */
51 if (!ifetch) {
51 - uint64_t status = env->mstatus;
52 -
53 - if (mode == PRV_M && get_field(status, MSTATUS_MPRV)) {
54 - mode = get_field(env->mstatus, MSTATUS_MPP);
55 - virt = get_field(env->mstatus, MSTATUS_MPV) &&
56 - (mode != PRV_M);
57 - if (virt) {
58 - status = env->vsstatus;
59 - }
60 - }
52 + mode_modified = riscv_cpu_eff_priv(env, &mode, &virt);
53 + uint64_t status = (mode_modified && virt) ? env->vsstatus :
54 + env->mstatus;
55 +
56 if (mode == PRV_S && get_field(status, MSTATUS_SUM)) {
57 mode = MMUIdx_S_SUM;
58 }