diff options
author | Alan Stern <stern@rowland.harvard.edu> | 2009-06-02 11:54:11 -0400 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@suse.de> | 2009-06-16 00:44:47 -0400 |
commit | c706ebdfc8955b850e477255a8c0f93f9f14712d (patch) | |
tree | 1f880601cdd2663ee4206783092d5fa9d90c8922 /drivers/usb/serial/bus.c | |
parent | c6994e6f067cf0fc4c6cca3d164018b1150916f8 (diff) |
USB: usb-serial: call port_probe and port_remove at the right times
This patch (as1253) prevents the usb-serial core from calling a
driver's port_probe and port_remove methods more than once per port.
It also removes some unnecessary try_module_get() calls and adds a
missing port_remove method call in a failure path.
Signed-off-by: Alan Stern <stern@rowland.harvard.edu>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/usb/serial/bus.c')
-rw-r--r-- | drivers/usb/serial/bus.c | 27 |
1 files changed, 11 insertions, 16 deletions
diff --git a/drivers/usb/serial/bus.c b/drivers/usb/serial/bus.c index 83bbb5bca2ef..ba555c528cc6 100644 --- a/drivers/usb/serial/bus.c +++ b/drivers/usb/serial/bus.c | |||
@@ -59,23 +59,22 @@ static int usb_serial_device_probe(struct device *dev) | |||
59 | retval = -ENODEV; | 59 | retval = -ENODEV; |
60 | goto exit; | 60 | goto exit; |
61 | } | 61 | } |
62 | if (port->dev_state != PORT_REGISTERING) | ||
63 | goto exit; | ||
62 | 64 | ||
63 | driver = port->serial->type; | 65 | driver = port->serial->type; |
64 | if (driver->port_probe) { | 66 | if (driver->port_probe) { |
65 | if (!try_module_get(driver->driver.owner)) { | ||
66 | dev_err(dev, "module get failed, exiting\n"); | ||
67 | retval = -EIO; | ||
68 | goto exit; | ||
69 | } | ||
70 | retval = driver->port_probe(port); | 67 | retval = driver->port_probe(port); |
71 | module_put(driver->driver.owner); | ||
72 | if (retval) | 68 | if (retval) |
73 | goto exit; | 69 | goto exit; |
74 | } | 70 | } |
75 | 71 | ||
76 | retval = device_create_file(dev, &dev_attr_port_number); | 72 | retval = device_create_file(dev, &dev_attr_port_number); |
77 | if (retval) | 73 | if (retval) { |
74 | if (driver->port_remove) | ||
75 | retval = driver->port_remove(port); | ||
78 | goto exit; | 76 | goto exit; |
77 | } | ||
79 | 78 | ||
80 | minor = port->number; | 79 | minor = port->number; |
81 | tty_register_device(usb_serial_tty_driver, minor, dev); | 80 | tty_register_device(usb_serial_tty_driver, minor, dev); |
@@ -98,19 +97,15 @@ static int usb_serial_device_remove(struct device *dev) | |||
98 | if (!port) | 97 | if (!port) |
99 | return -ENODEV; | 98 | return -ENODEV; |
100 | 99 | ||
100 | if (port->dev_state != PORT_UNREGISTERING) | ||
101 | return retval; | ||
102 | |||
101 | device_remove_file(&port->dev, &dev_attr_port_number); | 103 | device_remove_file(&port->dev, &dev_attr_port_number); |
102 | 104 | ||
103 | driver = port->serial->type; | 105 | driver = port->serial->type; |
104 | if (driver->port_remove) { | 106 | if (driver->port_remove) |
105 | if (!try_module_get(driver->driver.owner)) { | ||
106 | dev_err(dev, "module get failed, exiting\n"); | ||
107 | retval = -EIO; | ||
108 | goto exit; | ||
109 | } | ||
110 | retval = driver->port_remove(port); | 107 | retval = driver->port_remove(port); |
111 | module_put(driver->driver.owner); | 108 | |
112 | } | ||
113 | exit: | ||
114 | minor = port->number; | 109 | minor = port->number; |
115 | tty_unregister_device(usb_serial_tty_driver, minor); | 110 | tty_unregister_device(usb_serial_tty_driver, minor); |
116 | dev_info(dev, "%s converter now disconnected from ttyUSB%d\n", | 111 | dev_info(dev, "%s converter now disconnected from ttyUSB%d\n", |