[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PULL 07/39] target-arm: Update interrupt handling to use t
From: |
Peter Maydell |
Subject: |
[Qemu-devel] [PULL 07/39] target-arm: Update interrupt handling to use target EL |
Date: |
Fri, 29 May 2015 14:10:13 +0100 |
From: Greg Bellows <address@hidden>
Updated the interrupt handling to utilize and report through the target EL
exception field. This includes consolidating and cleaning up code where
needed. Target EL is now calculated once in arm_cpu_exec_interrupt() and
do_interrupt was updated to use the target_el exception field. The
necessary code from arm_excp_target_el() was merged in where needed and the
function removed.
Signed-off-by: Greg Bellows <address@hidden>
Acked-by: Edgar E. Iglesias <address@hidden>
Message-id: address@hidden
Signed-off-by: Peter Maydell <address@hidden>
---
target-arm/cpu.c | 61 +++++++++++++++++++++++++++++++++----------------
target-arm/cpu.h | 7 +++---
target-arm/helper-a64.c | 2 +-
target-arm/helper.c | 41 ++++-----------------------------
4 files changed, 50 insertions(+), 61 deletions(-)
diff --git a/target-arm/cpu.c b/target-arm/cpu.c
index 798c689..4a888ab 100644
--- a/target-arm/cpu.c
+++ b/target-arm/cpu.c
@@ -206,31 +206,52 @@ static void arm_cpu_reset(CPUState *s)
bool arm_cpu_exec_interrupt(CPUState *cs, int interrupt_request)
{
CPUClass *cc = CPU_GET_CLASS(cs);
+ CPUARMState *env = cs->env_ptr;
+ uint32_t cur_el = arm_current_el(env);
+ bool secure = arm_is_secure(env);
+ uint32_t target_el;
+ uint32_t excp_idx;
bool ret = false;
- if (interrupt_request & CPU_INTERRUPT_FIQ
- && arm_excp_unmasked(cs, EXCP_FIQ)) {
- cs->exception_index = EXCP_FIQ;
- cc->do_interrupt(cs);
- ret = true;
+ if (interrupt_request & CPU_INTERRUPT_FIQ) {
+ excp_idx = EXCP_FIQ;
+ 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;
+ }
}
- if (interrupt_request & CPU_INTERRUPT_HARD
- && arm_excp_unmasked(cs, EXCP_IRQ)) {
- cs->exception_index = EXCP_IRQ;
- cc->do_interrupt(cs);
- ret = true;
+ if (interrupt_request & CPU_INTERRUPT_HARD) {
+ excp_idx = EXCP_IRQ;
+ 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;
+ }
}
- if (interrupt_request & CPU_INTERRUPT_VIRQ
- && arm_excp_unmasked(cs, EXCP_VIRQ)) {
- cs->exception_index = EXCP_VIRQ;
- cc->do_interrupt(cs);
- ret = true;
+ if (interrupt_request & CPU_INTERRUPT_VIRQ) {
+ excp_idx = EXCP_VIRQ;
+ target_el = 1;
+ 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;
+ }
}
- if (interrupt_request & CPU_INTERRUPT_VFIQ
- && arm_excp_unmasked(cs, EXCP_VFIQ)) {
- cs->exception_index = EXCP_VFIQ;
- cc->do_interrupt(cs);
- ret = true;
+ if (interrupt_request & CPU_INTERRUPT_VFIQ) {
+ excp_idx = EXCP_VFIQ;
+ target_el = 1;
+ 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 6845666..9119a94 100644
--- a/target-arm/cpu.h
+++ b/target-arm/cpu.h
@@ -1000,7 +1000,8 @@ static inline bool access_secure_reg(CPUARMState *env)
(_val))
void arm_cpu_list(FILE *f, fprintf_function cpu_fprintf);
-unsigned int arm_excp_target_el(CPUState *cs, unsigned int excp_idx);
+uint32_t arm_phys_excp_target_el(CPUState *cs, uint32_t excp_idx,
+ uint32_t cur_el, bool secure);
/* Interface between CPU and Interrupt controller. */
void armv7m_nvic_set_pending(void *opaque, int irq);
@@ -1482,11 +1483,11 @@ bool write_cpustate_to_list(ARMCPU *cpu);
# define TARGET_VIRT_ADDR_SPACE_BITS 32
#endif
-static inline bool arm_excp_unmasked(CPUState *cs, unsigned int excp_idx)
+static inline bool arm_excp_unmasked(CPUState *cs, unsigned int excp_idx,
+ unsigned int target_el)
{
CPUARMState *env = cs->env_ptr;
unsigned int cur_el = arm_current_el(env);
- unsigned int target_el = arm_excp_target_el(cs, excp_idx);
bool secure = arm_is_secure(env);
uint32_t scr;
uint32_t hcr;
diff --git a/target-arm/helper-a64.c b/target-arm/helper-a64.c
index 861f6fa..e30af06 100644
--- a/target-arm/helper-a64.c
+++ b/target-arm/helper-a64.c
@@ -463,7 +463,7 @@ void aarch64_cpu_do_interrupt(CPUState *cs)
{
ARMCPU *cpu = ARM_CPU(cs);
CPUARMState *env = &cpu->env;
- unsigned int new_el = arm_excp_target_el(cs, cs->exception_index);
+ unsigned int new_el = env->exception.target_el;
target_ulong addr = env->cp15.vbar_el[new_el];
unsigned int new_mode = aarch64_pstate_mode(new_el, true);
diff --git a/target-arm/helper.c b/target-arm/helper.c
index a9e85b9..abfd70e 100644
--- a/target-arm/helper.c
+++ b/target-arm/helper.c
@@ -4087,7 +4087,8 @@ uint32_t HELPER(get_r13_banked)(CPUARMState *env,
uint32_t mode)
return 0;
}
-unsigned int arm_excp_target_el(CPUState *cs, unsigned int excp_idx)
+uint32_t arm_phys_excp_target_el(CPUState *cs, uint32_t excp_idx,
+ uint32_t cur_el, bool secure)
{
return 1;
}
@@ -4211,8 +4212,8 @@ const int8_t target_el_table[2][2][2][2][2][4] = {
/*
* Determine the target EL for physical exceptions
*/
-static inline uint32_t arm_phys_excp_target_el(CPUState *cs, uint32_t excp_idx,
- uint32_t cur_el, bool secure)
+uint32_t arm_phys_excp_target_el(CPUState *cs, uint32_t excp_idx,
+ uint32_t cur_el, bool secure)
{
CPUARMState *env = cs->env_ptr;
int rw = ((env->cp15.scr_el3 & SCR_RW) == SCR_RW);
@@ -4247,40 +4248,6 @@ static inline uint32_t arm_phys_excp_target_el(CPUState
*cs, uint32_t excp_idx,
return target_el;
}
-/*
- * Determine the target EL for a given exception type.
- */
-unsigned int arm_excp_target_el(CPUState *cs, unsigned int excp_idx)
-{
- ARMCPU *cpu = ARM_CPU(cs);
- CPUARMState *env = &cpu->env;
- unsigned int cur_el = arm_current_el(env);
- unsigned int target_el;
- bool secure = arm_is_secure(env);
-
- switch (excp_idx) {
- case EXCP_HVC:
- case EXCP_HYP_TRAP:
- target_el = 2;
- break;
- case EXCP_SMC:
- target_el = 3;
- break;
- case EXCP_FIQ:
- case EXCP_IRQ:
- target_el = arm_phys_excp_target_el(cs, excp_idx, cur_el, secure);
- break;
- case EXCP_VIRQ:
- case EXCP_VFIQ:
- target_el = 1;
- break;
- default:
- target_el = MAX(cur_el, 1);
- break;
- }
- return target_el;
-}
-
static void v7m_push(CPUARMState *env, uint32_t val)
{
CPUState *cs = CPU(arm_env_get_cpu(env));
--
1.9.1
- [Qemu-devel] [PULL 18/39] hw/arm/virt-acpi-build: Basic framework for building ACPI tables on ARM, (continued)
- [Qemu-devel] [PULL 18/39] hw/arm/virt-acpi-build: Basic framework for building ACPI tables on ARM, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 05/39] target-arm: Set exception target EL in tlb_fill, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 09/39] target-arm: Add AArch64 CPTR registers, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 19/39] hw/acpi/aml-build: Add aml_memory32_fixed() term, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 08/39] target-arm: Allow cp access functions to indicate traps to EL2 or EL3, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 03/39] target-arm: Set correct syndrome for faults on MSR DAIF*, imm, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 10/39] target-arm: Make singlestate TB flags common between AArch32/64, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 02/39] target-arm: Extend helpers to route exceptions, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 11/39] target-arm: Extend FP checks to use an EL, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 24/39] hw/arm/virt-acpi-build: Generate GTDT table, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 07/39] target-arm: Update interrupt handling to use target EL,
Peter Maydell <=
- [Qemu-devel] [PULL 16/39] hw/arm/virt: Move common definitions to virt.h, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 04/39] target-arm: Move setting of exception info into tlb_fill, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 12/39] target-arm: Move TB flags down to fill gap, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 15/39] hw/acpi/aml-build: Make enum values to be upper case to match coding style, Peter Maydell, 2015/05/29
- [Qemu-devel] [PULL 06/39] target-arm: Make raise_exception() take syndrome and target EL, Peter Maydell, 2015/05/29
- Re: [Qemu-devel] [PULL 00/39] target-arm queue, Peter Maydell, 2015/05/29