summaryrefslogtreecommitdiff
path: root/sys/arch/macppc/dev
diff options
context:
space:
mode:
authorMark Kettenis <kettenis@cvs.openbsd.org>2008-05-01 08:25:33 +0000
committerMark Kettenis <kettenis@cvs.openbsd.org>2008-05-01 08:25:33 +0000
commita97b2b7bde244fd3f4eb544a004755e242e64f0f (patch)
tree4ba472595f2dd4c973876e81f279aa7664ca2c52 /sys/arch/macppc/dev
parent0b4c8887958a97173d0c54954daf289589bd6fcf (diff)
Implement a nop IPI to signal other CPUs.
ok drahn@
Diffstat (limited to 'sys/arch/macppc/dev')
-rw-r--r--sys/arch/macppc/dev/openpic.c39
1 files changed, 34 insertions, 5 deletions
diff --git a/sys/arch/macppc/dev/openpic.c b/sys/arch/macppc/dev/openpic.c
index 5429b905212..f20a62f0472 100644
--- a/sys/arch/macppc/dev/openpic.c
+++ b/sys/arch/macppc/dev/openpic.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: openpic.c,v 1.42 2008/04/26 22:37:41 drahn Exp $ */
+/* $OpenBSD: openpic.c,v 1.43 2008/05/01 08:25:32 kettenis Exp $ */
/*-
* Copyright (c) 1995 Per Fogelstrom
@@ -75,6 +75,9 @@ void openpic_enable_irq_mask(int irq_mask);
#define HWIRQ_MAX 27
#define HWIRQ_MASK 0x0fffffff
+/* IRQ vector used for inter-processor interrupts. */
+#define IPI_VECTOR 64
+
static __inline u_int openpic_read(int);
static __inline void openpic_write(int, u_int);
void openpic_set_enable_irq(int, int);
@@ -624,6 +627,16 @@ openpic_eoi(int cpu)
openpic_read(OPENPIC_EOI(cpu));
}
+#ifdef MULTIPROCESSOR
+
+void
+openpic_send_ipi(int cpu)
+{
+ openpic_write(OPENPIC_IPI(curcpu()->ci_cpuid, 0), 1 << cpu);
+}
+
+#endif
+
void
ext_intr_openpic()
{
@@ -635,9 +648,17 @@ ext_intr_openpic()
pcpl = ci->ci_cpl;
- realirq = openpic_read_irq(0);
+ realirq = openpic_read_irq(ci->ci_cpuid);
while (realirq != 255) {
+#ifdef MULTIPROCESSOR
+ if (realirq == IPI_VECTOR) {
+ openpic_eoi(ci->ci_cpuid);
+ realirq = openpic_read_irq(ci->ci_cpuid);
+ continue;
+ }
+#endif
+
irq = o_virq[realirq];
/* XXX check range */
@@ -648,10 +669,10 @@ ext_intr_openpic()
/* Masked! Mark this as pending. */
ci->ci_ipending |= r_imen;
openpic_disable_irq(realirq);
- openpic_eoi(0);
+ openpic_eoi(ci->ci_cpuid);
} else {
openpic_disable_irq(realirq);
- openpic_eoi(0);
+ openpic_eoi(ci->ci_cpuid);
ocpl = splraise(o_intrmask[irq]);
ih = o_intrhand[irq];
@@ -674,7 +695,7 @@ ext_intr_openpic()
openpic_enable_irq(realirq);
}
- realirq = openpic_read_irq(0);
+ realirq = openpic_read_irq(ci->ci_cpuid);
}
ppc_intr_enable(1);
@@ -709,6 +730,14 @@ openpic_init()
openpic_write(OPENPIC_SRC_VECTOR(irq), x);
}
+#ifdef MULTIPROCESSOR
+ /* Set up inter-processor interrupts. */
+ x = openpic_read(OPENPIC_IPI_VECTOR(0));
+ x &= ~(OPENPIC_IMASK | OPENPIC_PRIORITY_MASK | OPENPIC_VECTOR_MASK);
+ x |= (15 << OPENPIC_PRIORITY_SHIFT) | IPI_VECTOR;
+ openpic_write(OPENPIC_IPI_VECTOR(0), x);
+#endif
+
/* XXX set spurious intr vector */
openpic_set_priority(0, 0);