diff options
author | imp <imp@FreeBSD.org> | 2004-04-23 05:25:13 +0000 |
---|---|---|
committer | imp <imp@FreeBSD.org> | 2004-04-23 05:25:13 +0000 |
commit | 800bba64fe69c02c7b292d0d136953ef3749cdc8 (patch) | |
tree | f5b1357f133ca320a4d82af82e8e7bdeb87c1813 /sys/dev/pccbb | |
parent | c8457a17a5edc36efcd781535b1388be1a70b0a2 (diff) | |
download | FreeBSD-src-800bba64fe69c02c7b292d0d136953ef3749cdc8.zip FreeBSD-src-800bba64fe69c02c7b292d0d136953ef3749cdc8.tar.gz |
Start programming the bus numbers for the pci<->cardbus. When the
secondary bus is 0, we program the primary bus, the secondary bus and
the suborindate bus. This isn't ideal, since we start at parent_bus +
1 and store this in a static.
Ideally, we'd walk the tree and assign bus numbers. However, that's
harder to accomplish without some help from the bus layer which we're
not planning on doing that until 6.
This fixes my CardBus problems on my Sony PCG-Z1WA, and might fix the
Dells that have had problems.
Diffstat (limited to 'sys/dev/pccbb')
-rw-r--r-- | sys/dev/pccbb/pccbb.c | 31 |
1 files changed, 30 insertions, 1 deletions
diff --git a/sys/dev/pccbb/pccbb.c b/sys/dev/pccbb/pccbb.c index 9d690bb..527cef9 100644 --- a/sys/dev/pccbb/pccbb.c +++ b/sys/dev/pccbb/pccbb.c @@ -683,9 +683,12 @@ cbb_print_config(device_t dev) static int cbb_attach(device_t brdev) { + static int curr_bus_number = 1; /* XXX EVILE BAD (see below) */ struct cbb_softc *sc = (struct cbb_softc *)device_get_softc(brdev); - int rid; + int rid, bus, pribus; + device_t parent; + parent = device_get_parent(brdev); mtx_init(&sc->mtx, device_get_nameunit(brdev), "cbb", MTX_DEF); cv_init(&sc->cv, "cbb cv"); sc->chipset = cbb_chipset(pci_get_devid(brdev), NULL); @@ -759,6 +762,32 @@ cbb_attach(device_t brdev) sc->exca.chipset = EXCA_CARDBUS; cbb_chipinit(sc); + /* + * This is a gross hack. We should be scanning the entire pci + * tree, assigning bus numbers in a way such that we (1) can + * reserve 1 extra bus just in case and (2) all sub busses + * are in an appropriate range. + */ + bus = pci_read_config(brdev, PCIR_SECBUS_2, 1); + pribus = pcib_get_bus(parent); + DEVPRINTF((brdev, "Secondary bus is %d\n", bus)); + if (bus == 0) { + if (curr_bus_number < pribus) + curr_bus_number = pribus + 1; + if (pci_read_config(brdev, PCIR_PRIBUS_2, 1) != pribus) { + DEVPRINTF((brdev, "Setting primary bus to %d\n", pribus)); + pci_write_config(brdev, PCIR_PRIBUS_2, pribus, 1); + } + bus = curr_bus_number; + DEVPRINTF((brdev, "Secondary bus set to %d subbus %d\n", bus, + bus + 1)); + sc->secbus = bus; + sc->subbus = bus + 1; + pci_write_config(brdev, PCIR_SECBUS_2, bus, 1); + pci_write_config(brdev, PCIR_SUBBUS_2, bus + 1, 1); + curr_bus_number += 2; + } + /* attach children */ sc->cbdev = device_add_child(brdev, "cardbus", -1); if (sc->cbdev == NULL) |