diff options
Diffstat (limited to 'target/arm/ptw.c')
-rw-r--r-- | target/arm/ptw.c | 26 |
1 files changed, 20 insertions, 6 deletions
diff --git a/target/arm/ptw.c b/target/arm/ptw.c index 4d97a24808..da478104f0 100644 --- a/target/arm/ptw.c +++ b/target/arm/ptw.c @@ -36,15 +36,29 @@ static const uint8_t pamax_map[] = { /* The cpu-specific constant value of PAMax; also used by hw/arm/virt. */ unsigned int arm_pamax(ARMCPU *cpu) { - unsigned int parange = - FIELD_EX64(cpu->isar.id_aa64mmfr0, ID_AA64MMFR0, PARANGE); + if (arm_feature(&cpu->env, ARM_FEATURE_AARCH64)) { + unsigned int parange = + FIELD_EX64(cpu->isar.id_aa64mmfr0, ID_AA64MMFR0, PARANGE); + + /* + * id_aa64mmfr0 is a read-only register so values outside of the + * supported mappings can be considered an implementation error. + */ + assert(parange < ARRAY_SIZE(pamax_map)); + return pamax_map[parange]; + } /* - * id_aa64mmfr0 is a read-only register so values outside of the - * supported mappings can be considered an implementation error. + * In machvirt_init, we call arm_pamax on a cpu that is not fully + * initialized, so we can't rely on the propagation done in realize. */ - assert(parange < ARRAY_SIZE(pamax_map)); - return pamax_map[parange]; + if (arm_feature(&cpu->env, ARM_FEATURE_LPAE) || + arm_feature(&cpu->env, ARM_FEATURE_V7VE)) { + /* v7 with LPAE */ + return 40; + } + /* Anything else */ + return 32; } /* |