From: Arnd Bergmann <arnd@arndb.de>
To: Greg KH <gregkh@suse.de>
Cc: linux-kernel@vger.kernel.org, Arnd Bergmann <arnd@arndb.de>,
linux-usb@vger.kernel.org,
Frederic Weisbecker <fweisbec@gmail.com>,
John Kacur <jkacur@redhat.com>, Andi Kleen <andi@firstfloor.org>,
Andi Kleen <ak@linux.intel.com>
Subject: [PATCH 3/6] USB-BKL: Remove BKL use for usb serial driver probing
Date: Tue, 1 Jun 2010 23:04:42 +0200 [thread overview]
Message-ID: <1275426285-9088-4-git-send-email-arnd@arndb.de> (raw)
In-Reply-To: <1275426285-9088-1-git-send-email-arnd@arndb.de>
From: Andi Kleen <ak@linux.intel.com>
The usb serial driver initialization tried to use the BKL to stop
driver modules from unloading, but that didn't work anyways.
There was already some code to do proper try_module_get,
but it was conditional on having a new probe interface.
I checked all the low level drivers and they all have proper
.owner = THIS_MODULE, so it's ok to always use.
The other problem was the usb_serial_driver_list needing
protection by a lock. This was broken anyways because unregister
did not necessarily have the BKL.
I extended the extending table_lock mutex to protect this case too.
With these changes the BKL can be removed here.
Signed-off-by: Andi Kleen <ak@linux.intel.com>
---
drivers/usb/serial/usb-serial.c | 30 ++++++++++++++----------------
1 files changed, 14 insertions(+), 16 deletions(-)
diff --git a/drivers/usb/serial/usb-serial.c b/drivers/usb/serial/usb-serial.c
index 941c2d4..443468e 100644
--- a/drivers/usb/serial/usb-serial.c
+++ b/drivers/usb/serial/usb-serial.c
@@ -653,6 +653,7 @@ exit:
return id;
}
+/* Caller must hold table_lock */
static struct usb_serial_driver *search_serial_device(
struct usb_interface *iface)
{
@@ -718,17 +719,23 @@ int usb_serial_probe(struct usb_interface *interface,
int num_ports = 0;
int max_endpoints;
- lock_kernel(); /* guard against unloading a serial driver module */
+ mutex_lock(&table_lock);
type = search_serial_device(interface);
if (!type) {
- unlock_kernel();
+ mutex_unlock(&table_lock);
dbg("none matched");
return -ENODEV;
}
+ if (!try_module_get(type->driver.owner)) {
+ mutex_unlock(&table_lock);
+ dev_err(&interface->dev, "module get failed, exiting\n");
+ return -EIO;
+ }
+ mutex_unlock(&table_lock);
+
serial = create_serial(dev, interface, type);
if (!serial) {
- unlock_kernel();
dev_err(&interface->dev, "%s - out of memory\n", __func__);
return -ENOMEM;
}
@@ -737,20 +744,11 @@ int usb_serial_probe(struct usb_interface *interface,
if (type->probe) {
const struct usb_device_id *id;
- if (!try_module_get(type->driver.owner)) {
- unlock_kernel();
- dev_err(&interface->dev,
- "module get failed, exiting\n");
- kfree(serial);
- return -EIO;
- }
-
id = get_iface_id(type, interface);
retval = type->probe(serial, id);
module_put(type->driver.owner);
if (retval) {
- unlock_kernel();
dbg("sub driver rejected device");
kfree(serial);
return retval;
@@ -822,7 +820,6 @@ int usb_serial_probe(struct usb_interface *interface,
* properly during a later invocation of usb_serial_probe
*/
if (num_bulk_in == 0 || num_bulk_out == 0) {
- unlock_kernel();
dev_info(&interface->dev, "PL-2303 hack: descriptors matched but endpoints did not\n");
kfree(serial);
return -ENODEV;
@@ -835,7 +832,6 @@ int usb_serial_probe(struct usb_interface *interface,
if (type == &usb_serial_generic_device) {
num_ports = num_bulk_out;
if (num_ports == 0) {
- unlock_kernel();
dev_err(&interface->dev,
"Generic device with no bulk out, not allowed.\n");
kfree(serial);
@@ -847,7 +843,6 @@ int usb_serial_probe(struct usb_interface *interface,
/* if this device type has a calc_num_ports function, call it */
if (type->calc_num_ports) {
if (!try_module_get(type->driver.owner)) {
- unlock_kernel();
dev_err(&interface->dev,
"module get failed, exiting\n");
kfree(serial);
@@ -878,7 +873,6 @@ int usb_serial_probe(struct usb_interface *interface,
max_endpoints = max(max_endpoints, num_interrupt_out);
max_endpoints = max(max_endpoints, (int)serial->num_ports);
serial->num_port_pointers = max_endpoints;
- unlock_kernel();
dbg("%s - setting up %d port structures for this device",
__func__, max_endpoints);
@@ -1349,6 +1343,7 @@ int usb_serial_register(struct usb_serial_driver *driver)
driver->description = driver->driver.name;
/* Add this device to our list of devices */
+ mutex_lock(&table_lock);
list_add(&driver->driver_list, &usb_serial_driver_list);
retval = usb_serial_bus_register(driver);
@@ -1360,6 +1355,7 @@ int usb_serial_register(struct usb_serial_driver *driver)
printk(KERN_INFO "USB Serial support registered for %s\n",
driver->description);
+ mutex_unlock(&table_lock);
return retval;
}
EXPORT_SYMBOL_GPL(usb_serial_register);
@@ -1370,8 +1366,10 @@ void usb_serial_deregister(struct usb_serial_driver *device)
/* must be called with BKL held */
printk(KERN_INFO "USB Serial deregistering driver %s\n",
device->description);
+ mutex_lock(&table_lock);
list_del(&device->driver_list);
usb_serial_bus_deregister(device);
+ mutex_unlock(&table_lock);
}
EXPORT_SYMBOL_GPL(usb_serial_deregister);
--
1.7.0.4
next prev parent reply other threads:[~2010-06-01 21:04 UTC|newest]
Thread overview: 15+ messages / expand[flat|nested] mbox.gz Atom feed top
2010-06-01 21:04 [PATCH 0/6] USB: BKL removal Arnd Bergmann
2010-06-01 21:04 ` [PATCH 1/6] USB-BKL: Remove lock_kernel in usbfs update_sb() Arnd Bergmann
2010-06-01 21:04 ` [PATCH 2/6] USB-BKL: Convert usb_driver ioctl to unlocked_ioctl Arnd Bergmann
2010-06-01 21:04 ` Arnd Bergmann [this message]
2010-06-01 21:04 ` [PATCH 4/6] USB-BKL: Remove BKL use in uhci-debug Arnd Bergmann
2010-06-02 10:11 ` Sergei Shtylyov
2010-06-17 17:44 ` Greg KH
2010-06-02 13:47 ` Alan Stern
2010-06-17 17:43 ` Greg KH
2010-06-01 21:04 ` [PATCH 5/6] usb/gadget: Do not take BKL for gadget->ops->ioctl Arnd Bergmann
2010-06-18 13:59 ` Michał Nazarewicz
2010-06-18 18:22 ` Arnd Bergmann
2010-06-29 14:08 ` David Brownell
2010-06-01 21:04 ` [PATCH 6/6] usb/mon: kill BKL usage Arnd Bergmann
2010-06-17 17:46 ` [PATCH 0/6] USB: BKL removal Greg KH
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1275426285-9088-4-git-send-email-arnd@arndb.de \
--to=arnd@arndb.de \
--cc=ak@linux.intel.com \
--cc=andi@firstfloor.org \
--cc=fweisbec@gmail.com \
--cc=gregkh@suse.de \
--cc=jkacur@redhat.com \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-usb@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
Powered by JetHome