Hi , While working on a new USB serial driver, I find it need call usb_serial_register() to register a serial driver, then call usb_register() to register the USB one. So calling usb_serial_register() is common for most of USB serial drivers, moreover, these drivers are using usb_searil_probe() to probe the USB devices. Then, how about move the calling of usb_serial_register() from these modules' init routine into usb_serial_probe() ? >From logical side, maybe it is reasonable: While initiating the module, it only registers a USB driver as what other usual USB drivers do, and passes the customized serial driver information through 'driver_info'. When the driver does probing, it can retrieve serial driver information from 'driver_info' to registers a serial driver to system in order to talk with other subsystem. Does this changes make sense to go ahead ? BTW, following is a draft patch to show the changes taking pl2303.c as an example: --- a/drivers/usb/serial/pl2303.c +++ b/drivers/usb/serial/pl2303.c @@ -37,62 +37,63 @@ #define DRIVER_DESC "Prolific PL2303 USB to serial adaptor driver" static int debug; +static struct usb_serial_driver pl2303_device; #define PL2303_CLOSING_WAIT (30*HZ) static const struct usb_device_id id_table[] = { - { USB_DEVICE(PL2303_VENDOR_ID, PL2303_PRODUCT_ID) }, + { USB_DEVICE(PL2303_VENDOR_ID, PL2303_PRODUCT_ID), .driver_info = (unsigned long)&pl2303_device }, @@ -859,24 +860,18 @@ static int __init pl2303_init(void) { int retval; - retval = usb_serial_register(&pl2303_device); - if (retval) - goto failed_usb_serial_register; retval = usb_register(&pl2303_driver); if (retval) goto failed_usb_register; printk(KERN_INFO KBUILD_MODNAME ": " DRIVER_DESC "\n"); return 0; failed_usb_register: - usb_serial_deregister(&pl2303_device); -failed_usb_serial_register: return retval; } static void __exit pl2303_exit(void) { usb_deregister(&pl2303_driver); - usb_serial_deregister(&pl2303_device); } module_init(pl2303_init); diff --git a/drivers/usb/serial/usb-serial.c b/drivers/usb/serial/usb-serial.c index cc274fd..c60147b4 100644 --- a/drivers/usb/serial/usb-serial.c +++ b/drivers/usb/serial/usb-serial.c @@ -731,14 +731,16 @@ int usb_serial_probe(struct usb_interface *interface, int num_ports = 0; int max_endpoints; - mutex_lock(&table_lock); - type = search_serial_device(interface); + type = (struct usb_serial_driver *)id->driver_info; if (!type) { - mutex_unlock(&table_lock); dbg("none matched"); return -ENODEV; } + usb_serial_register(type); + + mutex_lock(&table_lock); if (!try_module_get(type->driver.owner)) { mutex_unlock(&table_lock); dev_err(&interface->dev, "module get failed, exiting\n"); @@ -1146,6 +1148,11 @@ void usb_serial_disconnect(struct usb_interface *interface) /* let the last holder of this object cause it to be cleaned up */ usb_serial_put(serial); + + struct usb_serial_driver * drv = search_serial_device(interface); + if (drv) + usb_serial_deregister(drv); + dev_info(dev, "device disconnected\n"); } EXPORT_SYMBOL_GPL(usb_serial_disconnect); -- 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