uml: drivers get release methods
authorJeff Dike <jdike@addtoit.com>
Sun, 6 May 2007 21:51:29 +0000 (14:51 -0700)
committerLinus Torvalds <torvalds@woody.linux-foundation.org>
Mon, 7 May 2007 19:13:02 +0000 (12:13 -0700)
Define release methods for the ubd and net drivers.  They contain as much of
the remove methods as make sense.  All error checking must have already been
done as well as anything else that might be holding a reference on the device
kobject.

Signed-off-by: Jeff Dike <jdike@linux.intel.com>
Cc: Paolo 'Blaisorblade' Giarrusso <blaisorblade@yahoo.it>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
arch/um/drivers/net_kern.c
arch/um/drivers/ubd_kern.c

index b2c292a66218b8b6637a51e8bc8ff9df769b03cb..baac4ad5e68eda7916ead4c014e5872226e803fd 100644 (file)
@@ -341,6 +341,19 @@ static struct platform_driver uml_net_driver = {
 };
 static int driver_registered;
 
+static void net_device_release(struct device *dev)
+{
+       struct uml_net *device = dev->driver_data;
+       struct net_device *netdev = device->dev;
+       struct uml_net_private *lp = netdev->priv;
+
+       if(lp->remove != NULL)
+               (*lp->remove)(&lp->user);
+       list_del(&device->list);
+       kfree(device);
+       free_netdev(netdev);
+}
+
 static void eth_configure(int n, void *init, char *mac,
                          struct transport *transport)
 {
@@ -396,6 +409,8 @@ static void eth_configure(int n, void *init, char *mac,
        }
        device->pdev.id = n;
        device->pdev.name = DRIVER_NAME;
+       device->pdev.dev.release = net_device_release;
+       device->pdev.dev.driver_data = device;
        if(platform_device_register(&device->pdev))
                goto out_free_netdev;
        SET_NETDEV_DEV(dev,&device->pdev.dev);
@@ -689,13 +704,9 @@ static int net_remove(int n, char **error_out)
        lp = dev->priv;
        if(lp->fd > 0)
                return -EBUSY;
-       if(lp->remove != NULL) (*lp->remove)(&lp->user);
        unregister_netdev(dev);
        platform_device_unregister(&device->pdev);
 
-       list_del(&device->list);
-       kfree(device);
-       free_netdev(dev);
        return 0;
 }
 
index 962b8fb35f802a49b88ba2ab62f4120e574f1a79..83189e188c3f21f6f3eabc011f6dfb91cd38b74e 100644 (file)
@@ -622,6 +622,14 @@ static int ubd_open_dev(struct ubd *ubd_dev)
        return(err);
 }
 
+static void ubd_device_release(struct device *dev)
+{
+       struct ubd *ubd_dev = dev->driver_data;
+
+       blk_cleanup_queue(ubd_dev->queue);
+       *ubd_dev = ((struct ubd) DEFAULT_UBD);
+}
+
 static int ubd_disk_register(int major, u64 size, int unit,
                             struct gendisk **disk_out)
 {
@@ -644,6 +652,8 @@ static int ubd_disk_register(int major, u64 size, int unit,
        if (major == MAJOR_NR) {
                ubd_devs[unit].pdev.id   = unit;
                ubd_devs[unit].pdev.name = DRIVER_NAME;
+               ubd_devs[unit].pdev.dev.release = ubd_device_release;
+               ubd_devs[unit].pdev.dev.driver_data = &ubd_devs[unit];
                platform_device_register(&ubd_devs[unit].pdev);
                disk->driverfs_dev = &ubd_devs[unit].pdev.dev;
        }
@@ -787,7 +797,7 @@ static int ubd_id(char **str, int *start_out, int *end_out)
 
 static int ubd_remove(int n, char **error_out)
 {
-       struct gendisk *disk;
+       struct gendisk *disk = ubd_gendisk[n];
        struct ubd *ubd_dev;
        int err = -ENODEV;
 
@@ -803,7 +813,6 @@ static int ubd_remove(int n, char **error_out)
        if(ubd_dev->count > 0)
                goto out;
 
-       disk = ubd_gendisk[n];
        ubd_gendisk[n] = NULL;
        if(disk != NULL){
                del_gendisk(disk);
@@ -816,10 +825,8 @@ static int ubd_remove(int n, char **error_out)
                fake_gendisk[n] = NULL;
        }
 
-       blk_cleanup_queue(ubd_dev->queue);
-       platform_device_unregister(&ubd_dev->pdev);
-       *ubd_dev = ((struct ubd) DEFAULT_UBD);
        err = 0;
+       platform_device_unregister(&ubd_dev->pdev);
 out:
        mutex_unlock(&ubd_lock);
        return err;