/* * pcmu_init_child * * This function is called from our control ops routine on a * DDI_CTLOPS_INITCHILD request. It builds and sets the device's * parent private data area. * * used by: pcmu_ctlops() * * return value: none */ int pcmu_init_child(pcmu_t *pcmu_p, dev_info_t *child) { char name[10]; ddi_acc_handle_t config_handle; uint8_t bcr; uint8_t header_type; if (name_child(child, name, 10) != DDI_SUCCESS) return (DDI_FAILURE); ddi_set_name_addr(child, name); PCMU_DBG2(PCMU_DBG_PWR, ddi_get_parent(child), "INITCHILD: config regs setup for %s@%s\n", ddi_node_name(child), ddi_get_name_addr(child)); /* * Map the child configuration space to for initialization. * We assume the obp will do the following in the devices * config space: * * Set the latency-timer register to values appropriate * for the devices on the bus (based on other devices * MIN_GNT and MAX_LAT registers. * * Set the fast back-to-back enable bit in the command * register if it's supported and all devices on the bus * have the capability. * */ if (pci_config_setup(child, &config_handle) != DDI_SUCCESS) { ddi_set_name_addr(child, NULL); return (DDI_FAILURE); } /* * Determine the configuration header type. */ header_type = pci_config_get8(config_handle, PCI_CONF_HEADER); PCMU_DBG2(PCMU_DBG_INIT_CLD, pcmu_p->pcmu_dip, "%s: header_type=%x\n", ddi_driver_name(child), header_type); /* * If the device has a bus control register then program it * based on the settings in the command register. */ if ((header_type & PCI_HEADER_TYPE_M) == PCI_HEADER_ONE) { bcr = pci_config_get8(config_handle, PCI_BCNF_BCNTRL); if (pcmu_command_default & PCI_COMM_PARITY_DETECT) bcr |= PCI_BCNF_BCNTRL_PARITY_ENABLE; if (pcmu_command_default & PCI_COMM_SERR_ENABLE) bcr |= PCI_BCNF_BCNTRL_SERR_ENABLE; bcr |= PCI_BCNF_BCNTRL_MAST_AB_MODE; pci_config_put8(config_handle, PCI_BCNF_BCNTRL, bcr); } pci_config_teardown(&config_handle); return (DDI_SUCCESS); }
static int init_child(dev_info_t *child) { char name[MAXNAMELEN]; (void) name_child(child, name, MAXNAMELEN); ddi_set_name_addr(child, name); if ((ndi_dev_is_persistent_node(child) == 0) && (ndi_merge_node(child, name_child) == DDI_SUCCESS)) { impl_ddi_sunbus_removechild(child); return (DDI_FAILURE); } return (DDI_SUCCESS); }