target/arm: Correctly implement ACTLR2, HACTLR2

The ACTLR2 and HACTLR2 AArch32 system registers didn't exist in ARMv7
or the original ARMv8.  They were later added as optional registers,
whose presence is signaled by the ID_MMFR4.AC2 field.  From ARMv8.2
they are mandatory (ie ID_MMFR4.AC2 must be non-zero).

We implemented HACTLR2 in commit 0e0456ab88, but we
incorrectly made it exist for all v8 CPUs, and we didn't implement
ACTLR2 at all.

Sort this out by implementing both registers only when they are
supposed to exist, and setting the ID_MMFR4 bit for -cpu max.

Note that this removes HACTLR2 from our Cortex-A53, -A47 and -A72
CPU models; this is correct, because those CPUs do not implement
this register.

Fixes: 0e0456ab88
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Message-id: 20200214175116.9164-22-peter.maydell@linaro.org
This commit is contained in:
Peter Maydell 2020-02-14 17:51:16 +00:00
parent b3a816f6ce
commit f6287c24c6
4 changed files with 33 additions and 9 deletions

View File

@ -2718,6 +2718,7 @@ static void arm_max_initfn(Object *obj)
t = cpu->isar.id_mmfr4; t = cpu->isar.id_mmfr4;
t = FIELD_DP32(t, ID_MMFR4, HPDS, 1); /* AA32HPD */ t = FIELD_DP32(t, ID_MMFR4, HPDS, 1); /* AA32HPD */
t = FIELD_DP32(t, ID_MMFR4, AC2, 1); /* ACTLR2, HACTLR2 */
cpu->isar.id_mmfr4 = t; cpu->isar.id_mmfr4 = t;
} }
#endif #endif

View File

@ -3531,6 +3531,11 @@ static inline bool isar_feature_aa32_hpd(const ARMISARegisters *id)
return FIELD_EX32(id->id_mmfr4, ID_MMFR4, HPDS) != 0; return FIELD_EX32(id->id_mmfr4, ID_MMFR4, HPDS) != 0;
} }
static inline bool isar_feature_aa32_ac2(const ARMISARegisters *id)
{
return FIELD_EX32(id->id_mmfr4, ID_MMFR4, AC2) != 0;
}
/* /*
* 64-bit feature tests via id registers. * 64-bit feature tests via id registers.
*/ */

View File

@ -703,6 +703,10 @@ static void aarch64_max_initfn(Object *obj)
u = FIELD_DP32(u, ID_MMFR3, PAN, 2); /* ATS1E1 */ u = FIELD_DP32(u, ID_MMFR3, PAN, 2); /* ATS1E1 */
cpu->isar.id_mmfr3 = u; cpu->isar.id_mmfr3 = u;
u = cpu->isar.id_mmfr4;
u = FIELD_DP32(u, ID_MMFR4, AC2, 1); /* ACTLR2, HACTLR2 */
cpu->isar.id_mmfr4 = u;
u = cpu->isar.id_aa64dfr0; u = cpu->isar.id_aa64dfr0;
u = FIELD_DP64(u, ID_AA64DFR0, PMUVER, 5); /* v8.4-PMU */ u = FIELD_DP64(u, ID_AA64DFR0, PMUVER, 5); /* v8.4-PMU */
cpu->isar.id_aa64dfr0 = u; cpu->isar.id_aa64dfr0 = u;

View File

@ -6862,6 +6862,27 @@ static const ARMCPRegInfo ats1cp_reginfo[] = {
}; };
#endif #endif
/*
* ACTLR2 and HACTLR2 map to ACTLR_EL1[63:32] and
* ACTLR_EL2[63:32]. They exist only if the ID_MMFR4.AC2 field
* is non-zero, which is never for ARMv7, optionally in ARMv8
* and mandatorily for ARMv8.2 and up.
* ACTLR2 is banked for S and NS if EL3 is AArch32. Since QEMU's
* implementation is RAZ/WI we can ignore this detail, as we
* do for ACTLR.
*/
static const ARMCPRegInfo actlr2_hactlr2_reginfo[] = {
{ .name = "ACTLR2", .state = ARM_CP_STATE_AA32,
.cp = 15, .opc1 = 0, .crn = 1, .crm = 0, .opc2 = 3,
.access = PL1_RW, .type = ARM_CP_CONST,
.resetvalue = 0 },
{ .name = "HACTLR2", .state = ARM_CP_STATE_AA32,
.cp = 15, .opc1 = 4, .crn = 1, .crm = 0, .opc2 = 3,
.access = PL2_RW, .type = ARM_CP_CONST,
.resetvalue = 0 },
REGINFO_SENTINEL
};
void register_cp_regs_for_features(ARMCPU *cpu) void register_cp_regs_for_features(ARMCPU *cpu)
{ {
/* Register all the coprocessor registers based on feature bits */ /* Register all the coprocessor registers based on feature bits */
@ -7623,15 +7644,8 @@ void register_cp_regs_for_features(ARMCPU *cpu)
REGINFO_SENTINEL REGINFO_SENTINEL
}; };
define_arm_cp_regs(cpu, auxcr_reginfo); define_arm_cp_regs(cpu, auxcr_reginfo);
if (arm_feature(env, ARM_FEATURE_V8)) { if (cpu_isar_feature(aa32_ac2, cpu)) {
/* HACTLR2 maps to ACTLR_EL2[63:32] and is not in ARMv7 */ define_arm_cp_regs(cpu, actlr2_hactlr2_reginfo);
ARMCPRegInfo hactlr2_reginfo = {
.name = "HACTLR2", .state = ARM_CP_STATE_AA32,
.cp = 15, .opc1 = 4, .crn = 1, .crm = 0, .opc2 = 3,
.access = PL2_RW, .type = ARM_CP_CONST,
.resetvalue = 0
};
define_one_arm_cp_reg(cpu, &hactlr2_reginfo);
} }
} }