* should not trap to EL2 when HCR_EL2.NV is set.
*/
ARM_CP_NV_NO_TRAP = 1 << 22,
+ /*
+ * Flag: Access check for this sysreg is constrained by the
+ * ARM pseudocode function CheckFPMREnabled().
+ */
+ ARM_CP_FPMR = 1 << 23,
};
/*
return FIELD_EX64_IDREG(id, ID_AA64PFR2, GCIE) != 0;
}
+static inline bool isar_feature_aa64_fpmr(const ARMISARegisters *id)
+{
+ return FIELD_EX64_IDREG(id, ID_AA64PFR2, FPMR) != 0;
+}
+
static inline bool isar_feature_aa64_tgran4_lpa2(const ARMISARegisters *id)
{
return FIELD_SEX64_IDREG(id, ID_AA64MMFR0, TGRAN4) >= 1;
*/
uint64_t fpsr;
uint64_t fpcr;
+ uint64_t fpmr;
uint32_t xregs[16];
.type = ARM_CP_CONST, .resetvalue = 0 },
};
+static const ARMCPRegInfo fpmr_reginfo[] = {
+ { .name = "FPMR", .state = ARM_CP_STATE_AA64,
+ .opc0 = 3, .opc1 = 3, .crn = 4, .crm = 4, .opc2 = 2,
+ .access = PL0_RW, .type = ARM_CP_FPU | ARM_CP_FPMR,
+ .fieldoffset = offsetof(CPUARMState, vfp.fpmr),
+ }
+};
+
void register_cp_regs_for_features(ARMCPU *cpu)
{
/* Register all the coprocessor registers based on feature bits */
define_arm_cp_regs(cpu, mec_mte_reginfo);
}
}
-
if (cpu_isar_feature(aa64_aie, cpu)) {
define_arm_cp_regs(cpu, aie_reginfo);
}
+ if (cpu_isar_feature(aa64_fpmr, cpu)) {
+ define_arm_cp_regs(cpu, fpmr_reginfo);
+ }
if (cpu_isar_feature(any_predinv, cpu)) {
define_arm_cp_regs(cpu, predinv_reginfo);
FIELD(CNTHCTL, CNTVMASK, 18, 1)
FIELD(CNTHCTL, CNTPMASK, 19, 1)
+FIELD(FPMR, F8S1, 0, 3)
+FIELD(FPMR, F8S2, 3, 3)
+FIELD(FPMR, F8D, 6, 3)
+FIELD(FPMR, OSM, 14, 1)
+FIELD(FPMR, OSC, 15, 1)
+FIELD(FPMR, LSCALE, 16, 7)
+FIELD(FPMR, NSCALE, 24, 8)
+FIELD(FPMR, NSCALE_F16, 24, 5)
+FIELD(FPMR, LSCALE2, 32, 6)
+
/* We use a few fake FSR values for internal purposes in M profile.
* M profile cores don't have A/R format FSRs, but currently our
* get_phys_addr() code assumes A/R profile and reports failures via
},
};
+static bool fpmr_needed(void *opaque)
+{
+ ARMCPU *cpu = opaque;
+
+ return arm_feature(&cpu->env, ARM_FEATURE_AARCH64)
+ && cpu_isar_feature(aa64_fpmr, cpu);
+}
+
+static const VMStateDescription vmstate_fpmr = {
+ .name = "cpu/fpmr",
+ .version_id = 1,
+ .minimum_version_id = 1,
+ .needed = fpmr_needed,
+ .fields = (const VMStateField[]) {
+ VMSTATE_UINT64(env.vfp.fpmr, ARMCPU),
+ VMSTATE_END_OF_LIST()
+ },
+};
+
static int cpu_pre_save(void *opaque)
{
ARMCPU *cpu = opaque;
&vmstate_syndrome64,
&vmstate_pstate64,
&vmstate_event,
+ &vmstate_fpmr,
NULL
}
};