This allows to inject SError interrupt, which will be used on receiving QMP/HMP "nmi" command in next patch.
Signed-off-by: Gavin Shan <gs...@redhat.com> --- target/arm/cpu.c | 11 +++++++++++ target/arm/cpu.h | 12 +++++++++--- target/arm/helper.c | 4 ++++ 3 files changed, 24 insertions(+), 3 deletions(-) diff --git a/target/arm/cpu.c b/target/arm/cpu.c index f86e71a260..24fd77437b 100644 --- a/target/arm/cpu.c +++ b/target/arm/cpu.c @@ -461,6 +461,17 @@ bool arm_cpu_exec_interrupt(CPUState *cs, int interrupt_request) } } + if (interrupt_request & CPU_INTERRUPT_SERROR) { + excp_idx = EXCP_SERROR; + target_el = arm_phys_excp_target_el(cs, excp_idx, cur_el, secure); + if (arm_excp_unmasked(cs, excp_idx, target_el)) { + cs->exception_index = excp_idx; + env->exception.target_el = target_el; + cc->do_interrupt(cs); + ret = true; + } + } + return ret; } diff --git a/target/arm/cpu.h b/target/arm/cpu.h index 608fcbd0b7..0bbc46ff6d 100644 --- a/target/arm/cpu.h +++ b/target/arm/cpu.h @@ -49,6 +49,7 @@ #define EXCP_LAZYFP 20 /* v7M fault during lazy FP stacking */ #define EXCP_LSERR 21 /* v8M LSERR SecureFault */ #define EXCP_UNALIGNED 22 /* v7M UNALIGNED UsageFault */ +#define EXCP_SERROR 23 /* SError Interrupt */ /* NB: add new EXCP_ defines to the array in arm_log_exception() too */ #define ARMV7M_EXCP_RESET 1 @@ -79,9 +80,10 @@ enum { }; /* ARM-specific interrupt pending bits. */ -#define CPU_INTERRUPT_FIQ CPU_INTERRUPT_TGT_EXT_1 -#define CPU_INTERRUPT_VIRQ CPU_INTERRUPT_TGT_EXT_2 -#define CPU_INTERRUPT_VFIQ CPU_INTERRUPT_TGT_EXT_3 +#define CPU_INTERRUPT_FIQ CPU_INTERRUPT_TGT_EXT_1 +#define CPU_INTERRUPT_VIRQ CPU_INTERRUPT_TGT_EXT_2 +#define CPU_INTERRUPT_VFIQ CPU_INTERRUPT_TGT_EXT_3 +#define CPU_INTERRUPT_SERROR CPU_INTERRUPT_TGT_EXT_4 /* The usual mapping for an AArch64 system register to its AArch32 * counterpart is for the 32 bit world to have access to the lower @@ -2731,6 +2733,10 @@ static inline bool arm_excp_unmasked(CPUState *cs, unsigned int excp_idx, pstate_unmasked = !(env->daif & PSTATE_I); break; + case EXCP_SERROR: + pstate_unmasked = !(env->daif & PSTATE_A); + break; + case EXCP_VFIQ: if (secure || !(hcr_el2 & HCR_FMO) || (hcr_el2 & HCR_TGE)) { /* VFIQs are only taken when hypervized and non-secure. */ diff --git a/target/arm/helper.c b/target/arm/helper.c index 19a57a17da..622a1d8796 100644 --- a/target/arm/helper.c +++ b/target/arm/helper.c @@ -7980,6 +7980,7 @@ void arm_log_exception(int idx) [EXCP_LAZYFP] = "v7M exception during lazy FP stacking", [EXCP_LSERR] = "v8M LSERR UsageFault", [EXCP_UNALIGNED] = "v7M UNALIGNED UsageFault", + [EXCP_SERROR] = "SError Interrupt", }; if (idx >= 0 && idx < ARRAY_SIZE(excnames)) { @@ -8566,6 +8567,9 @@ static void arm_cpu_do_interrupt_aarch64(CPUState *cs) case EXCP_VFIQ: addr += 0x100; break; + case EXCP_SERROR: + addr += 0x180; + break; default: cpu_abort(cs, "Unhandled exception 0x%x\n", cs->exception_index); } -- 2.23.0