diff options
Diffstat (limited to 'sys/dev/pci/pci_pci.c')
-rw-r--r-- | sys/dev/pci/pci_pci.c | 509 |
1 files changed, 49 insertions, 460 deletions
diff --git a/sys/dev/pci/pci_pci.c b/sys/dev/pci/pci_pci.c index 35062d67050e..40ed5db4480e 100644 --- a/sys/dev/pci/pci_pci.c +++ b/sys/dev/pci/pci_pci.c @@ -58,19 +58,16 @@ #include "pcib_if.h" static int pcib_probe(device_t dev); -static int pcib_suspend(device_t dev); static int pcib_resume(device_t dev); static bus_child_present_t pcib_child_present; static bus_alloc_resource_t pcib_alloc_resource; -#ifdef NEW_PCIB static bus_adjust_resource_t pcib_adjust_resource; static bus_release_resource_t pcib_release_resource; static bus_activate_resource_t pcib_activate_resource; static bus_deactivate_resource_t pcib_deactivate_resource; static bus_map_resource_t pcib_map_resource; static bus_unmap_resource_t pcib_unmap_resource; -#endif static int pcib_reset_child(device_t dev, device_t child, int flags); static int pcib_power_for_sleep(device_t pcib, device_t dev, @@ -101,7 +98,7 @@ static device_method_t pcib_methods[] = { DEVMETHOD(device_attach, pcib_attach), DEVMETHOD(device_detach, pcib_detach), DEVMETHOD(device_shutdown, bus_generic_shutdown), - DEVMETHOD(device_suspend, pcib_suspend), + DEVMETHOD(device_suspend, bus_generic_suspend), DEVMETHOD(device_resume, pcib_resume), /* Bus interface */ @@ -109,19 +106,12 @@ static device_method_t pcib_methods[] = { DEVMETHOD(bus_read_ivar, pcib_read_ivar), DEVMETHOD(bus_write_ivar, pcib_write_ivar), DEVMETHOD(bus_alloc_resource, pcib_alloc_resource), -#ifdef NEW_PCIB DEVMETHOD(bus_adjust_resource, pcib_adjust_resource), DEVMETHOD(bus_release_resource, pcib_release_resource), DEVMETHOD(bus_activate_resource, pcib_activate_resource), DEVMETHOD(bus_deactivate_resource, pcib_deactivate_resource), DEVMETHOD(bus_map_resource, pcib_map_resource), DEVMETHOD(bus_unmap_resource, pcib_unmap_resource), -#else - DEVMETHOD(bus_adjust_resource, bus_generic_adjust_resource), - DEVMETHOD(bus_release_resource, bus_generic_release_resource), - DEVMETHOD(bus_activate_resource, bus_generic_activate_resource), - DEVMETHOD(bus_deactivate_resource, bus_generic_deactivate_resource), -#endif DEVMETHOD(bus_setup_intr, bus_generic_setup_intr), DEVMETHOD(bus_teardown_intr, bus_generic_teardown_intr), DEVMETHOD(bus_reset_child, pcib_reset_child), @@ -150,11 +140,8 @@ static device_method_t pcib_methods[] = { DEFINE_CLASS_0(pcib, pcib_driver, pcib_methods, sizeof(struct pcib_softc)); EARLY_DRIVER_MODULE(pcib, pci, pcib_driver, NULL, NULL, BUS_PASS_BUS); -#if defined(NEW_PCIB) || defined(PCI_HP) SYSCTL_DECL(_hw_pci); -#endif -#ifdef NEW_PCIB static int pci_clear_pcib; SYSCTL_INT(_hw_pci, OID_AUTO, clear_pcib, CTLFLAG_RDTUN, &pci_clear_pcib, 0, "Clear firmware-assigned resources for PCI-PCI bridge I/O windows."); @@ -191,10 +178,8 @@ static int pcib_is_resource_managed(struct pcib_softc *sc, struct resource *r) { -#ifdef PCI_RES_BUS if (rman_get_type(r) == PCI_RES_BUS) return (rman_is_region_manager(r, &sc->bus.rman)); -#endif return (pcib_get_resource_window(sc, r) != NULL); } @@ -618,7 +603,6 @@ pcib_free_windows(struct pcib_softc *sc) pcib_release_window(sc, &sc->io, SYS_RES_IOPORT); } -#ifdef PCI_RES_BUS /* * Allocate a suitable secondary bus for this bridge if needed and * initialize the resource manager for the secondary bus range. Note @@ -806,141 +790,6 @@ pcib_alloc_subbus(struct pcib_secbus *bus, device_t child, int *rid, flags)); return (NULL); } -#endif - -#else - -/* - * Is the prefetch window open (eg, can we allocate memory in it?) - */ -static int -pcib_is_prefetch_open(struct pcib_softc *sc) -{ - return (sc->pmembase > 0 && sc->pmembase < sc->pmemlimit); -} - -/* - * Is the nonprefetch window open (eg, can we allocate memory in it?) - */ -static int -pcib_is_nonprefetch_open(struct pcib_softc *sc) -{ - return (sc->membase > 0 && sc->membase < sc->memlimit); -} - -/* - * Is the io window open (eg, can we allocate ports in it?) - */ -static int -pcib_is_io_open(struct pcib_softc *sc) -{ - return (sc->iobase > 0 && sc->iobase < sc->iolimit); -} - -/* - * Get current I/O decode. - */ -static void -pcib_get_io_decode(struct pcib_softc *sc) -{ - device_t dev; - uint32_t iolow; - - dev = sc->dev; - - iolow = pci_read_config(dev, PCIR_IOBASEL_1, 1); - if ((iolow & PCIM_BRIO_MASK) == PCIM_BRIO_32) - sc->iobase = PCI_PPBIOBASE( - pci_read_config(dev, PCIR_IOBASEH_1, 2), iolow); - else - sc->iobase = PCI_PPBIOBASE(0, iolow); - - iolow = pci_read_config(dev, PCIR_IOLIMITL_1, 1); - if ((iolow & PCIM_BRIO_MASK) == PCIM_BRIO_32) - sc->iolimit = PCI_PPBIOLIMIT( - pci_read_config(dev, PCIR_IOLIMITH_1, 2), iolow); - else - sc->iolimit = PCI_PPBIOLIMIT(0, iolow); -} - -/* - * Get current memory decode. - */ -static void -pcib_get_mem_decode(struct pcib_softc *sc) -{ - device_t dev; - pci_addr_t pmemlow; - - dev = sc->dev; - - sc->membase = PCI_PPBMEMBASE(0, - pci_read_config(dev, PCIR_MEMBASE_1, 2)); - sc->memlimit = PCI_PPBMEMLIMIT(0, - pci_read_config(dev, PCIR_MEMLIMIT_1, 2)); - - pmemlow = pci_read_config(dev, PCIR_PMBASEL_1, 2); - if ((pmemlow & PCIM_BRPM_MASK) == PCIM_BRPM_64) - sc->pmembase = PCI_PPBMEMBASE( - pci_read_config(dev, PCIR_PMBASEH_1, 4), pmemlow); - else - sc->pmembase = PCI_PPBMEMBASE(0, pmemlow); - - pmemlow = pci_read_config(dev, PCIR_PMLIMITL_1, 2); - if ((pmemlow & PCIM_BRPM_MASK) == PCIM_BRPM_64) - sc->pmemlimit = PCI_PPBMEMLIMIT( - pci_read_config(dev, PCIR_PMLIMITH_1, 4), pmemlow); - else - sc->pmemlimit = PCI_PPBMEMLIMIT(0, pmemlow); -} - -/* - * Restore previous I/O decode. - */ -static void -pcib_set_io_decode(struct pcib_softc *sc) -{ - device_t dev; - uint32_t iohi; - - dev = sc->dev; - - iohi = sc->iobase >> 16; - if (iohi > 0) - pci_write_config(dev, PCIR_IOBASEH_1, iohi, 2); - pci_write_config(dev, PCIR_IOBASEL_1, sc->iobase >> 8, 1); - - iohi = sc->iolimit >> 16; - if (iohi > 0) - pci_write_config(dev, PCIR_IOLIMITH_1, iohi, 2); - pci_write_config(dev, PCIR_IOLIMITL_1, sc->iolimit >> 8, 1); -} - -/* - * Restore previous memory decode. - */ -static void -pcib_set_mem_decode(struct pcib_softc *sc) -{ - device_t dev; - pci_addr_t pmemhi; - - dev = sc->dev; - - pci_write_config(dev, PCIR_MEMBASE_1, sc->membase >> 16, 2); - pci_write_config(dev, PCIR_MEMLIMIT_1, sc->memlimit >> 16, 2); - - pmemhi = sc->pmembase >> 32; - if (pmemhi > 0) - pci_write_config(dev, PCIR_PMBASEH_1, pmemhi, 4); - pci_write_config(dev, PCIR_PMBASEL_1, sc->pmembase >> 16, 2); - - pmemhi = sc->pmemlimit >> 32; - if (pmemhi > 0) - pci_write_config(dev, PCIR_PMLIMITH_1, pmemhi, 4); - pci_write_config(dev, PCIR_PMLIMITL_1, sc->pmemlimit >> 16, 2); -} -#endif #ifdef PCI_HP /* @@ -951,7 +800,10 @@ SYSCTL_INT(_hw_pci, OID_AUTO, enable_pcie_hp, CTLFLAG_RDTUN, &pci_enable_pcie_hp, 0, "Enable support for native PCI-express HotPlug."); -TASKQUEUE_DEFINE_THREAD(pci_hp); +static sbintime_t pcie_hp_detach_timeout = 5 * SBT_1S; +SYSCTL_SBINTIME_MSEC(_hw_pci, OID_AUTO, pcie_hp_detach_timeout, CTLFLAG_RWTUN, + &pcie_hp_detach_timeout, + "Attention Button delay for PCI-express Eject."); static void pcib_probe_hotplug(struct pcib_softc *sc) @@ -1039,7 +891,7 @@ pcib_pcie_hotplug_command(struct pcib_softc *sc, uint16_t val, uint16_t mask) (ctl & new) & PCIEM_SLOT_CTL_CCIE) { sc->flags |= PCIB_HOTPLUG_CMD_PENDING; if (!cold) - taskqueue_enqueue_timeout(taskqueue_pci_hp, + taskqueue_enqueue_timeout(taskqueue_bus, &sc->pcie_cc_task, hz); } } @@ -1055,7 +907,7 @@ pcib_pcie_hotplug_command_completed(struct pcib_softc *sc) device_printf(dev, "Command Completed\n"); if (!(sc->flags & PCIB_HOTPLUG_CMD_PENDING)) return; - taskqueue_cancel_timeout(taskqueue_pci_hp, &sc->pcie_cc_task, NULL); + taskqueue_cancel_timeout(taskqueue_bus, &sc->pcie_cc_task, NULL); sc->flags &= ~PCIB_HOTPLUG_CMD_PENDING; wakeup(sc); } @@ -1078,7 +930,8 @@ pcib_hotplug_inserted(struct pcib_softc *sc) return (false); /* A power fault implicitly turns off power to the slot. */ - if (sc->pcie_slot_sta & PCIEM_SLOT_STA_PFD) + if (sc->pcie_slot_cap & PCIEM_SLOT_CAP_PCP && + sc->pcie_slot_sta & PCIEM_SLOT_STA_PFD) return (false); /* If the MRL is disengaged, the slot is powered off. */ @@ -1174,10 +1027,10 @@ pcib_pcie_hotplug_update(struct pcib_softc *sc, uint16_t val, uint16_t mask, device_printf(sc->dev, "Data Link Layer inactive\n"); else - taskqueue_enqueue_timeout(taskqueue_pci_hp, + taskqueue_enqueue_timeout(taskqueue_bus, &sc->pcie_dll_task, hz); } else if (sc->pcie_link_sta & PCIEM_LINK_STA_DL_ACTIVE) - taskqueue_cancel_timeout(taskqueue_pci_hp, &sc->pcie_dll_task, + taskqueue_cancel_timeout(taskqueue_bus, &sc->pcie_dll_task, NULL); pcib_pcie_hotplug_command(sc, val, mask); @@ -1189,7 +1042,7 @@ pcib_pcie_hotplug_update(struct pcib_softc *sc, uint16_t val, uint16_t mask, */ if (schedule_task && (pcib_hotplug_present(sc) != 0) != (sc->child != NULL)) - taskqueue_enqueue(taskqueue_pci_hp, &sc->pcie_hp_task); + taskqueue_enqueue(taskqueue_bus, &sc->pcie_hp_task); } static void @@ -1217,15 +1070,21 @@ pcib_pcie_intr_hotplug(void *arg) device_printf(dev, "Attention Button Pressed: Detach Cancelled\n"); sc->flags &= ~PCIB_DETACH_PENDING; - taskqueue_cancel_timeout(taskqueue_pci_hp, + taskqueue_cancel_timeout(taskqueue_bus, &sc->pcie_ab_task, NULL); } else if (old_slot_sta & PCIEM_SLOT_STA_PDS) { /* Only initiate detach sequence if device present. */ - device_printf(dev, - "Attention Button Pressed: Detaching in 5 seconds\n"); - sc->flags |= PCIB_DETACH_PENDING; - taskqueue_enqueue_timeout(taskqueue_pci_hp, - &sc->pcie_ab_task, 5 * hz); + if (pcie_hp_detach_timeout != 0) { + device_printf(dev, + "Attention Button Pressed: Detaching in %ld ms\n", + (long)(pcie_hp_detach_timeout / SBT_1MS)); + sc->flags |= PCIB_DETACH_PENDING; + taskqueue_enqueue_timeout_sbt(taskqueue_bus, + &sc->pcie_ab_task, pcie_hp_detach_timeout, + SBT_1S, 0); + } else { + sc->flags |= PCIB_DETACHING; + } } } if (sc->pcie_slot_sta & PCIEM_SLOT_STA_PFD) @@ -1264,8 +1123,8 @@ pcib_pcie_hotplug_task(void *context, int pending) dev = sc->dev; if (pcib_hotplug_present(sc) != 0) { if (sc->child == NULL) { - sc->child = device_add_child(dev, "pci", -1); - bus_generic_attach(dev); + sc->child = device_add_child(dev, "pci", DEVICE_UNIT_ANY); + bus_attach_children(dev); } } else { if (sc->child != NULL) { @@ -1422,11 +1281,11 @@ pcib_setup_hotplug(struct pcib_softc *sc) dev = sc->dev; TASK_INIT(&sc->pcie_hp_task, 0, pcib_pcie_hotplug_task, sc); - TIMEOUT_TASK_INIT(taskqueue_pci_hp, &sc->pcie_ab_task, 0, + TIMEOUT_TASK_INIT(taskqueue_bus, &sc->pcie_ab_task, 0, pcib_pcie_ab_timeout, sc); - TIMEOUT_TASK_INIT(taskqueue_pci_hp, &sc->pcie_cc_task, 0, + TIMEOUT_TASK_INIT(taskqueue_bus, &sc->pcie_cc_task, 0, pcib_pcie_cc_timeout, sc); - TIMEOUT_TASK_INIT(taskqueue_pci_hp, &sc->pcie_dll_task, 0, + TIMEOUT_TASK_INIT(taskqueue_bus, &sc->pcie_dll_task, 0, pcib_pcie_dll_timeout, sc); sc->pcie_hp_lock = bus_topo_mtx(); @@ -1439,6 +1298,7 @@ pcib_setup_hotplug(struct pcib_softc *sc) /* Clear any events previously pending. */ pcie_write_config(dev, PCIER_SLOT_STA, sc->pcie_slot_sta, 2); + sc->pcie_slot_sta = pcie_read_config(dev, PCIER_SLOT_STA, 2); /* Enable HotPlug events. */ mask = PCIEM_SLOT_CTL_DLLSCE | PCIEM_SLOT_CTL_HPIE | @@ -1472,13 +1332,13 @@ pcib_detach_hotplug(struct pcib_softc *sc) /* Disable the card in the slot and force it to detach. */ if (sc->flags & PCIB_DETACH_PENDING) { sc->flags &= ~PCIB_DETACH_PENDING; - taskqueue_cancel_timeout(taskqueue_pci_hp, &sc->pcie_ab_task, + taskqueue_cancel_timeout(taskqueue_bus, &sc->pcie_ab_task, NULL); } sc->flags |= PCIB_DETACHING; if (sc->flags & PCIB_HOTPLUG_CMD_PENDING) { - taskqueue_cancel_timeout(taskqueue_pci_hp, &sc->pcie_cc_task, + taskqueue_cancel_timeout(taskqueue_bus, &sc->pcie_cc_task, NULL); tsleep(sc, 0, "hpcmd", hz); sc->flags &= ~PCIB_HOTPLUG_CMD_PENDING; @@ -1501,53 +1361,21 @@ pcib_detach_hotplug(struct pcib_softc *sc) error = pcib_release_pcie_irq(sc); if (error) return (error); - taskqueue_drain(taskqueue_pci_hp, &sc->pcie_hp_task); - taskqueue_drain_timeout(taskqueue_pci_hp, &sc->pcie_ab_task); - taskqueue_drain_timeout(taskqueue_pci_hp, &sc->pcie_cc_task); - taskqueue_drain_timeout(taskqueue_pci_hp, &sc->pcie_dll_task); + taskqueue_drain(taskqueue_bus, &sc->pcie_hp_task); + taskqueue_drain_timeout(taskqueue_bus, &sc->pcie_ab_task); + taskqueue_drain_timeout(taskqueue_bus, &sc->pcie_cc_task); + taskqueue_drain_timeout(taskqueue_bus, &sc->pcie_dll_task); return (0); } #endif /* - * Get current bridge configuration. - */ -static void -pcib_cfg_save(struct pcib_softc *sc) -{ -#ifndef NEW_PCIB - device_t dev; - uint16_t command; - - dev = sc->dev; - - command = pci_read_config(dev, PCIR_COMMAND, 2); - if (command & PCIM_CMD_PORTEN) - pcib_get_io_decode(sc); - if (command & PCIM_CMD_MEMEN) - pcib_get_mem_decode(sc); -#endif -} - -/* * Restore previous bridge configuration. */ static void pcib_cfg_restore(struct pcib_softc *sc) { -#ifndef NEW_PCIB - uint16_t command; -#endif - -#ifdef NEW_PCIB pcib_write_windows(sc, WIN_IO | WIN_MEM | WIN_PMEM); -#else - command = pci_read_config(sc->dev, PCIR_COMMAND, 2); - if (command & PCIM_CMD_PORTEN) - pcib_set_io_decode(sc); - if (command & PCIM_CMD_MEMEN) - pcib_set_mem_decode(sc); -#endif } /* @@ -1579,12 +1407,7 @@ pcib_attach_common(device_t dev) * Get current bridge configuration. */ sc->domain = pci_get_domain(dev); -#if !(defined(NEW_PCIB) && defined(PCI_RES_BUS)) - sc->bus.sec = pci_read_config(dev, PCIR_SECBUS_1, 1); - sc->bus.sub = pci_read_config(dev, PCIR_SUBBUS_1, 1); -#endif sc->bridgectl = pci_read_config(dev, PCIR_BRIDGECTL_1, 2); - pcib_cfg_save(sc); /* * The primary bus register should always be the bus of the @@ -1611,20 +1434,6 @@ pcib_attach_common(device_t dev) * Quirk handling. */ switch (pci_get_devid(dev)) { -#if !(defined(NEW_PCIB) && defined(PCI_RES_BUS)) - case 0x12258086: /* Intel 82454KX/GX (Orion) */ - { - uint8_t supbus; - - supbus = pci_read_config(dev, 0x41, 1); - if (supbus != 0xff) { - sc->bus.sec = supbus + 1; - sc->bus.sub = supbus + 1; - } - break; - } -#endif - /* * The i82380FB mobile docking controller is a PCI-PCI bridge, * and it is a subtractive bridge. However, the ProgIf is wrong @@ -1637,34 +1446,6 @@ pcib_attach_common(device_t dev) case 0x060513d7: /* Toshiba ???? */ sc->flags |= PCIB_SUBTRACTIVE; break; - -#if !(defined(NEW_PCIB) && defined(PCI_RES_BUS)) - /* Compaq R3000 BIOS sets wrong subordinate bus number. */ - case 0x00dd10de: - { - char *cp; - - if ((cp = kern_getenv("smbios.planar.maker")) == NULL) - break; - if (strncmp(cp, "Compal", 6) != 0) { - freeenv(cp); - break; - } - freeenv(cp); - if ((cp = kern_getenv("smbios.planar.product")) == NULL) - break; - if (strncmp(cp, "08A0", 4) != 0) { - freeenv(cp); - break; - } - freeenv(cp); - if (sc->bus.sub < 0xa) { - pci_write_config(dev, PCIR_SUBBUS_1, 0xa, 1); - sc->bus.sub = pci_read_config(dev, PCIR_SUBBUS_1, 1); - } - break; - } -#endif } if (pci_msi_device_blacklisted(dev)) @@ -1688,12 +1469,8 @@ pcib_attach_common(device_t dev) #ifdef PCI_HP pcib_probe_hotplug(sc); #endif -#ifdef NEW_PCIB -#ifdef PCI_RES_BUS pcib_setup_secbus(dev, &sc->bus, 1); -#endif pcib_probe_windows(sc); -#endif #ifdef PCI_HP if (sc->flags & PCIB_HOTPLUG) pcib_setup_hotplug(sc); @@ -1702,7 +1479,6 @@ pcib_attach_common(device_t dev) device_printf(dev, " domain %d\n", sc->domain); device_printf(dev, " secondary bus %d\n", sc->bus.sec); device_printf(dev, " subordinate bus %d\n", sc->bus.sub); -#ifdef NEW_PCIB if (pcib_is_window_open(&sc->io)) device_printf(dev, " I/O decode 0x%jx-0x%jx\n", (uintmax_t)sc->io.base, (uintmax_t)sc->io.limit); @@ -1712,17 +1488,6 @@ pcib_attach_common(device_t dev) if (pcib_is_window_open(&sc->pmem)) device_printf(dev, " prefetched decode 0x%jx-0x%jx\n", (uintmax_t)sc->pmem.base, (uintmax_t)sc->pmem.limit); -#else - if (pcib_is_io_open(sc)) - device_printf(dev, " I/O decode 0x%x-0x%x\n", - sc->iobase, sc->iolimit); - if (pcib_is_nonprefetch_open(sc)) - device_printf(dev, " memory decode 0x%jx-0x%jx\n", - (uintmax_t)sc->membase, (uintmax_t)sc->memlimit); - if (pcib_is_prefetch_open(sc)) - device_printf(dev, " prefetched decode 0x%jx-0x%jx\n", - (uintmax_t)sc->pmembase, (uintmax_t)sc->pmemlimit); -#endif if (sc->bridgectl & (PCIB_BCR_ISA_ENABLE | PCIB_BCR_VGA_ENABLE) || sc->flags & PCIB_SUBTRACTIVE) { device_printf(dev, " special decode "); @@ -1778,8 +1543,9 @@ pcib_attach_child(device_t dev) } #endif - sc->child = device_add_child(dev, "pci", -1); - return (bus_generic_attach(dev)); + sc->child = device_add_child(dev, "pci", DEVICE_UNIT_ANY); + bus_attach_children(dev); + return (0); } int @@ -1793,15 +1559,11 @@ pcib_attach(device_t dev) int pcib_detach(device_t dev) { -#if defined(PCI_HP) || defined(NEW_PCIB) struct pcib_softc *sc; -#endif int error; -#if defined(PCI_HP) || defined(NEW_PCIB) sc = device_get_softc(dev); -#endif - error = bus_generic_detach(dev); + error = bus_detach_children(dev); if (error) return (error); #ifdef PCI_HP @@ -1814,24 +1576,12 @@ pcib_detach(device_t dev) error = device_delete_children(dev); if (error) return (error); -#ifdef NEW_PCIB pcib_free_windows(sc); -#ifdef PCI_RES_BUS pcib_free_secbus(dev, &sc->bus); -#endif -#endif return (0); } int -pcib_suspend(device_t dev) -{ - - pcib_cfg_save(device_get_softc(dev)); - return (bus_generic_suspend(dev)); -} - -int pcib_resume(device_t dev) { @@ -1905,7 +1655,6 @@ pcib_write_ivar(device_t dev, device_t child, int which, uintptr_t value) return(ENOENT); } -#ifdef NEW_PCIB /* * Attempt to allocate a resource from the existing resources assigned * to a window. @@ -2306,11 +2055,9 @@ pcib_alloc_resource(device_t dev, device_t child, int type, int *rid, } switch (type) { -#ifdef PCI_RES_BUS case PCI_RES_BUS: return (pcib_alloc_subbus(&sc->bus, child, rid, start, end, count, flags)); -#endif case SYS_RES_IOPORT: if (pcib_is_isa_range(sc, start, end, count)) return (NULL); @@ -2390,7 +2137,6 @@ pcib_adjust_resource(device_t bus, device_t child, struct resource *r, if (!pcib_is_resource_managed(sc, r)) return (bus_generic_adjust_resource(bus, child, r, start, end)); -#ifdef PCI_RES_BUS if (type == PCI_RES_BUS) { /* * If our bus range isn't big enough to grow the sub-allocation @@ -2404,9 +2150,7 @@ pcib_adjust_resource(device_t bus, device_t child, struct resource *r, if (error != 0) return (error); } - } else -#endif - { + } else { /* * Resource is managed and not a secondary bus number, must * be from one of our windows. @@ -2549,7 +2293,7 @@ pcib_map_resource(device_t dev, device_t child, struct resource *r, args.offset = start - rman_get_start(pres); args.length = length; - return (bus_generic_map_resource(dev, child, pres, &args, map)); + return (bus_map_resource(dev, pres, &args, map)); } static int @@ -2558,172 +2302,17 @@ pcib_unmap_resource(device_t dev, device_t child, struct resource *r, { struct pcib_softc *sc = device_get_softc(dev); struct pcib_window *w; + struct resource *pres; w = pcib_get_resource_window(sc, r); - if (w != NULL) { - r = pcib_find_parent_resource(w, r); - if (r == NULL) - return (ENOENT); - } - return (bus_generic_unmap_resource(dev, child, r, map)); -} -#else -/* - * We have to trap resource allocation requests and ensure that the bridge - * is set up to, or capable of handling them. - */ -static struct resource * -pcib_alloc_resource(device_t dev, device_t child, int type, int *rid, - rman_res_t start, rman_res_t end, rman_res_t count, u_int flags) -{ - struct pcib_softc *sc = device_get_softc(dev); - const char *name, *suffix; - int ok; - - /* - * Fail the allocation for this range if it's not supported. - */ - name = device_get_nameunit(child); - if (name == NULL) { - name = ""; - suffix = ""; - } else - suffix = " "; - switch (type) { - case SYS_RES_IOPORT: - ok = 0; - if (!pcib_is_io_open(sc)) - break; - ok = (start >= sc->iobase && end <= sc->iolimit); - - /* - * Make sure we allow access to VGA I/O addresses when the - * bridge has the "VGA Enable" bit set. - */ - if (!ok && pci_is_vga_ioport_range(start, end)) - ok = (sc->bridgectl & PCIB_BCR_VGA_ENABLE) ? 1 : 0; - - if ((sc->flags & PCIB_SUBTRACTIVE) == 0) { - if (!ok) { - if (start < sc->iobase) - start = sc->iobase; - if (end > sc->iolimit) - end = sc->iolimit; - if (start < end) - ok = 1; - } - } else { - ok = 1; -#if 0 - /* - * If we overlap with the subtractive range, then - * pick the upper range to use. - */ - if (start < sc->iolimit && end > sc->iobase) - start = sc->iolimit + 1; -#endif - } - if (end < start) { - device_printf(dev, "ioport: end (%jx) < start (%jx)\n", - end, start); - start = 0; - end = 0; - ok = 0; - } - if (!ok) { - device_printf(dev, "%s%srequested unsupported I/O " - "range 0x%jx-0x%jx (decoding 0x%x-0x%x)\n", - name, suffix, start, end, sc->iobase, sc->iolimit); - return (NULL); - } - if (bootverbose) - device_printf(dev, - "%s%srequested I/O range 0x%jx-0x%jx: in range\n", - name, suffix, start, end); - break; - - case SYS_RES_MEMORY: - ok = 0; - if (pcib_is_nonprefetch_open(sc)) - ok = ok || (start >= sc->membase && end <= sc->memlimit); - if (pcib_is_prefetch_open(sc)) - ok = ok || (start >= sc->pmembase && end <= sc->pmemlimit); - - /* - * Make sure we allow access to VGA memory addresses when the - * bridge has the "VGA Enable" bit set. - */ - if (!ok && pci_is_vga_memory_range(start, end)) - ok = (sc->bridgectl & PCIB_BCR_VGA_ENABLE) ? 1 : 0; - - if ((sc->flags & PCIB_SUBTRACTIVE) == 0) { - if (!ok) { - ok = 1; - if (flags & RF_PREFETCHABLE) { - if (pcib_is_prefetch_open(sc)) { - if (start < sc->pmembase) - start = sc->pmembase; - if (end > sc->pmemlimit) - end = sc->pmemlimit; - } else { - ok = 0; - } - } else { /* non-prefetchable */ - if (pcib_is_nonprefetch_open(sc)) { - if (start < sc->membase) - start = sc->membase; - if (end > sc->memlimit) - end = sc->memlimit; - } else { - ok = 0; - } - } - } - } else if (!ok) { - ok = 1; /* subtractive bridge: always ok */ -#if 0 - if (pcib_is_nonprefetch_open(sc)) { - if (start < sc->memlimit && end > sc->membase) - start = sc->memlimit + 1; - } - if (pcib_is_prefetch_open(sc)) { - if (start < sc->pmemlimit && end > sc->pmembase) - start = sc->pmemlimit + 1; - } -#endif - } - if (end < start) { - device_printf(dev, "memory: end (%jx) < start (%jx)\n", - end, start); - start = 0; - end = 0; - ok = 0; - } - if (!ok && bootverbose) - device_printf(dev, - "%s%srequested unsupported memory range %#jx-%#jx " - "(decoding %#jx-%#jx, %#jx-%#jx)\n", - name, suffix, start, end, - (uintmax_t)sc->membase, (uintmax_t)sc->memlimit, - (uintmax_t)sc->pmembase, (uintmax_t)sc->pmemlimit); - if (!ok) - return (NULL); - if (bootverbose) - device_printf(dev,"%s%srequested memory range " - "0x%jx-0x%jx: good\n", - name, suffix, start, end); - break; + if (w == NULL) + return (bus_generic_unmap_resource(dev, child, r, map)); - default: - break; - } - /* - * Bridge is OK decoding this resource, so pass it up. - */ - return (bus_generic_alloc_resource(dev, child, type, rid, start, end, - count, flags)); + pres = pcib_find_parent_resource(w, r); + if (pres == NULL) + return (ENOENT); + return (bus_unmap_resource(dev, pres, map)); } -#endif /* * If ARI is enabled on this downstream port, translate the function number |