aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/usb
diff options
context:
space:
mode:
authorElina Pasheva <epasheva@sierrawireless.com>2009-04-29 10:29:21 -0700
committerGreg Kroah-Hartman <gregkh@suse.de>2009-06-15 21:44:45 -0700
commitb0cda8c5f7b652c6c27bcb3891d174534d2f1a91 (patch)
tree8f72962f8fb4bc88e8d21dda0369fe4e08169d2a /drivers/usb
parentUSB: serial: sierra driver write path improvements (diff)
downloadlinux-dev-b0cda8c5f7b652c6c27bcb3891d174534d2f1a91.tar.xz
linux-dev-b0cda8c5f7b652c6c27bcb3891d174534d2f1a91.zip
USB: serial: sierra driver read path bug fix
This patch fixes a problem in function sierra_indat_callback() which would stop receiving traffic from a modem if a number of URB failures occur. Failed URBs are not resubmitted for the next read and there is only a limited number of URBs allocated for the IN path. After this number of failures, the receive path stops working on a particular interface. Signed-off-by: Elina Pasheva <epasheva@sierrawireless.com>
Diffstat (limited to 'drivers/usb')
-rw-r--r--drivers/usb/serial/sierra.c28
1 files changed, 17 insertions, 11 deletions
diff --git a/drivers/usb/serial/sierra.c b/drivers/usb/serial/sierra.c
index 27f41f95aefb..f494c5f659e2 100644
--- a/drivers/usb/serial/sierra.c
+++ b/drivers/usb/serial/sierra.c
@@ -509,10 +509,10 @@ static void sierra_indat_callback(struct urb *urb)
unsigned char *data = urb->transfer_buffer;
int status = urb->status;
- dbg("%s: %p", __func__, urb);
-
endpoint = usb_pipeendpoint(urb->pipe);
- port = urb->context;
+ port = urb->context;
+
+ dev_dbg(&port->dev, "%s: %p\n", __func__, urb);
if (status) {
dev_dbg(&port->dev, "%s: nonzero status: %d on"
@@ -520,22 +520,28 @@ static void sierra_indat_callback(struct urb *urb)
} else {
if (urb->actual_length) {
tty = tty_port_tty_get(&port->port);
+
tty_buffer_request_room(tty, urb->actual_length);
tty_insert_flip_string(tty, data, urb->actual_length);
tty_flip_buffer_push(tty);
+
tty_kref_put(tty);
- } else
+ usb_serial_debug_data(debug, &port->dev, __func__,
+ urb->actual_length, data);
+ } else {
dev_dbg(&port->dev, "%s: empty read urb"
" received\n", __func__);
-
- /* Resubmit urb so we continue receiving */
- if (port->port.count && status != -ESHUTDOWN && status != -EPERM) {
- err = usb_submit_urb(urb, GFP_ATOMIC);
- if (err)
- dev_err(&port->dev, "resubmit read urb failed."
- "(%d)\n", err);
}
}
+
+ /* Resubmit urb so we continue receiving */
+ if (port->port.count && status != -ESHUTDOWN && status != -EPERM) {
+ err = usb_submit_urb(urb, GFP_ATOMIC);
+ if (err)
+ dev_err(&port->dev, "resubmit read urb failed."
+ "(%d)\n", err);
+ }
+
return;
}