target/riscv: Create current pm fields in env
Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com> Reviewed-by: Alistair Francis <alistair.francis@wdc.com> Reviewed-by: Richard Henderson <richard.henderson@linaro.org> Message-id: 20220120122050.41546-12-zhiwei_liu@c-sky.com Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
This commit is contained in:
parent
83b519b8a4
commit
40bfa5f695
@ -430,6 +430,7 @@ static void riscv_cpu_reset(DeviceState *dev)
|
|||||||
env->mmte |= (PM_EXT_INITIAL | MMTE_M_PM_CURRENT);
|
env->mmte |= (PM_EXT_INITIAL | MMTE_M_PM_CURRENT);
|
||||||
#endif
|
#endif
|
||||||
env->xl = riscv_cpu_mxl(env);
|
env->xl = riscv_cpu_mxl(env);
|
||||||
|
riscv_cpu_update_mask(env);
|
||||||
cs->exception_index = RISCV_EXCP_NONE;
|
cs->exception_index = RISCV_EXCP_NONE;
|
||||||
env->load_res = -1;
|
env->load_res = -1;
|
||||||
set_default_nan_mode(1, &env->fp_status);
|
set_default_nan_mode(1, &env->fp_status);
|
||||||
|
@ -266,6 +266,8 @@ struct CPURISCVState {
|
|||||||
target_ulong upmmask;
|
target_ulong upmmask;
|
||||||
target_ulong upmbase;
|
target_ulong upmbase;
|
||||||
#endif
|
#endif
|
||||||
|
target_ulong cur_pmmask;
|
||||||
|
target_ulong cur_pmbase;
|
||||||
|
|
||||||
float_status fp_status;
|
float_status fp_status;
|
||||||
|
|
||||||
@ -515,6 +517,8 @@ static inline uint32_t vext_get_vlmax(RISCVCPU *cpu, target_ulong vtype)
|
|||||||
void cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
|
void cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
|
||||||
target_ulong *cs_base, uint32_t *pflags);
|
target_ulong *cs_base, uint32_t *pflags);
|
||||||
|
|
||||||
|
void riscv_cpu_update_mask(CPURISCVState *env);
|
||||||
|
|
||||||
RISCVException riscv_csrrw(CPURISCVState *env, int csrno,
|
RISCVException riscv_csrrw(CPURISCVState *env, int csrno,
|
||||||
target_ulong *ret_value,
|
target_ulong *ret_value,
|
||||||
target_ulong new_value, target_ulong write_mask);
|
target_ulong new_value, target_ulong write_mask);
|
||||||
|
@ -122,6 +122,48 @@ void cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
|
|||||||
*pflags = flags;
|
*pflags = flags;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void riscv_cpu_update_mask(CPURISCVState *env)
|
||||||
|
{
|
||||||
|
target_ulong mask = -1, base = 0;
|
||||||
|
/*
|
||||||
|
* TODO: Current RVJ spec does not specify
|
||||||
|
* how the extension interacts with XLEN.
|
||||||
|
*/
|
||||||
|
#ifndef CONFIG_USER_ONLY
|
||||||
|
if (riscv_has_ext(env, RVJ)) {
|
||||||
|
switch (env->priv) {
|
||||||
|
case PRV_M:
|
||||||
|
if (env->mmte & M_PM_ENABLE) {
|
||||||
|
mask = env->mpmmask;
|
||||||
|
base = env->mpmbase;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case PRV_S:
|
||||||
|
if (env->mmte & S_PM_ENABLE) {
|
||||||
|
mask = env->spmmask;
|
||||||
|
base = env->spmbase;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case PRV_U:
|
||||||
|
if (env->mmte & U_PM_ENABLE) {
|
||||||
|
mask = env->upmmask;
|
||||||
|
base = env->upmbase;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
g_assert_not_reached();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
if (env->xl == MXL_RV32) {
|
||||||
|
env->cur_pmmask = mask & UINT32_MAX;
|
||||||
|
env->cur_pmbase = base & UINT32_MAX;
|
||||||
|
} else {
|
||||||
|
env->cur_pmmask = mask;
|
||||||
|
env->cur_pmbase = base;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#ifndef CONFIG_USER_ONLY
|
#ifndef CONFIG_USER_ONLY
|
||||||
static int riscv_cpu_local_irq_pending(CPURISCVState *env)
|
static int riscv_cpu_local_irq_pending(CPURISCVState *env)
|
||||||
{
|
{
|
||||||
@ -334,6 +376,7 @@ void riscv_cpu_set_mode(CPURISCVState *env, target_ulong newpriv)
|
|||||||
/* tlb_flush is unnecessary as mode is contained in mmu_idx */
|
/* tlb_flush is unnecessary as mode is contained in mmu_idx */
|
||||||
env->priv = newpriv;
|
env->priv = newpriv;
|
||||||
env->xl = cpu_recompute_xl(env);
|
env->xl = cpu_recompute_xl(env);
|
||||||
|
riscv_cpu_update_mask(env);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Clear the load reservation - otherwise a reservation placed in one
|
* Clear the load reservation - otherwise a reservation placed in one
|
||||||
|
@ -1607,6 +1607,7 @@ static RISCVException write_mmte(CPURISCVState *env, int csrno,
|
|||||||
/* hardwiring pm.instruction bit to 0, since it's not supported yet */
|
/* hardwiring pm.instruction bit to 0, since it's not supported yet */
|
||||||
wpri_val &= ~(MMTE_M_PM_INSN | MMTE_S_PM_INSN | MMTE_U_PM_INSN);
|
wpri_val &= ~(MMTE_M_PM_INSN | MMTE_S_PM_INSN | MMTE_U_PM_INSN);
|
||||||
env->mmte = wpri_val | PM_EXT_DIRTY;
|
env->mmte = wpri_val | PM_EXT_DIRTY;
|
||||||
|
riscv_cpu_update_mask(env);
|
||||||
|
|
||||||
/* Set XS and SD bits, since PM CSRs are dirty */
|
/* Set XS and SD bits, since PM CSRs are dirty */
|
||||||
mstatus = env->mstatus | MSTATUS_XS;
|
mstatus = env->mstatus | MSTATUS_XS;
|
||||||
@ -1682,6 +1683,9 @@ static RISCVException write_mpmmask(CPURISCVState *env, int csrno,
|
|||||||
uint64_t mstatus;
|
uint64_t mstatus;
|
||||||
|
|
||||||
env->mpmmask = val;
|
env->mpmmask = val;
|
||||||
|
if ((env->priv == PRV_M) && (env->mmte & M_PM_ENABLE)) {
|
||||||
|
env->cur_pmmask = val;
|
||||||
|
}
|
||||||
env->mmte |= PM_EXT_DIRTY;
|
env->mmte |= PM_EXT_DIRTY;
|
||||||
|
|
||||||
/* Set XS and SD bits, since PM CSRs are dirty */
|
/* Set XS and SD bits, since PM CSRs are dirty */
|
||||||
@ -1707,6 +1711,9 @@ static RISCVException write_spmmask(CPURISCVState *env, int csrno,
|
|||||||
return RISCV_EXCP_NONE;
|
return RISCV_EXCP_NONE;
|
||||||
}
|
}
|
||||||
env->spmmask = val;
|
env->spmmask = val;
|
||||||
|
if ((env->priv == PRV_S) && (env->mmte & S_PM_ENABLE)) {
|
||||||
|
env->cur_pmmask = val;
|
||||||
|
}
|
||||||
env->mmte |= PM_EXT_DIRTY;
|
env->mmte |= PM_EXT_DIRTY;
|
||||||
|
|
||||||
/* Set XS and SD bits, since PM CSRs are dirty */
|
/* Set XS and SD bits, since PM CSRs are dirty */
|
||||||
@ -1732,6 +1739,9 @@ static RISCVException write_upmmask(CPURISCVState *env, int csrno,
|
|||||||
return RISCV_EXCP_NONE;
|
return RISCV_EXCP_NONE;
|
||||||
}
|
}
|
||||||
env->upmmask = val;
|
env->upmmask = val;
|
||||||
|
if ((env->priv == PRV_U) && (env->mmte & U_PM_ENABLE)) {
|
||||||
|
env->cur_pmmask = val;
|
||||||
|
}
|
||||||
env->mmte |= PM_EXT_DIRTY;
|
env->mmte |= PM_EXT_DIRTY;
|
||||||
|
|
||||||
/* Set XS and SD bits, since PM CSRs are dirty */
|
/* Set XS and SD bits, since PM CSRs are dirty */
|
||||||
@ -1753,6 +1763,9 @@ static RISCVException write_mpmbase(CPURISCVState *env, int csrno,
|
|||||||
uint64_t mstatus;
|
uint64_t mstatus;
|
||||||
|
|
||||||
env->mpmbase = val;
|
env->mpmbase = val;
|
||||||
|
if ((env->priv == PRV_M) && (env->mmte & M_PM_ENABLE)) {
|
||||||
|
env->cur_pmbase = val;
|
||||||
|
}
|
||||||
env->mmte |= PM_EXT_DIRTY;
|
env->mmte |= PM_EXT_DIRTY;
|
||||||
|
|
||||||
/* Set XS and SD bits, since PM CSRs are dirty */
|
/* Set XS and SD bits, since PM CSRs are dirty */
|
||||||
@ -1778,6 +1791,9 @@ static RISCVException write_spmbase(CPURISCVState *env, int csrno,
|
|||||||
return RISCV_EXCP_NONE;
|
return RISCV_EXCP_NONE;
|
||||||
}
|
}
|
||||||
env->spmbase = val;
|
env->spmbase = val;
|
||||||
|
if ((env->priv == PRV_S) && (env->mmte & S_PM_ENABLE)) {
|
||||||
|
env->cur_pmbase = val;
|
||||||
|
}
|
||||||
env->mmte |= PM_EXT_DIRTY;
|
env->mmte |= PM_EXT_DIRTY;
|
||||||
|
|
||||||
/* Set XS and SD bits, since PM CSRs are dirty */
|
/* Set XS and SD bits, since PM CSRs are dirty */
|
||||||
@ -1803,6 +1819,9 @@ static RISCVException write_upmbase(CPURISCVState *env, int csrno,
|
|||||||
return RISCV_EXCP_NONE;
|
return RISCV_EXCP_NONE;
|
||||||
}
|
}
|
||||||
env->upmbase = val;
|
env->upmbase = val;
|
||||||
|
if ((env->priv == PRV_U) && (env->mmte & U_PM_ENABLE)) {
|
||||||
|
env->cur_pmbase = val;
|
||||||
|
}
|
||||||
env->mmte |= PM_EXT_DIRTY;
|
env->mmte |= PM_EXT_DIRTY;
|
||||||
|
|
||||||
/* Set XS and SD bits, since PM CSRs are dirty */
|
/* Set XS and SD bits, since PM CSRs are dirty */
|
||||||
|
@ -220,6 +220,7 @@ static int riscv_cpu_post_load(void *opaque, int version_id)
|
|||||||
CPURISCVState *env = &cpu->env;
|
CPURISCVState *env = &cpu->env;
|
||||||
|
|
||||||
env->xl = cpu_recompute_xl(env);
|
env->xl = cpu_recompute_xl(env);
|
||||||
|
riscv_cpu_update_mask(env);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user