summaryrefslogtreecommitdiff
path: root/sys
diff options
context:
space:
mode:
authorMark Kettenis <kettenis@cvs.openbsd.org>2006-06-27 21:22:15 +0000
committerMark Kettenis <kettenis@cvs.openbsd.org>2006-06-27 21:22:15 +0000
commit3b04cdc3ff7ae587663d97378f727afa528c6ac5 (patch)
tree88517e9548bcac06a71f9a2f649fe4cd1a113c88 /sys
parentecc659c5fc44a1aedeab96ad777ecbe242dc948b (diff)
Fix interrupt mapping. This now seems to work on all machines, even with
pci cards that have a pci-pci bridge and lack fcode. tested by many, ok jason@, dlg@
Diffstat (limited to 'sys')
-rw-r--r--sys/arch/sparc64/dev/pci_machdep.c6
-rw-r--r--sys/arch/sparc64/dev/psycho.c63
-rw-r--r--sys/arch/sparc64/dev/schizo.c37
3 files changed, 48 insertions, 58 deletions
diff --git a/sys/arch/sparc64/dev/pci_machdep.c b/sys/arch/sparc64/dev/pci_machdep.c
index b4e4565b6ca..3d1dfada715 100644
--- a/sys/arch/sparc64/dev/pci_machdep.c
+++ b/sys/arch/sparc64/dev/pci_machdep.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: pci_machdep.c,v 1.24 2006/06/02 08:26:01 jason Exp $ */
+/* $OpenBSD: pci_machdep.c,v 1.25 2006/06/27 21:22:14 kettenis Exp $ */
/* $NetBSD: pci_machdep.c,v 1.22 2001/07/20 00:07:13 eeh Exp $ */
/*
@@ -436,7 +436,7 @@ pci_intr_map(pa, ihp)
if (OF_mapintr(node, &interrupts, sizeof(interrupts),
sizeof(interrupts)) < 0) {
- printf("OF_mapintr failed\n");
+ interrupts = -1;
}
/* Try to find an IPL for this type of device. */
if (OF_getprop(node, "device_type", &devtype, sizeof(devtype)) > 0) {
@@ -464,7 +464,7 @@ pci_intr_string(pc, ih)
static char str[16];
DPRINTF(SPDB_INTR, ("pci_intr_string: ih %u", ih));
- snprintf(str, sizeof str, "ivec %x", ih);
+ snprintf(str, sizeof str, "ivec 0x%x", INTVEC(ih));
DPRINTF(SPDB_INTR, ("; returning %s\n", str));
return (str);
diff --git a/sys/arch/sparc64/dev/psycho.c b/sys/arch/sparc64/dev/psycho.c
index 0f3defc211d..53c24be1878 100644
--- a/sys/arch/sparc64/dev/psycho.c
+++ b/sys/arch/sparc64/dev/psycho.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: psycho.c,v 1.43 2006/03/19 02:43:38 brad Exp $ */
+/* $OpenBSD: psycho.c,v 1.44 2006/06/27 21:22:14 kettenis Exp $ */
/* $NetBSD: psycho.c,v 1.39 2001/10/07 20:30:41 eeh Exp $ */
/*
@@ -1031,40 +1031,37 @@ psycho_intr_map(struct pci_attach_args *pa, pci_intr_handle_t *ihp)
struct psycho_pbm *pp = pa->pa_pc->cookie;
struct psycho_softc *sc = pp->pp_sc;
u_int dev;
- u_int ino;
- ino = *ihp;
-
- if ((ino & ~INTMAP_PCIINT) == 0) {
- /*
- * This deserves some documentation. Should anyone
- * have anything official looking, please speak up.
- */
- if (sc->sc_mode == PSYCHO_MODE_PSYCHO &&
- pp->pp_id == PSYCHO_PBM_B)
- dev = pa->pa_device - 2;
- else
- dev = pa->pa_device - 1;
-
- if (ino == 0 || ino > 4) {
- u_int32_t intreg;
-
- intreg = pci_conf_read(pa->pa_pc, pa->pa_tag,
- PCI_INTERRUPT_REG);
-
- ino = PCI_INTERRUPT_PIN(intreg) - 1;
- } else
- ino -= 1;
-
- ino &= INTMAP_PCIINT;
-
- ino |= sc->sc_ign;
- ino |= ((pp->pp_id == PSYCHO_PBM_B) ? INTMAP_PCIBUS : 0);
- ino |= (dev << 2) & INTMAP_PCISLOT;
-
- *ihp = ino;
+ if (*ihp != (pci_intr_handle_t)-1) {
+ *ihp |= sc->sc_ign;
+ return (0);
}
-
+
+ /*
+ * We didn't find a PROM mapping for this interrupt. Try to
+ * construct one ourselves based on the swizzled interrupt pin
+ * and the interrupt mapping for PCI slots documented in the
+ * UltraSPARC-IIi User's Manual.
+ */
+
+ if (pa->pa_intrpin == 0)
+ return (-1);
+
+ /*
+ * This deserves some documentation. Should anyone
+ * have anything official looking, please speak up.
+ */
+ if (sc->sc_mode == PSYCHO_MODE_PSYCHO &&
+ pp->pp_id == PSYCHO_PBM_B)
+ dev = PCITAG_DEV(pa->pa_intrtag) - 2;
+ else
+ dev = PCITAG_DEV(pa->pa_intrtag) - 1;
+
+ *ihp = (pa->pa_intrpin - 1) & INTMAP_PCIINT;
+ *ihp |= ((pp->pp_id == PSYCHO_PBM_B) ? INTMAP_PCIBUS : 0);
+ *ihp |= (dev << 2) & INTMAP_PCISLOT;
+ *ihp |= sc->sc_ign;
+
return (0);
}
diff --git a/sys/arch/sparc64/dev/schizo.c b/sys/arch/sparc64/dev/schizo.c
index b5960956182..d7062c61e8f 100644
--- a/sys/arch/sparc64/dev/schizo.c
+++ b/sys/arch/sparc64/dev/schizo.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: schizo.c,v 1.27 2006/06/23 16:09:45 deraadt Exp $ */
+/* $OpenBSD: schizo.c,v 1.28 2006/06/27 21:22:14 kettenis Exp $ */
/*
* Copyright (c) 2002 Jason L. Wright (jason@thought.net)
@@ -364,42 +364,35 @@ schizo_intr_map(struct pci_attach_args *pa, pci_intr_handle_t *ihp)
struct schizo_pbm *sp = pa->pa_pc->cookie;
struct schizo_softc *sc = sp->sp_sc;
u_int dev;
- u_int ino;
u_int64_t agentid;
- ino = *ihp;
-
agentid = schizo_read(sc, SCZ_CONTROL_STATUS);
agentid = ((agentid >> 20) & 31) << 6;
- if (ino & ~INTMAP_PCIINT) {
+ if (*ihp != (pci_intr_handle_t)-1) {
*ihp |= agentid;
return (0);
}
/*
+ * We didn't find a PROM mapping for this interrupt. Try to
+ * construct one ourselves based on the swizzled interrupt pin
+ * and the interrupt mapping for PCI slots documented in the
+ * UltraSPARC-IIi User's Manual.
+ */
+
+ if (pa->pa_intrpin == 0)
+ return (-1);
+
+ /*
* This deserves some documentation. Should anyone
* have anything official looking, please speak up.
*/
dev = pa->pa_device - 1;
- if (ino == 0 || ino > 4) {
- u_int32_t intreg;
-
- intreg = pci_conf_read(pa->pa_pc, pa->pa_tag,
- PCI_INTERRUPT_REG);
-
- ino = PCI_INTERRUPT_PIN(intreg) - 1;
- } else
- ino -= 1;
-
- ino &= INTMAP_PCIINT;
- ino |= agentid;
- ino |= (dev << 2) & INTMAP_PCISLOT;
-
- printf("******** mapping interrupt %x -> %x\n", *ihp, ino);
-
- *ihp = ino;
+ *ihp = (pa->pa_intrpin - 1) & INTMAP_PCIINT;
+ *ihp |= (dev << 2) & INTMAP_PCISLOT;
+ *ihp |= agentid;
return (0);
}