summaryrefslogtreecommitdiff
path: root/drivers/usb/core/message.c
diff options
context:
space:
mode:
authorDavid S. Miller <davem@davemloft.net>2020-05-06 22:10:13 -0700
committerDavid S. Miller <davem@davemloft.net>2020-05-06 22:10:13 -0700
commit3793faad7b5b730941b2efbc252d14374b60843a (patch)
treee1bea43727d87f8fd30ca169f465a3591f15d63b /drivers/usb/core/message.c
parentae1804de93f6f1626906567ae7deec8e0111259d (diff)
parenta811c1fa0a02c062555b54651065899437bacdbe (diff)
Merge git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net
Conflicts were all overlapping changes. Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/usb/core/message.c')
-rw-r--r--drivers/usb/core/message.c9
1 files changed, 8 insertions, 1 deletions
diff --git a/drivers/usb/core/message.c b/drivers/usb/core/message.c
index d5f834f16993..a48678a0c83a 100644
--- a/drivers/usb/core/message.c
+++ b/drivers/usb/core/message.c
@@ -589,12 +589,13 @@ void usb_sg_cancel(struct usb_sg_request *io)
int i, retval;
spin_lock_irqsave(&io->lock, flags);
- if (io->status) {
+ if (io->status || io->count == 0) {
spin_unlock_irqrestore(&io->lock, flags);
return;
}
/* shut everything down */
io->status = -ECONNRESET;
+ io->count++; /* Keep the request alive until we're done */
spin_unlock_irqrestore(&io->lock, flags);
for (i = io->entries - 1; i >= 0; --i) {
@@ -608,6 +609,12 @@ void usb_sg_cancel(struct usb_sg_request *io)
dev_warn(&io->dev->dev, "%s, unlink --> %d\n",
__func__, retval);
}
+
+ spin_lock_irqsave(&io->lock, flags);
+ io->count--;
+ if (!io->count)
+ complete(&io->complete);
+ spin_unlock_irqrestore(&io->lock, flags);
}
EXPORT_SYMBOL_GPL(usb_sg_cancel);