static int gem_pci_attach(device_t dev) { struct gem_softc *sc; int i; #if defined(__powerpc__) || defined(__sparc64__) char buf[sizeof(GEM_SHARED_PINS)]; #else int j; #endif sc = device_get_softc(dev); sc->sc_variant = GEM_UNKNOWN; for (i = 0; gem_pci_devlist[i].gpd_desc != NULL; i++) { if (pci_get_devid(dev) == gem_pci_devlist[i].gpd_devid) { sc->sc_variant = gem_pci_devlist[i].gpd_variant; break; } } if (sc->sc_variant == GEM_UNKNOWN) { device_printf(dev, "unknown adaptor\n"); return (ENXIO); } pci_enable_busmaster(dev); /* * Some Sun GEMs/ERIs do have their intpin register bogusly set to 0, * although it should be 1. Correct that. */ if (pci_get_intpin(dev) == 0) pci_set_intpin(dev, 1); /* Set the PCI latency timer for Sun ERIs. */ if (sc->sc_variant == GEM_SUN_ERI) pci_write_config(dev, PCIR_LATTIMER, GEM_ERI_LATENCY_TIMER, 1); sc->sc_dev = dev; sc->sc_flags |= GEM_PCI; if (bus_alloc_resources(dev, gem_pci_res_spec, sc->sc_res)) { device_printf(dev, "failed to allocate resources\n"); bus_release_resources(dev, gem_pci_res_spec, sc->sc_res); return (ENXIO); } GEM_LOCK_INIT(sc, device_get_nameunit(dev)); /* * Derive GEM_RES_BANK2 from GEM_RES_BANK1. This seemed cleaner * with the old way of using copies of the bus tag and handle in * the softc along with bus_space_*()... */ sc->sc_res[GEM_RES_BANK2] = malloc(sizeof(*sc->sc_res[GEM_RES_BANK2]), M_DEVBUF, M_NOWAIT | M_ZERO); if (sc->sc_res[GEM_RES_BANK2] == NULL) { device_printf(dev, "failed to allocate bank2 resource\n"); goto fail; } rman_set_bustag(sc->sc_res[GEM_RES_BANK2], rman_get_bustag(sc->sc_res[GEM_RES_BANK1])); bus_space_subregion(rman_get_bustag(sc->sc_res[GEM_RES_BANK1]), rman_get_bushandle(sc->sc_res[GEM_RES_BANK1]), GEM_PCI_BANK2_OFFSET, GEM_PCI_BANK2_SIZE, &sc->sc_res[GEM_RES_BANK2]->r_bushandle); /* Determine whether we're running at 66MHz. */ if ((GEM_BANK2_READ_4(sc, GEM_PCI_BIF_CONFIG) & GEM_PCI_BIF_CNF_M66EN) != 0) sc->sc_flags |= GEM_PCI66; #if defined(__powerpc__) || defined(__sparc64__) OF_getetheraddr(dev, sc->sc_enaddr); if (OF_getprop(ofw_bus_get_node(dev), GEM_SHARED_PINS, buf, sizeof(buf)) > 0) { buf[sizeof(buf) - 1] = '\0'; if (strcmp(buf, GEM_SHARED_PINS_SERDES) == 0) sc->sc_flags |= GEM_SERDES; } #else /* * Dig out VPD (vital product data) and read NA (network address). * The VPD resides in the PCI Expansion ROM (PCI FCode) and can't * be accessed via the PCI capability pointer. * ``Writing FCode 3.x Programs'' (newer ones, dated 1997 and later) * chapter 2 describes the data structure. */ #define PCI_ROMHDR_SIZE 0x1c #define PCI_ROMHDR_SIG 0x00 #define PCI_ROMHDR_SIG_MAGIC 0xaa55 /* little endian */ #define PCI_ROMHDR_PTR_DATA 0x18 #define PCI_ROM_SIZE 0x18 #define PCI_ROM_SIG 0x00 #define PCI_ROM_SIG_MAGIC 0x52494350 /* "PCIR", endian */ /* reversed */ #define PCI_ROM_VENDOR 0x04 #define PCI_ROM_DEVICE 0x06 #define PCI_ROM_PTR_VPD 0x08 #define PCI_VPDRES_BYTE0 0x00 #define PCI_VPDRES_ISLARGE(x) ((x) & 0x80) #define PCI_VPDRES_LARGE_NAME(x) ((x) & 0x7f) #define PCI_VPDRES_LARGE_LEN_LSB 0x01 #define PCI_VPDRES_LARGE_LEN_MSB 0x02 #define PCI_VPDRES_LARGE_SIZE 0x03 #define PCI_VPDRES_TYPE_VPD 0x10 /* large */ #define PCI_VPD_KEY0 0x00 #define PCI_VPD_KEY1 0x01 #define PCI_VPD_LEN 0x02 #define PCI_VPD_SIZE 0x03 #define GEM_ROM_READ_1(sc, offs) \ GEM_BANK1_READ_1((sc), GEM_PCI_ROM_OFFSET + (offs)) #define GEM_ROM_READ_2(sc, offs) \ GEM_BANK1_READ_2((sc), GEM_PCI_ROM_OFFSET + (offs)) #define GEM_ROM_READ_4(sc, offs) \ GEM_BANK1_READ_4((sc), GEM_PCI_ROM_OFFSET + (offs)) /* Read PCI Expansion ROM header. */ if (GEM_ROM_READ_2(sc, PCI_ROMHDR_SIG) != PCI_ROMHDR_SIG_MAGIC || (i = GEM_ROM_READ_2(sc, PCI_ROMHDR_PTR_DATA)) < PCI_ROMHDR_SIZE) { device_printf(dev, "unexpected PCI Expansion ROM header\n"); goto fail; } /* Read PCI Expansion ROM data. */ if (GEM_ROM_READ_4(sc, i + PCI_ROM_SIG) != PCI_ROM_SIG_MAGIC || GEM_ROM_READ_2(sc, i + PCI_ROM_VENDOR) != pci_get_vendor(dev) || GEM_ROM_READ_2(sc, i + PCI_ROM_DEVICE) != pci_get_device(dev) || (j = GEM_ROM_READ_2(sc, i + PCI_ROM_PTR_VPD)) < i + PCI_ROM_SIZE) { device_printf(dev, "unexpected PCI Expansion ROM data\n"); goto fail; } /* * Read PCI VPD. * SUNW,pci-gem cards have a single large resource VPD-R tag * containing one NA. The VPD used is not in PCI 2.2 standard * format however. The length in the resource header is in big * endian and the end tag is non-standard (0x79) and followed * by an all-zero "checksum" byte. Sun calls this a "Fresh * Choice Ethernet" VPD... */ if (PCI_VPDRES_ISLARGE(GEM_ROM_READ_1(sc, j + PCI_VPDRES_BYTE0)) == 0 || PCI_VPDRES_LARGE_NAME(GEM_ROM_READ_1(sc, j + PCI_VPDRES_BYTE0)) != PCI_VPDRES_TYPE_VPD || ((GEM_ROM_READ_1(sc, j + PCI_VPDRES_LARGE_LEN_LSB) << 8) | GEM_ROM_READ_1(sc, j + PCI_VPDRES_LARGE_LEN_MSB)) != PCI_VPD_SIZE + ETHER_ADDR_LEN || GEM_ROM_READ_1(sc, j + PCI_VPDRES_LARGE_SIZE + PCI_VPD_KEY0) != 0x4e /* N */ || GEM_ROM_READ_1(sc, j + PCI_VPDRES_LARGE_SIZE + PCI_VPD_KEY1) != 0x41 /* A */ || GEM_ROM_READ_1(sc, j + PCI_VPDRES_LARGE_SIZE + PCI_VPD_LEN) != ETHER_ADDR_LEN || GEM_ROM_READ_1(sc, j + PCI_VPDRES_LARGE_SIZE + PCI_VPD_SIZE + ETHER_ADDR_LEN) != 0x79) { device_printf(dev, "unexpected PCI VPD\n"); goto fail; } bus_read_region_1(sc->sc_res[GEM_RES_BANK1], GEM_PCI_ROM_OFFSET + j + PCI_VPDRES_LARGE_SIZE + PCI_VPD_SIZE, sc->sc_enaddr, ETHER_ADDR_LEN); #endif /* * The Xserve G5 has a fake GMAC with an all-zero MAC address. * Check for this, and don't attach in this case. */ for (i = 0; i < ETHER_ADDR_LEN && sc->sc_enaddr[i] == 0; i++) {} if (i == ETHER_ADDR_LEN) { device_printf(dev, "invalid MAC address\n"); goto fail; } if (gem_attach(sc) != 0) { device_printf(dev, "could not be attached\n"); goto fail; } if (bus_setup_intr(dev, sc->sc_res[GEM_RES_INTR], INTR_TYPE_NET | INTR_MPSAFE, NULL, gem_intr, sc, &sc->sc_ih) != 0) { device_printf(dev, "failed to set up interrupt\n"); gem_detach(sc); goto fail; } return (0); fail: if (sc->sc_res[GEM_RES_BANK2] != NULL) free(sc->sc_res[GEM_RES_BANK2], M_DEVBUF); GEM_LOCK_DESTROY(sc); bus_release_resources(dev, gem_pci_res_spec, sc->sc_res); return (ENXIO); }
static int mpt_pci_probe(device_t dev) { const char *desc; if (pci_get_vendor(dev) != MPI_MANUFACTPAGE_VENDORID_LSILOGIC) return (ENXIO); switch (pci_get_device(dev)) { case MPI_MANUFACTPAGE_DEVICEID_FC909_FB: desc = "LSILogic FC909 FC Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC909: desc = "LSILogic FC909A FC Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC919: desc = "LSILogic FC919 FC Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC919_LAN_FB: desc = "LSILogic FC919 LAN Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC929: desc = "Dual LSILogic FC929 FC Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC929_LAN_FB: desc = "Dual LSILogic FC929 LAN Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC919X: desc = "LSILogic FC919 FC PCI-X Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC919X_LAN_FB: desc = "LSILogic FC919 LAN PCI-X Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC929X: desc = "Dual LSILogic FC929X 2Gb/s FC PCI-X Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC929X_LAN_FB: desc = "Dual LSILogic FC929X LAN PCI-X Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC949E: desc = "Dual LSILogic FC7X04X 4Gb/s FC PCI-Express Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC949X: desc = "Dual LSILogic FC7X04X 4Gb/s FC PCI-X Adapter"; break; case MPI_MANUFACTPAGE_DEVID_53C1030: case MPI_MANUFACTPAGE_DEVID_53C1030ZC: desc = "LSILogic 1030 Ultra4 Adapter"; break; case MPI_MANUFACTPAGE_DEVID_SAS1064: case MPI_MANUFACTPAGE_DEVID_SAS1064A: case MPI_MANUFACTPAGE_DEVID_SAS1064E: case MPI_MANUFACTPAGE_DEVID_SAS1066: case MPI_MANUFACTPAGE_DEVID_SAS1066E: case MPI_MANUFACTPAGE_DEVID_SAS1068: case MPI_MANUFACTPAGE_DEVID_SAS1068A_FB: case MPI_MANUFACTPAGE_DEVID_SAS1068E: case MPI_MANUFACTPAGE_DEVID_SAS1078: case MPI_MANUFACTPAGE_DEVID_SAS1078DE_FB: desc = "LSILogic SAS/SATA Adapter"; break; default: return (ENXIO); } device_set_desc(dev, desc); return (0); }
static int iir_pci_attach(device_t dev) { struct gdt_softc *gdt; struct resource *io = NULL, *irq = NULL; int retries, rid, error = 0; void *ih; u_int8_t protocol; /* map DPMEM */ rid = PCI_DPMEM; io = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid, RF_ACTIVE); if (io == NULL) { device_printf(dev, "can't allocate register resources\n"); error = ENOMEM; goto err; } /* get IRQ */ rid = 0; irq = bus_alloc_resource_any(dev, SYS_RES_IRQ, &rid, RF_ACTIVE | RF_SHAREABLE); if (irq == NULL) { device_printf(dev, "can't find IRQ value\n"); error = ENOMEM; goto err; } gdt = device_get_softc(dev); gdt->sc_init_level = 0; gdt->sc_dpmemt = rman_get_bustag(io); gdt->sc_dpmemh = rman_get_bushandle(io); gdt->sc_dpmembase = rman_get_start(io); gdt->sc_hanum = device_get_unit(dev); gdt->sc_bus = pci_get_bus(dev); gdt->sc_slot = pci_get_slot(dev); gdt->sc_vendor = pci_get_vendor(dev); gdt->sc_device = pci_get_device(dev); gdt->sc_subdevice = pci_get_subdevice(dev); gdt->sc_class = GDT_MPR; /* no FC ctr. if (gdt->sc_device >= GDT_PCI_PRODUCT_FC) gdt->sc_class |= GDT_FC; */ /* initialize RP controller */ /* check and reset interface area */ bus_space_write_4(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC, htole32(GDT_MPR_MAGIC)); if (bus_space_read_4(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC) != htole32(GDT_MPR_MAGIC)) { kprintf("cannot access DPMEM at 0x%jx (shadowed?)\n", (uintmax_t)gdt->sc_dpmembase); error = ENXIO; goto err; } bus_space_set_region_4(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_I960_SZ, htole32(0), GDT_MPR_SZ >> 2); /* Disable everything */ bus_space_write_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_EDOOR_EN, bus_space_read_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_EDOOR_EN) | 4); bus_space_write_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_EDOOR, 0xff); bus_space_write_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_STATUS, 0); bus_space_write_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_CMD_INDEX, 0); bus_space_write_4(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_INFO, htole32(gdt->sc_dpmembase)); bus_space_write_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_CMD_INDX, 0xff); bus_space_write_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_LDOOR, 1); DELAY(20); retries = GDT_RETRIES; while (bus_space_read_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_STATUS) != 0xff) { if (--retries == 0) { kprintf("DEINIT failed\n"); error = ENXIO; goto err; } DELAY(1); } protocol = (uint8_t)le32toh(bus_space_read_4(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_INFO)); bus_space_write_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_STATUS, 0); if (protocol != GDT_PROTOCOL_VERSION) { kprintf("unsupported protocol %d\n", protocol); error = ENXIO; goto err; } /* special commnd to controller BIOS */ bus_space_write_4(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_INFO, htole32(0)); bus_space_write_4(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_INFO + sizeof (u_int32_t), htole32(0)); bus_space_write_4(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_INFO + 2 * sizeof (u_int32_t), htole32(1)); bus_space_write_4(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_INFO + 3 * sizeof (u_int32_t), htole32(0)); bus_space_write_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_CMD_INDX, 0xfe); bus_space_write_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_LDOOR, 1); DELAY(20); retries = GDT_RETRIES; while (bus_space_read_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_STATUS) != 0xfe) { if (--retries == 0) { kprintf("initialization error\n"); error = ENXIO; goto err; } DELAY(1); } bus_space_write_1(gdt->sc_dpmemt, gdt->sc_dpmemh, GDT_MPR_IC + GDT_S_STATUS, 0); gdt->sc_ic_all_size = GDT_MPR_SZ; gdt->sc_copy_cmd = gdt_mpr_copy_cmd; gdt->sc_get_status = gdt_mpr_get_status; gdt->sc_intr = gdt_mpr_intr; gdt->sc_release_event = gdt_mpr_release_event; gdt->sc_set_sema0 = gdt_mpr_set_sema0; gdt->sc_test_busy = gdt_mpr_test_busy; /* Allocate a dmatag representing the capabilities of this attachment */ /* XXX Should be a child of the PCI bus dma tag */ if (bus_dma_tag_create(/*parent*/NULL, /*alignemnt*/1, /*boundary*/0, /*lowaddr*/BUS_SPACE_MAXADDR_32BIT, /*highaddr*/BUS_SPACE_MAXADDR, /*filter*/NULL, /*filterarg*/NULL, /*maxsize*/BUS_SPACE_MAXSIZE_32BIT, /*nsegments*/GDT_MAXSG, /*maxsegsz*/BUS_SPACE_MAXSIZE_32BIT, /*flags*/0, &gdt->sc_parent_dmat) != 0) { error = ENXIO; goto err; } gdt->sc_init_level++; if (iir_init(gdt) != 0) { iir_free(gdt); error = ENXIO; goto err; } /* Register with the XPT */ iir_attach(gdt); /* associate interrupt handler */ error = bus_setup_intr(dev, irq, 0, iir_intr, gdt, &ih, NULL); if (error) { device_printf(dev, "Unable to register interrupt handler\n"); error = ENXIO; goto err; } gdt_pci_enable_intr(gdt); return (0); err: if (irq) bus_release_resource( dev, SYS_RES_IRQ, 0, irq ); /* if (io) bus_release_resource( dev, SYS_RES_MEMORY, rid, io ); */ return (error); }
static int sfxge_create(struct sfxge_softc *sc) { device_t dev; efx_nic_t *enp; int error; dev = sc->dev; sx_init(&sc->softc_lock, "sfxge_softc"); sc->stats_node = SYSCTL_ADD_NODE( device_get_sysctl_ctx(dev), SYSCTL_CHILDREN(device_get_sysctl_tree(dev)), OID_AUTO, "stats", CTLFLAG_RD, NULL, "Statistics"); if (!sc->stats_node) { error = ENOMEM; goto fail; } TASK_INIT(&sc->task_reset, 0, sfxge_reset, sc); (void) pci_enable_busmaster(dev); /* Initialize DMA mappings. */ if ((error = sfxge_dma_init(sc)) != 0) goto fail; /* Map the device registers. */ if ((error = sfxge_bar_init(sc)) != 0) goto fail; error = efx_family(pci_get_vendor(dev), pci_get_device(dev), &sc->family); KASSERT(error == 0, ("Family should be filtered by sfxge_probe()")); /* Create the common code nic object. */ mtx_init(&sc->enp_lock, "sfxge_nic", NULL, MTX_DEF); if ((error = efx_nic_create(sc->family, (efsys_identifier_t *)sc, &sc->bar, &sc->enp_lock, &enp)) != 0) goto fail3; sc->enp = enp; /* Initialize MCDI to talk to the microcontroller. */ if ((error = sfxge_mcdi_init(sc)) != 0) goto fail4; /* Probe the NIC and build the configuration data area. */ if ((error = efx_nic_probe(enp)) != 0) goto fail5; /* Initialize the NVRAM. */ if ((error = efx_nvram_init(enp)) != 0) goto fail6; /* Initialize the VPD. */ if ((error = efx_vpd_init(enp)) != 0) goto fail7; /* Reset the NIC. */ if ((error = efx_nic_reset(enp)) != 0) goto fail8; /* Initialize buffer table allocation. */ sc->buffer_table_next = 0; /* Set up interrupts. */ if ((error = sfxge_intr_init(sc)) != 0) goto fail8; /* Initialize event processing state. */ if ((error = sfxge_ev_init(sc)) != 0) goto fail11; /* Initialize receive state. */ if ((error = sfxge_rx_init(sc)) != 0) goto fail12; /* Initialize transmit state. */ if ((error = sfxge_tx_init(sc)) != 0) goto fail13; /* Initialize port state. */ if ((error = sfxge_port_init(sc)) != 0) goto fail14; sc->init_state = SFXGE_INITIALIZED; return (0); fail14: sfxge_tx_fini(sc); fail13: sfxge_rx_fini(sc); fail12: sfxge_ev_fini(sc); fail11: sfxge_intr_fini(sc); fail8: efx_vpd_fini(enp); fail7: efx_nvram_fini(enp); fail6: efx_nic_unprobe(enp); fail5: sfxge_mcdi_fini(sc); fail4: sc->enp = NULL; efx_nic_destroy(enp); mtx_destroy(&sc->enp_lock); fail3: sfxge_bar_fini(sc); (void) pci_disable_busmaster(sc->dev); fail: sc->dev = NULL; sx_destroy(&sc->softc_lock); return (error); }
/* * Silicon Integrated Systems Corp. (SiS) chipset support functions */ static int ata_sis_probe(device_t dev) { struct ata_pci_controller *ctlr = device_get_softc(dev); const struct ata_chip_id *idx; static const struct ata_chip_id ids[] = { { ATA_SIS182, 0x00, SIS_SATA, 0, ATA_SA150, "182" }, /* south */ { ATA_SIS181, 0x00, SIS_SATA, 0, ATA_SA150, "181" }, /* south */ { ATA_SIS180, 0x00, SIS_SATA, 0, ATA_SA150, "180" }, /* south */ { ATA_SIS965, 0x00, SIS_133NEW, 0, ATA_UDMA6, "965" }, /* south */ { ATA_SIS964, 0x00, SIS_133NEW, 0, ATA_UDMA6, "964" }, /* south */ { ATA_SIS963, 0x00, SIS_133NEW, 0, ATA_UDMA6, "963" }, /* south */ { ATA_SIS962, 0x00, SIS_133NEW, 0, ATA_UDMA6, "962" }, /* south */ { ATA_SIS745, 0x00, SIS_100NEW, 0, ATA_UDMA5, "745" }, /* 1chip */ { ATA_SIS735, 0x00, SIS_100NEW, 0, ATA_UDMA5, "735" }, /* 1chip */ { ATA_SIS733, 0x00, SIS_100NEW, 0, ATA_UDMA5, "733" }, /* 1chip */ { ATA_SIS730, 0x00, SIS_100OLD, 0, ATA_UDMA5, "730" }, /* 1chip */ { ATA_SIS635, 0x00, SIS_100NEW, 0, ATA_UDMA5, "635" }, /* 1chip */ { ATA_SIS633, 0x00, SIS_100NEW, 0, ATA_UDMA5, "633" }, /* unknown */ { ATA_SIS630, 0x30, SIS_100OLD, 0, ATA_UDMA5, "630S"}, /* 1chip */ { ATA_SIS630, 0x00, SIS_66, 0, ATA_UDMA4, "630" }, /* 1chip */ { ATA_SIS620, 0x00, SIS_66, 0, ATA_UDMA4, "620" }, /* 1chip */ { ATA_SIS550, 0x00, SIS_66, 0, ATA_UDMA5, "550" }, { ATA_SIS540, 0x00, SIS_66, 0, ATA_UDMA4, "540" }, { ATA_SIS530, 0x00, SIS_66, 0, ATA_UDMA4, "530" }, { ATA_SIS5513, 0xc2, SIS_33, 1, ATA_UDMA2, "5513" }, { ATA_SIS5513, 0x00, SIS_33, 1, ATA_WDMA2, "5513" }, { 0, 0, 0, 0, 0, 0 } }; static struct ata_chip_id id[] = {{ ATA_SISSOUTH, 0x10, 0, 0, 0, "" }, { 0, 0, 0, 0, 0, 0 }}; char buffer[64]; int found = 0; if (pci_get_class(dev) != PCIC_STORAGE) return (ENXIO); if (pci_get_vendor(dev) != ATA_SIS_ID) return ENXIO; if (!(idx = ata_find_chip(dev, ids, -pci_get_slot(dev)))) return ENXIO; if (idx->cfg2) { u_int8_t reg57 = pci_read_config(dev, 0x57, 1); pci_write_config(dev, 0x57, (reg57 & 0x7f), 1); if (pci_read_config(dev, PCIR_DEVVENDOR, 4) == ATA_SIS5518) { found = 1; memcpy(&id[0], idx, sizeof(id[0])); id[0].cfg1 = SIS_133NEW; id[0].max_dma = ATA_UDMA6; sprintf(buffer, "SiS 962/963 %s controller", ata_mode2str(idx->max_dma)); } pci_write_config(dev, 0x57, reg57, 1); } if (idx->cfg2 && !found) { u_int8_t reg4a = pci_read_config(dev, 0x4a, 1); pci_write_config(dev, 0x4a, (reg4a | 0x10), 1); if (pci_read_config(dev, PCIR_DEVVENDOR, 4) == ATA_SIS5517) { found = 1; if (ata_find_chip(dev, id, pci_get_slot(dev))) { id[0].cfg1 = SIS_133OLD; id[0].max_dma = ATA_UDMA6; } else { id[0].cfg1 = SIS_100NEW; id[0].max_dma = ATA_UDMA5; } sprintf(buffer, "SiS 961 %s controller",ata_mode2str(idx->max_dma)); } pci_write_config(dev, 0x4a, reg4a, 1); } if (!found) sprintf(buffer,"SiS %s %s controller", idx->text, ata_mode2str(idx->max_dma)); else idx = &id[0]; device_set_desc_copy(dev, buffer); ctlr->chip = idx; ctlr->chipinit = ata_sis_chipinit; return (BUS_PROBE_DEFAULT); }
static int xhci_pci_attach(device_t self) { struct xhci_softc *sc = device_get_softc(self); int err; int rid; /* XXX check for 64-bit capability */ if (xhci_init(sc, self)) { device_printf(self, "Could not initialize softc\n"); goto error; } pci_enable_busmaster(self); rid = PCI_XHCI_CBMEM; sc->sc_io_res = bus_alloc_resource_any(self, SYS_RES_MEMORY, &rid, RF_ACTIVE); if (!sc->sc_io_res) { device_printf(self, "Could not map memory\n"); goto error; } sc->sc_io_tag = rman_get_bustag(sc->sc_io_res); sc->sc_io_hdl = rman_get_bushandle(sc->sc_io_res); sc->sc_io_size = rman_get_size(sc->sc_io_res); rid = 0; sc->sc_irq_res = bus_alloc_resource_any(self, SYS_RES_IRQ, &rid, RF_SHAREABLE | RF_ACTIVE); if (sc->sc_irq_res == NULL) { device_printf(self, "Could not allocate IRQ\n"); goto error; } sc->sc_bus.bdev = device_add_child(self, "usbus", -1); if (sc->sc_bus.bdev == NULL) { device_printf(self, "Could not add USB device\n"); goto error; } device_set_ivars(sc->sc_bus.bdev, &sc->sc_bus); sprintf(sc->sc_vendor, "0x%04x", pci_get_vendor(self)); #if (__FreeBSD_version >= 700031) err = bus_setup_intr(self, sc->sc_irq_res, INTR_TYPE_BIO | INTR_MPSAFE, NULL, (driver_intr_t *)xhci_interrupt, sc, &sc->sc_intr_hdl); #else err = bus_setup_intr(self, sc->sc_irq_res, INTR_TYPE_BIO | INTR_MPSAFE, (driver_intr_t *)xhci_interrupt, sc, &sc->sc_intr_hdl); #endif if (err) { device_printf(self, "Could not setup IRQ, err=%d\n", err); sc->sc_intr_hdl = NULL; goto error; } xhci_pci_take_controller(self); err = xhci_halt_controller(sc); if (err == 0) err = xhci_start_controller(sc); if (err == 0) err = device_probe_and_attach(sc->sc_bus.bdev); if (err) { device_printf(self, "XHCI halt/start/probe failed err=%d\n", err); goto error; } return (0); error: xhci_pci_detach(self); return (ENXIO); }
/* * The probe routine. */ static int fwohci_pci_probe( device_t dev ) { #if 1 uint32_t id; id = pci_get_devid(dev); if (id == (FW_VENDORID_NATSEMI | FW_DEVICE_CS4210)) { device_set_desc(dev, "National Semiconductor CS4210"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_NEC | FW_DEVICE_UPD861)) { device_set_desc(dev, "NEC uPD72861"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_NEC | FW_DEVICE_UPD871)) { device_set_desc(dev, "NEC uPD72871/2"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_NEC | FW_DEVICE_UPD72870)) { device_set_desc(dev, "NEC uPD72870"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_NEC | FW_DEVICE_UPD72873)) { device_set_desc(dev, "NEC uPD72873"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_NEC | FW_DEVICE_UPD72874)) { device_set_desc(dev, "NEC uPD72874"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_SIS | FW_DEVICE_7007)) { /* It has no real identifier, using device id. */ device_set_desc(dev, "SiS 7007"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TITSB22)) { device_set_desc(dev, "Texas Instruments TSB12LV22"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TITSB23)) { device_set_desc(dev, "Texas Instruments TSB12LV23"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TITSB26)) { device_set_desc(dev, "Texas Instruments TSB12LV26"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TITSB43)) { device_set_desc(dev, "Texas Instruments TSB43AA22"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TITSB43A)) { device_set_desc(dev, "Texas Instruments TSB43AB22/A"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TITSB43AB21)) { device_set_desc(dev, "Texas Instruments TSB43AB21/A/AI/A-EP"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TITSB43AB23)) { device_set_desc(dev, "Texas Instruments TSB43AB23"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TITSB82AA2)) { device_set_desc(dev, "Texas Instruments TSB82AA2"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TIPCI4450)) { device_set_desc(dev, "Texas Instruments PCI4450"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TIPCI4410A)) { device_set_desc(dev, "Texas Instruments PCI4410A"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_TI | FW_DEVICE_TIPCI4451)) { device_set_desc(dev, "Texas Instruments PCI4451"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_SONY | FW_DEVICE_CXD1947)) { device_printf(dev, "Sony i.LINK (CXD1947) not supported\n"); return ENXIO; } if (id == (FW_VENDORID_SONY | FW_DEVICE_CXD3222)) { device_set_desc(dev, "Sony i.LINK (CXD3222)"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_VIA | FW_DEVICE_VT6306)) { device_set_desc(dev, "VIA Fire II (VT6306)"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_RICOH | FW_DEVICE_R5C551)) { device_set_desc(dev, "Ricoh R5C551"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_RICOH | FW_DEVICE_R5C552)) { device_set_desc(dev, "Ricoh R5C552"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_APPLE | FW_DEVICE_PANGEA)) { device_set_desc(dev, "Apple Pangea"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_APPLE | FW_DEVICE_UNINORTH)) { device_set_desc(dev, "Apple UniNorth"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_LUCENT | FW_DEVICE_FW322)) { device_set_desc(dev, "Lucent FW322/323"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_INTEL | FW_DEVICE_82372FB)) { device_set_desc(dev, "Intel 82372FB"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_ADAPTEC | FW_DEVICE_AIC5800)) { device_set_desc(dev, "Adaptec AHA-894x/AIC-5800"); return BUS_PROBE_DEFAULT; } if (id == (FW_VENDORID_SUN | FW_DEVICE_PCIO2FW)) { device_set_desc(dev, "Sun PCIO-2"); return BUS_PROBE_DEFAULT; } #endif if (pci_get_class(dev) == PCIC_SERIALBUS && pci_get_subclass(dev) == PCIS_SERIALBUS_FW && pci_get_progif(dev) == PCI_INTERFACE_OHCI) { if (bootverbose) device_printf(dev, "vendor=%x, dev=%x\n", pci_get_vendor(dev), pci_get_device(dev)); device_set_desc(dev, "1394 Open Host Controller Interface"); return BUS_PROBE_DEFAULT; } return ENXIO; }
static int xhci_pci_attach(device_t self) { struct xhci_softc *sc = device_get_softc(self); int count, err, rid; uint8_t usedma32; rid = PCI_XHCI_CBMEM; sc->sc_io_res = bus_alloc_resource_any(self, SYS_RES_MEMORY, &rid, RF_ACTIVE); if (!sc->sc_io_res) { device_printf(self, "Could not map memory\n"); return (ENOMEM); } sc->sc_io_tag = rman_get_bustag(sc->sc_io_res); sc->sc_io_hdl = rman_get_bushandle(sc->sc_io_res); sc->sc_io_size = rman_get_size(sc->sc_io_res); switch (pci_get_devid(self)) { case 0x01941033: /* NEC uPD720200 USB 3.0 controller */ /* Don't use 64-bit DMA on these controllers. */ usedma32 = 1; break; case 0x0f358086: /* BayTrail */ case 0x9c318086: /* Panther Point */ case 0x1e318086: /* Panther Point */ case 0x8c318086: /* Lynx Point */ case 0x8cb18086: /* Wildcat Point */ /* * On Intel chipsets, reroute ports from EHCI to XHCI * controller and use a different IMOD value. */ sc->sc_port_route = &xhci_pci_port_route; sc->sc_imod_default = XHCI_IMOD_DEFAULT_LP; /* FALLTHROUGH */ default: usedma32 = 0; break; } if (xhci_init(sc, self, usedma32)) { device_printf(self, "Could not initialize softc\n"); bus_release_resource(self, SYS_RES_MEMORY, PCI_XHCI_CBMEM, sc->sc_io_res); return (ENXIO); } pci_enable_busmaster(self); usb_callout_init_mtx(&sc->sc_callout, &sc->sc_bus.bus_mtx, 0); rid = 0; if (xhci_use_msi) { count = 1; if (pci_alloc_msi(self, &count) == 0) { if (bootverbose) device_printf(self, "MSI enabled\n"); rid = 1; } } sc->sc_irq_res = bus_alloc_resource_any(self, SYS_RES_IRQ, &rid, RF_ACTIVE | (rid != 0 ? 0 : RF_SHAREABLE)); if (sc->sc_irq_res == NULL) { pci_release_msi(self); device_printf(self, "Could not allocate IRQ\n"); /* goto error; FALLTHROUGH - use polling */ } sc->sc_bus.bdev = device_add_child(self, "usbus", -1); if (sc->sc_bus.bdev == NULL) { device_printf(self, "Could not add USB device\n"); goto error; } device_set_ivars(sc->sc_bus.bdev, &sc->sc_bus); sprintf(sc->sc_vendor, "0x%04x", pci_get_vendor(self)); if (sc->sc_irq_res != NULL) { err = bus_setup_intr(self, sc->sc_irq_res, INTR_TYPE_BIO | INTR_MPSAFE, NULL, (driver_intr_t *)xhci_interrupt, sc, &sc->sc_intr_hdl); if (err != 0) { bus_release_resource(self, SYS_RES_IRQ, rman_get_rid(sc->sc_irq_res), sc->sc_irq_res); sc->sc_irq_res = NULL; pci_release_msi(self); device_printf(self, "Could not setup IRQ, err=%d\n", err); sc->sc_intr_hdl = NULL; } } if (sc->sc_irq_res == NULL || sc->sc_intr_hdl == NULL) { if (xhci_use_polling() != 0) { device_printf(self, "Interrupt polling at %dHz\n", hz); USB_BUS_LOCK(&sc->sc_bus); xhci_interrupt_poll(sc); USB_BUS_UNLOCK(&sc->sc_bus); } else goto error; } xhci_pci_take_controller(self); err = xhci_halt_controller(sc); if (err == 0) err = xhci_start_controller(sc); if (err == 0) err = device_probe_and_attach(sc->sc_bus.bdev); if (err) { device_printf(self, "XHCI halt/start/probe failed err=%d\n", err); goto error; } return (0); error: xhci_pci_detach(self); return (ENXIO); }
/* * nVidia chipset support functions */ static int ata_nvidia_probe(device_t dev) { struct ata_pci_controller *ctlr = device_get_softc(dev); static const struct ata_chip_id ids[] = {{ ATA_NFORCE1, 0, 0, 0, ATA_UDMA5, "nForce" }, { ATA_NFORCE2, 0, 0, 0, ATA_UDMA6, "nForce2" }, { ATA_NFORCE2_PRO, 0, 0, 0, ATA_UDMA6, "nForce2 Pro" }, { ATA_NFORCE2_PRO_S1, 0, 0, 0, ATA_SA150, "nForce2 Pro" }, { ATA_NFORCE3, 0, 0, 0, ATA_UDMA6, "nForce3" }, { ATA_NFORCE3_PRO, 0, 0, 0, ATA_UDMA6, "nForce3 Pro" }, { ATA_NFORCE3_PRO_S1, 0, 0, 0, ATA_SA150, "nForce3 Pro" }, { ATA_NFORCE3_PRO_S2, 0, 0, 0, ATA_SA150, "nForce3 Pro" }, { ATA_NFORCE_MCP04, 0, 0, 0, ATA_UDMA6, "nForce MCP" }, { ATA_NFORCE_MCP04_S1, 0, NV4, 0, ATA_SA150, "nForce MCP" }, { ATA_NFORCE_MCP04_S2, 0, NV4, 0, ATA_SA150, "nForce MCP" }, { ATA_NFORCE_CK804, 0, 0, 0, ATA_UDMA6, "nForce CK804" }, { ATA_NFORCE_CK804_S1, 0, NV4, 0, ATA_SA300, "nForce CK804" }, { ATA_NFORCE_CK804_S2, 0, NV4, 0, ATA_SA300, "nForce CK804" }, { ATA_NFORCE_MCP51, 0, 0, 0, ATA_UDMA6, "nForce MCP51" }, { ATA_NFORCE_MCP51_S1, 0, NV4|NVQ, 0, ATA_SA300, "nForce MCP51" }, { ATA_NFORCE_MCP51_S2, 0, NV4|NVQ, 0, ATA_SA300, "nForce MCP51" }, { ATA_NFORCE_MCP55, 0, 0, 0, ATA_UDMA6, "nForce MCP55" }, { ATA_NFORCE_MCP55_S1, 0, NV4|NVQ, 0, ATA_SA300, "nForce MCP55" }, { ATA_NFORCE_MCP55_S2, 0, NV4|NVQ, 0, ATA_SA300, "nForce MCP55" }, { ATA_NFORCE_MCP61, 0, 0, 0, ATA_UDMA6, "nForce MCP61" }, { ATA_NFORCE_MCP61_S1, 0, NV4|NVQ, 0, ATA_SA300, "nForce MCP61" }, { ATA_NFORCE_MCP61_S2, 0, NV4|NVQ, 0, ATA_SA300, "nForce MCP61" }, { ATA_NFORCE_MCP61_S3, 0, NV4|NVQ, 0, ATA_SA300, "nForce MCP61" }, { ATA_NFORCE_MCP65, 0, 0, 0, ATA_UDMA6, "nForce MCP65" }, { ATA_NFORCE_MCP65_A0, 0, NVAHCI, 0, ATA_SA300, "nForce MCP65" }, { ATA_NFORCE_MCP65_A1, 0, NVAHCI, 0, ATA_SA300, "nForce MCP65" }, { ATA_NFORCE_MCP65_A2, 0, NVAHCI, 0, ATA_SA300, "nForce MCP65" }, { ATA_NFORCE_MCP65_A3, 0, NVAHCI, 0, ATA_SA300, "nForce MCP65" }, { ATA_NFORCE_MCP65_A4, 0, NVAHCI, 0, ATA_SA300, "nForce MCP65" }, { ATA_NFORCE_MCP65_A5, 0, NVAHCI, 0, ATA_SA300, "nForce MCP65" }, { ATA_NFORCE_MCP65_A6, 0, NVAHCI, 0, ATA_SA300, "nForce MCP65" }, { ATA_NFORCE_MCP65_A7, 0, NVAHCI, 0, ATA_SA300, "nForce MCP65" }, { ATA_NFORCE_MCP67, 0, 0, 0, ATA_UDMA6, "nForce MCP67" }, { ATA_NFORCE_MCP67_A0, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_A1, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_A2, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_A3, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_A4, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_A5, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_A6, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_A7, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_A8, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_A9, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_AA, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_AB, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP67_AC, 0, NVAHCI, 0, ATA_SA300, "nForce MCP67" }, { ATA_NFORCE_MCP73, 0, 0, 0, ATA_UDMA6, "nForce MCP73" }, { ATA_NFORCE_MCP73_A0, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_A1, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_A2, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_A3, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_A4, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_A5, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_A6, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_A7, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_A8, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_A9, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_AA, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP73_AB, 0, NVAHCI, 0, ATA_SA300, "nForce MCP73" }, { ATA_NFORCE_MCP77, 0, 0, 0, ATA_UDMA6, "nForce MCP77" }, { ATA_NFORCE_MCP77_A0, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_A1, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_A2, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_A3, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_A4, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_A5, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_A6, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_A7, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_A8, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_A9, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_AA, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP77_AB, 0, NVAHCI, 0, ATA_SA300, "nForce MCP77" }, { ATA_NFORCE_MCP79_A0, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_A1, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_A2, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_A3, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_A4, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_A5, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_A6, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_A7, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_A8, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_A9, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_AA, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP79_AB, 0, NVAHCI, 0, ATA_SA300, "nForce MCP79" }, { ATA_NFORCE_MCP89_A0, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_A1, 0, NVAHCI|NVNOFORCE, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_A2, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_A3, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_A4, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_A5, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_A6, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_A7, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_A8, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_A9, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_AA, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { ATA_NFORCE_MCP89_AB, 0, NVAHCI, 0, ATA_SA300, "nForce MCP89" }, { 0, 0, 0, 0, 0, 0}} ; if (pci_get_vendor(dev) != ATA_NVIDIA_ID) return ENXIO; if (!(ctlr->chip = ata_match_chip(dev, ids))) return ENXIO; ata_set_desc(dev); if ((ctlr->chip->cfg1 & NVAHCI) && ((force_ahci == 1 && (ctlr->chip->cfg1 & NVNOFORCE) == 0) || pci_get_subclass(dev) != PCIS_STORAGE_IDE)) ctlr->chipinit = ata_ahci_chipinit; else ctlr->chipinit = ata_nvidia_chipinit; return (BUS_PROBE_DEFAULT); }
static int ql_eioctl(struct cdev *dev, u_long cmd, caddr_t data, int fflag, struct thread *td) { qla_host_t *ha; int rval = 0; device_t pci_dev; struct ifnet *ifp; q80_offchip_mem_val_t val; qla_rd_pci_ids_t *pci_ids; qla_rd_fw_dump_t *fw_dump; union { qla_reg_val_t *rv; qla_rd_flash_t *rdf; qla_wr_flash_t *wrf; qla_erase_flash_t *erf; qla_offchip_mem_val_t *mem; } u; if ((ha = (qla_host_t *)dev->si_drv1) == NULL) return ENXIO; pci_dev= ha->pci_dev; switch(cmd) { case QLA_RDWR_REG: u.rv = (qla_reg_val_t *)data; if (u.rv->direct) { if (u.rv->rd) { u.rv->val = READ_REG32(ha, u.rv->reg); } else { WRITE_REG32(ha, u.rv->reg, u.rv->val); } } else { if ((rval = ql_rdwr_indreg32(ha, u.rv->reg, &u.rv->val, u.rv->rd))) rval = ENXIO; } break; case QLA_RD_FLASH: if (!ha->hw.flags.fdt_valid) { rval = EIO; break; } u.rdf = (qla_rd_flash_t *)data; if ((rval = ql_rd_flash32(ha, u.rdf->off, &u.rdf->data))) rval = ENXIO; break; case QLA_WR_FLASH: ifp = ha->ifp; if (ifp == NULL) { rval = ENXIO; break; } if (ifp->if_drv_flags & (IFF_DRV_OACTIVE | IFF_DRV_RUNNING)) { rval = ENXIO; break; } if (!ha->hw.flags.fdt_valid) { rval = EIO; break; } u.wrf = (qla_wr_flash_t *)data; if ((rval = ql_wr_flash_buffer(ha, u.wrf->off, u.wrf->size, u.wrf->buffer))) { printf("flash write failed[%d]\n", rval); rval = ENXIO; } break; case QLA_ERASE_FLASH: ifp = ha->ifp; if (ifp == NULL) { rval = ENXIO; break; } if (ifp->if_drv_flags & (IFF_DRV_OACTIVE | IFF_DRV_RUNNING)) { rval = ENXIO; break; } if (!ha->hw.flags.fdt_valid) { rval = EIO; break; } u.erf = (qla_erase_flash_t *)data; if ((rval = ql_erase_flash(ha, u.erf->off, u.erf->size))) { printf("flash erase failed[%d]\n", rval); rval = ENXIO; } break; case QLA_RDWR_MS_MEM: u.mem = (qla_offchip_mem_val_t *)data; if ((rval = ql_rdwr_offchip_mem(ha, u.mem->off, &val, u.mem->rd))) rval = ENXIO; else { u.mem->data_lo = val.data_lo; u.mem->data_hi = val.data_hi; u.mem->data_ulo = val.data_ulo; u.mem->data_uhi = val.data_uhi; } break; case QLA_RD_FW_DUMP_SIZE: if (ha->hw.mdump_init == 0) { rval = EINVAL; break; } fw_dump = (qla_rd_fw_dump_t *)data; fw_dump->template_size = ha->hw.dma_buf.minidump.size; fw_dump->pci_func = ha->pci_func; break; case QLA_RD_FW_DUMP: if (ha->hw.mdump_init == 0) { rval = EINVAL; break; } fw_dump = (qla_rd_fw_dump_t *)data; if ((fw_dump->md_template == NULL) || (fw_dump->template_size != ha->hw.dma_buf.minidump.size)) { rval = EINVAL; break; } if ((rval = copyout(ha->hw.dma_buf.minidump.dma_b, fw_dump->md_template, fw_dump->template_size))) rval = ENXIO; break; case QLA_RD_PCI_IDS: pci_ids = (qla_rd_pci_ids_t *)data; pci_ids->ven_id = pci_get_vendor(pci_dev); pci_ids->dev_id = pci_get_device(pci_dev); pci_ids->subsys_ven_id = pci_get_subvendor(pci_dev); pci_ids->subsys_dev_id = pci_get_subdevice(pci_dev); pci_ids->rev_id = pci_read_config(pci_dev, PCIR_REVID, 1); break; default: break; } return rval; }
static void ichss_identify(driver_t *driver, device_t parent) { device_t child; uint32_t pmbase; if (resource_disabled("ichss", 0)) return; /* * It appears that ICH SpeedStep only requires a single CPU to * set the value (since the chipset is shared by all CPUs.) * Thus, we only add a child to cpu 0. */ if (device_get_unit(parent) != 0) return; /* Avoid duplicates. */ if (device_find_child(parent, "ichss", -1)) return; /* * ICH2/3/4-M I/O Controller Hub is at bus 0, slot 1F, function 0. * E.g. see Section 6.1 "PCI Devices and Functions" and table 6.1 of * Intel(r) 82801BA I/O Controller Hub 2 (ICH2) and Intel(r) 82801BAM * I/O Controller Hub 2 Mobile (ICH2-M). */ ich_device = pci_find_bsf(0, 0x1f, 0); if (ich_device == NULL || pci_get_vendor(ich_device) != PCI_VENDOR_INTEL || (pci_get_device(ich_device) != PCI_DEV_82801BA && pci_get_device(ich_device) != PCI_DEV_82801CA && pci_get_device(ich_device) != PCI_DEV_82801DB)) return; /* * Certain systems with ICH2 and an Intel 82815_MC host bridge * where the host bridge's revision is < 5 lockup if SpeedStep * is used. */ if (pci_get_device(ich_device) == PCI_DEV_82801BA) { device_t hostb; hostb = pci_find_bsf(0, 0, 0); if (hostb != NULL && pci_get_vendor(hostb) == PCI_VENDOR_INTEL && pci_get_device(hostb) == PCI_DEV_82815_MC && pci_get_revid(hostb) < 5) return; } /* Find the PMBASE register from our PCI config header. */ pmbase = pci_read_config(ich_device, ICHSS_PMBASE_OFFSET, sizeof(pmbase)); if ((pmbase & ICHSS_IO_REG) == 0) { printf("ichss: invalid PMBASE memory type\n"); return; } pmbase &= ICHSS_PMBASE_MASK; if (pmbase == 0) { printf("ichss: invalid zero PMBASE address\n"); return; } DPRINT("ichss: PMBASE is %#x\n", pmbase); child = BUS_ADD_CHILD(parent, 20, "ichss", 0); if (child == NULL) { device_printf(parent, "add SpeedStep child failed\n"); return; } /* Add the bus master arbitration and control registers. */ bus_set_resource(child, SYS_RES_IOPORT, 0, pmbase + ICHSS_BM_OFFSET, 1); bus_set_resource(child, SYS_RES_IOPORT, 1, pmbase + ICHSS_CTRL_OFFSET, 1); }
static int ad_attach(device_t dev) { struct ata_channel *ch = device_get_softc(device_get_parent(dev)); struct ata_device *atadev = device_get_softc(dev); struct ad_softc *adp; device_t parent; /* check that we have a virgin disk to attach */ if (device_get_ivars(dev)) return EEXIST; if (!(adp = malloc(sizeof(struct ad_softc), M_AD, M_NOWAIT | M_ZERO))) { device_printf(dev, "out of memory\n"); return ENOMEM; } device_set_ivars(dev, adp); /* get device geometry into internal structs */ if (ad_get_geometry(dev)) return ENXIO; /* set the max size if configured */ if (ata_setmax) ad_set_geometry(dev); /* init device parameters */ ad_init(dev); /* announce we are here */ ad_describe(dev); /* create the disk device */ adp->disk = disk_alloc(); adp->disk->d_strategy = ad_strategy; adp->disk->d_ioctl = ad_ioctl; adp->disk->d_dump = ad_dump; adp->disk->d_name = "ad"; adp->disk->d_drv1 = dev; adp->disk->d_maxsize = ch->dma.max_iosize ? ch->dma.max_iosize : DFLTPHYS; if (atadev->param.support.command2 & ATA_SUPPORT_ADDRESS48) adp->disk->d_maxsize = min(adp->disk->d_maxsize, 65536 * DEV_BSIZE); else /* 28bit ATA command limit */ adp->disk->d_maxsize = min(adp->disk->d_maxsize, 256 * DEV_BSIZE); adp->disk->d_sectorsize = DEV_BSIZE; adp->disk->d_mediasize = DEV_BSIZE * (off_t)adp->total_secs; adp->disk->d_fwsectors = adp->sectors; adp->disk->d_fwheads = adp->heads; adp->disk->d_unit = device_get_unit(dev); if (atadev->param.support.command2 & ATA_SUPPORT_FLUSHCACHE) adp->disk->d_flags |= DISKFLAG_CANFLUSHCACHE; if ((atadev->param.support.command2 & ATA_SUPPORT_CFA) || atadev->param.config == ATA_PROTO_CFA) adp->disk->d_flags |= DISKFLAG_CANDELETE; strlcpy(adp->disk->d_ident, atadev->param.serial, sizeof(adp->disk->d_ident)); strlcpy(adp->disk->d_descr, atadev->param.model, sizeof(adp->disk->d_descr)); parent = device_get_parent(ch->dev); if (parent != NULL && device_get_parent(parent) != NULL && (device_get_devclass(parent) == devclass_find("atapci") || device_get_devclass(device_get_parent(parent)) == devclass_find("pci"))) { adp->disk->d_hba_vendor = pci_get_vendor(parent); adp->disk->d_hba_device = pci_get_device(parent); adp->disk->d_hba_subvendor = pci_get_subvendor(parent); adp->disk->d_hba_subdevice = pci_get_subdevice(parent); } ata_disk_firmware_geom_adjust(adp->disk); disk_create(adp->disk, DISK_VERSION); device_add_child(dev, "subdisk", device_get_unit(dev)); bus_generic_attach(dev); callout_init(&atadev->spindown_timer, 1); return 0; }
static int ehci_pci_attach(device_t self) { ehci_softc_t *sc = device_get_softc(self); devclass_t dc; device_t parent; device_t *neighbors; device_t *nbus; struct usbd_bus *bsc; int err; int rid; int ncomp; int count, buscount; int slot, function; int res; int i; switch(pci_read_config(self, PCI_USBREV, 1) & PCI_USBREV_MASK) { case PCI_USBREV_PRE_1_0: case PCI_USBREV_1_0: case PCI_USBREV_1_1: device_printf(self, "pre-2.0 USB rev\n"); if (pci_get_devid(self) == PCI_EHCI_DEVICEID_CS5536) { sc->sc_bus.usbrev = USBREV_2_0; device_printf(self, "Quirk for CS5536 USB 2.0 enabled\n"); break; } sc->sc_bus.usbrev = USBREV_UNKNOWN; return ENXIO; case PCI_USBREV_2_0: sc->sc_bus.usbrev = USBREV_2_0; break; default: sc->sc_bus.usbrev = USBREV_UNKNOWN; break; } pci_enable_busmaster(self); rid = PCI_CBMEM; sc->io_res = bus_alloc_resource_any(self, SYS_RES_MEMORY, &rid, RF_ACTIVE); if (!sc->io_res) { device_printf(self, "Could not map memory\n"); return ENXIO; } sc->iot = rman_get_bustag(sc->io_res); sc->ioh = rman_get_bushandle(sc->io_res); rid = 0; sc->irq_res = bus_alloc_resource_any(self, SYS_RES_IRQ, &rid, RF_SHAREABLE | RF_ACTIVE); if (sc->irq_res == NULL) { device_printf(self, "Could not allocate irq\n"); ehci_pci_detach(self); return ENXIO; } sc->sc_bus.bdev = device_add_child(self, "usb", -1); if (!sc->sc_bus.bdev) { device_printf(self, "Could not add USB device\n"); ehci_pci_detach(self); return ENOMEM; } device_set_ivars(sc->sc_bus.bdev, &sc->sc_bus); /* ehci_pci_match will never return NULL if ehci_pci_probe succeeded */ device_set_desc(sc->sc_bus.bdev, ehci_pci_match(self)); switch (pci_get_vendor(self)) { case PCI_EHCI_VENDORID_ACERLABS: sprintf(sc->sc_vendor, "AcerLabs"); break; case PCI_EHCI_VENDORID_AMD: sprintf(sc->sc_vendor, "AMD"); break; case PCI_EHCI_VENDORID_APPLE: sprintf(sc->sc_vendor, "Apple"); break; case PCI_EHCI_VENDORID_ATI: sprintf(sc->sc_vendor, "ATI"); break; case PCI_EHCI_VENDORID_CMDTECH: sprintf(sc->sc_vendor, "CMDTECH"); break; case PCI_EHCI_VENDORID_INTEL: sprintf(sc->sc_vendor, "Intel"); break; case PCI_EHCI_VENDORID_NEC: sprintf(sc->sc_vendor, "NEC"); break; case PCI_EHCI_VENDORID_OPTI: sprintf(sc->sc_vendor, "OPTi"); break; case PCI_EHCI_VENDORID_SIS: sprintf(sc->sc_vendor, "SiS"); break; case PCI_EHCI_VENDORID_NVIDIA: case PCI_EHCI_VENDORID_NVIDIA2: sprintf(sc->sc_vendor, "nVidia"); break; case PCI_EHCI_VENDORID_VIA: sprintf(sc->sc_vendor, "VIA"); break; default: if (bootverbose) device_printf(self, "(New EHCI DeviceId=0x%08x)\n", pci_get_devid(self)); sprintf(sc->sc_vendor, "(0x%04x)", pci_get_vendor(self)); } err = bus_setup_intr(self, sc->irq_res, INTR_TYPE_BIO, NULL, (driver_intr_t *)ehci_intr, sc, &sc->ih); if (err) { device_printf(self, "Could not setup irq, %d\n", err); sc->ih = NULL; ehci_pci_detach(self); return ENXIO; } /* Enable workaround for dropped interrupts as required */ switch (pci_get_vendor(self)) { case PCI_EHCI_VENDORID_ATI: case PCI_EHCI_VENDORID_VIA: sc->sc_flags |= EHCI_SCFLG_LOSTINTRBUG; if (bootverbose) device_printf(self, "Dropped interrupts workaround enabled\n"); break; default: break; } /* * Find companion controllers. According to the spec they always * have lower function numbers so they should be enumerated already. */ parent = device_get_parent(self); res = device_get_children(parent, &neighbors, &count); if (res != 0) { device_printf(self, "Error finding companion busses\n"); ehci_pci_detach(self); return ENXIO; } ncomp = 0; dc = devclass_find("usb"); slot = pci_get_slot(self); function = pci_get_function(self); for (i = 0; i < count; i++) { if (pci_get_slot(neighbors[i]) == slot && \ pci_get_function(neighbors[i]) < function) { res = device_get_children(neighbors[i], &nbus, &buscount); if (res != 0) continue; if (buscount != 1) { free(nbus, M_TEMP); continue; } if (device_get_devclass(nbus[0]) != dc) { free(nbus, M_TEMP); continue; } bsc = device_get_softc(nbus[0]); free(nbus, M_TEMP); DPRINTF(("ehci_pci_attach: companion %s\n", device_get_nameunit(bsc->bdev))); sc->sc_comps[ncomp++] = bsc; if (ncomp >= EHCI_COMPANION_MAX) break; } } sc->sc_ncomp = ncomp; /* Allocate a parent dma tag for DMA maps */ err = bus_dma_tag_create(bus_get_dma_tag(self), 1, 0, BUS_SPACE_MAXADDR_32BIT, BUS_SPACE_MAXADDR, NULL, NULL, BUS_SPACE_MAXSIZE_32BIT, USB_DMA_NSEG, BUS_SPACE_MAXSIZE_32BIT, 0, NULL, NULL, &sc->sc_bus.parent_dmatag); if (err) { device_printf(self, "Could not allocate parent DMA tag (%d)\n", err); ehci_pci_detach(self); return ENXIO; } /* Allocate a dma tag for transfer buffers */ err = bus_dma_tag_create(sc->sc_bus.parent_dmatag, 1, 0, BUS_SPACE_MAXADDR_32BIT, BUS_SPACE_MAXADDR, NULL, NULL, BUS_SPACE_MAXSIZE_32BIT, USB_DMA_NSEG, BUS_SPACE_MAXSIZE_32BIT, 0, busdma_lock_mutex, &Giant, &sc->sc_bus.buffer_dmatag); if (err) { device_printf(self, "Could not allocate buffer DMA tag (%d)\n", err); ehci_pci_detach(self); return ENXIO; } ehci_pci_takecontroller(self); err = ehci_init(sc); if (!err) { sc->sc_flags |= EHCI_SCFLG_DONEINIT; err = device_probe_and_attach(sc->sc_bus.bdev); } if (err) { device_printf(self, "USB init failed err=%d\n", err); ehci_pci_detach(self); return EIO; } return 0; }
static int mlx_pci_attach(device_t dev) { struct mlx_softc *sc; int i, error; u_int32_t command; debug_called(1); /* * Make sure we are going to be able to talk to this board. */ command = pci_read_config(dev, PCIR_COMMAND, 2); if ((command & PCIM_CMD_MEMEN) == 0) { device_printf(dev, "memory window not available\n"); return(ENXIO); } /* force the busmaster enable bit on */ command |= PCIM_CMD_BUSMASTEREN; pci_write_config(dev, PCIR_COMMAND, command, 2); /* * Initialise softc. */ sc = device_get_softc(dev); bzero(sc, sizeof(*sc)); sc->mlx_dev = dev; /* * Work out what sort of adapter this is (we need to know this in order * to map the appropriate interface resources). */ sc->mlx_iftype = 0; for (i = 0; mlx_identifiers[i].vendor != 0; i++) { if ((mlx_identifiers[i].vendor == pci_get_vendor(dev)) && (mlx_identifiers[i].device == pci_get_device(dev))) { sc->mlx_iftype = mlx_identifiers[i].iftype; break; } } if (sc->mlx_iftype == 0) /* shouldn't happen */ return(ENXIO); /* * Allocate the PCI register window. */ /* type 2/3 adapters have an I/O region we don't prefer at base 0 */ switch(sc->mlx_iftype) { case MLX_IFTYPE_2: case MLX_IFTYPE_3: sc->mlx_mem_type = SYS_RES_MEMORY; sc->mlx_mem_rid = MLX_CFG_BASE1; sc->mlx_mem = bus_alloc_resource_any(dev, sc->mlx_mem_type, &sc->mlx_mem_rid, RF_ACTIVE); if (sc->mlx_mem == NULL) { sc->mlx_mem_type = SYS_RES_IOPORT; sc->mlx_mem_rid = MLX_CFG_BASE0; sc->mlx_mem = bus_alloc_resource_any(dev, sc->mlx_mem_type, &sc->mlx_mem_rid, RF_ACTIVE); } break; case MLX_IFTYPE_4: case MLX_IFTYPE_5: sc->mlx_mem_type = SYS_RES_MEMORY; sc->mlx_mem_rid = MLX_CFG_BASE0; sc->mlx_mem = bus_alloc_resource_any(dev, sc->mlx_mem_type, &sc->mlx_mem_rid, RF_ACTIVE); break; } if (sc->mlx_mem == NULL) { device_printf(sc->mlx_dev, "couldn't allocate mailbox window\n"); mlx_free(sc); return(ENXIO); } sc->mlx_btag = rman_get_bustag(sc->mlx_mem); sc->mlx_bhandle = rman_get_bushandle(sc->mlx_mem); /* * Allocate the parent bus DMA tag appropriate for PCI. */ error = bus_dma_tag_create(NULL, /* parent */ 1, 0, /* alignment, boundary */ BUS_SPACE_MAXADDR_32BIT, /* lowaddr */ BUS_SPACE_MAXADDR, /* highaddr */ NULL, NULL, /* filter, filterarg */ MAXBSIZE, MLX_NSEG, /* maxsize, nsegments */ BUS_SPACE_MAXSIZE_32BIT, /* maxsegsize */ BUS_DMA_ALLOCNOW, /* flags */ NULL, /* lockfunc */ NULL, /* lockarg */ &sc->mlx_parent_dmat); if (error != 0) { device_printf(dev, "can't allocate parent DMA tag\n"); mlx_free(sc); return(ENOMEM); } /* * Do bus-independant initialisation. */ error = mlx_attach(sc); if (error != 0) { mlx_free(sc); return(error); } /* * Start the controller. */ mlx_startup(sc); return(0); }
static int tdfx_attach(device_t dev) { /* * The attach routine is called after the probe routine successfully says it * supports a given card. We now proceed to initialize this card for use with * the system. I want to map the device memory for userland allocation and * fill an information structure with information on this card. I'd also like * to set Write Combining with the MTRR code so that we can hopefully speed * up memory writes. The last thing is to register the character device * interface to the card, so we can open it from /dev/3dfxN, where N is a * small, whole number. */ struct tdfx_softc *tdfx_info; u_long val; /* rid value tells bus_alloc_resource where to find the addresses of ports or * of memory ranges in the PCI config space*/ int rid = PCIR_BAR(0); /* Increment the card counter (for the ioctl code) */ tdfx_count++; /* Enable MemMap on Voodoo */ val = pci_read_config(dev, PCIR_COMMAND, 2); val |= (PCIM_CMD_MEMEN); pci_write_config(dev, PCIR_COMMAND, val, 2); val = pci_read_config(dev, PCIR_COMMAND, 2); /* Fill the soft config struct with info about this device*/ tdfx_info = device_get_softc(dev); tdfx_info->dev = dev; tdfx_info->vendor = pci_get_vendor(dev); tdfx_info->type = pci_get_devid(dev) >> 16; tdfx_info->bus = pci_get_bus(dev); tdfx_info->dv = pci_get_slot(dev); tdfx_info->curFile = NULL; /* * Get the Memory Location from the PCI Config, mask out lower word, since * the config space register is only one word long (this is nicer than a * bitshift). */ tdfx_info->addr0 = (pci_read_config(dev, 0x10, 4) & 0xffff0000); #ifdef DEBUG device_printf(dev, "Base0 @ 0x%x\n", tdfx_info->addr0); #endif /* Notify the VM that we will be mapping some memory later */ tdfx_info->memrange = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid, RF_ACTIVE | RF_SHAREABLE); if(tdfx_info->memrange == NULL) { #ifdef DEBUG device_printf(dev, "Error mapping mem, won't be able to use mmap()\n"); #endif tdfx_info->memrid = 0; } else { tdfx_info->memrid = rid; #ifdef DEBUG device_printf(dev, "Mapped to: 0x%x\n", (unsigned int)rman_get_start(tdfx_info->memrange)); #endif } /* Setup for Voodoo3 and Banshee, PIO and an extram Memrange */ if(pci_get_devid(dev) == PCI_DEVICE_3DFX_VOODOO3 || pci_get_devid(dev) == PCI_DEVICE_3DFX_BANSHEE) { rid = 0x14; /* 2nd mem map */ tdfx_info->addr1 = (pci_read_config(dev, 0x14, 4) & 0xffff0000); #ifdef DEBUG device_printf(dev, "Base1 @ 0x%x\n", tdfx_info->addr1); #endif tdfx_info->memrange2 = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid, RF_ACTIVE | RF_SHAREABLE); if(tdfx_info->memrange2 == NULL) { #ifdef DEBUG device_printf(dev, "Mem1 couldn't be allocated, glide may not work."); #endif tdfx_info->memrid2 = 0; } else { tdfx_info->memrid2 = rid; } /* Now to map the PIO stuff */ rid = PCIR_IOBASE0_2; tdfx_info->pio0 = pci_read_config(dev, 0x2c, 2); tdfx_info->pio0max = pci_read_config(dev, 0x30, 2) + tdfx_info->pio0; tdfx_info->piorange = bus_alloc_resource_any(dev, SYS_RES_IOPORT, &rid, RF_ACTIVE | RF_SHAREABLE); if(tdfx_info->piorange == NULL) { #ifdef DEBUG device_printf(dev, "Couldn't map PIO range."); #endif tdfx_info->piorid = 0; } else { tdfx_info->piorid = rid; } } else { tdfx_info->addr1 = 0; tdfx_info->memrange2 = NULL; tdfx_info->piorange = NULL; } /* * Set Writecombining, or at least Uncacheable for the memory region, if we * are able to */ if(tdfx_setmtrr(dev) != 0) { #ifdef DEBUG device_printf(dev, "Some weird error setting MTRRs"); #endif return -1; } /* * make_dev registers the cdev to access the 3dfx card from /dev * use hex here for the dev num, simply to provide better support if > 10 * voodoo cards, for the mad. The user must set the link, or use MAKEDEV. * Why would we want that many voodoo cards anyhow? */ tdfx_info->devt = make_dev(&tdfx_cdev, device_get_unit(dev), UID_ROOT, GID_WHEEL, 0600, "3dfx%x", device_get_unit(dev)); tdfx_info->devt->si_drv1 = tdfx_info; return 0; }
static int xhci_pci_attach(device_t self) { struct xhci_softc *sc = device_get_softc(self); int count, err, rid; /* XXX check for 64-bit capability */ if (xhci_init(sc, self)) { device_printf(self, "Could not initialize softc\n"); goto error; } pci_enable_busmaster(self); rid = PCI_XHCI_CBMEM; sc->sc_io_res = bus_alloc_resource_any(self, SYS_RES_MEMORY, &rid, RF_ACTIVE); if (!sc->sc_io_res) { device_printf(self, "Could not map memory\n"); goto error; } sc->sc_io_tag = rman_get_bustag(sc->sc_io_res); sc->sc_io_hdl = rman_get_bushandle(sc->sc_io_res); sc->sc_io_size = rman_get_size(sc->sc_io_res); usb_callout_init_mtx(&sc->sc_callout, &sc->sc_bus.bus_mtx, 0); sc->sc_irq_rid = 0; if (xhci_use_msi) { count = pci_msi_count(self); if (count >= 1) { count = 1; if (pci_alloc_msi(self, &count) == 0) { if (bootverbose) device_printf(self, "MSI enabled\n"); sc->sc_irq_rid = 1; } } } sc->sc_irq_res = bus_alloc_resource_any(self, SYS_RES_IRQ, &sc->sc_irq_rid, RF_SHAREABLE | RF_ACTIVE); if (sc->sc_irq_res == NULL) { device_printf(self, "Could not allocate IRQ\n"); /* goto error; FALLTHROUGH - use polling */ } sc->sc_bus.bdev = device_add_child(self, "usbus", -1); if (sc->sc_bus.bdev == NULL) { device_printf(self, "Could not add USB device\n"); goto error; } device_set_ivars(sc->sc_bus.bdev, &sc->sc_bus); sprintf(sc->sc_vendor, "0x%04x", pci_get_vendor(self)); if (sc->sc_irq_res != NULL) { err = bus_setup_intr(self, sc->sc_irq_res, INTR_TYPE_BIO | INTR_MPSAFE, NULL, (driver_intr_t *)xhci_interrupt, sc, &sc->sc_intr_hdl); if (err != 0) { device_printf(self, "Could not setup IRQ, err=%d\n", err); sc->sc_intr_hdl = NULL; } } if (sc->sc_irq_res == NULL || sc->sc_intr_hdl == NULL || xhci_use_polling() != 0) { device_printf(self, "Interrupt polling at %dHz\n", hz); USB_BUS_LOCK(&sc->sc_bus); xhci_interrupt_poll(sc); USB_BUS_UNLOCK(&sc->sc_bus); } /* On Intel chipsets reroute ports from EHCI to XHCI controller. */ switch (pci_get_devid(self)) { case 0x9c318086: /* Panther Point */ case 0x1e318086: /* Panther Point */ case 0x8c318086: /* Lynx Point */ sc->sc_port_route = &xhci_pci_port_route; sc->sc_imod_default = XHCI_IMOD_DEFAULT_LP; break; default: break; } xhci_pci_take_controller(self); err = xhci_halt_controller(sc); if (err == 0) err = xhci_start_controller(sc); if (err == 0) err = device_probe_and_attach(sc->sc_bus.bdev); if (err) { device_printf(self, "XHCI halt/start/probe failed err=%d\n", err); goto error; } return (0); error: xhci_pci_detach(self); return (ENXIO); }
/*main(int argc, char *argv[])*/ int pci_scan(pciinfo_t *pci_list,unsigned *num_pci) { unsigned int idx = 0; struct pci_config_reg pcr; int do_mode1_scan = 0; #if !defined(__alpha__) && !defined(__powerpc__) int do_mode2_scan = 0; #endif int func, hostbridges=0; int ret = -1; pci_lst = pci_list; *num_pci = 0; ret = enable_os_io(); if (ret != 0) return ret; if((pcr._configtype = pci_config_type()) == 0xFFFF) return ENODEV; /* Try pci config 1 probe first */ if ((pcr._configtype == 1) || do_mode1_scan) { /*printf("\nPCI probing configuration type 1\n");*/ pcr._ioaddr = 0xFFFF; pcr._pcibuses[0] = 0; pcr._pcinumbus = 1; pcr._pcibusidx = 0; do { /*printf("Probing for devices on PCI bus %d:\n\n", pcr._pcibusidx);*/ for (pcr._cardnum = 0x0; pcr._cardnum < MAX_PCI_DEVICES_PER_BUS; pcr._cardnum += 0x1) { func = 0; do { /* loop over the different functions, if present */ pcr._device_vendor = pci_get_vendor(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum, func); if ((pcr._vendor == 0xFFFF) || (pcr._device == 0xFFFF)) break; /* nothing there */ /*printf("\npci bus 0x%x cardnum 0x%02x function 0x%04x: vendor 0x%04x device 0x%04x\n", pcr._pcibuses[pcr._pcibusidx], pcr._cardnum, func, pcr._vendor, pcr._device);*/ pcibus = pcr._pcibuses[pcr._pcibusidx]; pcicard = pcr._cardnum; pcifunc = func; pcr._status_command = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_CMD_STAT_REG); pcr._class_revision = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_CLASS_REG); pcr._bist_header_latency_cache = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_HEADER_MISC); pcr._base0 = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_MAP_REG_START); pcr._base1 = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_MAP_REG_START+4); pcr._base2 = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_MAP_REG_START+8); pcr._base3 = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_MAP_REG_START+0x0C); pcr._base4 = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_MAP_REG_START+0x10); pcr._base5 = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_MAP_REG_START+0x14); pcr._baserom = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_MAP_ROM_REG); pcr._max_min_ipin_iline = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_INTERRUPT_REG); pcr._user_config = pci_config_read_long(pcr._pcibuses[pcr._pcibusidx], pcr._cardnum,func,PCI_REG_USERCONFIG); /* check for pci-pci bridges */ #define PCI_CLASS_MASK 0xff000000 #define PCI_SUBCLASS_MASK 0x00ff0000 #define PCI_CLASS_BRIDGE 0x06000000 #define PCI_SUBCLASS_BRIDGE_PCI 0x00040000 switch(pcr._class_revision & (PCI_CLASS_MASK|PCI_SUBCLASS_MASK)) { case PCI_CLASS_BRIDGE|PCI_SUBCLASS_BRIDGE_PCI: if (pcr._secondary_bus_number > 0) { pcr._pcibuses[pcr._pcinumbus++] = pcr._secondary_bus_number; } break; case PCI_CLASS_BRIDGE: if ( ++hostbridges > 1) { pcr._pcibuses[pcr._pcinumbus] = pcr._pcinumbus; pcr._pcinumbus++; } break; default: break; } if((func==0) && ((pcr._header_type & PCI_MULTIFUNC_DEV) == 0)) { /* not a multi function device */ func = 8; } else { func++; } if (idx++ >= MAX_PCI_DEVICES) continue; identify_card(&pcr, (*num_pci)++); } while( func < 8 ); } } while (++pcr._pcibusidx < pcr._pcinumbus); } #if !defined(__alpha__) && !defined(__powerpc__) && !defined(__sh__) /* Now try pci config 2 probe (deprecated) */ if ((pcr._configtype == 2) || do_mode2_scan) { outb(PCI_MODE2_ENABLE_REG, 0xF1); outb(PCI_MODE2_FORWARD_REG, 0x00); /* bus 0 for now */ /*printf("\nPCI probing configuration type 2\n");*/ pcr._pcibuses[0] = 0; pcr._pcinumbus = 1; pcr._pcibusidx = 0; idx = 0; do { for (pcr._ioaddr = 0xC000; pcr._ioaddr < 0xD000; pcr._ioaddr += 0x0100) { outb(PCI_MODE2_FORWARD_REG, pcr._pcibuses[pcr._pcibusidx]); /* bus 0 for now */ pcr._device_vendor = inl(pcr._ioaddr); outb(PCI_MODE2_FORWARD_REG, 0x00); /* bus 0 for now */ if ((pcr._vendor == 0xFFFF) || (pcr._device == 0xFFFF)) continue; if ((pcr._vendor == 0xF0F0) || (pcr._device == 0xF0F0)) continue; /* catch ASUS P55TP4XE motherboards */ /*printf("\npci bus 0x%x slot at 0x%04x, vendor 0x%04x device 0x%04x\n", pcr._pcibuses[pcr._pcibusidx], pcr._ioaddr, pcr._vendor, pcr._device);*/ pcibus = pcr._pcibuses[pcr._pcibusidx] ; pcicard = pcr._ioaddr ; pcifunc = 0 ; outb(PCI_MODE2_FORWARD_REG, pcr._pcibuses[pcr._pcibusidx]); /* bus 0 for now */ pcr._status_command = inl(pcr._ioaddr + 0x04); pcr._class_revision = inl(pcr._ioaddr + 0x08); pcr._bist_header_latency_cache = inl(pcr._ioaddr + 0x0C); pcr._base0 = inl(pcr._ioaddr + 0x10); pcr._base1 = inl(pcr._ioaddr + 0x14); pcr._base2 = inl(pcr._ioaddr + 0x18); pcr._base3 = inl(pcr._ioaddr + 0x1C); pcr._base4 = inl(pcr._ioaddr + 0x20); pcr._base5 = inl(pcr._ioaddr + 0x24); pcr._baserom = inl(pcr._ioaddr + 0x30); pcr._max_min_ipin_iline = inl(pcr._ioaddr + 0x3C); pcr._user_config = inl(pcr._ioaddr + 0x40); outb(PCI_MODE2_FORWARD_REG, 0x00); /* bus 0 for now */ /* check for pci-pci bridges (currently we only know Digital) */ if ((pcr._vendor == 0x1011) && (pcr._device == 0x0001)) if (pcr._secondary_bus_number > 0) pcr._pcibuses[pcr._pcinumbus++] = pcr._secondary_bus_number; if (idx++ >= MAX_PCI_DEVICES) continue; identify_card(&pcr, (*num_pci)++); } } while (++pcr._pcibusidx < pcr._pcinumbus); outb(PCI_MODE2_ENABLE_REG, 0x00); } #endif /* !__alpha__ && !__powerpc__ && !__sh__ */ disable_os_io(); return 0 ; }
static int uhci_pci_attach(device_t self) { uhci_softc_t *sc = device_get_softc(self); int rid; int err; /* initialise some bus fields */ sc->sc_bus.parent = self; sc->sc_bus.devices = sc->sc_devices; sc->sc_bus.devices_max = UHCI_MAX_DEVICES; sc->sc_bus.dma_bits = 32; /* get all DMA memory */ if (usb_bus_mem_alloc_all(&sc->sc_bus, USB_GET_DMA_TAG(self), &uhci_iterate_hw_softc)) { return ENOMEM; } sc->sc_dev = self; pci_enable_busmaster(self); rid = PCI_UHCI_BASE_REG; sc->sc_io_res = bus_alloc_resource_any(self, SYS_RES_IOPORT, &rid, RF_ACTIVE); if (!sc->sc_io_res) { device_printf(self, "Could not map ports\n"); goto error; } sc->sc_io_tag = rman_get_bustag(sc->sc_io_res); sc->sc_io_hdl = rman_get_bushandle(sc->sc_io_res); sc->sc_io_size = rman_get_size(sc->sc_io_res); /* disable interrupts */ bus_space_write_2(sc->sc_io_tag, sc->sc_io_hdl, UHCI_INTR, 0); rid = 0; sc->sc_irq_res = bus_alloc_resource_any(self, SYS_RES_IRQ, &rid, RF_SHAREABLE | RF_ACTIVE); if (sc->sc_irq_res == NULL) { device_printf(self, "Could not allocate irq\n"); goto error; } sc->sc_bus.bdev = device_add_child(self, "usbus", -1); if (!sc->sc_bus.bdev) { device_printf(self, "Could not add USB device\n"); goto error; } device_set_ivars(sc->sc_bus.bdev, &sc->sc_bus); /* * uhci_pci_match must never return NULL if uhci_pci_probe * succeeded */ device_set_desc(sc->sc_bus.bdev, uhci_pci_match(self)); switch (pci_get_vendor(self)) { case PCI_UHCI_VENDORID_INTEL: sprintf(sc->sc_vendor, "Intel"); break; case PCI_UHCI_VENDORID_HP: sprintf(sc->sc_vendor, "HP"); break; case PCI_UHCI_VENDORID_VIA: sprintf(sc->sc_vendor, "VIA"); break; default: if (bootverbose) { device_printf(self, "(New UHCI DeviceId=0x%08x)\n", pci_get_devid(self)); } sprintf(sc->sc_vendor, "(0x%04x)", pci_get_vendor(self)); } switch (pci_read_config(self, PCI_USBREV, 1) & PCI_USB_REV_MASK) { case PCI_USB_REV_PRE_1_0: sc->sc_bus.usbrev = USB_REV_PRE_1_0; break; case PCI_USB_REV_1_0: sc->sc_bus.usbrev = USB_REV_1_0; break; default: /* Quirk for Parallels Desktop 4.0 */ device_printf(self, "USB revision is unknown. Assuming v1.1.\n"); sc->sc_bus.usbrev = USB_REV_1_1; break; } #if (__FreeBSD_version >= 700031) err = bus_setup_intr(self, sc->sc_irq_res, INTR_TYPE_BIO | INTR_MPSAFE, NULL, (driver_intr_t *)uhci_interrupt, sc, &sc->sc_intr_hdl); #else err = bus_setup_intr(self, sc->sc_irq_res, INTR_TYPE_BIO | INTR_MPSAFE, (driver_intr_t *)uhci_interrupt, sc, &sc->sc_intr_hdl); #endif if (err) { device_printf(self, "Could not setup irq, %d\n", err); sc->sc_intr_hdl = NULL; goto error; } /* * Set the PIRQD enable bit and switch off all the others. We don't * want legacy support to interfere with us XXX Does this also mean * that the BIOS won't touch the keyboard anymore if it is connected * to the ports of the root hub? */ #ifdef USB_DEBUG if (pci_read_config(self, PCI_LEGSUP, 2) != PCI_LEGSUP_USBPIRQDEN) { device_printf(self, "LegSup = 0x%04x\n", pci_read_config(self, PCI_LEGSUP, 2)); } #endif pci_write_config(self, PCI_LEGSUP, PCI_LEGSUP_USBPIRQDEN, 2); err = uhci_init(sc); if (!err) { err = device_probe_and_attach(sc->sc_bus.bdev); } if (err) { device_printf(self, "USB init failed\n"); goto error; } return (0); error: uhci_pci_detach(self); return (ENXIO); }
int qla_eioctl(struct cdev *dev, u_long cmd, caddr_t data, int fflag, struct thread *td) { qla_host_t *ha; int rval = 0; qla_reg_val_t *rv; qla_rd_flash_t *rdf; qla_wr_flash_t *wrf; qla_rd_pci_ids_t *pci_ids; device_t pci_dev; if ((ha = (qla_host_t *)dev->si_drv1) == NULL) return ENXIO; pci_dev= ha->pci_dev; switch(cmd) { case QLA_RDWR_REG: rv = (qla_reg_val_t *)data; if (rv->direct) { if (rv->rd) { rv->val = READ_OFFSET32(ha, rv->reg); } else { WRITE_OFFSET32(ha, rv->reg, rv->val); } } else { if ((rval = qla_rdwr_indreg32(ha, rv->reg, &rv->val, rv->rd))) rval = ENXIO; } break; case QLA_RD_FLASH: rdf = (qla_rd_flash_t *)data; if ((rval = qla_rd_flash32(ha, rdf->off, &rdf->data))) rval = ENXIO; break; case QLA_WR_FLASH: wrf = (qla_wr_flash_t *)data; if ((rval = qla_wr_flash_buffer(ha, wrf->off, wrf->size, wrf->buffer, wrf->pattern))) rval = ENXIO; break; case QLA_ERASE_FLASH: if (qla_erase_flash(ha, ((qla_erase_flash_t *)data)->off, ((qla_erase_flash_t *)data)->size)) rval = ENXIO; break; case QLA_RD_PCI_IDS: pci_ids = (qla_rd_pci_ids_t *)data; pci_ids->ven_id = pci_get_vendor(pci_dev); pci_ids->dev_id = pci_get_device(pci_dev); pci_ids->subsys_ven_id = pci_get_subvendor(pci_dev); pci_ids->subsys_dev_id = pci_get_subdevice(pci_dev); pci_ids->rev_id = pci_read_config(pci_dev, PCIR_REVID, 1); break; default: break; } return rval; }
static int uhci_pci_attach(device_t self) { uhci_softc_t *sc = device_get_softc(self); int rid; int err; pci_enable_busmaster(self); rid = PCI_UHCI_BASE_REG; sc->io_res = bus_alloc_resource(self, SYS_RES_IOPORT, &rid, 0, ~0, 1, RF_ACTIVE); if (!sc->io_res) { device_printf(self, "Could not map ports\n"); return ENXIO; } sc->iot = rman_get_bustag(sc->io_res); sc->ioh = rman_get_bushandle(sc->io_res); /* disable interrupts */ bus_space_write_2(sc->iot, sc->ioh, UHCI_INTR, 0); rid = 0; sc->irq_res = bus_alloc_resource(self, SYS_RES_IRQ, &rid, 0, ~0, 1, RF_SHAREABLE | RF_ACTIVE); if (sc->irq_res == NULL) { device_printf(self, "Could not allocate irq\n"); uhci_pci_detach(self); return ENXIO; } sc->sc_bus.bdev = device_add_child(self, "usb", -1); if (!sc->sc_bus.bdev) { device_printf(self, "Could not add USB device\n"); uhci_pci_detach(self); return ENOMEM; } device_set_ivars(sc->sc_bus.bdev, sc); /* uhci_pci_match must never return NULL if uhci_pci_probe succeeded */ device_set_desc(sc->sc_bus.bdev, uhci_pci_match(self)); switch (pci_get_vendor(self)) { case PCI_UHCI_VENDORID_INTEL: sprintf(sc->sc_vendor, "Intel"); break; case PCI_UHCI_VENDORID_VIA: sprintf(sc->sc_vendor, "VIA"); break; default: if (bootverbose) device_printf(self, "(New UHCI DeviceId=0x%08x)\n", pci_get_devid(self)); sprintf(sc->sc_vendor, "(0x%04x)", pci_get_vendor(self)); } switch (pci_read_config(self, PCI_USBREV, 1) & PCI_USBREV_MASK) { case PCI_USBREV_PRE_1_0: sc->sc_bus.usbrev = USBREV_PRE_1_0; break; case PCI_USBREV_1_0: sc->sc_bus.usbrev = USBREV_1_0; break; default: sc->sc_bus.usbrev = USBREV_UNKNOWN; break; } err = bus_setup_intr(self, sc->irq_res, INTR_TYPE_BIO, (driver_intr_t *) uhci_intr, sc, &sc->ih); if (err) { device_printf(self, "Could not setup irq, %d\n", err); sc->ih = NULL; uhci_pci_detach(self); return ENXIO; } /* * Set the PIRQD enable bit and switch off all the others. We don't * want legacy support to interfere with us XXX Does this also mean * that the BIOS won't touch the keyboard anymore if it is connected * to the ports of the root hub? */ #ifdef USB_DEBUG if (pci_read_config(self, PCI_LEGSUP, 2) != PCI_LEGSUP_USBPIRQDEN) device_printf(self, "LegSup = 0x%04x\n", pci_read_config(self, PCI_LEGSUP, 2)); #endif pci_write_config(self, PCI_LEGSUP, PCI_LEGSUP_USBPIRQDEN, 2); err = uhci_init(sc); if (!err) err = device_probe_and_attach(sc->sc_bus.bdev); if (err) { device_printf(self, "USB init failed\n"); uhci_pci_detach(self); return EIO; } return 0; /* success */ }
static int hpt_attach(device_t dev) { PHBA hba = (PHBA)device_get_softc(dev); HIM *him = hba->ldm_adapter.him; PCI_ID pci_id; HPT_UINT size; PVBUS vbus; PVBUS_EXT vbus_ext; KdPrint(("hpt_attach(%d/%d/%d)", pci_get_bus(dev), pci_get_slot(dev), pci_get_function(dev))); #if __FreeBSD_version >=440000 pci_enable_busmaster(dev); #endif pci_id.vid = pci_get_vendor(dev); pci_id.did = pci_get_device(dev); pci_id.rev = pci_get_revid(dev); pci_id.subsys = (HPT_U32)(pci_get_subdevice(dev)) << 16 | pci_get_subvendor(dev); size = him->get_adapter_size(&pci_id); hba->ldm_adapter.him_handle = malloc(size, M_DEVBUF, M_WAITOK); if (!hba->ldm_adapter.him_handle) return ENXIO; hba->pcidev = dev; hba->pciaddr.tree = 0; hba->pciaddr.bus = pci_get_bus(dev); hba->pciaddr.device = pci_get_slot(dev); hba->pciaddr.function = pci_get_function(dev); if (!him->create_adapter(&pci_id, hba->pciaddr, hba->ldm_adapter.him_handle, hba)) { free(hba->ldm_adapter.him_handle, M_DEVBUF); return -1; } os_printk("adapter at PCI %d:%d:%d, IRQ %d", hba->pciaddr.bus, hba->pciaddr.device, hba->pciaddr.function, pci_get_irq(dev)); if (!ldm_register_adapter(&hba->ldm_adapter)) { size = ldm_get_vbus_size(); vbus_ext = malloc(sizeof(VBUS_EXT) + size, M_DEVBUF, M_WAITOK); if (!vbus_ext) { free(hba->ldm_adapter.him_handle, M_DEVBUF); return -1; } memset(vbus_ext, 0, sizeof(VBUS_EXT)); vbus_ext->ext_type = EXT_TYPE_VBUS; ldm_create_vbus((PVBUS)vbus_ext->vbus, vbus_ext); ldm_register_adapter(&hba->ldm_adapter); } ldm_for_each_vbus(vbus, vbus_ext) { if (hba->ldm_adapter.vbus==vbus) { hba->vbus_ext = vbus_ext; hba->next = vbus_ext->hba_list; vbus_ext->hba_list = hba; break; } } return 0; }
static void ataaction(struct cam_sim *sim, union ccb *ccb) { device_t dev, parent; struct ata_channel *ch; CAM_DEBUG(ccb->ccb_h.path, CAM_DEBUG_TRACE, ("ataaction func_code=%x\n", ccb->ccb_h.func_code)); ch = (struct ata_channel *)cam_sim_softc(sim); dev = ch->dev; switch (ccb->ccb_h.func_code) { /* Common cases first */ case XPT_ATA_IO: /* Execute the requested I/O operation */ case XPT_SCSI_IO: if (ata_check_ids(dev, ccb)) return; if ((ch->devices & ((ATA_ATA_MASTER | ATA_ATAPI_MASTER) << ccb->ccb_h.target_id)) == 0) { ccb->ccb_h.status = CAM_SEL_TIMEOUT; break; } if (ch->running) device_printf(dev, "already running!\n"); if (ccb->ccb_h.func_code == XPT_ATA_IO && (ccb->ataio.cmd.flags & CAM_ATAIO_CONTROL) && (ccb->ataio.cmd.control & ATA_A_RESET)) { struct ata_res *res = &ccb->ataio.res; bzero(res, sizeof(*res)); if (ch->devices & (ATA_ATA_MASTER << ccb->ccb_h.target_id)) { res->lba_high = 0; res->lba_mid = 0; } else { res->lba_high = 0xeb; res->lba_mid = 0x14; } ccb->ccb_h.status = CAM_REQ_CMP; break; } ata_cam_begin_transaction(dev, ccb); return; case XPT_EN_LUN: /* Enable LUN as a target */ case XPT_TARGET_IO: /* Execute target I/O request */ case XPT_ACCEPT_TARGET_IO: /* Accept Host Target Mode CDB */ case XPT_CONT_TARGET_IO: /* Continue Host Target I/O Connection*/ case XPT_ABORT: /* Abort the specified CCB */ /* XXX Implement */ ccb->ccb_h.status = CAM_REQ_INVALID; break; case XPT_SET_TRAN_SETTINGS: { struct ccb_trans_settings *cts = &ccb->cts; struct ata_cam_device *d; if (ata_check_ids(dev, ccb)) return; if (cts->type == CTS_TYPE_CURRENT_SETTINGS) d = &ch->curr[ccb->ccb_h.target_id]; else d = &ch->user[ccb->ccb_h.target_id]; if (ch->flags & ATA_SATA) { if (cts->xport_specific.sata.valid & CTS_SATA_VALID_REVISION) d->revision = cts->xport_specific.sata.revision; if (cts->xport_specific.sata.valid & CTS_SATA_VALID_MODE) { if (cts->type == CTS_TYPE_CURRENT_SETTINGS) { d->mode = ATA_SETMODE(ch->dev, ccb->ccb_h.target_id, cts->xport_specific.sata.mode); } else d->mode = cts->xport_specific.sata.mode; } if (cts->xport_specific.sata.valid & CTS_SATA_VALID_BYTECOUNT) d->bytecount = min(8192, cts->xport_specific.sata.bytecount); if (cts->xport_specific.sata.valid & CTS_SATA_VALID_ATAPI) d->atapi = cts->xport_specific.sata.atapi; if (cts->xport_specific.sata.valid & CTS_SATA_VALID_CAPS) d->caps = cts->xport_specific.sata.caps; } else { if (cts->xport_specific.ata.valid & CTS_ATA_VALID_MODE) { if (cts->type == CTS_TYPE_CURRENT_SETTINGS) { d->mode = ATA_SETMODE(ch->dev, ccb->ccb_h.target_id, cts->xport_specific.ata.mode); } else d->mode = cts->xport_specific.ata.mode; } if (cts->xport_specific.ata.valid & CTS_ATA_VALID_BYTECOUNT) d->bytecount = cts->xport_specific.ata.bytecount; if (cts->xport_specific.ata.valid & CTS_ATA_VALID_ATAPI) d->atapi = cts->xport_specific.ata.atapi; if (cts->xport_specific.ata.valid & CTS_ATA_VALID_CAPS) d->caps = cts->xport_specific.ata.caps; } ccb->ccb_h.status = CAM_REQ_CMP; break; } case XPT_GET_TRAN_SETTINGS: { struct ccb_trans_settings *cts = &ccb->cts; struct ata_cam_device *d; if (ata_check_ids(dev, ccb)) return; if (cts->type == CTS_TYPE_CURRENT_SETTINGS) d = &ch->curr[ccb->ccb_h.target_id]; else d = &ch->user[ccb->ccb_h.target_id]; cts->protocol = PROTO_UNSPECIFIED; cts->protocol_version = PROTO_VERSION_UNSPECIFIED; if (ch->flags & ATA_SATA) { cts->transport = XPORT_SATA; cts->transport_version = XPORT_VERSION_UNSPECIFIED; cts->xport_specific.sata.valid = 0; cts->xport_specific.sata.mode = d->mode; cts->xport_specific.sata.valid |= CTS_SATA_VALID_MODE; cts->xport_specific.sata.bytecount = d->bytecount; cts->xport_specific.sata.valid |= CTS_SATA_VALID_BYTECOUNT; if (cts->type == CTS_TYPE_CURRENT_SETTINGS) { cts->xport_specific.sata.revision = ATA_GETREV(dev, ccb->ccb_h.target_id); if (cts->xport_specific.sata.revision != 0xff) { cts->xport_specific.sata.valid |= CTS_SATA_VALID_REVISION; } cts->xport_specific.sata.caps = d->caps & CTS_SATA_CAPS_D; if (ch->pm_level) { cts->xport_specific.sata.caps |= CTS_SATA_CAPS_H_PMREQ; } cts->xport_specific.sata.caps &= ch->user[ccb->ccb_h.target_id].caps; } else { cts->xport_specific.sata.revision = d->revision; cts->xport_specific.sata.valid |= CTS_SATA_VALID_REVISION; cts->xport_specific.sata.caps = d->caps; } cts->xport_specific.sata.valid |= CTS_SATA_VALID_CAPS; cts->xport_specific.sata.atapi = d->atapi; cts->xport_specific.sata.valid |= CTS_SATA_VALID_ATAPI; } else { cts->transport = XPORT_ATA; cts->transport_version = XPORT_VERSION_UNSPECIFIED; cts->xport_specific.ata.valid = 0; cts->xport_specific.ata.mode = d->mode; cts->xport_specific.ata.valid |= CTS_ATA_VALID_MODE; cts->xport_specific.ata.bytecount = d->bytecount; cts->xport_specific.ata.valid |= CTS_ATA_VALID_BYTECOUNT; if (cts->type == CTS_TYPE_CURRENT_SETTINGS) { cts->xport_specific.ata.caps = d->caps & CTS_ATA_CAPS_D; if (!(ch->flags & ATA_NO_48BIT_DMA)) cts->xport_specific.ata.caps |= CTS_ATA_CAPS_H_DMA48; cts->xport_specific.ata.caps &= ch->user[ccb->ccb_h.target_id].caps; } else cts->xport_specific.ata.caps = d->caps; cts->xport_specific.ata.valid |= CTS_ATA_VALID_CAPS; cts->xport_specific.ata.atapi = d->atapi; cts->xport_specific.ata.valid |= CTS_ATA_VALID_ATAPI; } ccb->ccb_h.status = CAM_REQ_CMP; break; } case XPT_RESET_BUS: /* Reset the specified SCSI bus */ case XPT_RESET_DEV: /* Bus Device Reset the specified SCSI device */ ata_reinit(dev); ccb->ccb_h.status = CAM_REQ_CMP; break; case XPT_TERM_IO: /* Terminate the I/O process */ /* XXX Implement */ ccb->ccb_h.status = CAM_REQ_INVALID; break; case XPT_PATH_INQ: /* Path routing inquiry */ { struct ccb_pathinq *cpi = &ccb->cpi; parent = device_get_parent(dev); cpi->version_num = 1; /* XXX??? */ cpi->hba_inquiry = PI_SDTR_ABLE; cpi->target_sprt = 0; cpi->hba_misc = PIM_SEQSCAN | PIM_UNMAPPED; cpi->hba_eng_cnt = 0; if (ch->flags & ATA_NO_SLAVE) cpi->max_target = 0; else cpi->max_target = 1; cpi->max_lun = 0; cpi->initiator_id = 0; cpi->bus_id = cam_sim_bus(sim); if (ch->flags & ATA_SATA) cpi->base_transfer_speed = 150000; else cpi->base_transfer_speed = 3300; strncpy(cpi->sim_vid, "FreeBSD", SIM_IDLEN); strncpy(cpi->hba_vid, "ATA", HBA_IDLEN); strncpy(cpi->dev_name, cam_sim_name(sim), DEV_IDLEN); cpi->unit_number = cam_sim_unit(sim); if (ch->flags & ATA_SATA) cpi->transport = XPORT_SATA; else cpi->transport = XPORT_ATA; cpi->transport_version = XPORT_VERSION_UNSPECIFIED; cpi->protocol = PROTO_ATA; cpi->protocol_version = PROTO_VERSION_UNSPECIFIED; cpi->maxio = ch->dma.max_iosize ? ch->dma.max_iosize : DFLTPHYS; if (device_get_devclass(device_get_parent(parent)) == devclass_find("pci")) { cpi->hba_vendor = pci_get_vendor(parent); cpi->hba_device = pci_get_device(parent); cpi->hba_subvendor = pci_get_subvendor(parent); cpi->hba_subdevice = pci_get_subdevice(parent); } cpi->ccb_h.status = CAM_REQ_CMP; break; } default: ccb->ccb_h.status = CAM_REQ_INVALID; break; } xpt_done(ccb); }
static int xhci_pci_attach(device_t self) { struct xhci_softc *sc = device_get_softc(self); int count, err, rid; uint8_t usedma32; rid = PCI_XHCI_CBMEM; sc->sc_io_res = bus_alloc_resource_any(self, SYS_RES_MEMORY, &rid, RF_ACTIVE); if (!sc->sc_io_res) { device_printf(self, "Could not map memory\n"); return (ENOMEM); } sc->sc_io_tag = rman_get_bustag(sc->sc_io_res); sc->sc_io_hdl = rman_get_bushandle(sc->sc_io_res); sc->sc_io_size = rman_get_size(sc->sc_io_res); /* check for USB 3.0 controllers which don't support 64-bit DMA */ switch (pci_get_devid(self)) { case 0x01941033: /* NEC uPD720200 USB 3.0 controller */ case 0x00141912: /* NEC uPD720201 USB 3.0 controller */ case 0x78141022: /* AMD A10-7300, tested does not work w/64-bit DMA */ usedma32 = 1; break; default: usedma32 = 0; break; } if (xhci_init(sc, self, usedma32)) { device_printf(self, "Could not initialize softc\n"); bus_release_resource(self, SYS_RES_MEMORY, PCI_XHCI_CBMEM, sc->sc_io_res); return (ENXIO); } pci_enable_busmaster(self); usb_callout_init_mtx(&sc->sc_callout, &sc->sc_bus.bus_lock, 0); rid = 0; if (xhci_use_msi) { count = pci_msi_count(self); if (count >= 1) { count = 1; if (pci_alloc_msi(self, &rid, 1, count) == 0) { if (bootverbose) device_printf(self, "MSI enabled\n"); sc->sc_irq_rid = 1; } } } /* * hw.usb.xhci.use_polling=1 to force polling. */ if (xhci_use_polling() == 0) { sc->sc_irq_res = bus_alloc_resource_any( self, SYS_RES_IRQ, &sc->sc_irq_rid, RF_SHAREABLE | RF_ACTIVE); if (sc->sc_irq_res == NULL) { pci_release_msi(self); device_printf(self, "Could not allocate IRQ\n"); /* goto error; FALLTHROUGH - use polling */ } } sc->sc_bus.bdev = device_add_child(self, "usbus", -1); if (sc->sc_bus.bdev == NULL) { device_printf(self, "Could not add USB device\n"); goto error; } device_set_ivars(sc->sc_bus.bdev, &sc->sc_bus); ksprintf(sc->sc_vendor, "0x%04x", pci_get_vendor(self)); if (sc->sc_irq_res != NULL) { err = bus_setup_intr(self, sc->sc_irq_res, INTR_MPSAFE, (driver_intr_t *)xhci_interrupt, sc, &sc->sc_intr_hdl, NULL); if (err != 0) { bus_release_resource(self, SYS_RES_IRQ, rman_get_rid(sc->sc_irq_res), sc->sc_irq_res); sc->sc_irq_res = NULL; pci_release_msi(self); device_printf(self, "Could not setup IRQ, err=%d\n", err); sc->sc_intr_hdl = NULL; } } if (sc->sc_irq_res == NULL || sc->sc_intr_hdl == NULL) { if (xhci_use_polling() != 0) { device_printf(self, "Interrupt polling at %dHz\n", hz); USB_BUS_LOCK(&sc->sc_bus); xhci_interrupt_poll(sc); USB_BUS_UNLOCK(&sc->sc_bus); } else goto error; } /* On Intel chipsets reroute ports from EHCI to XHCI controller. */ switch (pci_get_devid(self)) { case 0x0f358086: /* BayTrail */ case 0x9c318086: /* Panther Point */ case 0x1e318086: /* Panther Point */ case 0x8c318086: /* Lynx Point */ case 0x8cb18086: /* Wildcat Point */ case 0x9cb18086: /* Wildcat Point-LP */ sc->sc_port_route = &xhci_pci_port_route; sc->sc_imod_default = XHCI_IMOD_DEFAULT_LP; break; default: break; } xhci_pci_take_controller(self); err = xhci_halt_controller(sc); if (err == 0) err = xhci_start_controller(sc); if (err == 0) err = device_probe_and_attach(sc->sc_bus.bdev); if (err) { device_printf(self, "XHCI halt/start/probe failed err=%d\n", err); goto error; } return (0); error: xhci_pci_detach(self); return (ENXIO); }
void intel_detect_pch(struct drm_device *dev) { struct drm_i915_private *dev_priv = dev->dev_private; struct device *pch = NULL; /* In all current cases, num_pipes is equivalent to the PCH_NOP setting * (which really amounts to a PCH but no South Display). */ if (INTEL_INFO(dev)->num_pipes == 0) { dev_priv->pch_type = PCH_NOP; return; } /* XXX The ISA bridge probe causes some old Core2 machines to hang */ if (INTEL_INFO(dev)->gen < 5) return; /* * The reason to probe ISA bridge instead of Dev31:Fun0 is to * make graphics device passthrough work easy for VMM, that only * need to expose ISA bridge to let driver know the real hardware * underneath. This is a requirement from virtualization team. * * In some virtualized environments (e.g. XEN), there is irrelevant * ISA bridge in the system. To work reliably, we should scan trhough * all the ISA bridge devices and check for the first match, instead * of only checking the first one. */ while ((pch = pci_find_class(PCIC_BRIDGE, PCIS_BRIDGE_ISA))) { if (pci_get_vendor(pch) == PCI_VENDOR_INTEL) { unsigned short id = pci_get_device(pch) & INTEL_PCH_DEVICE_ID_MASK; dev_priv->pch_id = id; if (id == INTEL_PCH_IBX_DEVICE_ID_TYPE) { dev_priv->pch_type = PCH_IBX; DRM_DEBUG_KMS("Found Ibex Peak PCH\n"); WARN_ON(!IS_GEN5(dev)); } else if (id == INTEL_PCH_CPT_DEVICE_ID_TYPE) { dev_priv->pch_type = PCH_CPT; DRM_DEBUG_KMS("Found CougarPoint PCH\n"); WARN_ON(!(IS_GEN6(dev) || IS_IVYBRIDGE(dev))); } else if (id == INTEL_PCH_PPT_DEVICE_ID_TYPE) { /* PantherPoint is CPT compatible */ dev_priv->pch_type = PCH_CPT; DRM_DEBUG_KMS("Found PantherPoint PCH\n"); WARN_ON(!(IS_GEN6(dev) || IS_IVYBRIDGE(dev))); } else if (id == INTEL_PCH_LPT_DEVICE_ID_TYPE) { dev_priv->pch_type = PCH_LPT; DRM_DEBUG_KMS("Found LynxPoint PCH\n"); WARN_ON(!IS_HASWELL(dev)); WARN_ON(IS_ULT(dev)); } else if (IS_BROADWELL(dev)) { dev_priv->pch_type = PCH_LPT; dev_priv->pch_id = INTEL_PCH_LPT_LP_DEVICE_ID_TYPE; DRM_DEBUG_KMS("This is Broadwell, assuming " "LynxPoint LP PCH\n"); } else if (id == INTEL_PCH_LPT_LP_DEVICE_ID_TYPE) { dev_priv->pch_type = PCH_LPT; DRM_DEBUG_KMS("Found LynxPoint LP PCH\n"); WARN_ON(!IS_HASWELL(dev)); WARN_ON(!IS_ULT(dev)); } else continue; break; } } if (!pch) DRM_DEBUG_KMS("No PCH found.\n"); #if 0 pci_dev_put(pch); #endif }
static int ql_eioctl(struct cdev *dev, u_long cmd, caddr_t data, int fflag, struct thread *td) { qla_host_t *ha; int rval = 0; device_t pci_dev; struct ifnet *ifp; int count; q80_offchip_mem_val_t val; qla_rd_pci_ids_t *pci_ids; qla_rd_fw_dump_t *fw_dump; union { qla_reg_val_t *rv; qla_rd_flash_t *rdf; qla_wr_flash_t *wrf; qla_erase_flash_t *erf; qla_offchip_mem_val_t *mem; } u; if ((ha = (qla_host_t *)dev->si_drv1) == NULL) return ENXIO; pci_dev= ha->pci_dev; switch(cmd) { case QLA_RDWR_REG: u.rv = (qla_reg_val_t *)data; if (u.rv->direct) { if (u.rv->rd) { u.rv->val = READ_REG32(ha, u.rv->reg); } else { WRITE_REG32(ha, u.rv->reg, u.rv->val); } } else { if ((rval = ql_rdwr_indreg32(ha, u.rv->reg, &u.rv->val, u.rv->rd))) rval = ENXIO; } break; case QLA_RD_FLASH: if (!ha->hw.flags.fdt_valid) { rval = EIO; break; } u.rdf = (qla_rd_flash_t *)data; if ((rval = ql_rd_flash32(ha, u.rdf->off, &u.rdf->data))) rval = ENXIO; break; case QLA_WR_FLASH: ifp = ha->ifp; if (ifp == NULL) { rval = ENXIO; break; } if (ifp->if_drv_flags & IFF_DRV_RUNNING) { rval = ENXIO; break; } if (!ha->hw.flags.fdt_valid) { rval = EIO; break; } u.wrf = (qla_wr_flash_t *)data; if ((rval = ql_wr_flash_buffer(ha, u.wrf->off, u.wrf->size, u.wrf->buffer))) { printf("flash write failed[%d]\n", rval); rval = ENXIO; } break; case QLA_ERASE_FLASH: ifp = ha->ifp; if (ifp == NULL) { rval = ENXIO; break; } if (ifp->if_drv_flags & IFF_DRV_RUNNING) { rval = ENXIO; break; } if (!ha->hw.flags.fdt_valid) { rval = EIO; break; } u.erf = (qla_erase_flash_t *)data; if ((rval = ql_erase_flash(ha, u.erf->off, u.erf->size))) { printf("flash erase failed[%d]\n", rval); rval = ENXIO; } break; case QLA_RDWR_MS_MEM: u.mem = (qla_offchip_mem_val_t *)data; if ((rval = ql_rdwr_offchip_mem(ha, u.mem->off, &val, u.mem->rd))) rval = ENXIO; else { u.mem->data_lo = val.data_lo; u.mem->data_hi = val.data_hi; u.mem->data_ulo = val.data_ulo; u.mem->data_uhi = val.data_uhi; } break; case QLA_RD_FW_DUMP_SIZE: if (ha->hw.mdump_init == 0) { rval = EINVAL; break; } fw_dump = (qla_rd_fw_dump_t *)data; fw_dump->minidump_size = ha->hw.mdump_buffer_size + ha->hw.mdump_template_size; fw_dump->pci_func = ha->pci_func; break; case QLA_RD_FW_DUMP: if (ha->hw.mdump_init == 0) { device_printf(pci_dev, "%s: minidump not initialized\n", __func__); rval = EINVAL; break; } fw_dump = (qla_rd_fw_dump_t *)data; if ((fw_dump->minidump == NULL) || (fw_dump->minidump_size != (ha->hw.mdump_buffer_size + ha->hw.mdump_template_size))) { device_printf(pci_dev, "%s: minidump buffer [%p] size = [%d, %d] invalid\n", __func__, fw_dump->minidump, fw_dump->minidump_size, (ha->hw.mdump_buffer_size + ha->hw.mdump_template_size)); rval = EINVAL; break; } if ((ha->pci_func & 0x1)) { device_printf(pci_dev, "%s: mindump allowed only on Port0\n", __func__); rval = ENXIO; break; } fw_dump->saved = 1; if (ha->offline) { if (ha->enable_minidump) ql_minidump(ha); fw_dump->saved = 0; fw_dump->usec_ts = ha->hw.mdump_usec_ts; if (!ha->hw.mdump_done) { device_printf(pci_dev, "%s: port offline minidump failed\n", __func__); rval = ENXIO; break; } } else { #define QLA_LOCK_MDUMP_MS_TIMEOUT (QLA_LOCK_DEFAULT_MS_TIMEOUT * 5) if (QLA_LOCK(ha, __func__, QLA_LOCK_MDUMP_MS_TIMEOUT, 0) == 0) { if (!ha->hw.mdump_done) { fw_dump->saved = 0; QL_INITIATE_RECOVERY(ha); device_printf(pci_dev, "%s: recovery initiated " " to trigger minidump\n", __func__); } QLA_UNLOCK(ha, __func__); } else { device_printf(pci_dev, "%s: QLA_LOCK() failed0\n", __func__); rval = ENXIO; break; } #define QLNX_DUMP_WAIT_SECS 30 count = QLNX_DUMP_WAIT_SECS * 1000; while (count) { if (ha->hw.mdump_done) break; qla_mdelay(__func__, 100); count -= 100; } if (!ha->hw.mdump_done) { device_printf(pci_dev, "%s: port not offline minidump failed\n", __func__); rval = ENXIO; break; } fw_dump->usec_ts = ha->hw.mdump_usec_ts; if (QLA_LOCK(ha, __func__, QLA_LOCK_MDUMP_MS_TIMEOUT, 0) == 0) { ha->hw.mdump_done = 0; QLA_UNLOCK(ha, __func__); } else { device_printf(pci_dev, "%s: QLA_LOCK() failed1\n", __func__); rval = ENXIO; break; } } if ((rval = copyout(ha->hw.mdump_template, fw_dump->minidump, ha->hw.mdump_template_size))) { device_printf(pci_dev, "%s: template copyout failed\n", __func__); rval = ENXIO; break; } if ((rval = copyout(ha->hw.mdump_buffer, ((uint8_t *)fw_dump->minidump + ha->hw.mdump_template_size), ha->hw.mdump_buffer_size))) { device_printf(pci_dev, "%s: minidump copyout failed\n", __func__); rval = ENXIO; } break; case QLA_RD_DRVR_STATE: rval = ql_drvr_state(ha, (qla_driver_state_t *)data); break; case QLA_RD_SLOWPATH_LOG: rval = ql_slowpath_log(ha, (qla_sp_log_t *)data); break; case QLA_RD_PCI_IDS: pci_ids = (qla_rd_pci_ids_t *)data; pci_ids->ven_id = pci_get_vendor(pci_dev); pci_ids->dev_id = pci_get_device(pci_dev); pci_ids->subsys_ven_id = pci_get_subvendor(pci_dev); pci_ids->subsys_dev_id = pci_get_subdevice(pci_dev); pci_ids->rev_id = pci_read_config(pci_dev, PCIR_REVID, 1); break; default: break; } return rval; }
static int ohci_pci_attach(device_t self) { ohci_softc_t *sc = device_get_softc(self); int err; int rid; /* XXX where does it say so in the spec? */ sc->sc_bus.usbrev = USBREV_1_0; pci_enable_busmaster(self); /* * Some Sun PCIO-2 USB controllers have their intpin register * bogusly set to 0, although it should be 4. Correct that. */ if (pci_get_devid(self) == PCI_OHCI_DEVICEID_PCIO2USB && pci_get_intpin(self) == 0) pci_set_intpin(self, 4); rid = PCI_CBMEM; sc->io_res = bus_alloc_resource_any(self, SYS_RES_MEMORY, &rid, RF_ACTIVE); if (!sc->io_res) { device_printf(self, "Could not map memory\n"); return ENXIO; } sc->iot = rman_get_bustag(sc->io_res); sc->ioh = rman_get_bushandle(sc->io_res); rid = 0; sc->irq_res = bus_alloc_resource_any(self, SYS_RES_IRQ, &rid, RF_SHAREABLE | RF_ACTIVE); if (sc->irq_res == NULL) { device_printf(self, "Could not allocate irq\n"); ohci_pci_detach(self); return ENXIO; } sc->sc_bus.bdev = device_add_child(self, "usb", -1); if (!sc->sc_bus.bdev) { device_printf(self, "Could not add USB device\n"); ohci_pci_detach(self); return ENOMEM; } device_set_ivars(sc->sc_bus.bdev, &sc->sc_bus); /* ohci_pci_match will never return NULL if ohci_pci_probe succeeded */ device_set_desc(sc->sc_bus.bdev, ohci_pci_match(self)); switch (pci_get_vendor(self)) { case PCI_OHCI_VENDORID_ACERLABS: sprintf(sc->sc_vendor, "AcerLabs"); break; case PCI_OHCI_VENDORID_AMD: sprintf(sc->sc_vendor, "AMD"); break; case PCI_OHCI_VENDORID_APPLE: sprintf(sc->sc_vendor, "Apple"); break; case PCI_OHCI_VENDORID_ATI: sprintf(sc->sc_vendor, "ATI"); break; case PCI_OHCI_VENDORID_CMDTECH: sprintf(sc->sc_vendor, "CMDTECH"); break; case PCI_OHCI_VENDORID_NEC: sprintf(sc->sc_vendor, "NEC"); break; case PCI_OHCI_VENDORID_NVIDIA: case PCI_OHCI_VENDORID_NVIDIA2: sprintf(sc->sc_vendor, "nVidia"); break; case PCI_OHCI_VENDORID_OPTI: sprintf(sc->sc_vendor, "OPTi"); break; case PCI_OHCI_VENDORID_SIS: sprintf(sc->sc_vendor, "SiS"); break; default: if (bootverbose) device_printf(self, "(New OHCI DeviceId=0x%08x)\n", pci_get_devid(self)); sprintf(sc->sc_vendor, "(0x%04x)", pci_get_vendor(self)); } err = bus_setup_intr(self, sc->irq_res, INTR_TYPE_BIO, NULL, ohci_intr, sc, &sc->ih); if (err) { device_printf(self, "Could not setup irq, %d\n", err); sc->ih = NULL; ohci_pci_detach(self); return ENXIO; } /* Allocate a parent dma tag for DMA maps */ err = bus_dma_tag_create(bus_get_dma_tag(self), 1, 0, BUS_SPACE_MAXADDR_32BIT, BUS_SPACE_MAXADDR, NULL, NULL, BUS_SPACE_MAXSIZE_32BIT, USB_DMA_NSEG, BUS_SPACE_MAXSIZE_32BIT, 0, NULL, NULL, &sc->sc_bus.parent_dmatag); if (err) { device_printf(self, "Could not allocate parent DMA tag (%d)\n", err); ohci_pci_detach(self); return ENXIO; } /* Allocate a dma tag for transfer buffers */ err = bus_dma_tag_create(sc->sc_bus.parent_dmatag, 1, 0, BUS_SPACE_MAXADDR_32BIT, BUS_SPACE_MAXADDR, NULL, NULL, BUS_SPACE_MAXSIZE_32BIT, USB_DMA_NSEG, BUS_SPACE_MAXSIZE_32BIT, 0, busdma_lock_mutex, &Giant, &sc->sc_bus.buffer_dmatag); if (err) { device_printf(self, "Could not allocate transfer tag (%d)\n", err); ohci_pci_detach(self); return ENXIO; } err = ohci_init(sc); if (!err) { sc->sc_flags |= OHCI_SCFLG_DONEINIT; err = device_probe_and_attach(sc->sc_bus.bdev); } if (err) { device_printf(self, "USB init failed\n"); ohci_pci_detach(self); return EIO; } return 0; }
static int mpt_pci_probe(device_t dev) { const char *desc; int rval; if (pci_get_vendor(dev) != MPI_MANUFACTPAGE_VENDORID_LSILOGIC) return (ENXIO); rval = BUS_PROBE_DEFAULT; switch (pci_get_device(dev)) { case MPI_MANUFACTPAGE_DEVICEID_FC909_FB: desc = "LSILogic FC909 FC Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC909: desc = "LSILogic FC909A FC Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC919: desc = "LSILogic FC919 FC Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC919_LAN_FB: desc = "LSILogic FC919 LAN Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC929: desc = "Dual LSILogic FC929 FC Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC929_LAN_FB: desc = "Dual LSILogic FC929 LAN Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC919X: desc = "LSILogic FC919 FC PCI-X Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC919X_LAN_FB: desc = "LSILogic FC919 LAN PCI-X Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC929X: desc = "Dual LSILogic FC929X 2Gb/s FC PCI-X Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC929X_LAN_FB: desc = "Dual LSILogic FC929X LAN PCI-X Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC949E: desc = "Dual LSILogic FC7X04X 4Gb/s FC PCI-Express Adapter"; break; case MPI_MANUFACTPAGE_DEVICEID_FC949X: desc = "Dual LSILogic FC7X04X 4Gb/s FC PCI-X Adapter"; break; case MPI_MANUFACTPAGE_DEVID_53C1030: case MPI_MANUFACTPAGE_DEVID_53C1030ZC: desc = "LSILogic 1030 Ultra4 Adapter"; break; case MPI_MANUFACTPAGE_DEVID_SAS1068E_FB: /* * Allow mfi(4) to claim this device in case it's in MegaRAID * mode. */ rval = BUS_PROBE_LOW_PRIORITY; /* FALLTHROUGH */ case MPI_MANUFACTPAGE_DEVID_SAS1064: case MPI_MANUFACTPAGE_DEVID_SAS1064A: case MPI_MANUFACTPAGE_DEVID_SAS1064E: case MPI_MANUFACTPAGE_DEVID_SAS1066: case MPI_MANUFACTPAGE_DEVID_SAS1066E: case MPI_MANUFACTPAGE_DEVID_SAS1068: case MPI_MANUFACTPAGE_DEVID_SAS1068A_FB: case MPI_MANUFACTPAGE_DEVID_SAS1068E: case MPI_MANUFACTPAGE_DEVID_SAS1078: case MPI_MANUFACTPAGE_DEVID_SAS1078DE_FB: desc = "LSILogic SAS/SATA Adapter"; break; default: return (ENXIO); } device_set_desc(dev, desc); return (rval); }
static int ohci_pci_attach(device_t self) { ohci_softc_t *sc = device_get_softc(self); int err; int rid; /* XXX where does it say so in the spec? */ sc->sc_bus.usbrev = USBREV_1_0; pci_enable_busmaster(self); /* * Some Sun PCIO-2 USB controllers have their intpin register * bogusly set to 0, although it should be 4. Correct that. */ if (pci_get_devid(self) == PCI_OHCI_DEVICEID_PCIO2USB && pci_get_intpin(self) == 0) pci_set_intpin(self, 4); rid = PCI_CBMEM; sc->io_res = bus_alloc_resource_any(self, SYS_RES_MEMORY, &rid, RF_ACTIVE); if (!sc->io_res) { device_printf(self, "Could not map memory\n"); return ENXIO; } sc->iot = rman_get_bustag(sc->io_res); sc->ioh = rman_get_bushandle(sc->io_res); rid = 0; sc->irq_res = bus_alloc_resource_any(self, SYS_RES_IRQ, &rid, RF_SHAREABLE | RF_ACTIVE); if (sc->irq_res == NULL) { device_printf(self, "Could not allocate irq\n"); ohci_pci_detach(self); return ENXIO; } sc->sc_bus.bdev = device_add_child(self, "usb", -1); if (!sc->sc_bus.bdev) { device_printf(self, "Could not add USB device\n"); ohci_pci_detach(self); return ENOMEM; } device_set_ivars(sc->sc_bus.bdev, &sc->sc_bus); /* ohci_pci_match will never return NULL if ohci_pci_probe succeeded */ device_set_desc(sc->sc_bus.bdev, ohci_pci_match(self)); switch (pci_get_vendor(self)) { case PCI_OHCI_VENDORID_ACERLABS: ksprintf(sc->sc_vendor, "AcerLabs"); break; case PCI_OHCI_VENDORID_AMD: ksprintf(sc->sc_vendor, "AMD"); break; case PCI_OHCI_VENDORID_APPLE: ksprintf(sc->sc_vendor, "Apple"); break; case PCI_OHCI_VENDORID_ATI: ksprintf(sc->sc_vendor, "ATI"); break; case PCI_OHCI_VENDORID_CMDTECH: ksprintf(sc->sc_vendor, "CMDTECH"); break; case PCI_OHCI_VENDORID_NEC: ksprintf(sc->sc_vendor, "NEC"); break; case PCI_OHCI_VENDORID_NVIDIA: case PCI_OHCI_VENDORID_NVIDIA2: ksprintf(sc->sc_vendor, "nVidia"); break; case PCI_OHCI_VENDORID_OPTI: ksprintf(sc->sc_vendor, "OPTi"); break; case PCI_OHCI_VENDORID_SIS: ksprintf(sc->sc_vendor, "SiS"); break; default: if (bootverbose) device_printf(self, "(New OHCI DeviceId=0x%08x)\n", pci_get_devid(self)); ksprintf(sc->sc_vendor, "(0x%04x)", pci_get_vendor(self)); } err = bus_setup_intr(self, sc->irq_res, 0, (driver_intr_t *) ohci_intr, sc, &sc->ih, NULL); if (err) { device_printf(self, "Could not setup irq, %d\n", err); sc->ih = NULL; ohci_pci_detach(self); return ENXIO; } /* * OHCI interrupts which occur early will leave them disabled, * so run the interrupt manually once we're done with the init. */ err = ohci_init(sc); if (err == 0) err = device_probe_and_attach(sc->sc_bus.bdev); if (err) { device_printf(self, "USB init failed\n"); ohci_pci_detach(self); return EIO; } return 0; }
int hme_pci_attach(device_t dev) { struct hme_pci_softc *hsc; struct hme_softc *sc; bus_space_tag_t memt; bus_space_handle_t memh; int i, error = 0; #if !(defined(__powerpc__) || defined(__sparc64__)) device_t *children, ebus_dev; struct resource *ebus_rres; int j, slot; #endif pci_enable_busmaster(dev); /* * Some Sun HMEs do have their intpin register bogusly set to 0, * although it should be 1. Correct that. */ if (pci_get_intpin(dev) == 0) pci_set_intpin(dev, 1); hsc = device_get_softc(dev); sc = &hsc->hsc_hme; sc->sc_dev = dev; sc->sc_flags |= HME_PCI; mtx_init(&sc->sc_lock, device_get_nameunit(dev), MTX_NETWORK_LOCK, MTX_DEF); /* * Map five register banks: * * bank 0: HME SEB registers: +0x0000 * bank 1: HME ETX registers: +0x2000 * bank 2: HME ERX registers: +0x4000 * bank 3: HME MAC registers: +0x6000 * bank 4: HME MIF registers: +0x7000 * */ i = PCIR_BAR(0); hsc->hsc_sres = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &i, RF_ACTIVE); if (hsc->hsc_sres == NULL) { device_printf(dev, "could not map device registers\n"); error = ENXIO; goto fail_mtx; } i = 0; hsc->hsc_ires = bus_alloc_resource_any(dev, SYS_RES_IRQ, &i, RF_SHAREABLE | RF_ACTIVE); if (hsc->hsc_ires == NULL) { device_printf(dev, "could not allocate interrupt\n"); error = ENXIO; goto fail_sres; } memt = rman_get_bustag(hsc->hsc_sres); memh = rman_get_bushandle(hsc->hsc_sres); sc->sc_sebt = sc->sc_etxt = sc->sc_erxt = sc->sc_mact = sc->sc_mift = memt; bus_space_subregion(memt, memh, 0x0000, 0x1000, &sc->sc_sebh); bus_space_subregion(memt, memh, 0x2000, 0x1000, &sc->sc_etxh); bus_space_subregion(memt, memh, 0x4000, 0x1000, &sc->sc_erxh); bus_space_subregion(memt, memh, 0x6000, 0x1000, &sc->sc_mach); bus_space_subregion(memt, memh, 0x7000, 0x1000, &sc->sc_mifh); #if defined(__powerpc__) || defined(__sparc64__) OF_getetheraddr(dev, sc->sc_enaddr); #else /* * Dig out VPD (vital product data) and read NA (network address). * * The PCI HME is a PCIO chip, which is composed of two functions: * function 0: PCI-EBus2 bridge, and * function 1: HappyMeal Ethernet controller. * * The VPD of HME resides in the Boot PROM (PCI FCode) attached * to the EBus bridge and can't be accessed via the PCI capability * pointer. * ``Writing FCode 3.x Programs'' (newer ones, dated 1997 and later) * chapter 2 describes the data structure. * * We don't have a MI EBus driver since no EBus device exists * (besides the FCode PROM) on add-on HME boards. The ``no driver * attached'' message for function 0 therefore is what is expected. */ #define PCI_ROMHDR_SIZE 0x1c #define PCI_ROMHDR_SIG 0x00 #define PCI_ROMHDR_SIG_MAGIC 0xaa55 /* little endian */ #define PCI_ROMHDR_PTR_DATA 0x18 #define PCI_ROM_SIZE 0x18 #define PCI_ROM_SIG 0x00 #define PCI_ROM_SIG_MAGIC 0x52494350 /* "PCIR", endian */ /* reversed */ #define PCI_ROM_VENDOR 0x04 #define PCI_ROM_DEVICE 0x06 #define PCI_ROM_PTR_VPD 0x08 #define PCI_VPDRES_BYTE0 0x00 #define PCI_VPDRES_ISLARGE(x) ((x) & 0x80) #define PCI_VPDRES_LARGE_NAME(x) ((x) & 0x7f) #define PCI_VPDRES_TYPE_VPD 0x10 /* large */ #define PCI_VPDRES_LARGE_LEN_LSB 0x01 #define PCI_VPDRES_LARGE_LEN_MSB 0x02 #define PCI_VPDRES_LARGE_DATA 0x03 #define PCI_VPD_SIZE 0x03 #define PCI_VPD_KEY0 0x00 #define PCI_VPD_KEY1 0x01 #define PCI_VPD_LEN 0x02 #define PCI_VPD_DATA 0x03 #define HME_ROM_READ_N(n, offs) bus_space_read_ ## n (memt, memh, (offs)) #define HME_ROM_READ_1(offs) HME_ROM_READ_N(1, (offs)) #define HME_ROM_READ_2(offs) HME_ROM_READ_N(2, (offs)) #define HME_ROM_READ_4(offs) HME_ROM_READ_N(4, (offs)) /* Search accompanying EBus bridge. */ slot = pci_get_slot(dev); if (device_get_children(device_get_parent(dev), &children, &i) != 0) { device_printf(dev, "could not get children\n"); error = ENXIO; goto fail_sres; } ebus_dev = NULL; for (j = 0; j < i; j++) { if (pci_get_class(children[j]) == PCIC_BRIDGE && pci_get_vendor(children[j]) == PCI_VENDOR_SUN && pci_get_device(children[j]) == PCI_PRODUCT_SUN_EBUS && pci_get_slot(children[j]) == slot) { ebus_dev = children[j]; break; } } if (ebus_dev == NULL) { device_printf(dev, "could not find EBus bridge\n"); error = ENXIO; goto fail_children; } /* Map EBus bridge PROM registers. */ i = PCIR_BAR(0); if ((ebus_rres = bus_alloc_resource_any(ebus_dev, SYS_RES_MEMORY, &i, RF_ACTIVE)) == NULL) { device_printf(dev, "could not map PROM registers\n"); error = ENXIO; goto fail_children; } memt = rman_get_bustag(ebus_rres); memh = rman_get_bushandle(ebus_rres); /* Read PCI Expansion ROM header. */ if (HME_ROM_READ_2(PCI_ROMHDR_SIG) != PCI_ROMHDR_SIG_MAGIC || (i = HME_ROM_READ_2(PCI_ROMHDR_PTR_DATA)) < PCI_ROMHDR_SIZE) { device_printf(dev, "unexpected PCI Expansion ROM header\n"); error = ENXIO; goto fail_rres; } /* Read PCI Expansion ROM data. */ if (HME_ROM_READ_4(i + PCI_ROM_SIG) != PCI_ROM_SIG_MAGIC || HME_ROM_READ_2(i + PCI_ROM_VENDOR) != pci_get_vendor(dev) || HME_ROM_READ_2(i + PCI_ROM_DEVICE) != pci_get_device(dev) || (j = HME_ROM_READ_2(i + PCI_ROM_PTR_VPD)) < i + PCI_ROM_SIZE) { device_printf(dev, "unexpected PCI Expansion ROM data\n"); error = ENXIO; goto fail_rres; } /* * Read PCI VPD. * SUNW,hme cards have a single large resource VPD-R tag * containing one NA. SUNW,qfe cards have four large resource * VPD-R tags containing one NA each (all four HME chips share * the same PROM). * The VPD used on both cards is not in PCI 2.2 standard format * however. The length in the resource header is in big endian * and the end tag is non-standard (0x79) and followed by an * all-zero "checksum" byte. Sun calls this a "Fresh Choice * Ethernet" VPD... */ /* Look at the end tag to determine whether this is a VPD with 4 NAs. */ if (HME_ROM_READ_1(j + PCI_VPDRES_LARGE_DATA + PCI_VPD_SIZE + ETHER_ADDR_LEN) != 0x79 && HME_ROM_READ_1(j + 4 * (PCI_VPDRES_LARGE_DATA + PCI_VPD_SIZE + ETHER_ADDR_LEN)) == 0x79) /* Use the Nth NA for the Nth HME on this SUNW,qfe. */ j += slot * (PCI_VPDRES_LARGE_DATA + PCI_VPD_SIZE + ETHER_ADDR_LEN); if (PCI_VPDRES_ISLARGE(HME_ROM_READ_1(j + PCI_VPDRES_BYTE0)) == 0 || PCI_VPDRES_LARGE_NAME(HME_ROM_READ_1(j + PCI_VPDRES_BYTE0)) != PCI_VPDRES_TYPE_VPD || (HME_ROM_READ_1(j + PCI_VPDRES_LARGE_LEN_LSB) << 8 | HME_ROM_READ_1(j + PCI_VPDRES_LARGE_LEN_MSB)) != PCI_VPD_SIZE + ETHER_ADDR_LEN || HME_ROM_READ_1(j + PCI_VPDRES_LARGE_DATA + PCI_VPD_KEY0) != 0x4e /* N */ || HME_ROM_READ_1(j + PCI_VPDRES_LARGE_DATA + PCI_VPD_KEY1) != 0x41 /* A */ || HME_ROM_READ_1(j + PCI_VPDRES_LARGE_DATA + PCI_VPD_LEN) != ETHER_ADDR_LEN) { device_printf(dev, "unexpected PCI VPD\n"); error = ENXIO; goto fail_rres; } bus_space_read_region_1(memt, memh, j + PCI_VPDRES_LARGE_DATA + PCI_VPD_DATA, sc->sc_enaddr, ETHER_ADDR_LEN); fail_rres: bus_release_resource(ebus_dev, SYS_RES_MEMORY, rman_get_rid(ebus_rres), ebus_rres); fail_children: free(children, M_TEMP); if (error != 0) goto fail_sres; #endif sc->sc_burst = 64; /* XXX */ /* * call the main configure */ if ((error = hme_config(sc)) != 0) { device_printf(dev, "could not be configured\n"); goto fail_ires; } if ((error = bus_setup_intr(dev, hsc->hsc_ires, INTR_TYPE_NET | INTR_MPSAFE, NULL, hme_intr, sc, &hsc->hsc_ih)) != 0) { device_printf(dev, "couldn't establish interrupt\n"); hme_detach(sc); goto fail_ires; } return (0); fail_ires: bus_release_resource(dev, SYS_RES_IRQ, rman_get_rid(hsc->hsc_ires), hsc->hsc_ires); fail_sres: bus_release_resource(dev, SYS_RES_MEMORY, rman_get_rid(hsc->hsc_sres), hsc->hsc_sres); fail_mtx: mtx_destroy(&sc->sc_lock); return (error); }
/* Attach the PHY to the MII bus */ static int brgphy_attach(device_t dev) { struct brgphy_softc *bsc; struct bge_softc *bge_sc = NULL; struct bce_softc *bce_sc = NULL; struct mii_softc *sc; struct mii_attach_args *ma; struct mii_data *mii; struct ifnet *ifp; int fast_ether; bsc = device_get_softc(dev); sc = &bsc->mii_sc; ma = device_get_ivars(dev); sc->mii_dev = device_get_parent(dev); mii = device_get_softc(sc->mii_dev); LIST_INSERT_HEAD(&mii->mii_phys, sc, mii_list); /* Initialize mii_softc structure */ sc->mii_inst = mii->mii_instance; sc->mii_phy = ma->mii_phyno; sc->mii_service = brgphy_service; sc->mii_pdata = mii; sc->mii_anegticks = MII_ANEGTICKS_GIGE; sc->mii_flags |= MIIF_NOISOLATE | MIIF_NOLOOP; mii->mii_instance++; /* Initialize brgphy_softc structure */ bsc->mii_oui = MII_OUI(ma->mii_id1, ma->mii_id2); bsc->mii_model = MII_MODEL(ma->mii_id2); bsc->mii_rev = MII_REV(ma->mii_id2); bsc->serdes_flags = 0; fast_ether = 0; if (bootverbose) device_printf(dev, "OUI 0x%06x, model 0x%04x, rev. %d\n", bsc->mii_oui, bsc->mii_model, bsc->mii_rev); /* Handle any special cases based on the PHY ID */ switch (bsc->mii_oui) { case MII_OUI_BROADCOM: case MII_OUI_BROADCOM2: break; case MII_OUI_xxBROADCOM: switch (bsc->mii_model) { case MII_MODEL_xxBROADCOM_BCM5706: /* * The 5464 PHY used in the 5706 supports both copper * and fiber interfaces over GMII. Need to check the * shadow registers to see which mode is actually * in effect, and therefore whether we have 5706C or * 5706S. */ PHY_WRITE(sc, BRGPHY_MII_SHADOW_1C, BRGPHY_SHADOW_1C_MODE_CTRL); if (PHY_READ(sc, BRGPHY_MII_SHADOW_1C) & BRGPHY_SHADOW_1C_ENA_1000X) { bsc->serdes_flags |= BRGPHY_5706S; sc->mii_flags |= MIIF_HAVEFIBER; } break; } break; case MII_OUI_xxBROADCOM_ALT1: switch (bsc->mii_model) { case MII_MODEL_xxBROADCOM_ALT1_BCM5708S: bsc->serdes_flags |= BRGPHY_5708S; sc->mii_flags |= MIIF_HAVEFIBER; break; } break; default: device_printf(dev, "Unrecognized OUI for PHY!\n"); } ifp = sc->mii_pdata->mii_ifp; /* Find the MAC driver associated with this PHY. */ if (strcmp(ifp->if_dname, "bge") == 0) { bge_sc = ifp->if_softc; } else if (strcmp(ifp->if_dname, "bce") == 0) { bce_sc = ifp->if_softc; } /* Todo: Need to add additional controllers such as 5906 & 5787F */ /* The 590x chips are 10/100 only. */ if (bge_sc && pci_get_vendor(bge_sc->bge_dev) == BCOM_VENDORID && (pci_get_device(bge_sc->bge_dev) == BCOM_DEVICEID_BCM5901 || pci_get_device(bge_sc->bge_dev) == BCOM_DEVICEID_BCM5901A2 || pci_get_device(bge_sc->bge_dev) == BCOM_DEVICEID_BCM5906 || pci_get_device(bge_sc->bge_dev) == BCOM_DEVICEID_BCM5906M)) { fast_ether = 1; sc->mii_anegticks = MII_ANEGTICKS; } brgphy_reset(sc); /* Read the PHY's capabilities. */ sc->mii_capabilities = PHY_READ(sc, MII_BMSR) & ma->mii_capmask; if (sc->mii_capabilities & BMSR_EXTSTAT) sc->mii_extcapabilities = PHY_READ(sc, MII_EXTSR); device_printf(dev, " "); #define ADD(m, c) ifmedia_add(&mii->mii_media, (m), (c), NULL) /* Create an instance of Ethernet media. */ ADD(IFM_MAKEWORD(IFM_ETHER, IFM_NONE, 0, sc->mii_inst), BMCR_ISO); /* Add the supported media types */ if ((sc->mii_flags & MIIF_HAVEFIBER) == 0) { ADD(IFM_MAKEWORD(IFM_ETHER, IFM_10_T, 0, sc->mii_inst), BRGPHY_S10); printf("10baseT, "); ADD(IFM_MAKEWORD(IFM_ETHER, IFM_10_T, IFM_FDX, sc->mii_inst), BRGPHY_S10 | BRGPHY_BMCR_FDX); printf("10baseT-FDX, "); ADD(IFM_MAKEWORD(IFM_ETHER, IFM_100_TX, 0, sc->mii_inst), BRGPHY_S100); printf("100baseTX, "); ADD(IFM_MAKEWORD(IFM_ETHER, IFM_100_TX, IFM_FDX, sc->mii_inst), BRGPHY_S100 | BRGPHY_BMCR_FDX); printf("100baseTX-FDX, "); if (fast_ether == 0) { ADD(IFM_MAKEWORD(IFM_ETHER, IFM_1000_T, 0, sc->mii_inst), BRGPHY_S1000); printf("1000baseT, "); ADD(IFM_MAKEWORD(IFM_ETHER, IFM_1000_T, IFM_FDX, sc->mii_inst), BRGPHY_S1000 | BRGPHY_BMCR_FDX); printf("1000baseT-FDX, "); } } else { ADD(IFM_MAKEWORD(IFM_ETHER, IFM_1000_SX, IFM_FDX, sc->mii_inst), BRGPHY_S1000 | BRGPHY_BMCR_FDX); printf("1000baseSX-FDX, "); /* 2.5G support is a software enabled feature on the 5708S and 5709S. */ if (bce_sc && (bce_sc->bce_phy_flags & BCE_PHY_2_5G_CAPABLE_FLAG)) { ADD(IFM_MAKEWORD(IFM_ETHER, IFM_2500_SX, IFM_FDX, sc->mii_inst), 0); printf("2500baseSX-FDX, "); } } ADD(IFM_MAKEWORD(IFM_ETHER, IFM_AUTO, 0, sc->mii_inst), 0); printf("auto\n"); #undef ADD MIIBUS_MEDIAINIT(sc->mii_dev); return (0); }