mirror of
https://github.com/Motorhead1991/qemu.git
synced 2025-08-06 09:13:55 -06:00
target/arm: Implement FEAT_IDST
The Armv8.4 feature FEAT_IDST specifies that exceptions generated by read accesses to the feature ID space should report a syndrome code of 0x18 (EC_SYSTEMREGISTERTRAP) rather than 0x00 (EC_UNCATEGORIZED). The feature ID space is defined to be: op0 == 3, op1 == {0,1,3}, CRn == 0, CRm == {0-7}, op2 == {0-7} In our implementation we might return the EC_UNCATEGORIZED syndrome value for a system register access in four cases: * no reginfo struct in the hashtable * cp_access_ok() fails (ie ri->access doesn't permit the access) * ri->accessfn returns CP_ACCESS_TRAP_UNCATEGORIZED at runtime * ri->type includes ARM_CP_RAISES_EXC, and the readfn raises an UNDEF exception at runtime We have very few regdefs that set ARM_CP_RAISES_EXC, and none of them are in the feature ID space. (In the unlikely event that any are added in future they would need to take care of setting the correct syndrome themselves.) This patch deals with the other three cases, and enables FEAT_IDST for AArch64 -cpu max. Signed-off-by: Peter Maydell <peter.maydell@linaro.org> Reviewed-by: Richard Henderson <richard.henderson@linaro.org> Message-id: 20220509155457.3560724-1-peter.maydell@linaro.org
This commit is contained in:
parent
e04bf5a793
commit
75662f36e3
6 changed files with 66 additions and 2 deletions
|
@ -1795,6 +1795,30 @@ static void gen_set_nzcv(TCGv_i64 tcg_rt)
|
|||
tcg_temp_free_i32(nzcv);
|
||||
}
|
||||
|
||||
static void gen_sysreg_undef(DisasContext *s, bool isread,
|
||||
uint8_t op0, uint8_t op1, uint8_t op2,
|
||||
uint8_t crn, uint8_t crm, uint8_t rt)
|
||||
{
|
||||
/*
|
||||
* Generate code to emit an UNDEF with correct syndrome
|
||||
* information for a failed system register access.
|
||||
* This is EC_UNCATEGORIZED (ie a standard UNDEF) in most cases,
|
||||
* but if FEAT_IDST is implemented then read accesses to registers
|
||||
* in the feature ID space are reported with the EC_SYSTEMREGISTERTRAP
|
||||
* syndrome.
|
||||
*/
|
||||
uint32_t syndrome;
|
||||
|
||||
if (isread && dc_isar_feature(aa64_ids, s) &&
|
||||
arm_cpreg_encoding_in_idspace(op0, op1, op2, crn, crm)) {
|
||||
syndrome = syn_aa64_sysregtrap(op0, op1, op2, crn, crm, rt, isread);
|
||||
} else {
|
||||
syndrome = syn_uncategorized();
|
||||
}
|
||||
gen_exception_insn(s, s->pc_curr, EXCP_UDEF, syndrome,
|
||||
default_exception_el(s));
|
||||
}
|
||||
|
||||
/* MRS - move from system register
|
||||
* MSR (register) - move to system register
|
||||
* SYS
|
||||
|
@ -1820,13 +1844,13 @@ static void handle_sys(DisasContext *s, uint32_t insn, bool isread,
|
|||
qemu_log_mask(LOG_UNIMP, "%s access to unsupported AArch64 "
|
||||
"system register op0:%d op1:%d crn:%d crm:%d op2:%d\n",
|
||||
isread ? "read" : "write", op0, op1, crn, crm, op2);
|
||||
unallocated_encoding(s);
|
||||
gen_sysreg_undef(s, isread, op0, op1, op2, crn, crm, rt);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Check access permissions */
|
||||
if (!cp_access_ok(s->current_el, ri, isread)) {
|
||||
unallocated_encoding(s);
|
||||
gen_sysreg_undef(s, isread, op0, op1, op2, crn, crm, rt);
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue