From 2682e21d3d7e1e5ebd6dfe07f193efe48caa3e14 Mon Sep 17 00:00:00 2001 From: Hans de Goede Date: Wed, 10 Aug 2016 12:17:00 +0200 Subject: [PATCH] Revert "io: Fix race condition in handle_timeout()" This reverts commit bd8d5b5019b72b2dc2d074d96c9992e2f6e7e0b7. Chris Dickens and me have been working on a patch-set refactoring the transfer flag handling which fixes this differently. Revert this commit so that the refactoring changes can be merged cleanly. Signed-off-by: Hans de Goede --- libusb/io.c | 57 ++++++++++++++++++--------------------------------- libusb/version_nano.h | 2 +- 2 files changed, 21 insertions(+), 38 deletions(-) diff --git a/libusb/io.c b/libusb/io.c index 8944461..4d03b8b 100644 --- a/libusb/io.c +++ b/libusb/io.c @@ -1530,34 +1530,6 @@ out: return r; } -static int cancel_transfer_locked(struct libusb_transfer *transfer) -{ - struct usbi_transfer *itransfer = - LIBUSB_TRANSFER_TO_USBI_TRANSFER(transfer); - int r; - if (!(itransfer->flags & USBI_TRANSFER_IN_FLIGHT) - || (itransfer->flags & USBI_TRANSFER_CANCELLING)) { - return LIBUSB_ERROR_NOT_FOUND; - } - - r = usbi_backend->cancel_transfer(itransfer); - if (r < 0) { - if (r != LIBUSB_ERROR_NOT_FOUND && - r != LIBUSB_ERROR_NO_DEVICE) - usbi_err(TRANSFER_CTX(transfer), - "cancel transfer failed error %d", r); - else - usbi_dbg("cancel transfer failed error %d", r); - - if (r == LIBUSB_ERROR_NO_DEVICE) - itransfer->flags |= USBI_TRANSFER_DEVICE_DISAPPEARED; - } - - itransfer->flags |= USBI_TRANSFER_CANCELLING; - - return r; -} - /** \ingroup libusb_asyncio * Asynchronously cancel a previously submitted transfer. * This function returns immediately, but this does not indicate cancellation @@ -1581,9 +1553,27 @@ int API_EXPORTED libusb_cancel_transfer(struct libusb_transfer *transfer) usbi_dbg("transfer %p", transfer ); usbi_mutex_lock(&itransfer->lock); usbi_mutex_lock(&itransfer->flags_lock); + if (!(itransfer->flags & USBI_TRANSFER_IN_FLIGHT) + || (itransfer->flags & USBI_TRANSFER_CANCELLING)) { + r = LIBUSB_ERROR_NOT_FOUND; + goto out; + } + r = usbi_backend->cancel_transfer(itransfer); + if (r < 0) { + if (r != LIBUSB_ERROR_NOT_FOUND && + r != LIBUSB_ERROR_NO_DEVICE) + usbi_err(TRANSFER_CTX(transfer), + "cancel transfer failed error %d", r); + else + usbi_dbg("cancel transfer failed error %d", r); - r = cancel_transfer_locked(transfer); + if (r == LIBUSB_ERROR_NO_DEVICE) + itransfer->flags |= USBI_TRANSFER_DEVICE_DISAPPEARED; + } + + itransfer->flags |= USBI_TRANSFER_CANCELLING; +out: usbi_mutex_unlock(&itransfer->flags_lock); usbi_mutex_unlock(&itransfer->lock); return r; @@ -1977,20 +1967,13 @@ static void handle_timeout(struct usbi_transfer *itransfer) USBI_TRANSFER_TO_LIBUSB_TRANSFER(itransfer); int r; - usbi_mutex_lock(&itransfer->lock); - usbi_mutex_lock(&itransfer->flags_lock); - itransfer->flags |= USBI_TRANSFER_TIMEOUT_HANDLED; - r = cancel_transfer_locked(transfer); - + r = libusb_cancel_transfer(transfer); if (r == 0) itransfer->flags |= USBI_TRANSFER_TIMED_OUT; else usbi_warn(TRANSFER_CTX(transfer), "async cancel failed %d errno=%d", r, errno); - - usbi_mutex_unlock(&itransfer->flags_lock); - usbi_mutex_unlock(&itransfer->lock); } static int handle_timeouts_locked(struct libusb_context *ctx) diff --git a/libusb/version_nano.h b/libusb/version_nano.h index a806b19..e92bc71 100644 --- a/libusb/version_nano.h +++ b/libusb/version_nano.h @@ -1 +1 @@ -#define LIBUSB_NANO 11127 +#define LIBUSB_NANO 11128 -- 2.7.4