summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authornwhitehorn <nwhitehorn@FreeBSD.org>2010-07-06 15:27:05 +0000
committernwhitehorn <nwhitehorn@FreeBSD.org>2010-07-06 15:27:05 +0000
commit6075124f5d4f68fbf2a03a70240288f2e9947813 (patch)
treec8b2a364e3c3e7b441b1a17da10a88a9b5af194a
parentda1f525af04cd62596668038387a53d2eedd6b09 (diff)
downloadFreeBSD-src-6075124f5d4f68fbf2a03a70240288f2e9947813.zip
FreeBSD-src-6075124f5d4f68fbf2a03a70240288f2e9947813.tar.gz
Move the EOI logic when starting ithreads into intr_machdep instead of
relying on it as a side effect of PIC_MASK() in the PIC drivers, and add an inmplementation of assign_cpu() for the kernel interrupt layer.
-rw-r--r--sys/powerpc/mpc85xx/atpic.c2
-rw-r--r--sys/powerpc/powermac/hrowpic.c3
-rw-r--r--sys/powerpc/powerpc/intr_machdep.c37
-rw-r--r--sys/powerpc/powerpc/openpic.c1
4 files changed, 25 insertions, 18 deletions
diff --git a/sys/powerpc/mpc85xx/atpic.c b/sys/powerpc/mpc85xx/atpic.c
index 03ae9b4..3a749c7 100644
--- a/sys/powerpc/mpc85xx/atpic.c
+++ b/sys/powerpc/mpc85xx/atpic.c
@@ -308,12 +308,10 @@ atpic_mask(device_t dev, u_int irq)
if (irq > 7) {
sc->sc_mask[ATPIC_SLAVE] |= 1 << (irq - 8);
atpic_write(sc, ATPIC_SLAVE, 1, sc->sc_mask[ATPIC_SLAVE]);
- atpic_write(sc, ATPIC_SLAVE, 0, OCW2_EOI);
} else {
sc->sc_mask[ATPIC_MASTER] |= 1 << irq;
atpic_write(sc, ATPIC_MASTER, 1, sc->sc_mask[ATPIC_MASTER]);
}
- atpic_write(sc, ATPIC_MASTER, 0, OCW2_EOI);
}
static void
diff --git a/sys/powerpc/powermac/hrowpic.c b/sys/powerpc/powermac/hrowpic.c
index b94ebd9..0e839d9 100644
--- a/sys/powerpc/powermac/hrowpic.c
+++ b/sys/powerpc/powermac/hrowpic.c
@@ -269,12 +269,9 @@ static void
hrowpic_mask(device_t dev, u_int irq)
{
struct hrowpic_softc *sc;
- int bank;
sc = device_get_softc(dev);
hrowpic_toggle_irq(sc, irq, 0);
- bank = (irq >= 32) ? HPIC_SECONDARY : HPIC_PRIMARY ;
- hrowpic_write_reg(sc, HPIC_CLEAR, bank, 1U << (irq & 0x1f));
}
static void
diff --git a/sys/powerpc/powerpc/intr_machdep.c b/sys/powerpc/powerpc/intr_machdep.c
index 8c018c8..697f4b0 100644
--- a/sys/powerpc/powerpc/intr_machdep.c
+++ b/sys/powerpc/powerpc/intr_machdep.c
@@ -239,21 +239,42 @@ powerpc_intr_eoi(void *arg)
}
static void
-powerpc_intr_mask(void *arg)
+powerpc_intr_pre_ithread(void *arg)
{
struct powerpc_intr *i = arg;
PIC_MASK(i->pic, i->intline);
+ PIC_EOI(i->pic, i->intline);
}
static void
-powerpc_intr_unmask(void *arg)
+powerpc_intr_post_ithread(void *arg)
{
struct powerpc_intr *i = arg;
PIC_UNMASK(i->pic, i->intline);
}
+static int
+powerpc_assign_intr_cpu(void *arg, u_char cpu)
+{
+#ifdef SMP
+ struct powerpc_intr *i = arg;
+
+ if (cpu == NOCPU)
+ i->cpu = all_cpus;
+ else
+ i->cpu = 1 << cpu;
+
+ if (!cold && i->pic != NULL && i->pic == root_pic)
+ PIC_BIND(i->pic, i->intline, i->cpu);
+
+ return (0);
+#else
+ return (EOPNOTSUPP);
+#endif
+}
+
void
powerpc_register_pic(device_t dev, u_int ipi)
{
@@ -360,8 +381,8 @@ powerpc_setup_intr(const char *name, u_int irq, driver_filter_t filter,
if (i->event == NULL) {
error = intr_event_create(&i->event, (void *)i, 0, irq,
- powerpc_intr_mask, powerpc_intr_unmask, powerpc_intr_eoi,
- NULL, "irq%u:", irq);
+ powerpc_intr_pre_ithread, powerpc_intr_post_ithread,
+ powerpc_intr_eoi, powerpc_assign_intr_cpu, "irq%u:", irq);
if (error)
return (error);
@@ -410,14 +431,6 @@ powerpc_bind_intr(u_int irq, u_char cpu)
if (i == NULL)
return (ENOMEM);
- if (cpu == NOCPU)
- i->cpu = all_cpus;
- else
- i->cpu = 1 << cpu;
-
- if (!cold && i->pic != NULL && i->pic == root_pic)
- PIC_BIND(i->pic, i->intline, i->cpu);
-
return (intr_event_bind(i->event, cpu));
}
#endif
diff --git a/sys/powerpc/powerpc/openpic.c b/sys/powerpc/powerpc/openpic.c
index d4cccf3..cf06c6a 100644
--- a/sys/powerpc/powerpc/openpic.c
+++ b/sys/powerpc/powerpc/openpic.c
@@ -351,7 +351,6 @@ openpic_mask(device_t dev, u_int irq)
x |= OPENPIC_IMASK;
openpic_write(sc, OPENPIC_IPI_VECTOR(0), x);
}
- openpic_write(sc, OPENPIC_PCPU_EOI(PCPU_GET(cpuid)), 0);
}
void
OpenPOWER on IntegriCloud