This just allows read/write of three feature bits. ASID is still ignored. Any writes to TTBR0_EL0 and TTBR1_EL0, including changing the ASID, will still cause a complete flush of the TLB.
Signed-off-by: Jim MacArthur <[email protected]> --- target/arm/cpu-features.h | 7 +++++++ target/arm/helper.c | 18 ++++++++++++++++++ 2 files changed, 25 insertions(+) diff --git a/target/arm/cpu-features.h b/target/arm/cpu-features.h index 579fa8f8f4..d56bda9ce0 100644 --- a/target/arm/cpu-features.h +++ b/target/arm/cpu-features.h @@ -346,6 +346,8 @@ FIELD(ID_AA64MMFR3, SDERR, 52, 4) FIELD(ID_AA64MMFR3, ADERR, 56, 4) FIELD(ID_AA64MMFR3, SPEC_FPACC, 60, 4) +FIELD(ID_AA64MMFR4, ASID2, 8, 4) + FIELD(ID_AA64DFR0, DEBUGVER, 0, 4) FIELD(ID_AA64DFR0, TRACEVER, 4, 4) FIELD(ID_AA64DFR0, PMUVER, 8, 4) @@ -1369,6 +1371,11 @@ static inline bool isar_feature_aa64_aie(const ARMISARegisters *id) return FIELD_EX64_IDREG(id, ID_AA64MMFR3, AIE) != 0; } +static inline bool isar_feature_aa64_asid2(const ARMISARegisters *id) +{ + return FIELD_EX64_IDREG(id, ID_AA64MMFR4, ASID2) != 0; +} + static inline bool isar_feature_aa64_mec(const ARMISARegisters *id) { return FIELD_EX64_IDREG(id, ID_AA64MMFR3, MEC) != 0; diff --git a/target/arm/helper.c b/target/arm/helper.c index c20334fa65..ecb31b058c 100644 --- a/target/arm/helper.c +++ b/target/arm/helper.c @@ -6095,6 +6095,7 @@ static void tcr2_el1_write(CPUARMState *env, const ARMCPRegInfo *ri, { ARMCPU *cpu = env_archcpu(env); uint64_t valid_mask = 0; + bool require_flush = false; if (cpu_isar_feature(aa64_s1pie, cpu)) { valid_mask |= TCR2_PIE; @@ -6102,8 +6103,16 @@ static void tcr2_el1_write(CPUARMState *env, const ARMCPRegInfo *ri, if (cpu_isar_feature(aa64_aie, cpu)) { valid_mask |= TCR2_AIE; } + if (cpu_isar_feature(aa64_asid2, cpu)) { + valid_mask |= TCR2_FNG1 | TCR2_FNG0 | TCR2_A2; + require_flush = true; + } value &= valid_mask; raw_write(env, ri, value); + + if (require_flush) { + tlb_flush(CPU(cpu)); + } } static void tcr2_el2_write(CPUARMState *env, const ARMCPRegInfo *ri, @@ -6111,6 +6120,7 @@ static void tcr2_el2_write(CPUARMState *env, const ARMCPRegInfo *ri, { ARMCPU *cpu = env_archcpu(env); uint64_t valid_mask = 0; + bool require_flush = false; if (cpu_isar_feature(aa64_s1pie, cpu)) { valid_mask |= TCR2_PIE; @@ -6121,8 +6131,16 @@ static void tcr2_el2_write(CPUARMState *env, const ARMCPRegInfo *ri, if (cpu_isar_feature(aa64_mec, cpu)) { valid_mask |= TCR2_AMEC0 | TCR2_AMEC1; } + if (cpu_isar_feature(aa64_asid2, cpu)) { + valid_mask |= TCR2_FNG1 | TCR2_FNG0 | TCR2_A2; + require_flush = true; + } value &= valid_mask; raw_write(env, ri, value); + + if (require_flush) { + tlb_flush(CPU(cpu)); + } } static const ARMCPRegInfo tcr2_reginfo[] = { -- 2.43.0
