Am Sonntag 18 Dezember 2011, 09:10:48 schrieb Russell King - ARM Linux: > On Sat, Dec 17, 2011 at 08:26:33PM +0100, Heiko Stübner wrote: > > As the driver is also buildable as a module it should need > > a cleanup function for the removal of the module. > > My guess is that this wasn't implemented because of the embedded struct > device lifetime rules for the gadget - to prevent the unbinding of the > driver. > > Until the struct device lifetime gets fixed, you must not allow the module > nor the data structure containing the struct device to be freed. I understand where this problem comes from (the release method is potentially gone with the module before it is called) but after more reading, I have a hard time believing that a lot of the other gadget drivers would be wrong as well. Some of them since 2009 or possibly earlier. Gadgets with embedded release methods: langwell_udc, goku_udc, fsl_qe_udc (and fsl_udc_core), amd5536udc, net2280, pch_udc, cil13xxx_udc, dummy_hcd, omap_udc, net2272, mc_udc_core Gadgets which use the release method from its pdev->dev but also free the struct with the gadget in their remove method: r8a66597-udc, m66592-udc, fusb300_udc. (possibly before the release function is called) On the other hand, the gets and puts of the udc->gadget.dev should be paired correctly and it's only an intermediate device between the udc and the gadget driver, so that the call to device_unregister in the remove method should put the refcount to 0 and thus init the cleanup (including the call to release) before the module is removed. So, I am very confused :-). Heiko > > Signed-off-by: Heiko Stuebner <heiko@xxxxxxxxx> > > --- > > > > drivers/usb/gadget/s3c-hsudc.c | 25 +++++++++++++++++++++++++ > > 1 files changed, 25 insertions(+), 0 deletions(-) > > > > diff --git a/drivers/usb/gadget/s3c-hsudc.c > > b/drivers/usb/gadget/s3c-hsudc.c index 3e5673d..7cb0850 100644 > > --- a/drivers/usb/gadget/s3c-hsudc.c > > +++ b/drivers/usb/gadget/s3c-hsudc.c > > > > @@ -1370,12 +1370,37 @@ err_res: > > return ret; > > > > } > > > > +static int __devexit s3c_hsudc_remove(struct platform_device *pdev) > > +{ > > + struct s3c_hsudc *hsudc = the_controller; > > + > > + usb_del_gadget_udc(&hsudc->gadget); > > + > > + clk_disable(hsudc->uclk); > > + clk_put(hsudc->uclk); > > + > > + free_irq(hsudc->irq, hsudc); > > + > > + iounmap(hsudc->regs); > > + > > + release_resource(hsudc->mem_rsrc); > > + kfree(hsudc->mem_rsrc); > > + > > + if (hsudc->transceiver) > > + otg_put_transceiver(hsudc->transceiver); > > + > > + the_controller = NULL; > > + kfree(hsudc); > > + return 0; > > +} > > + > > > > static struct platform_driver s3c_hsudc_driver = { > > > > .driver = { > > > > .owner = THIS_MODULE, > > .name = "s3c-hsudc", > > > > }, > > .probe = s3c_hsudc_probe, > > > > + .remove = __devexit_p(s3c_hsudc_remove), > > > > }; > > > > module_platform_driver(s3c_hsudc_driver); -- To unsubscribe from this list: send the line "unsubscribe linux-usb" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html