Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

macOS: Fix set_configuration and reset by using USBDeviceOpen #88

Merged
merged 3 commits into from
Oct 30, 2024

Conversation

kevinmehall
Copy link
Owner

@kevinmehall kevinmehall commented Oct 28, 2024

Fixes #87

USBDeviceOpen is not required for claiming interfaces. The documentation says it's required for control transfers, but it works without. It is, however, required for set_configuration and reset.

Having an interface claimed does not cause set_configuration and reset to fail on macOS like it does on Linux. After doing some testing, I ended up doing what libusb does and attempting to USBDeviceOpen when opening a device to try to get exclusive access, but ignoring failures, and trying again and requiring success only before set_configuration and reset. That's not perfect -- you can be the second process to open a device and fail USBDeviceOpen, then the first process closes it, and a third process is then able to call these methods, but I can't find a better way.

Copy link

@carlossless carlossless left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have tested this against my project and it does seem to work. Though, I'm curious why not use USBDeviceOpenSeize() instead of USBDeviceOpen() same as libusb does.

Only USBDeviceOpenSeize is documented, but given that the docs state that it opens the device for exclusive access I assume USBDeviceOpen is the non-exclusive variant.

Having this in mind, shouldn't USBDeviceOpenSeize be used here?

@kevinmehall
Copy link
Owner Author

Though, I'm curious why not use USBDeviceOpenSeize() instead of USBDeviceOpen() same as libusb does.

The old documentation describes both:

  • USBDeviceOpen: Open up the IOUSBDevice for exclusive access.
  • USBDeviceOpenSeize: Open up the IOUSBDevice for exclusive access. If another client has the device opened, an attempt is made to get that client to close it before returning.

I don't know what it does to the other app, but that doesn't seem like the desired behavior. I guess that means I should test what happens when libusb opens a device that nusb has already opened.

@carlossless
Copy link

that doesn't seem like the desired behavior

Yep, I agree.

I guess that means I should test what happens when libusb opens a device that nusb has already opened.

I dug a bit more and found this description. Assuming everything behaves the same way since that was published, I would expect that: if the app that's holding exclusive access to a device doesn't register to receive those IOServiceInterestNotifications and act on them, both USBDeviceOpen and USBDeviceOpenSeize will fail in the same way.

@kevinmehall kevinmehall merged commit f8f23b2 into main Oct 30, 2024
8 checks passed
@kevinmehall kevinmehall deleted the macos-fix branch October 30, 2024 15:20
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

macOS implementation lacks USBDeviceOpenSeize
2 participants