ChangeSet 1.1063.1.4, 2003/05/06 11:15:45-05:00, Matt_Domsch@dell.com

dynids: call driver_attach() when new IDs are added

This causes the driver to create proper device symlinks in sysfs when
new IDs are added and thus new devices found by the driver.

drivers/base/bus.c
    make driver_attach non-static
drivers/pci/pci-driver.c
    delete probe_each_pci_dev, call driver_attach instead.
    Whitespace cleanups.
include/linux/device.h
    add declaration of driver_attach.


 drivers/base/bus.c       |    2 -
 drivers/pci/pci-driver.c |   82 ++++++++++++++++++-----------------------------
 include/linux/device.h   |    1 
 3 files changed, 35 insertions(+), 50 deletions(-)


diff -Nru a/drivers/base/bus.c b/drivers/base/bus.c
--- a/drivers/base/bus.c	Thu May 22 14:51:15 2003
+++ b/drivers/base/bus.c	Thu May 22 14:51:15 2003
@@ -316,7 +316,7 @@
  *	Note that we ignore the error from bus_match(), since it's perfectly
  *	valid for a driver not to bind to any devices.
  */
-static void driver_attach(struct device_driver * drv)
+void driver_attach(struct device_driver * drv)
 {
 	struct bus_type * bus = drv->bus;
 	struct list_head * entry;
diff -Nru a/drivers/pci/pci-driver.c b/drivers/pci/pci-driver.c
--- a/drivers/pci/pci-driver.c	Thu May 22 14:51:15 2003
+++ b/drivers/pci/pci-driver.c	Thu May 22 14:51:15 2003
@@ -15,7 +15,8 @@
  */
 
 /**
- * pci_match_one_device - Tell if a PCI device structure has a matching PCI device id structure
+ * pci_match_one_device - Tell if a PCI device structure has a matching
+ *                        PCI device id structure
  * @id: single PCI device id structure to match
  * @dev: the PCI device structure to match against
  * 
@@ -35,7 +36,8 @@
 }
 
 /**
- * pci_match_device - Tell if a PCI device structure has a matching PCI device id structure
+ * pci_match_device - Tell if a PCI device structure has a matching
+ *                    PCI device id structure
  * @ids: array of PCI device id structures to search in
  * @dev: the PCI device structure to match against
  * 
@@ -48,7 +50,7 @@
 {
 	while (ids->vendor || ids->subvendor || ids->class_mask) {
 		if (pci_match_one_device(ids, dev))
-		    return ids;
+			return ids;
 		ids++;
 	}
 	return NULL;
@@ -60,8 +62,7 @@
  * returns 0 and sets pci_dev->driver when drv claims pci_dev, else error.
  */
 static int
-pci_device_probe_static(struct pci_driver *drv,
-			  struct pci_dev *pci_dev)
+pci_device_probe_static(struct pci_driver *drv, struct pci_dev *pci_dev)
 {		   
 	int error = -ENODEV;
 	const struct pci_device_id *id;
@@ -85,13 +86,12 @@
  * returns 0 and sets pci_dev->driver when drv claims pci_dev, else error.
  */
 static int
-pci_device_probe_dynamic(struct pci_driver *drv,
-			   struct pci_dev *pci_dev)
+pci_device_probe_dynamic(struct pci_driver *drv, struct pci_dev *pci_dev)
 {		   
 	int error = -ENODEV;
 	struct list_head *pos;
 	struct dynid *dynid;
-	
+
 	spin_lock(&drv->dynids.lock);
 	list_for_each(pos, &drv->dynids.list) {
 		dynid = list_entry(pos, struct dynid, node);
@@ -116,8 +116,7 @@
  * side-effect: pci_dev->driver is set to drv when drv claims pci_dev.
  */
 static int
-__pci_device_probe(struct pci_driver *drv,
-		   struct pci_dev *pci_dev)
+__pci_device_probe(struct pci_driver *drv, struct pci_dev *pci_dev)
 {		   
 	int error = 0;
 
@@ -188,28 +187,6 @@
 	return 0;
 }
 
-/*
- * If __pci_device_probe() returns 0, it matched at least one previously
- * unclaimed device.  If it returns -ENODEV, it didn't match.  Both are
- * alright in this case, just keep searching for new devices.
- */
-
-static int
-probe_each_pci_dev(struct pci_driver *drv)
-{
-	struct pci_dev *pci_dev=NULL;
-	int error = 0;
-	pci_for_each_dev(pci_dev) {
-		if (get_device(&pci_dev->dev)) {
-			error = __pci_device_probe(drv, pci_dev);
-			put_device(&pci_dev->dev);
-			if (error && error != -ENODEV)
-				return error;
-		}
-	}
-	return error;
-}
-
 static inline void
 dynid_init(struct dynid *dynid)
 {
@@ -230,19 +207,22 @@
 store_new_id(struct device_driver * driver, const char * buf, size_t count)
 {
 	struct dynid *dynid;
+	struct bus_type * bus;
 	struct pci_driver *pdrv = to_pci_driver(driver);
 	__u32 vendor=PCI_ANY_ID, device=PCI_ANY_ID, subvendor=PCI_ANY_ID,
 		subdevice=PCI_ANY_ID, class=0, class_mask=0;
 	unsigned long driver_data=0;
-	int fields=0, error=0;
+	int fields=0;
 
 	fields = sscanf(buf, "%x %x %x %x %x %x %lux",
 			&vendor, &device, &subvendor, &subdevice,
 			&class, &class_mask, &driver_data);
-	if (fields < 0) return -EINVAL;
+	if (fields < 0)
+		return -EINVAL;
 
 	dynid = kmalloc(sizeof(*dynid), GFP_KERNEL);
-	if (!dynid) return -ENOMEM;
+	if (!dynid)
+		return -ENOMEM;
 	dynid_init(dynid);
 
 	dynid->id.vendor = vendor;
@@ -251,21 +231,24 @@
 	dynid->id.subdevice = subdevice;
 	dynid->id.class = class;
 	dynid->id.class_mask = class_mask;
-	dynid->id.driver_data = pdrv->dynids.use_driver_data ? driver_data : 0UL;
+	dynid->id.driver_data = pdrv->dynids.use_driver_data ?
+		driver_data : 0UL;
 
 	spin_lock(&pdrv->dynids.lock);
 	list_add(&pdrv->dynids.list, &dynid->node);
 	spin_unlock(&pdrv->dynids.lock);
 
-        if (get_driver(&pdrv->driver)) {
-                error = probe_each_pci_dev(pdrv);
-                put_driver(&pdrv->driver);
-        }
-        if (error < 0)
-                return error;
-        return count;
-
-
+	bus = get_bus(pdrv->driver.bus);
+	if (bus) {
+		if (get_driver(&pdrv->driver)) {
+			down_write(&bus->subsys.rwsem);
+			driver_attach(&pdrv->driver);
+			up_write(&bus->subsys.rwsem);
+			put_driver(&pdrv->driver);
+		}
+		put_bus(bus);
+	}
+	
 	return count;
 }
 
@@ -310,7 +293,7 @@
 	.store = pci_driver_attr_store,
 };
 static struct kobj_type pci_driver_kobj_type = {
-	.sysfs_ops     = &pci_driver_sysfs_ops,
+	.sysfs_ops = &pci_driver_sysfs_ops,
 };
 
 static int
@@ -319,7 +302,8 @@
 	int error = 0;
 
 	if (drv->probe != NULL)
-		error = sysfs_create_file(&drv->driver.kobj,&driver_attr_new_id.attr);
+		error = sysfs_create_file(&drv->driver.kobj,
+					  &driver_attr_new_id.attr);
 	return error;
 }
 
@@ -361,7 +345,7 @@
 	if (count >= 0) {
 		pci_populate_driver_dir(drv);
 	}
-		
+
 	return count ? count : 1;
 }
 
@@ -428,7 +412,7 @@
 		return 0;
 
 	found_id = pci_match_device(ids, pci_dev);
-	if (found_id) 
+	if (found_id)
 		return 1;
 
 	spin_lock(&pci_drv->dynids.lock);
diff -Nru a/include/linux/device.h b/include/linux/device.h
--- a/include/linux/device.h	Thu May 22 14:51:15 2003
+++ b/include/linux/device.h	Thu May 22 14:51:15 2003
@@ -318,6 +318,7 @@
  */
 extern void device_bind_driver(struct device * dev);
 extern void device_release_driver(struct device * dev);
+extern void driver_attach(struct device_driver * drv);
 
 
 /* driverfs interface for exporting device attributes */
