Prototypes
 ----------------------------------------------------------------------------- */
 /* Base stuff */
-int zpci_create_device(u32 fid, u32 fh, enum zpci_state state);
+struct zpci_dev *zpci_create_device(u32 fid, u32 fh, enum zpci_state state);
 int zpci_enable_device(struct zpci_dev *);
 int zpci_disable_device(struct zpci_dev *);
 int zpci_configure_device(struct zpci_dev *zdev, u32 fh);
 
  * Creates a new zpci device and adds it to its, possibly newly created, zbus
  * as well as zpci_list.
  *
- * Returns: 0 on success, an error value otherwise
+ * Returns: the zdev on success or an error pointer otherwise
  */
-int zpci_create_device(u32 fid, u32 fh, enum zpci_state state)
+struct zpci_dev *zpci_create_device(u32 fid, u32 fh, enum zpci_state state)
 {
        struct zpci_dev *zdev;
        int rc;
        zpci_dbg(3, "add fid:%x, fh:%x, c:%d\n", fid, fh, state);
        zdev = kzalloc(sizeof(*zdev), GFP_KERNEL);
        if (!zdev)
-               return -ENOMEM;
+               return ERR_PTR(-ENOMEM);
 
        /* FID and Function Handle are the static/dynamic identifiers */
        zdev->fid = fid;
        list_add_tail(&zdev->entry, &zpci_list);
        spin_unlock(&zpci_list_lock);
 
-       return 0;
+       return zdev;
 
 error_destroy_iommu:
        zpci_destroy_iommu(zdev);
 error:
        zpci_dbg(0, "add fid:%x, rc:%d\n", fid, rc);
        kfree(zdev);
-       return rc;
+       return ERR_PTR(rc);
 }
 
 /**
        rc = clp_scan_pci_devices();
        if (rc)
                goto out_find;
+       zpci_bus_scan_busses();
 
        s390_pci_initialized = 1;
        return 0;
 
        return ret;
 }
 
+/* zpci_bus_scan_busses - Scan all registered busses
+ *
+ * Scan all available zbusses
+ *
+ */
+void zpci_bus_scan_busses(void)
+{
+       struct zpci_bus *zbus = NULL;
+
+       mutex_lock(&zbus_list_lock);
+       list_for_each_entry(zbus, &zbus_list, bus_next) {
+               zpci_bus_scan_bus(zbus);
+               cond_resched();
+       }
+       mutex_unlock(&zbus_list_lock);
+}
+
 /* zpci_bus_create_pci_bus - Create the PCI bus associated with this zbus
  * @zbus: the zbus holding the zdevices
  * @f0: function 0 of the bus
        if (rc)
                goto error;
 
-       if (zdev->state != ZPCI_FN_STATE_CONFIGURED)
-               return 0;
-
-       /* the PCI function will be scanned once function 0 appears */
-       if (!zdev->zbus->bus)
-               return 0;
-
-       /* For function 0 scan whole bus as we might have to pick up existing
-        * functions waiting for it to allow creating the PCI bus
-        */
-       if (zdev->devfn == 0 && zdev->zbus->multifunction)
-               rc = zpci_bus_scan_bus(zdev->zbus);
-       else
-               rc = zpci_bus_scan_device(zdev);
-
-       if (rc)
-               goto error;
-
        return 0;
 
 error:
 
 void zpci_bus_device_unregister(struct zpci_dev *zdev);
 
 int zpci_bus_scan_bus(struct zpci_bus *zbus);
+void zpci_bus_scan_busses(void);
 
 int zpci_bus_scan_device(struct zpci_dev *zdev);
 void zpci_bus_remove_device(struct zpci_dev *zdev, bool set_error);
 
        switch (ccdf->pec) {
        case 0x0301: /* Reserved|Standby -> Configured */
                if (!zdev) {
-                       zpci_create_device(ccdf->fid, ccdf->fh, ZPCI_FN_STATE_CONFIGURED);
-                       break;
+                       zdev = zpci_create_device(ccdf->fid, ccdf->fh, ZPCI_FN_STATE_CONFIGURED);
+                       if (IS_ERR(zdev))
+                               break;
+               } else {
+                       /* the configuration request may be stale */
+                       if (zdev->state != ZPCI_FN_STATE_STANDBY)
+                               break;
+                       zdev->state = ZPCI_FN_STATE_CONFIGURED;
                }
-               /* the configuration request may be stale */
-               if (zdev->state != ZPCI_FN_STATE_STANDBY)
-                       break;
-               zdev->state = ZPCI_FN_STATE_CONFIGURED;
                zpci_configure_device(zdev, ccdf->fh);
                break;
        case 0x0302: /* Reserved -> Standby */