diff options
author | Matthew Maurer <mmaurer@google.com> | 2018-12-28 15:52:10 -0800 |
---|---|---|
committer | Matthew Maurer <mmaurer@google.com> | 2019-01-02 11:43:31 -0800 |
commit | f060068503259b661be8bd8c803291ff6412d2d6 (patch) | |
tree | b1c268c593ffe58284c06902bf63460b6ab9ce05 | |
parent | 7ed6ed988d60efda5dbf308ca539844e8eb184e1 (diff) | |
download | qemu-f060068503259b661be8bd8c803291ff6412d2d6.tar.gz |
Fix GIC model for aliased interrupts
Secure access to GICC_AEOIR was reading GICC_CTLR.EOImodeNS instead of
GICC_CTLR.EOImodeS.
The spec says that EOImodeS should be used for this.
Bug: 122116622
Change-Id: Ie7ac8b5980801c23aab825293687e86157327d9e
-rw-r--r-- | hw/intc/arm_gic.c | 11 |
1 files changed, 6 insertions, 5 deletions
diff --git a/hw/intc/arm_gic.c b/hw/intc/arm_gic.c index e57cc26279..4a5fc20b08 100644 --- a/hw/intc/arm_gic.c +++ b/hw/intc/arm_gic.c @@ -830,7 +830,8 @@ static void gic_deactivate_irq(GICState *s, int cpu, int irq, MemTxAttrs attrs) gic_clear_active(s, irq, cpu); } -static void gic_complete_irq(GICState *s, int cpu, int irq, MemTxAttrs attrs) +static void gic_complete_irq(GICState *s, int cpu, int irq, MemTxAttrs attrs, + bool ns_irq) { int cm = 1 << cpu; int group; @@ -898,7 +899,7 @@ static void gic_complete_irq(GICState *s, int cpu, int irq, MemTxAttrs attrs) group = gic_has_groups(s) && gic_test_group(s, irq, cpu); - if (gic_cpu_ns_access(s, cpu, attrs) && !group) { + if (ns_irq && !group) { DPRINTF("Non-secure EOI for Group0 interrupt %d ignored\n", irq); return; } @@ -1693,14 +1694,14 @@ static MemTxResult gic_cpu_write(GICState *s, int cpu, int offset, } break; case 0x10: /* End Of Interrupt */ - gic_complete_irq(s, cpu, value & 0x3ff, attrs); + gic_complete_irq(s, cpu, value & 0x3ff, attrs, + gic_cpu_ns_access(s, cpu, attrs)); return MEMTX_OK; case 0x24: /* Aliased End Of Interrupt */ if (!gic_has_groups(s) || (s->security_extn && !attrs.secure)) { /* unimplemented, or NS access: RAZ/WI */ } else { - attrs.secure = false; - gic_complete_irq(s, cpu, value & 0x3ff, attrs); + gic_complete_irq(s, cpu, value & 0x3ff, attrs, true); } return MEMTX_OK; case 0x1c: /* Aliased Binary Point */ |