#785578 libusb occasionally hangs after suspend/resume

#785578#5
Date:
2015-05-17 22:01:47 UTC
From:
To:
Dear Maintainer,

I'm trying to make g15daemon correctly recover after suspend/resume and found that it occasionally hangs after resume in libusb's usb_urb_transfer() (linux.c) on this line:
ioctl(dev->fd, IOCTL_USB_REAPURB, &context);

After some research I found that linux kernel internally has lists of pending and completed requests. All requests - successful or not - are moved from pending list to completed list, no requests should be lost. But it looks like after suspend/resume some request may be lost (may be a kernel bug). It that case IOCTL_USB_REAPURB would hang forever since request it's waiting for will never appear on completed list.

There is simple workaround. After preceding IOCTL_USB_DISCARDURB call our request is guaranteed to be completed, so there is no need to use blocking IOCTL_USB_DISCARDURB, we may use non-blocking IOCTL_USB_REAPURBNDELAY instead.

I've attached patch with this workaround. It also fixes race condition existed in original code, which may cause corruption of stack.

  * Added debian/patches/12_hang_after_resume.diff to fix occasional hang
    after suspend/resume. (LP: #1455924)


Thanks for considering the patch.