diff options
author | Dale S. Rahn <rahnds@cvs.openbsd.org> | 2000-07-07 13:22:44 +0000 |
---|---|---|
committer | Dale S. Rahn <rahnds@cvs.openbsd.org> | 2000-07-07 13:22:44 +0000 |
commit | d25c5758ea35b3a5510242ed2943f124cc00de19 (patch) | |
tree | 1e338355a8d04ce7cee98d0970155bc4b701edad | |
parent | 0193f0c2db48a9f4d692c17a58ca88ace3dc1323 (diff) |
Since it is possible for the interrupt controller to be configured late
in the config cycle, and pci devices as well as mac onboard devices
do not use interrupts to probe. It is possible to record that the
interrupt is to be configured, but not configure it with the interrupt
controller until the interrupt controller configures itself.
This is lazy binding of interrupts. If there is a conflicting interrupt
or other problem it will be noticed when the interrupt controller configures
and collects the data rather than when the device configures.
Currently on the openpic interrupt controller supports these pre-configured
interrupts.
-rw-r--r-- | sys/arch/powerpc/include/intr.h | 5 | ||||
-rw-r--r-- | sys/arch/powerpc/mac/openpic.c | 35 | ||||
-rw-r--r-- | sys/arch/powerpc/powerpc/machdep.c | 24 |
3 files changed, 55 insertions, 9 deletions
diff --git a/sys/arch/powerpc/include/intr.h b/sys/arch/powerpc/include/intr.h index f2387c0a9fe..55fe476c175 100644 --- a/sys/arch/powerpc/include/intr.h +++ b/sys/arch/powerpc/include/intr.h @@ -1,4 +1,4 @@ -/* $OpenBSD: intr.h,v 1.6 2000/07/06 15:29:53 ho Exp $ */ +/* $OpenBSD: intr.h,v 1.7 2000/07/07 13:22:42 rahnds Exp $ */ /* * Copyright (c) 1997 Per Fogelstrom, Opsycon AB and RTMX Inc, USA. @@ -162,6 +162,9 @@ struct intrhand { int ih_irq; char *ih_what; }; +extern int ppc_configed_intr_cnt; +#define MAX_PRECONF_INTR 16 +extern struct intrhand ppc_configed_intr[MAX_PRECONF_INTR]; #endif /* _LOCORE */ diff --git a/sys/arch/powerpc/mac/openpic.c b/sys/arch/powerpc/mac/openpic.c index 099648c8af7..1f435ac1e01 100644 --- a/sys/arch/powerpc/mac/openpic.c +++ b/sys/arch/powerpc/mac/openpic.c @@ -1,4 +1,4 @@ -/* $OpenBSD: openpic.c,v 1.3 2000/06/15 03:11:01 rahnds Exp $ */ +/* $OpenBSD: openpic.c,v 1.4 2000/07/07 13:22:42 rahnds Exp $ */ /*- * Copyright (c) 1995 Per Fogelstrom @@ -58,12 +58,12 @@ #include <machine/pio.h> #include <powerpc/mac/openpicreg.h> -#define ICU_LEN 64 +#define ICU_LEN 128 #define LEGAL_IRQ(x) ((x >= 0) && (x < ICU_LEN)) static int intrtype[ICU_LEN], intrmask[ICU_LEN], intrlevel[ICU_LEN]; static struct intrhand *intrhand[ICU_LEN] = { 0 }; -static int hwirq[ICU_LEN], virq[64]; +static int hwirq[ICU_LEN], virq[ICU_LEN]; unsigned int imen /* = 0xffffffff */; /* XXX */ static int virq_max = 0; @@ -145,6 +145,7 @@ vaddr_t openpic_base; void * openpic_intr_establish( void * lcv, int irq, int type, int level, int (*ih_fun) __P((void *)), void *ih_arg, char *name); void openpic_intr_disestablish( void *lcp, void *arg); +void openpic_collect_preconf_intr(); void openpic_attach(parent, self, aux) @@ -171,6 +172,10 @@ openpic_attach(parent, self, aux) mac_intr_establish_func = openpic_intr_establish; mac_intr_disestablish_func = openpic_intr_disestablish; install_extint(ext_intr_openpic); + +#if 1 + openpic_collect_preconf_intr(); +#endif #if 1 mac_intr_establish(parent, 0x37, IST_LEVEL, @@ -179,6 +184,28 @@ openpic_attach(parent, self, aux) printf("\n"); } +void +openpic_collect_preconf_intr() +{ + int i; + printf("postconfiguring interrupts\n"); + for (i = 0; i < ppc_configed_intr_cnt; i++) { + printf("\t%s irq %d level %d fun %x arg %x\n", + ppc_configed_intr[i].ih_what, + ppc_configed_intr[i].ih_irq, + ppc_configed_intr[i].ih_level, + ppc_configed_intr[i].ih_fun, + ppc_configed_intr[i].ih_arg + ); + openpic_intr_establish(NULL, + ppc_configed_intr[i].ih_irq, + IST_LEVEL, + ppc_configed_intr[i].ih_level, + ppc_configed_intr[i].ih_fun, + ppc_configed_intr[i].ih_arg, + ppc_configed_intr[i].ih_what); + } +} static int prog_switch (void *arg) @@ -419,7 +446,7 @@ mapirq(irq) { int v; - if (irq < 0 || irq >= 64) + if (irq < 0 || irq >= ICU_LEN) panic("invalid irq"); virq_max++; v = virq_max; diff --git a/sys/arch/powerpc/powerpc/machdep.c b/sys/arch/powerpc/powerpc/machdep.c index 7fe2e3727a2..528a77ea4fd 100644 --- a/sys/arch/powerpc/powerpc/machdep.c +++ b/sys/arch/powerpc/powerpc/machdep.c @@ -1,4 +1,4 @@ -/* $OpenBSD: machdep.c,v 1.42 2000/06/08 22:25:22 niklas Exp $ */ +/* $OpenBSD: machdep.c,v 1.43 2000/07/07 13:22:43 rahnds Exp $ */ /* $NetBSD: machdep.c,v 1.4 1996/10/16 19:33:11 ws Exp $ */ /* @@ -998,19 +998,35 @@ systype(char *name) */ #include <dev/pci/pcivar.h> typedef void *(intr_establish_t) __P((void *, pci_intr_handle_t, - int, int (*func)(void *), void *, char *)); + int, int, int (*func)(void *), void *, char *)); typedef void (intr_disestablish_t) __P((void *, void *)); +int ppc_configed_intr_cnt = 0; +struct intrhand ppc_configed_intr[MAX_PRECONF_INTR]; + void * -ppc_intr_establish(lcv, ih, level, func, arg, name) +ppc_intr_establish(lcv, ih, type, level, func, arg, name) void *lcv; pci_intr_handle_t ih; + int type; int level; int (*func) __P((void *)); void *arg; char *name; { - panic("ppc_intr_establish called before interrupt controller configured: driver %s", name); + if (ppc_configed_intr_cnt < MAX_PRECONF_INTR) { + ppc_configed_intr[ppc_configed_intr_cnt].ih_fun = func; + ppc_configed_intr[ppc_configed_intr_cnt].ih_arg = arg; + ppc_configed_intr[ppc_configed_intr_cnt].ih_level = level; + ppc_configed_intr[ppc_configed_intr_cnt].ih_irq = ih; + ppc_configed_intr[ppc_configed_intr_cnt].ih_what = name; + ppc_configed_intr_cnt++; + } else { + panic("ppc_intr_establish called before interrupt controller" + " configured: driver %s too many interrupts\n", name); + } + /* disestablish is going to be tricky to supported for these :-) */ + return (void *)ppc_configed_intr_cnt; } intr_establish_t *intr_establish_func = ppc_intr_establish;; |