diff options
Diffstat (limited to 'dev/interrupt/arm_gic/arm_gic.c')
-rw-r--r-- | dev/interrupt/arm_gic/arm_gic.c | 25 |
1 files changed, 13 insertions, 12 deletions
diff --git a/dev/interrupt/arm_gic/arm_gic.c b/dev/interrupt/arm_gic/arm_gic.c index ba29ad17..c38decff 100644 --- a/dev/interrupt/arm_gic/arm_gic.c +++ b/dev/interrupt/arm_gic/arm_gic.c @@ -388,15 +388,20 @@ static status_t arm_gic_set_priority_locked(u_int irq, uint8_t priority) status_t arm_gic_sgi(u_int irq, u_int flags, u_int cpu_mask) { + if (irq >= 16) { + return ERR_INVALID_ARGS; + } + #if GIC_VERSION > 2 - /* This assumes that all CPUs are in the same cluster */ - u_int val = ((irq & 0xf) << 24) | (cpu_mask & 0xffff); + for (size_t cpu = 0; cpu < SMP_MAX_CPUS; cpu++) { + if (!((cpu_mask >> cpu) & 1)) { + continue; + } - if (irq >= (1U << 16)) - return ERR_INVALID_ARGS; + uint64_t val = arm_gicv3_sgir_val(irq, cpu); - LTRACEF("GICC_PRIMARY_SGIR: %x\n", val); - GICCREG_WRITE(0, GICC_PRIMARY_SGIR, val); + GICCREG_WRITE(0, GICC_PRIMARY_SGIR, val); + } #else /* else GIC_VERSION > 2 */ @@ -406,9 +411,6 @@ status_t arm_gic_sgi(u_int irq, u_int flags, u_int cpu_mask) ((flags & ARM_GIC_SGI_FLAG_NS) ? (1U << 15) : 0) | (irq & 0xf); - if (irq >= 16) - return ERR_INVALID_ARGS; - LTRACEF("GICD_SGIR: %x\n", val); GICDREG_WRITE(0, GICD_SGIR, val); @@ -695,13 +697,12 @@ status_t sm_intc_fiq_enter(void) if (irq >= 1020) { #if ARM_GIC_USE_DOORBELL_NS_IRQ uint cpu = arch_curr_cpu_num(); - uint cpu_mask = 1U << cpu; - u_int val = (ARM_GIC_DOORBELL_IRQ << 24) | (cpu_mask & 0xffff); + uint64_t val = arm_gicv3_sgir_val(ARM_GIC_DOORBELL_IRQ, cpu); GICCREG_WRITE(0, icc_igrpen1_el1, 0); /* Disable secure Group 1 */ if (doorbell_enabled) { - LTRACEF("GICD_SGIR: %x\n", val); + LTRACEF("GICD_SGIR: %llx\n", val); GICCREG_WRITE(0, icc_asgi1r_el1, val); } #else |