This adds __init section annotations to gadget driver bind() routines to
remove calls from .text into .init sections (for endpoint autoconfig).
Likewise it adds __exit section annotations to their unbind() routines.

The specification of the gadget driver register/unregister functions is
updated to explicitly allow use of those sections.

Signed-off-by: David Brownell <[EMAIL PROTECTED]>
Signed-off-by: Greg Kroah-Hartman <[EMAIL PROTECTED]>

---

 drivers/usb/gadget/ether.c        |    4 ++--
 drivers/usb/gadget/file_storage.c |    4 ++--
 drivers/usb/gadget/serial.c       |    6 +++---
 drivers/usb/gadget/zero.c         |    6 +++---
 include/linux/usb_gadget.h        |    7 +++++--
 5 files changed, 15 insertions(+), 12 deletions(-)

329af28b141ab4ae847aff1362864c4cc332641f
diff --git a/drivers/usb/gadget/ether.c b/drivers/usb/gadget/ether.c
index 3d2603e..0d9d9bb 100644
--- a/drivers/usb/gadget/ether.c
+++ b/drivers/usb/gadget/ether.c
@@ -2125,7 +2125,7 @@ eth_req_free (struct usb_ep *ep, struct 
 }
 
 
-static void
+static void __exit
 eth_unbind (struct usb_gadget *gadget)
 {
        struct eth_dev          *dev = get_gadget_data (gadget);
@@ -2532,7 +2532,7 @@ static struct usb_gadget_driver eth_driv
 
        .function       = (char *) driver_desc,
        .bind           = eth_bind,
-       .unbind         = eth_unbind,
+       .unbind         = __exit_p(eth_unbind),
 
        .setup          = eth_setup,
        .disconnect     = eth_disconnect,
diff --git a/drivers/usb/gadget/file_storage.c 
b/drivers/usb/gadget/file_storage.c
index de59c58..cf3be29 100644
--- a/drivers/usb/gadget/file_storage.c
+++ b/drivers/usb/gadget/file_storage.c
@@ -3678,7 +3678,7 @@ static void lun_release(struct device *d
        kref_put(&fsg->ref, fsg_release);
 }
 
-static void fsg_unbind(struct usb_gadget *gadget)
+static void __exit fsg_unbind(struct usb_gadget *gadget)
 {
        struct fsg_dev          *fsg = get_gadget_data(gadget);
        int                     i;
@@ -4064,7 +4064,7 @@ static struct usb_gadget_driver           fsg_dri
 #endif
        .function       = (char *) longname,
        .bind           = fsg_bind,
-       .unbind         = fsg_unbind,
+       .unbind         = __exit_p(fsg_unbind),
        .disconnect     = fsg_disconnect,
        .setup          = fsg_setup,
        .suspend        = fsg_suspend,
diff --git a/drivers/usb/gadget/serial.c b/drivers/usb/gadget/serial.c
index ba9acd5..548feaa 100644
--- a/drivers/usb/gadget/serial.c
+++ b/drivers/usb/gadget/serial.c
@@ -369,7 +369,7 @@ static struct usb_gadget_driver gs_gadge
 #endif /* CONFIG_USB_GADGET_DUALSPEED */
        .function =             GS_LONG_NAME,
        .bind =                 gs_bind,
-       .unbind =               gs_unbind,
+       .unbind =               __exit_p(gs_unbind),
        .setup =                gs_setup,
        .disconnect =           gs_disconnect,
        .driver = {
@@ -1413,7 +1413,7 @@ requeue:
  * Called on module load.  Allocates and initializes the device
  * structure and a control request.
  */
-static int gs_bind(struct usb_gadget *gadget)
+static int __init gs_bind(struct usb_gadget *gadget)
 {
        int ret;
        struct usb_ep *ep;
@@ -1538,7 +1538,7 @@ autoconf_fail:
  * Called on module unload.  Frees the control request and device
  * structure.
  */
-static void gs_unbind(struct usb_gadget *gadget)
+static void __exit gs_unbind(struct usb_gadget *gadget)
 {
        struct gs_dev *dev = get_gadget_data(gadget);
 
diff --git a/drivers/usb/gadget/zero.c b/drivers/usb/gadget/zero.c
index 5e9fe8a..44d8e5e 100644
--- a/drivers/usb/gadget/zero.c
+++ b/drivers/usb/gadget/zero.c
@@ -1119,7 +1119,7 @@ zero_autoresume (unsigned long _dev)
 
 /*-------------------------------------------------------------------------*/
 
-static void
+static void __exit
 zero_unbind (struct usb_gadget *gadget)
 {
        struct zero_dev         *dev = get_gadget_data (gadget);
@@ -1136,7 +1136,7 @@ zero_unbind (struct usb_gadget *gadget)
        set_gadget_data (gadget, NULL);
 }
 
-static int
+static int __init
 zero_bind (struct usb_gadget *gadget)
 {
        struct zero_dev         *dev;
@@ -1288,7 +1288,7 @@ static struct usb_gadget_driver zero_dri
 #endif
        .function       = (char *) longname,
        .bind           = zero_bind,
-       .unbind         = zero_unbind,
+       .unbind         = __exit_p(zero_unbind),
 
        .setup          = zero_setup,
        .disconnect     = zero_disconnect,
diff --git a/include/linux/usb_gadget.h b/include/linux/usb_gadget.h
index ff81117..1d78870 100644
--- a/include/linux/usb_gadget.h
+++ b/include/linux/usb_gadget.h
@@ -801,7 +801,9 @@ struct usb_gadget_driver {
  * Call this in your gadget driver's module initialization function,
  * to tell the underlying usb controller driver about your driver.
  * The driver's bind() function will be called to bind it to a
- * gadget.  This function must be called in a context that can sleep.
+ * gadget before this registration call returns.  It's expected that
+ * the bind() functions will be in init sections.
+ * This function must be called in a context that can sleep.
  */
 int usb_gadget_register_driver (struct usb_gadget_driver *driver);
 
@@ -814,7 +816,8 @@ int usb_gadget_register_driver (struct u
  * going away.  If the controller is connected to a USB host,
  * it will first disconnect().  The driver is also requested
  * to unbind() and clean up any device state, before this procedure
- * finally returns.
+ * finally returns.  It's expected that the unbind() functions
+ * will in in exit sections, so may not be linked in some kernels.
  * This function must be called in a context that can sleep.
  */
 int usb_gadget_unregister_driver (struct usb_gadget_driver *driver);
-- 
1.2.4




-------------------------------------------------------
This SF.Net email is sponsored by xPML, a groundbreaking scripting language
that extends applications into web and mobile media. Attend the live webcast
and join the prime developer group breaking into this new coding territory!
http://sel.as-us.falkag.net/sel?cmd=lnk&kid=110944&bid=241720&dat=121642
_______________________________________________
linux-usb-devel@lists.sourceforge.net
To unsubscribe, use the last form field at:
https://lists.sourceforge.net/lists/listinfo/linux-usb-devel

Reply via email to