summaryrefslogtreecommitdiffstats
path: root/sys/i386
diff options
context:
space:
mode:
authorbde <bde@FreeBSD.org>1999-07-10 14:54:19 +0000
committerbde <bde@FreeBSD.org>1999-07-10 14:54:19 +0000
commite6fc77dffd553aad0c4a874b9b44ead56c782867 (patch)
tree0448b00db9b4018c31bd9eba08d044d69fae01bc /sys/i386
parent0c64553e0f5d7cc0e11915bcb244010ed4b52de5 (diff)
downloadFreeBSD-src-e6fc77dffd553aad0c4a874b9b44ead56c782867.zip
FreeBSD-src-e6fc77dffd553aad0c4a874b9b44ead56c782867.tar.gz
Fixed a longstanding scheduling bug. ASTs and softclock interrupts were
not masked during handling of shared PCI interrupts. This resulted in ASTs sometimes being discarded and softclock interrupts sometimes being handled prematurely (sometimes = quite often on systems with shared PCI interrupts, never on other systems). Debugged by: gibbs and other people at plutotech.com PR: 6944, maybe 12381
Diffstat (limited to 'sys/i386')
-rw-r--r--sys/i386/isa/intr_machdep.c25
-rw-r--r--sys/i386/isa/nmi.c25
2 files changed, 26 insertions, 24 deletions
diff --git a/sys/i386/isa/intr_machdep.c b/sys/i386/isa/intr_machdep.c
index 7076748..3a214a9 100644
--- a/sys/i386/isa/intr_machdep.c
+++ b/sys/i386/isa/intr_machdep.c
@@ -34,7 +34,7 @@
* SUCH DAMAGE.
*
* from: @(#)isa.c 7.2 (Berkeley) 5/13/91
- * $Id: intr_machdep.c,v 1.21 1999/05/04 21:18:20 dfr Exp $
+ * $Id: intr_machdep.c,v 1.22 1999/05/22 09:39:31 peter Exp $
*/
/*
* This file contains an aggregated module marked:
@@ -313,7 +313,7 @@ update_intr_masks(void)
maskptr = intr_mptr[intr];
if (!maskptr)
continue;
- *maskptr |= 1 << intr;
+ *maskptr |= SWI_CLOCK_MASK | (1 << intr);
mask = *maskptr;
if (mask != intr_mask[intr]) {
#if 0
@@ -400,7 +400,7 @@ icu_setup(int intr, inthand2_t *handler, void *arg, u_int *maskptr, int flags)
disable_intr();
intr_handler[intr] = handler;
intr_mptr[intr] = maskptr;
- intr_mask[intr] = mask | (1 << intr);
+ intr_mask[intr] = mask | SWI_CLOCK_MASK | (1 << intr);
intr_unit[intr] = arg;
#ifdef FAST_HI
if (flags & INTR_FAST) {
@@ -506,7 +506,7 @@ icu_unset(intr, handler)
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
- * $Id: intr_machdep.c,v 1.21 1999/05/04 21:18:20 dfr Exp $
+ * $Id: intr_machdep.c,v 1.22 1999/05/22 09:39:31 peter Exp $
*
*/
@@ -531,22 +531,23 @@ typedef struct isarec {
static isarec *isareclist[ICU_LEN];
/*
- * The interrupt multiplexer calls each of the handlers in turn,
- * and applies the associated interrupt mask to "cpl", which is
- * defined as a ".long" in /sys/i386/isa/ipl.s
+ * The interrupt multiplexer calls each of the handlers in turn. The
+ * ipl is initially quite low. It is raised as necessary for each call
+ * and lowered after the call. Thus out of order handling is possible
+ * even for interrupts of the same type. This is probably no more
+ * harmful than out of order handling in general (not harmful except
+ * for real time response which we don't support anyway).
*/
-
static void
intr_mux(void *arg)
{
- intrec *p = arg;
- int oldspl;
+ intrec *p;
+ intrmask_t oldspl;
- while (p != NULL) {
+ for (p = arg; p != NULL; p = p->next) {
oldspl = splq(p->mask);
p->handler(p->argument);
splx(oldspl);
- p = p->next;
}
}
diff --git a/sys/i386/isa/nmi.c b/sys/i386/isa/nmi.c
index 7076748..3a214a9 100644
--- a/sys/i386/isa/nmi.c
+++ b/sys/i386/isa/nmi.c
@@ -34,7 +34,7 @@
* SUCH DAMAGE.
*
* from: @(#)isa.c 7.2 (Berkeley) 5/13/91
- * $Id: intr_machdep.c,v 1.21 1999/05/04 21:18:20 dfr Exp $
+ * $Id: intr_machdep.c,v 1.22 1999/05/22 09:39:31 peter Exp $
*/
/*
* This file contains an aggregated module marked:
@@ -313,7 +313,7 @@ update_intr_masks(void)
maskptr = intr_mptr[intr];
if (!maskptr)
continue;
- *maskptr |= 1 << intr;
+ *maskptr |= SWI_CLOCK_MASK | (1 << intr);
mask = *maskptr;
if (mask != intr_mask[intr]) {
#if 0
@@ -400,7 +400,7 @@ icu_setup(int intr, inthand2_t *handler, void *arg, u_int *maskptr, int flags)
disable_intr();
intr_handler[intr] = handler;
intr_mptr[intr] = maskptr;
- intr_mask[intr] = mask | (1 << intr);
+ intr_mask[intr] = mask | SWI_CLOCK_MASK | (1 << intr);
intr_unit[intr] = arg;
#ifdef FAST_HI
if (flags & INTR_FAST) {
@@ -506,7 +506,7 @@ icu_unset(intr, handler)
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
- * $Id: intr_machdep.c,v 1.21 1999/05/04 21:18:20 dfr Exp $
+ * $Id: intr_machdep.c,v 1.22 1999/05/22 09:39:31 peter Exp $
*
*/
@@ -531,22 +531,23 @@ typedef struct isarec {
static isarec *isareclist[ICU_LEN];
/*
- * The interrupt multiplexer calls each of the handlers in turn,
- * and applies the associated interrupt mask to "cpl", which is
- * defined as a ".long" in /sys/i386/isa/ipl.s
+ * The interrupt multiplexer calls each of the handlers in turn. The
+ * ipl is initially quite low. It is raised as necessary for each call
+ * and lowered after the call. Thus out of order handling is possible
+ * even for interrupts of the same type. This is probably no more
+ * harmful than out of order handling in general (not harmful except
+ * for real time response which we don't support anyway).
*/
-
static void
intr_mux(void *arg)
{
- intrec *p = arg;
- int oldspl;
+ intrec *p;
+ intrmask_t oldspl;
- while (p != NULL) {
+ for (p = arg; p != NULL; p = p->next) {
oldspl = splq(p->mask);
p->handler(p->argument);
splx(oldspl);
- p = p->next;
}
}
OpenPOWER on IntegriCloud