Register one slot per slot, rather than one slot per function.
Change the name of the slot to fake%d instead of the pci address.

Signed-off-by: Alex Chiang <[EMAIL PROTECTED]>
Signed-off-by: Matthew Wilcox <[EMAIL PROTECTED]>
---
 drivers/pci/hotplug/fakephp.c |   75 +++++++++++++++--------------------------
 1 files changed, 27 insertions(+), 48 deletions(-)

diff --git a/drivers/pci/hotplug/fakephp.c b/drivers/pci/hotplug/fakephp.c
index 027f686..828335e 100644
--- a/drivers/pci/hotplug/fakephp.c
+++ b/drivers/pci/hotplug/fakephp.c
@@ -93,6 +93,7 @@ static int add_slot(struct pci_dev *dev)
        struct dummy_slot *dslot;
        struct hotplug_slot *slot;
        int retval = -ENOMEM;
+       static int count = 1;
 
        slot = kzalloc(sizeof(struct hotplug_slot), GFP_KERNEL);
        if (!slot)
@@ -106,7 +107,8 @@ static int add_slot(struct pci_dev *dev)
        slot->info->max_bus_speed = PCI_SPEED_UNKNOWN;
        slot->info->cur_bus_speed = PCI_SPEED_UNKNOWN;
 
-       slot->name = &dev->dev.bus_id[0];
+       slot->name = kmalloc(8, GFP_KERNEL);
+       sprintf(slot->name, "fake%d", count++);
        dbg("slot->name = %s\n", slot->name);
 
        dslot = kmalloc(sizeof(struct dummy_slot), GFP_KERNEL);
@@ -141,17 +143,17 @@ error:
 static int __init pci_scan_buses(void)
 {
        struct pci_dev *dev = NULL;
-       int retval = 0;
+       int lastslot = 0;
 
        while ((dev = pci_get_device(PCI_ANY_ID, PCI_ANY_ID, dev)) != NULL) {
-               retval = add_slot(dev);
-               if (retval) {
-                       pci_dev_put(dev);
-                       break;
-               }
+               if (PCI_FUNC(dev->devfn) > 0 &&
+                               lastslot == PCI_SLOT(dev->devfn))
+                       continue;
+               lastslot = PCI_SLOT(dev->devfn);
+               add_slot(dev);
        }
 
-       return retval;
+       return 0;
 }
 
 static void remove_slot(struct dummy_slot *dslot)
@@ -275,23 +277,9 @@ static int enable_slot(struct hotplug_slot *hotplug_slot)
        return -ENODEV;
 }
 
-/* find the hotplug_slot for the pci_dev */
-static struct hotplug_slot *get_slot_from_dev(struct pci_dev *dev)
-{
-       struct dummy_slot *dslot;
-
-       list_for_each_entry(dslot, &slot_list, node) {
-               if (dslot->dev == dev)
-                       return dslot->slot;
-       }
-       return NULL;
-}
-
-
 static int disable_slot(struct hotplug_slot *slot)
 {
        struct dummy_slot *dslot;
-       struct hotplug_slot *hslot;
        struct pci_dev *dev;
        int func;
 
@@ -301,36 +289,27 @@ static int disable_slot(struct hotplug_slot *slot)
 
        dbg("%s - physical_slot = %s\n", __FUNCTION__, slot->name);
 
-       /* don't disable bridged devices just yet, we can't handle them 
easily... */
-       if (dslot->dev->subordinate) {
-               err("Can't remove PCI devices with other PCI devices behind it 
yet.\n");
-               return -ENODEV;
-       }
-       /* search for subfunctions and disable them first */
-       if (!(dslot->dev->devfn & 7)) {
-               for (func = 1; func < 8; func++) {
-                       dev = pci_get_slot(dslot->dev->bus,
-                                       dslot->dev->devfn + func);
-                       if (dev) {
-                               hslot = get_slot_from_dev(dev);
-                               if (hslot)
-                                       disable_slot(hslot);
-                               else {
-                                       err("Hotplug slot not found for 
subfunction of PCI device\n");
-                                       return -ENODEV;
-                               }
-                               pci_dev_put(dev);
-                       } else
-                               dbg("No device in slot found\n");
+       for (func = 7; func >= 0; func--) {
+               dev = pci_get_slot(dslot->dev->bus, dslot->dev->devfn + func);
+               if (!dev)
+                       continue;
+
+               /* don't disable bridged devices just yet, we can't handle
+                * them easily... */
+               if (dev->subordinate) {
+                       err("Can't remove PCI devices with other PCI devices 
behind it yet.\n");
+                       return -ENODEV;
                }
-       }
 
-       /* remove the device from the pci core */
-       pci_remove_bus_device(dslot->dev);
 
-       /* blow away this sysfs entry and other parts. */
-       remove_slot(dslot);
+               /* remove the device from the pci core */
+               pci_remove_bus_device(dslot->dev);
 
+               /* blow away this sysfs entry and other parts. */
+               remove_slot(dslot);
+
+               pci_dev_put(dev);
+       }
        return 0;
 }
 
-- 
1.5.3.1.1.g1e61

-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

Reply via email to