[PATCH] target/arm: Don't enforce alignment faults on Device memory for SCTLR.U == 0
Peter Maydell <[email protected]>
| Newsgroups | org.nongnu.qemu-arm,org.nongnu.qemu-devel |
|---|---|
| Message-ID | <[email protected]> |
We enforce that we take alignment faults for unaligned accesses when the MMU is disabled or the access is to Device memory. This is correct for the new-style unaligned accesses rules that were introduced in ARMv6 when SCTLR.U == 1 and then became the only option from ARMv7 (where SCTLR.U is RES1). However, it isn't right for the old ARMv4 and ARMv5 setup (and ARMv6 when SCTLR.U = 0). We don't emulate the v4/v5 alignment rules (which notably include "for unaligned LDR, do an aligned load and rotate"); but taking an alignment fault is definitely wrong and isn't what QEMU has traditionally done. Restrict this behaviour to when SCTLR.U is 1. (The other place we enable alignment checks on Device memory is in ptw.c, but we only set TLB_CHECK_ALIGNED for LPAE translations, which are guaranteed to be v7 or later.) Signed-off-by: Peter Maydell <[email protected]> --- target/arm/tcg/hflags.c | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/target/arm/tcg/hflags.c b/target/arm/tcg/hflags.c index 0716ca98fd..5047b7b697 100644 --- a/target/arm/tcg/hflags.c +++ b/target/arm/tcg/hflags.c @@ -47,6 +47,18 @@ static bool aprofile_require_alignment(CPUARMState *env, int el, uint64_t sctlr) return false; } + /* + * Pre-v6 had a completely different model for unaligned accesses, + * which doesn't include taking unaligned faults for Device memory. + * v6 has the new model only when SCTLR.U is set. Later architecture + * versions repurpose the SCTLR bit for something else, so we mustn't + * test it except for actual v6 CPUs. + */ + if (!arm_feature(env, ARM_FEATURE_V6) || + (!arm_feature(env, ARM_FEATURE_V7) && !(sctlr & SCTLR_U))) { + return false; + } + /* * With VMSA, if translation is disabled, then the default memory type * is Device(-nGnRnE) instead of Normal, which requires that alignment -- 2.43.0