diff options
Diffstat (limited to 'sys')
-rw-r--r-- | sys/powerpc/include/intr_machdep.h | 12 | ||||
-rw-r--r-- | sys/powerpc/include/openpicvar.h | 2 | ||||
-rw-r--r-- | sys/powerpc/mambo/mambo_openpic.c | 21 | ||||
-rw-r--r-- | sys/powerpc/mpc85xx/atpic.c | 15 | ||||
-rw-r--r-- | sys/powerpc/mpc85xx/isa.c | 8 | ||||
-rw-r--r-- | sys/powerpc/mpc85xx/openpic_fdt.c | 11 | ||||
-rw-r--r-- | sys/powerpc/mpc85xx/pci_fdt.c | 109 | ||||
-rw-r--r-- | sys/powerpc/powermac/cpcht.c | 16 | ||||
-rw-r--r-- | sys/powerpc/powermac/hrowpic.c | 13 | ||||
-rw-r--r-- | sys/powerpc/powermac/openpic_macio.c | 13 | ||||
-rw-r--r-- | sys/powerpc/powerpc/intr_machdep.c | 112 | ||||
-rw-r--r-- | sys/powerpc/powerpc/openpic.c | 5 | ||||
-rw-r--r-- | sys/powerpc/powerpc/pic_if.m | 4 | ||||
-rw-r--r-- | sys/powerpc/ps3/ps3pic.c | 13 | ||||
-rw-r--r-- | sys/powerpc/psim/openpic_iobus.c | 10 |
15 files changed, 162 insertions, 202 deletions
diff --git a/sys/powerpc/include/intr_machdep.h b/sys/powerpc/include/intr_machdep.h index 67d7e79..d0c6c1b 100644 --- a/sys/powerpc/include/intr_machdep.h +++ b/sys/powerpc/include/intr_machdep.h @@ -29,13 +29,9 @@ #define _MACHINE_INTR_MACHDEP_H_ #define INTR_VECTORS 256 -#define MAX_PICS 5 -#define IGN_SHIFT 8 -#define INTR_INTLINE(irq) (irq & ((1 << IGN_SHIFT) - 1)) -#define INTR_IGN(irq) (irq >> IGN_SHIFT) - -#define INTR_VEC(pic_id, irq) ((powerpc_ign_lookup(pic_id) << IGN_SHIFT) | (irq)) +#define MAX_PICS 5 +#define INTR_VEC(node, pin) powerpc_get_irq(node, pin) /* * Default base address for MSI messages on PowerPC @@ -50,8 +46,8 @@ driver_filter_t powerpc_ipi_handler; void intrcnt_add(const char *name, u_long **countp); -void powerpc_register_pic(device_t, u_int); -int powerpc_ign_lookup(uint32_t pic_id); +void powerpc_register_pic(device_t, uint32_t, u_int, u_int, u_int); +u_int powerpc_get_irq(uint32_t, u_int); void powerpc_dispatch_intr(u_int, struct trapframe *); int powerpc_enable_intr(void); diff --git a/sys/powerpc/include/openpicvar.h b/sys/powerpc/include/openpicvar.h index 5468542..4fb9aa7 100644 --- a/sys/powerpc/include/openpicvar.h +++ b/sys/powerpc/include/openpicvar.h @@ -52,7 +52,7 @@ extern devclass_t openpic_devclass; /* * Bus-independent attach i/f */ -int openpic_attach(device_t); +int openpic_common_attach(device_t, uint32_t); /* * PIC interface. diff --git a/sys/powerpc/mambo/mambo_openpic.c b/sys/powerpc/mambo/mambo_openpic.c index 3edb027..883c9d7 100644 --- a/sys/powerpc/mambo/mambo_openpic.c +++ b/sys/powerpc/mambo/mambo_openpic.c @@ -56,12 +56,11 @@ __FBSDID("$FreeBSD$"); * Mambo interface */ static int openpic_mambo_probe(device_t); -static uint32_t openpic_mambo_id(device_t dev); +static int openpic_mambo_attach(device_t); static int openpicbus_mambo_probe(device_t dev); static int openpicbus_mambo_attach(device_t dev); -static struct resource *openpicbus_alloc_resource(device_t bus, device_t dev, - int type, int *rid, u_long start, u_long end, u_long count, - u_int flags); +static struct resource *openpicbus_alloc_resource(device_t bus, device_t dev, + int type, int *rid, u_long start, u_long end, u_long count, u_int flags); static device_method_t openpicbus_mambo_methods[] = { /* Device interface */ @@ -87,7 +86,7 @@ static driver_t openpicbus_mambo_driver = { static device_method_t openpic_mambo_methods[] = { /* Device interface */ DEVMETHOD(device_probe, openpic_mambo_probe), - DEVMETHOD(device_attach, openpic_attach), + DEVMETHOD(device_attach, openpic_mambo_attach), /* PIC interface */ DEVMETHOD(pic_config, openpic_config), @@ -97,7 +96,6 @@ static device_method_t openpic_mambo_methods[] = { DEVMETHOD(pic_ipi, openpic_ipi), DEVMETHOD(pic_mask, openpic_mask), DEVMETHOD(pic_unmask, openpic_unmask), - DEVMETHOD(pic_id, openpic_mambo_id), { 0, 0 }, }; @@ -167,14 +165,15 @@ openpicbus_alloc_resource(device_t bus, device_t dev, int type, int *rid, static int openpic_mambo_probe(device_t dev) { + device_set_desc(dev, OPENPIC_DEVSTR); - return (0); } -static uint32_t -openpic_mambo_id(device_t dev) +static int +openpic_mambo_attach(device_t dev) { - return (ofw_bus_get_node(device_get_parent(dev))); + + return (openpic_common_attach(dev, + ofw_bus_get_node(device_get_parent(dev)))); } - diff --git a/sys/powerpc/mpc85xx/atpic.c b/sys/powerpc/mpc85xx/atpic.c index e903dbc..e1d0b39 100644 --- a/sys/powerpc/mpc85xx/atpic.c +++ b/sys/powerpc/mpc85xx/atpic.c @@ -36,7 +36,6 @@ __FBSDID("$FreeBSD$"); #include <machine/bus.h> #include <machine/intr_machdep.h> -#include <machine/ocpbus.h> #include <machine/pio.h> #include <powerpc/mpc85xx/mpc85xx.h> @@ -79,7 +78,6 @@ static void atpic_eoi(device_t, u_int); static void atpic_ipi(device_t, u_int); static void atpic_mask(device_t, u_int); static void atpic_unmask(device_t, u_int); -static uint32_t atpic_id (device_t dev); static device_method_t atpic_isa_methods[] = { /* Device interface */ @@ -95,7 +93,6 @@ static device_method_t atpic_isa_methods[] = { DEVMETHOD(pic_ipi, atpic_ipi), DEVMETHOD(pic_mask, atpic_mask), DEVMETHOD(pic_unmask, atpic_unmask), - DEVMETHOD(pic_id, atpic_id), { 0, 0 }, }; @@ -154,7 +151,7 @@ atpic_isa_identify(driver_t *drv, device_t parent) bus_set_resource(child, SYS_RES_IOPORT, ATPIC_SLAVE, IO_ICU2, 2); /* ISA interrupts are routed through external interrupt 0. */ - bus_set_resource(child, SYS_RES_IRQ, 0, PIC_IRQ_EXT(0), 1); + bus_set_resource(child, SYS_RES_IRQ, 0, 16, 1); } static int @@ -221,7 +218,7 @@ atpic_isa_attach(device_t dev) atpic_init(sc, ATPIC_SLAVE); atpic_init(sc, ATPIC_MASTER); - powerpc_register_pic(dev, 0x10); + powerpc_register_pic(dev, 0, 16, 0, TRUE); return (0); fail: @@ -328,11 +325,3 @@ atpic_unmask(device_t dev, u_int irq) atpic_write(sc, ATPIC_MASTER, 1, sc->sc_mask[ATPIC_MASTER]); } } - -static uint32_t -atpic_id (device_t dev) -{ - - return (ATPIC_ID); -} - diff --git a/sys/powerpc/mpc85xx/isa.c b/sys/powerpc/mpc85xx/isa.c index eeffbfd..a1715ef 100644 --- a/sys/powerpc/mpc85xx/isa.c +++ b/sys/powerpc/mpc85xx/isa.c @@ -33,15 +33,12 @@ __FBSDID("$FreeBSD$"); #include <sys/rman.h> #include <machine/intr_machdep.h> -#include <machine/ocpbus.h> #include <machine/resource.h> #include <isa/isareg.h> #include <isa/isavar.h> #include <isa/isa_common.h> -#include "ocpbus.h" - void isa_init(device_t dev) { @@ -62,10 +59,7 @@ isa_alloc_resource(device_t bus, device_t child, int type, int *rid, resource_list_find(rl, type, *rid) == NULL) { switch (type) { case SYS_RES_IOPORT: rids = ISA_PNP_NPORT; break; - case SYS_RES_IRQ: - rids = ISA_PNP_NIRQ; - start = ISA_IRQ(start); - break; + case SYS_RES_IRQ: rids = ISA_PNP_NIRQ; break; case SYS_RES_MEMORY: rids = ISA_PNP_NMEM; break; default: rids = 0; break; } diff --git a/sys/powerpc/mpc85xx/openpic_fdt.c b/sys/powerpc/mpc85xx/openpic_fdt.c index da70542..7cf18ea 100644 --- a/sys/powerpc/mpc85xx/openpic_fdt.c +++ b/sys/powerpc/mpc85xx/openpic_fdt.c @@ -45,12 +45,12 @@ __FBSDID("$FreeBSD$"); #include "pic_if.h" static int openpic_fdt_probe(device_t); -static uint32_t openpic_fdt_id(device_t); +static int openpic_fdt_attach(device_t); static device_method_t openpic_fdt_methods[] = { /* Device interface */ DEVMETHOD(device_probe, openpic_fdt_probe), - DEVMETHOD(device_attach, openpic_attach), + DEVMETHOD(device_attach, openpic_fdt_attach), /* PIC interface */ DEVMETHOD(pic_bind, openpic_bind), @@ -61,7 +61,6 @@ static device_method_t openpic_fdt_methods[] = { DEVMETHOD(pic_ipi, openpic_ipi), DEVMETHOD(pic_mask, openpic_mask), DEVMETHOD(pic_unmask, openpic_unmask), - DEVMETHOD(pic_id, openpic_fdt_id), { 0, 0 }, }; @@ -85,9 +84,9 @@ openpic_fdt_probe(device_t dev) return (BUS_PROBE_DEFAULT); } -static uint32_t -openpic_fdt_id(device_t dev) +static int +openpic_fdt_attach(device_t dev) { - return (ofw_bus_get_node(dev)); + return (openpic_common_attach(dev, ofw_bus_get_node(dev))); } diff --git a/sys/powerpc/mpc85xx/pci_fdt.c b/sys/powerpc/mpc85xx/pci_fdt.c index 9d67aae..7965167 100644 --- a/sys/powerpc/mpc85xx/pci_fdt.c +++ b/sys/powerpc/mpc85xx/pci_fdt.c @@ -136,7 +136,7 @@ static int fsl_pcib_decode_win(phandle_t, struct fsl_pcib_softc *); static void fsl_pcib_err_init(device_t); static void fsl_pcib_inbound(struct fsl_pcib_softc *, int, int, u_long, u_long, u_long); -static int fsl_pcib_init(struct fsl_pcib_softc *, int, int, int); +static int fsl_pcib_init(struct fsl_pcib_softc *, int, int); static int fsl_pcib_intr_info(phandle_t, struct fsl_pcib_softc *); static int fsl_pcib_set_range(struct fsl_pcib_softc *, int, int, u_long, u_long); @@ -160,8 +160,6 @@ static uint32_t fsl_pcib_read_config(device_t, u_int, u_int, u_int, u_int, int); static void fsl_pcib_write_config(device_t, u_int, u_int, u_int, u_int, uint32_t, int); -static int next_busnr = 0; - /* Configuration r/w mutex. */ struct mtx pcicfg_mtx; static int mtx_initialized = 0; @@ -215,23 +213,17 @@ DRIVER_MODULE(pcib, fdtbus, fsl_pcib_driver, pcib_devclass, 0, 0); static int fsl_pcib_probe(device_t dev) { - phandle_t parnode; + phandle_t node; - /* - * The PCI subnode does not have the 'compatible' property, so we need - * to check in the parent PCI node. However the parent is not - * represented by a separate ofw_bus child, and therefore - * ofw_bus_is_compatible() cannot be used, but direct fdt equivalent. - */ - parnode = OF_parent(ofw_bus_get_node(dev)); - if (parnode == 0) + node = ofw_bus_get_node(dev); + if (!fdt_is_type(node, "pci")) return (ENXIO); - if (!(fdt_is_compatible(parnode, "fsl,mpc8548-pcie") || - fdt_is_compatible(parnode, "fsl,mpc8548-pcie"))) + + if (!(fdt_is_compatible(node, "fsl,mpc8540-pci") || + fdt_is_compatible(node, "fsl,mpc8548-pcie"))) return (ENXIO); device_set_desc(dev, "Freescale Integrated PCI/PCI-E Controller"); - return (BUS_PROBE_DEFAULT); } @@ -241,7 +233,7 @@ fsl_pcib_attach(device_t dev) struct fsl_pcib_softc *sc; phandle_t node; uint32_t cfgreg; - int maxslot, subbus; + int maxslot; uint8_t ltssm, capptr; sc = device_get_softc(dev); @@ -304,23 +296,13 @@ fsl_pcib_attach(device_t dev) sc->sc_devfn_tundra = -1; sc->sc_devfn_via_ide = -1; - maxslot = (sc->sc_pcie) ? 1 : 31; /* - * Scan bus using firmware configured, 0 based bus numbering, - * let fsl_pcib_init() shift bus number by next_busnr offset. + * Scan bus using firmware configured, 0 based bus numbering. */ - sc->sc_busnr = 1; - subbus = fsl_pcib_init(sc, 0, next_busnr, maxslot); - - if (bootverbose) - printf("PCI: domain %d, busnr = %d, next_busnr = %d\n", - device_get_unit(dev), next_busnr + 1, - next_busnr + subbus + 1); - - /* Set final busnr */ - sc->sc_busnr = next_busnr + 1; - next_busnr += subbus + 1; + sc->sc_busnr = 0; + maxslot = (sc->sc_pcie) ? 0 : PCI_SLOTMAX; + fsl_pcib_init(sc, sc->sc_busnr, maxslot); if (sc->sc_pcie) { ltssm = fsl_pcib_cfgread(sc, 0, 0, 0, PCIR_LTSSM, 1); @@ -455,7 +437,7 @@ fsl_pcib_maxslots(device_t dev) { struct fsl_pcib_softc *sc = device_get_softc(dev); - return ((sc->sc_pcie) ? 1 : 31); + return ((sc->sc_pcie) ? 0 : PCI_SLOTMAX); } static uint32_t @@ -572,14 +554,11 @@ fsl_pcib_route_int(struct fsl_pcib_softc *sc, u_int bus, u_int slot, u_int func, devfn = DEVFN(bus, slot, func); if (devfn == sc->sc_devfn_via_ide) -#if 0 - intline = INTR_VEC(ATPIC_ID, 14); + intline = INTR_VEC(0, 14); else if (devfn == sc->sc_devfn_via_ide + 1) - intline = INTR_VEC(ATPIC_ID, 10); + intline = INTR_VEC(0, 10); else if (devfn == sc->sc_devfn_via_ide + 2) - intline = INTR_VEC(ATPIC_ID, 10); -#endif - ; + intline = INTR_VEC(0, 10); else { if (intpin != 0) err = fdt_pci_route_intr(bus, slot, func, intpin, @@ -596,10 +575,9 @@ fsl_pcib_route_int(struct fsl_pcib_softc *sc, u_int bus, u_int slot, u_int func, } static int -fsl_pcib_init(struct fsl_pcib_softc *sc, int bus, int busnr_offset, - int maxslot) +fsl_pcib_init(struct fsl_pcib_softc *sc, int bus, int maxslot) { - int secbus, subbus; + int secbus; int old_pribus, old_secbus, old_subbus; int new_pribus, new_secbus, new_subbus; int slot, func, maxfunc; @@ -608,11 +586,10 @@ fsl_pcib_init(struct fsl_pcib_softc *sc, int bus, int busnr_offset, uint8_t command, hdrtype, class, subclass; uint8_t intline, intpin; - subbus = bus; + secbus = bus; for (slot = 0; slot <= maxslot; slot++) { maxfunc = 0; for (func = 0; func <= maxfunc; func++) { - hdrtype = fsl_pcib_read_config(sc->sc_dev, bus, slot, func, PCIR_HDRTYPE, 1); @@ -667,19 +644,14 @@ fsl_pcib_init(struct fsl_pcib_softc *sc, int bus, int busnr_offset, func, PCIR_CLASS, 1); subclass = fsl_pcib_read_config(sc->sc_dev, bus, slot, func, PCIR_SUBCLASS, 1); -#if 0 + /* Allow only proper PCI-PCI briges */ if (class != PCIC_BRIDGE) continue; if (subclass != PCIS_BRIDGE_PCI) continue; -#endif - /* Allow all DEVTYPE 1 devices */ - if (hdrtype != PCIM_HDRTYPE_BRIDGE) - continue; - subbus++; - secbus = subbus; + secbus++; /* Program I/O decoder. */ fsl_pcib_write_config(sc->sc_dev, bus, slot, func, @@ -718,31 +690,20 @@ fsl_pcib_init(struct fsl_pcib_softc *sc, int bus, int busnr_offset, if (bootverbose) printf("PCI: reading firmware bus numbers for " "secbus = %d (bus/sec/sub) = (%d/%d/%d)\n", - secbus + busnr_offset, old_pribus, - old_secbus, old_subbus); + secbus, old_pribus, old_secbus, old_subbus); - /* Skip unconfigured devices */ - if ((old_pribus == 0) && - (old_secbus == 0) && (old_subbus == 0)) - continue; - - subbus += fsl_pcib_init(sc, secbus, busnr_offset, - (subclass == PCIS_BRIDGE_PCI) ? 31 : 1); + new_pribus = bus; + new_secbus = secbus; - new_pribus = bus + busnr_offset; - new_secbus = secbus + busnr_offset; - new_subbus = subbus + busnr_offset; + secbus = fsl_pcib_init(sc, secbus, + (subclass == PCIS_BRIDGE_PCI) ? PCI_SLOTMAX : 0); - /* Fixup pribus for MPC8572 PCIE controller */ - if ((vendor == 0x1957) && ((device = 0x0040) || - (device == 0x0041))) - new_pribus = 0; + new_subbus = secbus; if (bootverbose) - printf("PCI: translate firmware bus numbers for " - "secbus %d (%d/%d/%d) -> (%d/%d/%d)\n", - secbus + busnr_offset, - old_pribus, old_secbus, old_subbus, + printf("PCI: translate firmware bus numbers " + "for secbus %d (%d/%d/%d) -> (%d/%d/%d)\n", + secbus, old_pribus, old_secbus, old_subbus, new_pribus, new_secbus, new_subbus); fsl_pcib_write_config(sc->sc_dev, bus, slot, func, @@ -754,11 +715,7 @@ fsl_pcib_init(struct fsl_pcib_softc *sc, int bus, int busnr_offset, } } - if (bootverbose) - printf("PCI: bus %d, #subbus = %d\n", - bus + busnr_offset, subbus - bus); - - return (subbus - bus); + return (secbus); } static void @@ -938,12 +895,10 @@ fsl_pcib_alloc_resource(device_t dev, device_t child, int type, int *rid, va = sc->sc_iomem_va; break; case SYS_RES_IRQ: -#if 0 - if (INTR_IGN(start) == powerpc_ign_lookup(ATPIC_ID)) { + if (start < 16) { device_printf(dev, "%s requested ISA interrupt %lu\n", device_get_nameunit(child), start); } -#endif flags |= RF_SHAREABLE; return (BUS_ALLOC_RESOURCE(device_get_parent(dev), child, type, rid, start, end, count, flags)); diff --git a/sys/powerpc/powermac/cpcht.c b/sys/powerpc/powermac/cpcht.c index 4ee6aee..9359cd8 100644 --- a/sys/powerpc/powermac/cpcht.c +++ b/sys/powerpc/powermac/cpcht.c @@ -757,7 +757,6 @@ static void openpic_cpcht_config(device_t, u_int irq, static void openpic_cpcht_enable(device_t, u_int irq, u_int vector); static void openpic_cpcht_unmask(device_t, u_int irq); static void openpic_cpcht_eoi(device_t, u_int irq); -static uint32_t openpic_cpcht_id(device_t); static device_method_t openpic_cpcht_methods[] = { /* Device interface */ @@ -773,7 +772,6 @@ static device_method_t openpic_cpcht_methods[] = { DEVMETHOD(pic_ipi, openpic_ipi), DEVMETHOD(pic_mask, openpic_mask), DEVMETHOD(pic_unmask, openpic_cpcht_unmask), - DEVMETHOD(pic_id, openpic_cpcht_id), { 0, 0 }, }; @@ -808,9 +806,11 @@ static int openpic_cpcht_attach(device_t dev) { struct openpic_cpcht_softc *sc; + phandle_t node; int err, irq; - err = openpic_attach(dev); + node = ofw_bus_get_node(dev); + err = openpic_common_attach(dev, node); if (err != 0) return (err); @@ -839,9 +839,8 @@ openpic_cpcht_attach(device_t dev) * be necessary, but Linux does it, and I cannot find any U3 machines * with MSI devices to test. */ - if (dev == root_pic) - cpcht_msipic = PIC_ID(dev); + cpcht_msipic = node; return (0); } @@ -981,10 +980,3 @@ openpic_cpcht_eoi(device_t dev, u_int irq) openpic_eoi(dev, irq); } - -static uint32_t -openpic_cpcht_id(device_t dev) -{ - return (ofw_bus_get_node(dev)); -} - diff --git a/sys/powerpc/powermac/hrowpic.c b/sys/powerpc/powermac/hrowpic.c index 0e839d9..0142173 100644 --- a/sys/powerpc/powermac/hrowpic.c +++ b/sys/powerpc/powermac/hrowpic.c @@ -69,7 +69,6 @@ static void hrowpic_eoi(device_t, u_int); static void hrowpic_ipi(device_t, u_int); static void hrowpic_mask(device_t, u_int); static void hrowpic_unmask(device_t, u_int); -static uint32_t hrowpic_id(device_t dev); static device_method_t hrowpic_methods[] = { /* Device interface */ @@ -80,7 +79,6 @@ static device_method_t hrowpic_methods[] = { DEVMETHOD(pic_dispatch, hrowpic_dispatch), DEVMETHOD(pic_enable, hrowpic_enable), DEVMETHOD(pic_eoi, hrowpic_eoi), - DEVMETHOD(pic_id, hrowpic_id), DEVMETHOD(pic_ipi, hrowpic_ipi), DEVMETHOD(pic_mask, hrowpic_mask), DEVMETHOD(pic_unmask, hrowpic_unmask), @@ -169,9 +167,7 @@ hrowpic_attach(device_t dev) hrowpic_write_reg(sc, HPIC_ENABLE, HPIC_SECONDARY, 0); hrowpic_write_reg(sc, HPIC_CLEAR, HPIC_SECONDARY, 0xffffffff); - powerpc_register_pic(dev, 64); - root_pic = dev; /* Heathrow systems have only one PIC */ - + powerpc_register_pic(dev, ofw_bus_get_node(dev), 64, 0, FALSE); return (0); } @@ -282,10 +278,3 @@ hrowpic_unmask(device_t dev, u_int irq) sc = device_get_softc(dev); hrowpic_toggle_irq(sc, irq, 1); } - -static uint32_t -hrowpic_id(device_t dev) -{ - return (ofw_bus_get_node(dev)); -} - diff --git a/sys/powerpc/powermac/openpic_macio.c b/sys/powerpc/powermac/openpic_macio.c index 880b8f7..e542ae3 100644 --- a/sys/powerpc/powermac/openpic_macio.c +++ b/sys/powerpc/powermac/openpic_macio.c @@ -58,12 +58,12 @@ __FBSDID("$FreeBSD$"); * MacIO interface */ static int openpic_macio_probe(device_t); -static uint32_t openpic_macio_id(device_t); +static int openpic_macio_attach(device_t); static device_method_t openpic_macio_methods[] = { /* Device interface */ DEVMETHOD(device_probe, openpic_macio_probe), - DEVMETHOD(device_attach, openpic_attach), + DEVMETHOD(device_attach, openpic_macio_attach), /* PIC interface */ DEVMETHOD(pic_bind, openpic_bind), @@ -74,7 +74,6 @@ static device_method_t openpic_macio_methods[] = { DEVMETHOD(pic_ipi, openpic_ipi), DEVMETHOD(pic_mask, openpic_mask), DEVMETHOD(pic_unmask, openpic_unmask), - DEVMETHOD(pic_id, openpic_macio_id), { 0, 0 }, }; @@ -99,9 +98,9 @@ openpic_macio_probe(device_t dev) return (0); } -static uint32_t -openpic_macio_id(device_t dev) +static int +openpic_macio_attach(device_t dev) { - return (ofw_bus_get_node(dev)); + + return (openpic_common_attach(dev, ofw_bus_get_node(dev))); } - diff --git a/sys/powerpc/powerpc/intr_machdep.c b/sys/powerpc/powerpc/intr_machdep.c index a33bddb..b8b703d 100644 --- a/sys/powerpc/powerpc/intr_machdep.c +++ b/sys/powerpc/powerpc/intr_machdep.c @@ -60,6 +60,8 @@ * $FreeBSD$ */ +#include "opt_isa.h" + #include <sys/param.h> #include <sys/systm.h> #include <sys/kernel.h> @@ -102,9 +104,11 @@ struct powerpc_intr { }; struct pic { - device_t pic; - uint32_t pic_id; - int ipi_irq; + device_t dev; + uint32_t node; + u_int irqs; + u_int ipis; + int base; }; static u_int intrcnt_index = 0; @@ -113,6 +117,11 @@ static struct powerpc_intr *powerpc_intrs[INTR_VECTORS]; static struct pic piclist[MAX_PICS]; static u_int nvectors; /* Allocated vectors */ static u_int npics; /* PICs registered */ +#ifdef DEV_ISA +static u_int nirqs = 16; /* Allocated IRQS (ISA pre-allocated). */ +#else +static u_int nirqs = 0; /* Allocated IRQs. */ +#endif static u_int stray_count; device_t root_pic; @@ -142,7 +151,6 @@ smp_intr_init(void *dummy __unused) PIC_BIND(i->pic, i->intline, i->cpu); } } - SYSINIT(smp_intr_init, SI_SUB_SMP, SI_ORDER_ANY, smp_intr_init, NULL); #endif @@ -231,9 +239,21 @@ intr_lookup(u_int irq) static int powerpc_map_irq(struct powerpc_intr *i) { + struct pic *p; + u_int cnt; + int idx; - i->intline = INTR_INTLINE(i->irq); - i->pic = piclist[INTR_IGN(i->irq)].pic; + for (idx = 0; idx < npics; idx++) { + p = &piclist[idx]; + cnt = p->irqs + p->ipis; + if (i->irq >= p->base && i->irq < p->base + cnt) + break; + } + if (idx == npics) + return (EINVAL); + + i->intline = i->irq - p->base; + i->pic = p->dev; /* Try a best guess if that failed */ if (i->pic == NULL) @@ -288,46 +308,76 @@ powerpc_assign_intr_cpu(void *arg, u_char cpu) } void -powerpc_register_pic(device_t dev, u_int ipi) +powerpc_register_pic(device_t dev, uint32_t node, u_int irqs, u_int ipis, + u_int atpic) { - int i; + struct pic *p; + u_int irq; + int idx; mtx_lock(&intr_table_lock); - for (i = 0; i < npics; i++) { - if (piclist[i].pic_id == PIC_ID(dev)) + /* XXX see powerpc_get_irq(). */ + for (idx = 0; idx < npics; idx++) { + p = &piclist[idx]; + if (p->node != node) + continue; + if (node != 0 || p->dev == dev) break; } - piclist[i].pic = dev; - piclist[i].pic_id = PIC_ID(dev); - piclist[i].ipi_irq = ipi; - if (i == npics) + p = &piclist[idx]; + + p->dev = dev; + p->node = node; + p->irqs = irqs; + p->ipis = ipis; + if (idx == npics) { +#ifdef DEV_ISA + p->base = (atpic) ? 0 : nirqs; +#else + p->base = nirqs; +#endif + irq = p->base + irqs + ipis; + nirqs = MAX(nirqs, irq); npics++; + } mtx_unlock(&intr_table_lock); } -int -powerpc_ign_lookup(uint32_t pic_id) +u_int +powerpc_get_irq(uint32_t node, u_int pin) { - int i; + int idx; - mtx_lock(&intr_table_lock); + if (node == 0) + return (pin); - for (i = 0; i < npics; i++) { - if (piclist[i].pic_id == pic_id) { + mtx_lock(&intr_table_lock); + for (idx = 0; idx < npics; idx++) { + if (piclist[idx].node == node) { mtx_unlock(&intr_table_lock); - return (i); + return (piclist[idx].base + pin); } } - piclist[i].pic = NULL; - piclist[i].pic_id = pic_id; - piclist[i].ipi_irq = 0; + + /* + * XXX we should never encounter an unregistered PIC, but that + * can only be done when we properly support bus enumeration + * using multiple passes. Until then, fake an entry and give it + * some adhoc maximum number of IRQs and IPIs. + */ + piclist[idx].dev = NULL; + piclist[idx].node = node; + piclist[idx].irqs = 124; + piclist[idx].ipis = 4; + piclist[idx].base = nirqs; + nirqs += 128; npics++; mtx_unlock(&intr_table_lock); - return (i); + return (piclist[idx].base + pin); } int @@ -342,15 +392,18 @@ powerpc_enable_intr(void) if (npics == 0) panic("no PIC detected\n"); + if (root_pic == NULL) + root_pic = piclist[0].dev; + #ifdef SMP /* Install an IPI handler. */ - for (n = 0; n < npics; n++) { - if (piclist[n].pic != root_pic) + if (piclist[n].dev != root_pic) continue; + KASSERT(piclist[n].ipis != 0, ("%s", __func__)); error = powerpc_setup_intr("IPI", - INTR_VEC(piclist[n].pic_id, piclist[n].ipi_irq), + INTR_VEC(piclist[n].node, piclist[n].irqs), powerpc_ipi_handler, NULL, NULL, INTR_TYPE_MISC | INTR_EXCL, &ipi_cookie); if (error) { @@ -373,6 +426,9 @@ powerpc_enable_intr(void) i->pol != INTR_POLARITY_CONFORM) PIC_CONFIG(i->pic, i->intline, i->trig, i->pol); + if (i != NULL && i->pic == root_pic) + PIC_BIND(i->pic, i->intline, i->cpu); + if (i->event != NULL) PIC_ENABLE(i->pic, i->intline, vector); } diff --git a/sys/powerpc/powerpc/openpic.c b/sys/powerpc/powerpc/openpic.c index 7668f77..042f8b8 100644 --- a/sys/powerpc/powerpc/openpic.c +++ b/sys/powerpc/powerpc/openpic.c @@ -83,7 +83,7 @@ openpic_set_priority(struct openpic_softc *sc, int pri) } int -openpic_attach(device_t dev) +openpic_common_attach(device_t dev, uint32_t node) { struct openpic_softc *sc; u_int cpu, ipi, irq; @@ -217,7 +217,7 @@ openpic_attach(device_t dev) for (cpu = 0; cpu < sc->sc_ncpu; cpu++) openpic_write(sc, OPENPIC_PCPU_TPR(cpu), 0); - powerpc_register_pic(dev, sc->sc_nirq); + powerpc_register_pic(dev, node, sc->sc_nirq, 4, FALSE); /* If this is not a cascaded PIC, it must be the root PIC */ if (sc->sc_intr == NULL) @@ -285,7 +285,6 @@ openpic_dispatch(device_t dev, struct trapframe *tf) cpuid = (dev == root_pic) ? PCPU_GET(cpuid) : 0; sc = device_get_softc(dev); - while (1) { vector = openpic_read(sc, OPENPIC_PCPU_IACK(cpuid)); vector &= OPENPIC_VECTOR_MASK; diff --git a/sys/powerpc/powerpc/pic_if.m b/sys/powerpc/powerpc/pic_if.m index 04f1c1e..185cc08 100644 --- a/sys/powerpc/powerpc/pic_if.m +++ b/sys/powerpc/powerpc/pic_if.m @@ -66,10 +66,6 @@ METHOD void ipi { u_int cpu; }; -METHOD uint32_t id { - device_t dev; -}; - METHOD void mask { device_t dev; u_int irq; diff --git a/sys/powerpc/ps3/ps3pic.c b/sys/powerpc/ps3/ps3pic.c index 5d56d3e..c00585b 100644 --- a/sys/powerpc/ps3/ps3pic.c +++ b/sys/powerpc/ps3/ps3pic.c @@ -54,7 +54,6 @@ static void ps3pic_eoi(device_t, u_int); static void ps3pic_ipi(device_t, u_int); static void ps3pic_mask(device_t, u_int); static void ps3pic_unmask(device_t, u_int); -static uint32_t ps3pic_id(device_t dev); struct ps3pic_softc { uint64_t *bitmap_thread0; @@ -76,7 +75,6 @@ static device_method_t ps3pic_methods[] = { DEVMETHOD(pic_dispatch, ps3pic_dispatch), DEVMETHOD(pic_enable, ps3pic_enable), DEVMETHOD(pic_eoi, ps3pic_eoi), - DEVMETHOD(pic_id, ps3pic_id), DEVMETHOD(pic_ipi, ps3pic_ipi), DEVMETHOD(pic_mask, ps3pic_mask), DEVMETHOD(pic_unmask, ps3pic_unmask), @@ -146,9 +144,7 @@ ps3pic_attach(device_t dev) sc->sc_ipi_outlet[1], 0); #endif - powerpc_register_pic(dev, sc->sc_ipi_outlet[0]); - root_pic = dev; /* PS3s have only one PIC */ - + powerpc_register_pic(dev, 0, sc->sc_ipi_outlet[0], 1, FALSE); return (0); } @@ -245,10 +241,3 @@ ps3pic_unmask(device_t dev, u_int irq) lv1_did_update_interrupt_mask(ppe, 0); lv1_did_update_interrupt_mask(ppe, 1); } - -static uint32_t -ps3pic_id(device_t dev) -{ - return (0); -} - diff --git a/sys/powerpc/psim/openpic_iobus.c b/sys/powerpc/psim/openpic_iobus.c index 6522985..f2e7cdb 100644 --- a/sys/powerpc/psim/openpic_iobus.c +++ b/sys/powerpc/psim/openpic_iobus.c @@ -62,11 +62,12 @@ __FBSDID("$FreeBSD$"); * PSIM IOBus interface */ static int openpic_iobus_probe(device_t); +static int openpic_iobus_attach(device_t); static device_method_t openpic_iobus_methods[] = { /* Device interface */ DEVMETHOD(device_probe, openpic_iobus_probe), - DEVMETHOD(device_attach, openpic_attach), + DEVMETHOD(device_attach, openpic_iobus_attach), /* PIC interface */ DEVMETHOD(pic_config, openpic_config), @@ -109,3 +110,10 @@ openpic_iobus_probe(device_t dev) return (0); } + +static int +openpic_iobus_attach(device_t dev) +{ + + return (openpic_common_attach(dev, 0)); +} |