Module Name: src Committed By: jmcneill Date: Sun Sep 26 13:38:50 UTC 2021
Modified Files: src/sys/arch/arm/cortex: gic.c gicv3.c src/sys/arch/arm/pic: pic.c picvar.h Log Message: If an SGI or PPI is established after interrupts are enabled, make sure we unblock the source on _all_ CPUs and not just the CPU that is establishing the interrupt. To generate a diff of this commit: cvs rdiff -u -r1.49 -r1.50 src/sys/arch/arm/cortex/gic.c cvs rdiff -u -r1.47 -r1.48 src/sys/arch/arm/cortex/gicv3.c cvs rdiff -u -r1.71 -r1.72 src/sys/arch/arm/pic/pic.c cvs rdiff -u -r1.36 -r1.37 src/sys/arch/arm/pic/picvar.h Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/arch/arm/cortex/gic.c diff -u src/sys/arch/arm/cortex/gic.c:1.49 src/sys/arch/arm/cortex/gic.c:1.50 --- src/sys/arch/arm/cortex/gic.c:1.49 Tue Aug 10 17:12:31 2021 +++ src/sys/arch/arm/cortex/gic.c Sun Sep 26 13:38:50 2021 @@ -1,4 +1,4 @@ -/* $NetBSD: gic.c,v 1.49 2021/08/10 17:12:31 jmcneill Exp $ */ +/* $NetBSD: gic.c,v 1.50 2021/09/26 13:38:50 jmcneill Exp $ */ /*- * Copyright (c) 2012 The NetBSD Foundation, Inc. * All rights reserved. @@ -35,7 +35,7 @@ #define _INTR_PRIVATE #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: gic.c,v 1.49 2021/08/10 17:12:31 jmcneill Exp $"); +__KERNEL_RCSID(0, "$NetBSD: gic.c,v 1.50 2021/09/26 13:38:50 jmcneill Exp $"); #include <sys/param.h> #include <sys/bus.h> @@ -462,6 +462,7 @@ armgic_establish_irq(struct pic_softc *p * default. */ is->is_mpsafe = true; + is->is_percpu = true; #endif } Index: src/sys/arch/arm/cortex/gicv3.c diff -u src/sys/arch/arm/cortex/gicv3.c:1.47 src/sys/arch/arm/cortex/gicv3.c:1.48 --- src/sys/arch/arm/cortex/gicv3.c:1.47 Sat Sep 11 01:49:11 2021 +++ src/sys/arch/arm/cortex/gicv3.c Sun Sep 26 13:38:50 2021 @@ -1,4 +1,4 @@ -/* $NetBSD: gicv3.c,v 1.47 2021/09/11 01:49:11 jmcneill Exp $ */ +/* $NetBSD: gicv3.c,v 1.48 2021/09/26 13:38:50 jmcneill Exp $ */ /*- * Copyright (c) 2018 Jared McNeill <jmcne...@invisible.ca> @@ -32,7 +32,7 @@ #define _INTR_PRIVATE #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: gicv3.c,v 1.47 2021/09/11 01:49:11 jmcneill Exp $"); +__KERNEL_RCSID(0, "$NetBSD: gicv3.c,v 1.48 2021/09/26 13:38:50 jmcneill Exp $"); #include <sys/param.h> #include <sys/kernel.h> @@ -185,8 +185,9 @@ gicv3_establish_irq(struct pic_softc *pi const u_int icfg_shift = (is->is_irq & 0xf) * 2; if (group == 0) { - /* SGIs and PPIs are always MP-safe */ + /* SGIs and PPIs are per-CPU and always MP-safe */ is->is_mpsafe = true; + is->is_percpu = true; /* Update interrupt configuration and priority on all redistributors */ for (n = 0; n < sc->sc_bsh_r_count; n++) { Index: src/sys/arch/arm/pic/pic.c diff -u src/sys/arch/arm/pic/pic.c:1.71 src/sys/arch/arm/pic/pic.c:1.72 --- src/sys/arch/arm/pic/pic.c:1.71 Sun Aug 8 19:28:08 2021 +++ src/sys/arch/arm/pic/pic.c Sun Sep 26 13:38:49 2021 @@ -1,4 +1,4 @@ -/* $NetBSD: pic.c,v 1.71 2021/08/08 19:28:08 skrll Exp $ */ +/* $NetBSD: pic.c,v 1.72 2021/09/26 13:38:49 jmcneill Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. * All rights reserved. @@ -33,7 +33,7 @@ #include "opt_multiprocessor.h" #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: pic.c,v 1.71 2021/08/08 19:28:08 skrll Exp $"); +__KERNEL_RCSID(0, "$NetBSD: pic.c,v 1.72 2021/09/26 13:38:49 jmcneill Exp $"); #include <sys/param.h> #include <sys/atomic.h> @@ -704,6 +704,16 @@ pic_percpu_evcnt_attach(void *v0, void * pcpu->pcpu_name, is->is_source); } +static void +pic_unblock_percpu(void *arg1, void *arg2) +{ + struct pic_softc *pic = arg1; + struct intrsource *is = arg2; + + (*pic->pic_ops->pic_unblock_irqs)(pic, is->is_irq & ~0x1f, + __BIT(is->is_irq & 0x1f)); +} + void * pic_establish_intr(struct pic_softc *pic, int irq, int ipl, int type, int (*func)(void *), void *arg, const char *xname) @@ -780,8 +790,13 @@ pic_establish_intr(struct pic_softc *pic (*pic->pic_ops->pic_establish_irq)(pic, is); unblock: - (*pic->pic_ops->pic_unblock_irqs)(pic, is->is_irq & ~0x1f, - __BIT(is->is_irq & 0x1f)); + if (cold || !is->is_mpsafe) { + (*pic->pic_ops->pic_unblock_irqs)(pic, is->is_irq & ~0x1f, + __BIT(is->is_irq & 0x1f)); + } else { + uint64_t xc = xc_broadcast(0, pic_unblock_percpu, pic, is); + xc_wait(xc); + } if (xname) { if (is->is_xname == NULL) Index: src/sys/arch/arm/pic/picvar.h diff -u src/sys/arch/arm/pic/picvar.h:1.36 src/sys/arch/arm/pic/picvar.h:1.37 --- src/sys/arch/arm/pic/picvar.h:1.36 Mon Sep 20 21:05:15 2021 +++ src/sys/arch/arm/pic/picvar.h Sun Sep 26 13:38:49 2021 @@ -1,4 +1,4 @@ -/* $NetBSD: picvar.h,v 1.36 2021/09/20 21:05:15 jmcneill Exp $ */ +/* $NetBSD: picvar.h,v 1.37 2021/09/26 13:38:49 jmcneill Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. * All rights reserved. @@ -128,6 +128,7 @@ struct intrsource { char is_source[16]; char *is_xname; uint32_t is_mask_count; + bool is_percpu; }; struct pic_percpu {