Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/netbsd-6]: src/sys/arch/x86 Pull up following revision(s) (requested by ...



details:   https://anonhg.NetBSD.org/src/rev/9ee1fa631a56
branches:  netbsd-6
changeset: 775749:9ee1fa631a56
user:      riz <riz%NetBSD.org@localhost>
date:      Sun Mar 31 20:32:01 2013 +0000

description:
Pull up following revision(s) (requested by chs in ticket #855):
        sys/arch/x86/acpi/acpi_machdep.c: revision 1.5
        sys/arch/x86/acpi/acpi_machdep.c: revision 1.6
        sys/arch/x86/x86/mpacpi.c: revision 1.97
redo the ACPI interrupt handler setup again, this time handling
MADT overrides that change the pin as well as the polarity.
fixes PR 47648.
yet more fixes for PR 47648 / PR 47016:
when using a temporary mp_intr_map, initialize the "flags" field
as well as "redir" since apic_set_redir() uses both.  fix how
the flags field is change when applying an override, the trigger
and polarity sub-fields aren't just one bit like they are in redir.

diffstat:

 sys/arch/x86/acpi/acpi_machdep.c |  128 +++++++++++++++++++++++++++-----------
 sys/arch/x86/x86/mpacpi.c        |   16 +----
 2 files changed, 93 insertions(+), 51 deletions(-)

diffs (236 lines):

diff -r 24f9750fa02e -r 9ee1fa631a56 sys/arch/x86/acpi/acpi_machdep.c
--- a/sys/arch/x86/acpi/acpi_machdep.c  Sun Mar 31 20:26:33 2013 +0000
+++ b/sys/arch/x86/acpi/acpi_machdep.c  Sun Mar 31 20:32:01 2013 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: acpi_machdep.c,v 1.3.2.1 2012/11/22 00:39:00 riz Exp $ */
+/* $NetBSD: acpi_machdep.c,v 1.3.2.2 2013/03/31 20:32:01 riz Exp $ */
 
 /*
  * Copyright 2001 Wasabi Systems, Inc.
@@ -40,7 +40,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: acpi_machdep.c,v 1.3.2.1 2012/11/22 00:39:00 riz Exp $");
+__KERNEL_RCSID(0, "$NetBSD: acpi_machdep.c,v 1.3.2.2 2013/03/31 20:32:01 riz Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -93,6 +93,31 @@
        return PhysicalAddress;
 }
 
+struct acpi_md_override {
+       int irq;
+       int pin;
+       int flags;
+};
+
+static ACPI_STATUS
+acpi_md_findoverride(ACPI_SUBTABLE_HEADER *hdrp, void *aux)
+{
+       ACPI_MADT_INTERRUPT_OVERRIDE *iop;
+       struct acpi_md_override *ovrp;
+
+       if (hdrp->Type != ACPI_MADT_TYPE_INTERRUPT_OVERRIDE) {
+               return AE_OK;
+       }
+
+       iop = (void *)hdrp;
+       ovrp = aux;
+       if (iop->SourceIrq == ovrp->irq) {
+               ovrp->pin = iop->GlobalIrq;
+               ovrp->flags = iop->IntiFlags;
+       }
+       return AE_OK;
+}
+
 ACPI_STATUS
 acpi_md_OsInstallInterruptHandler(uint32_t InterruptNumber,
     ACPI_OSD_HANDLER ServiceRoutine, void *Context, void **cookiep)
@@ -101,41 +126,63 @@
        struct pic *pic;
 #if NIOAPIC > 0
        struct ioapic_softc *sc;
+       struct acpi_md_override ovr;
+       struct mp_intr_map tmpmap, *mip, **mipp = NULL;
 #endif
-       int irq, pin, trigger;
+       int irq, pin, type, redir, mpflags;
+
+       /*
+        * ACPI interrupts default to level-triggered active-low.
+        */
+
+       type = IST_LEVEL;
+       mpflags = (MPS_INTTR_LEVEL << 2) | MPS_INTPO_ACTLO;
+       redir = IOAPIC_REDLO_LEVEL | IOAPIC_REDLO_ACTLO;
 
 #if NIOAPIC > 0
-       /*
-        * Can only match on ACPI global interrupt numbers if the ACPI
-        * interrupt info was extracted, which is in the ACPI case.
-        */
-       if (mpacpi_sci_override != NULL) {
-               pic = mpacpi_sci_override->ioapic;
-               pin = mpacpi_sci_override->ioapic_pin;
-               if (mpacpi_sci_override->redir & IOAPIC_REDLO_LEVEL)
-                       trigger = IST_LEVEL;
-               else
-                       trigger = IST_EDGE;
-               if (pic->pic_type == PIC_IOAPIC)
-                       irq = -1;
-               else
-                       irq = (int)InterruptNumber;
-               goto sci_override;
-       }
-#endif
 
        /*
-        * There was no ACPI interrupt source override,
-        *
-        * If the interrupt is handled via IOAPIC, mark it
-        * as level-triggered, active low in the table.
+        * Apply any MADT override setting.
         */
 
-#if NIOAPIC > 0
+       ovr.irq = InterruptNumber;
+       ovr.pin = -1;
+       if (acpi_madt_map() == AE_OK) {
+               acpi_madt_walk(acpi_md_findoverride, &ovr);
+               acpi_madt_unmap();
+       } else {
+               aprint_debug("acpi_madt_map() failed, can't check for MADT override\n");
+       }
+
+       if (ovr.pin != -1) {
+               bool sci = InterruptNumber == AcpiGbl_FADT.SciInterrupt;
+               int polarity = ovr.flags & ACPI_MADT_POLARITY_MASK;
+               int trigger = ovr.flags & ACPI_MADT_TRIGGER_MASK;
+
+               InterruptNumber = ovr.pin;
+               if (polarity == ACPI_MADT_POLARITY_ACTIVE_HIGH ||
+                   (!sci && polarity == ACPI_MADT_POLARITY_CONFORMS)) {
+                       mpflags &= ~MPS_INTPO_ACTLO;
+                       mpflags |= MPS_INTPO_ACTHI;
+                       redir &= ~IOAPIC_REDLO_ACTLO;
+               }
+               if (trigger == ACPI_MADT_TRIGGER_EDGE ||
+                   (!sci && trigger == ACPI_MADT_TRIGGER_CONFORMS)) {
+                       type = IST_EDGE;
+                       mpflags &= ~(MPS_INTTR_LEVEL << 2);
+                       mpflags |= (MPS_INTTR_EDGE << 2);
+                       redir &= ~IOAPIC_REDLO_LEVEL;
+               }
+       }
+
+       /*
+        * If the interrupt is handled via IOAPIC, update the map.
+        * If the map isn't set up yet, install a temporary one.
+        */
+
        sc = ioapic_find_bybase(InterruptNumber);
        if (sc != NULL) {
                pic = &sc->sc_pic;
-               struct mp_intr_map *mip;
 
                if (pic->pic_type == PIC_IOAPIC) {
                        pin = (int)InterruptNumber - pic->pic_vecbase;
@@ -146,9 +193,16 @@
 
                mip = sc->sc_pins[pin].ip_map;
                if (mip) {
-                       mip->flags &= ~3;
-                       mip->flags |= MPS_INTPO_ACTLO;
-                       mip->redir |= IOAPIC_REDLO_ACTLO;
+                       mip->flags &= ~0xf;
+                       mip->flags |= mpflags;
+                       mip->redir &= ~(IOAPIC_REDLO_LEVEL |
+                                       IOAPIC_REDLO_ACTLO);
+                       mip->redir |= redir;
+               } else {
+                       mipp = &sc->sc_pins[pin].ip_map;
+                       *mipp = &tmpmap;
+                       tmpmap.redir = redir;
+                       tmpmap.flags = mpflags;
                }
        } else
 #endif
@@ -157,18 +211,18 @@
                irq = pin = (int)InterruptNumber;
        }
 
-       trigger = IST_LEVEL;
-
-#if NIOAPIC > 0
-sci_override:
-#endif
-
        /*
         * XXX probably, IPL_BIO is enough.
         */
-       ih = intr_establish(irq, pic, pin, trigger, IPL_TTY,
+       ih = intr_establish(irq, pic, pin, type, IPL_TTY,
            (int (*)(void *)) ServiceRoutine, Context, false);
 
+#if NIOAPIC > 0
+       if (mipp) {
+               *mipp = NULL;
+       }
+#endif
+
        if (ih == NULL)
                return AE_NO_MEMORY;
 
diff -r 24f9750fa02e -r 9ee1fa631a56 sys/arch/x86/x86/mpacpi.c
--- a/sys/arch/x86/x86/mpacpi.c Sun Mar 31 20:26:33 2013 +0000
+++ b/sys/arch/x86/x86/mpacpi.c Sun Mar 31 20:32:01 2013 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: mpacpi.c,v 1.92.8.1 2012/11/22 00:39:00 riz Exp $      */
+/*     $NetBSD: mpacpi.c,v 1.92.8.2 2013/03/31 20:32:01 riz Exp $      */
 
 /*
  * Copyright (c) 2003 Wasabi Systems, Inc.
@@ -36,7 +36,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: mpacpi.c,v 1.92.8.1 2012/11/22 00:39:00 riz Exp $");
+__KERNEL_RCSID(0, "$NetBSD: mpacpi.c,v 1.92.8.2 2013/03/31 20:32:01 riz Exp $");
 
 #include "acpica.h"
 #include "opt_acpi.h"
@@ -133,8 +133,6 @@
 static int mpacpi_npciroots;
 #endif
 
-struct mp_intr_map *mpacpi_sci_override;
-
 static int mpacpi_intr_index;
 static paddr_t mpacpi_lapic_base = LAPIC_BASE;
 
@@ -299,9 +297,6 @@
                if (pic->pic_type == PIC_IOAPIC)
                        pic->pic_ioapic->sc_pins[pin].ip_map = mpi;
 #endif
-               if (isa_ovr->SourceIrq == AcpiGbl_FADT.SciInterrupt)
-                       mpacpi_sci_override = mpi;
-
                break;
 
        case ACPI_MADT_TYPE_LOCAL_X2APIC_NMI:
@@ -942,13 +937,6 @@
                printf("mpacpi: %d PCI busses\n", mpacpi_npci);
 #endif
        mpacpi_config_irouting(acpi);
-#if NIOAPIC > 0
-       /*
-        * XXX fix up the SCI interrupt polarity.
-        * it's installed before we have parsed the MADT.
-        */
-       ioapic_reenable();
-#endif
        if (mp_verbose)
                for (i = 0; i < mp_nintr; i++)
                        mpacpi_print_intr(&mp_intrs[i]);



Home | Main Index | Thread Index | Old Index