On Wed, Apr 26, 2017 at 1:17 PM, Lorenzo Pieralisi <lorenzo.pieralisi@xxxxxxx> wrote: > Current pci_scan_root_bus() interface is made up of two main > code paths: > > - pci_create_root_bus() > - pci_scan_child_bus() > > pci_create_root_bus() is a wrapper function that allows to create > a struct pci_host_bridge structure, initialize it with the passed > parameters and register it with the kernel. > > As the struct pci_host_bridge require additional struct members, > pci_create_root_bus() parameters list has grown in time, making > it unwieldy to add further parameters to it in case the struct > pci_host_bridge gains more members fields to augment its functionality. > > Since PCI core code provides functions to allocate struct > pci_host_bridge, instead of forcing the pci_create_root_bus() interface > to add new parameters to cater for new struct pci_host_bridge > functionality, it is more suitable to add an interface in PCI > core code to scan a PCI bus straight from a struct pci_host_bridge > created and customized by each specific PCI host controller driver. > > Add a pci_scan_root_bus_bridge() function to allow PCI host controller > drivers to create and initialize struct pci_host_bridge and scan > the resulting bus. > > Signed-off-by: Lorenzo Pieralisi <lorenzo.pieralisi@xxxxxxx> > Cc: Arnd Bergmann <arnd@xxxxxxxx> > Cc: Bjorn Helgaas <bhelgaas@xxxxxxxxxx> Good idea, yes. To avoid growing the number of interfaces too much, should we change the existing users of pci_register_host_bridge in host drivers over to this entry point, and make the other one local to probe.c then? > diff --git a/drivers/pci/probe.c b/drivers/pci/probe.c > index 7e4ffc4..c7a7f72 100644 > --- a/drivers/pci/probe.c > +++ b/drivers/pci/probe.c > @@ -2412,6 +2412,44 @@ void pci_bus_release_busn_res(struct pci_bus *b) > res, ret ? "can not be" : "is"); > } > > +int pci_scan_root_bus_bridge(struct pci_host_bridge *bridge) > +{ > + struct resource_entry *window; > + bool found = false; > + struct pci_bus *b; > + int max, bus, ret; > + > + if (!bridge) > + return -EINVAL; > + > + resource_list_for_each_entry(window, &bridge->windows) > + if (window->res->flags & IORESOURCE_BUS) { > + found = true; > + break; > + } > + > + ret = pci_register_host_bridge(bridge); > + if (ret < 0) > + return ret; > + > + b = bridge->bus; > + bus = bridge->busnr; > + > + if (!found) { > + dev_info(&b->dev, > + "No busn resource found for root bus, will use [bus %02x-ff]\n", > + bus); > + pci_bus_insert_busn_res(b, bus, 255); > + } > + > + max = pci_scan_child_bus(b); > + > + if (!found) > + pci_bus_update_busn_res_end(b, max); > + > + return 0; > +} > + We probably want an EXPORT_SYMBOL() here as well. Arnd