pciio_provider_t * pciio_to_provider_fns(vertex_hdl_t dev) { pciio_info_t card_info; pciio_provider_t *provider_fns; /* * We're called with two types of vertices, one is * the bridge vertex (ends with "pci") and the other is the * pci slot vertex (ends with "pci/[0-8]"). For the first type * we need to get the provider from the PFUNCS label. For * the second we get it from fastinfo/c_pops. */ provider_fns = pciio_provider_fns_get(dev); if (provider_fns == NULL) { card_info = pciio_info_get(dev); if (card_info != NULL) { provider_fns = pciio_info_pops_get(card_info); } } if (provider_fns == NULL) { char devname[MAXDEVNAME]; panic("%s: provider_fns == NULL", vertex_to_name(dev, devname, MAXDEVNAME)); } return provider_fns; }
/*ARGSUSED */ int pciio_attach(vertex_hdl_t pciio) { #if DEBUG && ATTACH_DEBUG char devname[MAXDEVNAME]; printk("%s: pciio_attach\n", vertex_to_name(pciio, devname, MAXDEVNAME)); #endif return 0; }
static void baseio_ctlr_num_set(void) { char name[MAXDEVNAME]; devfs_handle_t console_vhdl, pci_vhdl, enet_vhdl; devfs_handle_t ioc3_console_vhdl_get(void); DBG("baseio_ctlr_num_set; FIXME\n"); console_vhdl = ioc3_console_vhdl_get(); if (console_vhdl == GRAPH_VERTEX_NONE) return; /* Useful for setting up the system critical graph */ baseio_console_vhdl = console_vhdl; vertex_to_name(console_vhdl,name,MAXDEVNAME); strcat(name,__DEVSTR1); pci_vhdl = hwgraph_path_to_vertex(name); scsi_ctlr_nums_add(pci_vhdl); /* Unref the pci_vhdl due to the reference by hwgraph_path_to_vertex */ hwgraph_vertex_unref(pci_vhdl); vertex_to_name(console_vhdl, name, MAXDEVNAME); strcat(name, __DEVSTR4); enet_vhdl = hwgraph_path_to_vertex(name); /* Useful for setting up the system critical graph */ baseio_enet_vhdl = enet_vhdl; device_controller_num_set(enet_vhdl, 0); /* Unref the enet_vhdl due to the reference by hwgraph_path_to_vertex */ hwgraph_vertex_unref(enet_vhdl); }
/* ARGSUSED */ static void volunteer_for_widgets(vertex_hdl_t xswitch, vertex_hdl_t master) { xswitch_vol_t xvolinfo = NULL; vertex_hdl_t hubv; hubinfo_t hubinfo; (void)hwgraph_info_get_LBL(xswitch, INFO_LBL_XSWITCH_VOL, (arbitrary_info_t *)&xvolinfo); if (xvolinfo == NULL) { if (!is_headless_node_vertex(master)) { char name[MAXDEVNAME]; printk(KERN_WARNING "volunteer for widgets: vertex %s has no info label", vertex_to_name(xswitch, name, MAXDEVNAME)); } return; } down(&xvolinfo->xswitch_volunteer_mutex); ASSERT(xvolinfo->xswitch_volunteer_count < NUM_XSWITCH_VOLUNTEER); xvolinfo->xswitch_volunteer[xvolinfo->xswitch_volunteer_count] = master; xvolinfo->xswitch_volunteer_count++; /* * if dual ported, make the lowest widgetid always be * xswitch_volunteer[0]. */ if (xvolinfo->xswitch_volunteer_count == NUM_XSWITCH_VOLUNTEER) { hubv = xvolinfo->xswitch_volunteer[0]; hubinfo_get(hubv, &hubinfo); if (hubinfo->h_widgetid != XBOW_HUBLINK_LOW) { xvolinfo->xswitch_volunteer[0] = xvolinfo->xswitch_volunteer[1]; xvolinfo->xswitch_volunteer[1] = hubv; } } up(&xvolinfo->xswitch_volunteer_mutex); }
void devnamefromarcs(char *devnm) { int val; char tmpnm[MAXDEVNAME]; char *tmp1, *tmp2; val = strncmp(devnm, "dks", 3); if (val != 0) return; tmp1 = devnm + 3; if (!isdigit(*tmp1)) return; val = 0; while (isdigit(*tmp1)) { val = 10*val+toint(*tmp1); tmp1++; } if(*tmp1 != 'd') return; else tmp1++; if ((val < 0) || (val >= num_base_io_scsi_ctlr)) { int i; int viable_found = 0; DBG("Only controller numbers 0..%d are supported for\n", NUM_BASE_IO_SCSI_CTLR-1); DBG("prom \"root\" variables of the form dksXdXsX.\n"); DBG("To use another disk you must use the full hardware graph path\n\n"); DBG("Possible controller numbers for use in 'dksXdXsX' on this system: "); for (i=0; i<NUM_BASE_IO_SCSI_CTLR; i++) { if (base_io_scsi_ctlr_vhdl[i] != GRAPH_VERTEX_NONE) { DBG("%d ", i); viable_found=1; } } if (viable_found) DBG("\n"); else DBG("none found!\n"); udelay(15000000); //prom_reboot(); panic("FIXME: devnamefromarcs: should call prom_reboot here.\n"); /* NOTREACHED */ } ASSERT(base_io_scsi_ctlr_vhdl[val] != GRAPH_VERTEX_NONE); vertex_to_name(base_io_scsi_ctlr_vhdl[val], tmpnm, MAXDEVNAME); tmp2 = tmpnm + strlen(tmpnm); strcpy(tmp2, __DEVSTR2); tmp2 += strlen(__DEVSTR2); while (*tmp1 != 's') { if((*tmp2++ = *tmp1++) == '\0') return; } tmp1++; strcpy(tmp2, __DEVSTR3); tmp2 += strlen(__DEVSTR3); while ( (*tmp2++ = *tmp1++) ) ; tmp2--; *tmp2++ = '/'; strcpy(tmp2, EDGE_LBL_BLOCK); strcpy(devnm,tmpnm); }
/* ** dev_to_name converts a devfs_handle_t into a canonical name. If the devfs_handle_t ** represents a vertex in the hardware graph, it is converted in the ** normal way for vertices. If the devfs_handle_t is an old devfs_handle_t (one which ** does not represent a hwgraph vertex), we synthesize a name based ** on major/minor number. ** ** Usually returns a pointer to the original buffer, filled in as ** appropriate. If the buffer is too small to hold the entire name, ** or if anything goes wrong while determining the name, dev_to_name ** returns "UnknownDevice". */ char * dev_to_name(devfs_handle_t dev, char *buf, uint buflen) { return(vertex_to_name(dev, buf, buflen)); }
/* ARGSUSED */ static void assign_widgets_to_volunteers(vertex_hdl_t xswitch, vertex_hdl_t hubv) { xswitch_info_t xswitch_info; xswitch_vol_t xvolinfo = NULL; xwidgetnum_t widgetnum; int num_volunteer; nasid_t nasid; hubinfo_t hubinfo; extern int iobrick_type_get_nasid(nasid_t); hubinfo_get(hubv, &hubinfo); nasid = hubinfo->h_nasid; xswitch_info = xswitch_info_get(xswitch); ASSERT(xswitch_info != NULL); (void)hwgraph_info_get_LBL(xswitch, INFO_LBL_XSWITCH_VOL, (arbitrary_info_t *)&xvolinfo); if (xvolinfo == NULL) { if (!is_headless_node_vertex(hubv)) { char name[MAXDEVNAME]; printk(KERN_WARNING "assign_widgets_to_volunteers:vertex %s has " " no info label", vertex_to_name(xswitch, name, MAXDEVNAME)); } return; } num_volunteer = xvolinfo->xswitch_volunteer_count; ASSERT(num_volunteer > 0); /* Assign master hub for xswitch itself. */ if (HUB_WIDGET_ID_MIN > 0) { hubv = xvolinfo->xswitch_volunteer[0]; xswitch_info_master_assignment_set(xswitch_info, (xwidgetnum_t)0, hubv); } /* * TBD: Use administrative information to alter assignment of * widgets to hubs. */ for (widgetnum=HUB_WIDGET_ID_MIN; widgetnum <= HUB_WIDGET_ID_MAX; widgetnum++) { int i; if (!xbow_port_io_enabled(nasid, widgetnum)) continue; /* * If this is the master IO board, assign it to the same * hub that owned it in the prom. */ if (is_master_baseio_nasid_widget(nasid, widgetnum)) { extern nasid_t snia_get_master_baseio_nasid(void); for (i=0; i<num_volunteer; i++) { hubv = xvolinfo->xswitch_volunteer[i]; hubinfo_get(hubv, &hubinfo); nasid = hubinfo->h_nasid; if (nasid == snia_get_master_baseio_nasid()) goto do_assignment; } printk("Nasid == %d, console nasid == %d", nasid, snia_get_master_baseio_nasid()); nasid = 0; } /* * Assuming that we're dual-hosted and that PCI cards * are naturally placed left-to-right, alternate PCI * buses across both Cbricks. For Pbricks, and Ibricks, * io_brick_map_widget() returns the PCI bus number * associated with the given brick type and widget number. * For Xbricks, it returns the XIO slot number. */ i = 0; if (num_volunteer > 1) { int bt; bt = iobrick_type_get_nasid(nasid); if (bt >= 0) { i = io_brick_map_widget(bt, widgetnum) & 1; } } hubv = xvolinfo->xswitch_volunteer[i]; do_assignment: /* * At this point, we want to make hubv the master of widgetnum. */ xswitch_info_master_assignment_set(xswitch_info, widgetnum, hubv); } xswitch_volunteer_delete(xswitch); }