diff options
Diffstat (limited to 'libusb/os/darwin_usb.c')
-rw-r--r-- | libusb/os/darwin_usb.c | 20 |
1 files changed, 17 insertions, 3 deletions
diff --git a/libusb/os/darwin_usb.c b/libusb/os/darwin_usb.c index dd391db..f6e853b 100644 --- a/libusb/os/darwin_usb.c +++ b/libusb/os/darwin_usb.c @@ -297,10 +297,24 @@ static usb_device_t **darwin_device_from_service (io_service_t service) usb_device_t **device; IOReturn kresult; SInt32 score; + const int max_retries = 5; + + /* The IOCreatePlugInInterfaceForService function might consistently return + an "out of resources" error with certain USB devices the first time we run + it. The reason is still unclear, but retrying fixes the problem */ + for (int count = 0; count < max_retries; count++) { + kresult = IOCreatePlugInInterfaceForService(service, kIOUSBDeviceUserClientTypeID, + kIOCFPlugInInterfaceID, &plugInInterface, + &score); + if (kIOReturnSuccess == kresult && plugInInterface) { + break; + } - kresult = IOCreatePlugInInterfaceForService(service, kIOUSBDeviceUserClientTypeID, - kIOCFPlugInInterfaceID, &plugInInterface, - &score); + usbi_dbg ("set up plugin for service retry: %s", darwin_error_str (kresult)); + + /* sleep for a little while before trying again */ + nanosleep(&(struct timespec){.tv_sec = 0, .tv_nsec = 1000}, NULL); + } if (kIOReturnSuccess != kresult || !plugInInterface) { usbi_dbg ("could not set up plugin for service: %s", darwin_error_str (kresult)); |