Add hid_set_input_report_buffer_size() API#787
Add hid_set_input_report_buffer_size() API#787auxcorelabs wants to merge 2 commits intolibusb:masterfrom
Conversation
Exposes a new public function to resize the per-device input report queue. High-throughput HID devices (medical telemetry, high-poll-rate gaming peripherals, data acquisition hardware) emit bursts of input reports that exceed the current hardcoded queue sizes (30 on macOS and the libusb backend, 64 on Windows). When a burst exceeds the queue, reports are silently dropped with no error indication to the caller. This adds: - hid_set_input_report_buffer_size(dev, size) in hidapi.h - HID_API_MAX_INPUT_REPORT_BUFFER_SIZE (1024) cap to prevent unbounded memory growth Per-backend behavior: - macOS: resizes the userspace IOHIDQueue-fed report queue - Linux libusb: resizes the userspace report queue - Windows: wraps HidD_SetNumInputBuffers (parity with existing behavior) - Linux hidraw: no-op (kernel manages buffering) - NetBSD: no-op (kernel manages buffering) Defaults are unchanged, so existing callers are unaffected. Values outside [1, HID_API_MAX_INPUT_REPORT_BUFFER_SIZE] are rejected with -1. Thread-safe on macOS (dev->mutex) and libusb (dev->thread_state), matching the locks used by the respective report callbacks. Addresses the same need as closed issue libusb#154 (HidD_SetNumInputBuffers exposure) and complements libusb#725 (callback-based input API).
| if (!dev) { | ||
| register_global_error("Device is NULL"); | ||
| return -1; | ||
| } |
There was a problem hiding this comment.
remove this check (from all backends) - device functions do not check for validity of the device handle
the only exception is hid_close
| /* hidraw: kernel manages the input report buffer, no userspace queue | ||
| to resize. Accept the call to preserve a consistent cross-platform | ||
| API so callers do not need per-backend conditional code. */ |
There was a problem hiding this comment.
too bad we don't have a logging mechanism
this looks like a perfect spot for a warning
making this completely silent might confuse some users
anyway - even though documentation mentiones that there is no user-space queue for linux backend - we should explicitly document that this function for linux and bsd backend is a no-op
There was a problem hiding this comment.
Have updated the comment to explicitly call out no-op. Thanks
| if (!dev) { | ||
| register_global_error("Device is NULL"); | ||
| return -1; | ||
| } |
| if (!dev) { | ||
| register_global_error("Device is NULL"); | ||
| return -1; | ||
| } |
| if (!dev) { | ||
| register_global_error(L"Device is NULL"); | ||
| return -1; | ||
| } |
Youw
left a comment
There was a problem hiding this comment.
refer to comments, otherwise looks good
Per maintainer feedback on PR libusb#787: - Remove if (!dev) validation from all 5 backends. hidapi convention is that device functions trust the caller to pass a valid handle; only hid_close is permitted to accept NULL. - Reword the inline comment in linux/hid.c and netbsd/hid.c to lead with "No-op" so the caller-visible behavior is explicit at the implementation site.
|
Thanks for reviewing. I have made the changes. |
Exposes a new public function
hid_set_input_report_buffer_size(dev, size)to resize the per-device input report queue.High-throughput HID devices (medical telemetry, high-poll-rate gaming peripherals, data acquisition hardware) can emit bursts of input reports that exceed the current hardcoded queue sizes (30 on macOS and Linux/libusb, 64 on Windows). When a burst exceeds the queue, reports are silently dropped with no error indication to the caller. Observed on hardware emitting ~90 reports in 200 ms bursts: both the macOS and Linux/libusb backends silently drop ~20% of frames.
Per-backend behavior
HidD_SetNumInputBuffers(parity with existing behavior)Safety
[1, HID_API_MAX_INPUT_REPORT_BUFFER_SIZE]return -1; NULL dev returns -1 with a global errordev->mutex/dev->thread_state) as the respective report callbackDesign notes
hid_deviceis opaque inhidapi.h, so struct field additions in backend-private files are not an ABI break.INT_MAX(malicious or buggy). We've measured bursts up to ~90 reports deep in practice; 1024 leaves room for devices ~10× more demanding. Overridable via-DHID_API_MAX_INPUT_REPORT_BUFFER_SIZE=Nat build time for memory-constrained targets.hid_get_input_report()instead? That API issues a host-initiatedGET_REPORTrequest (via the control endpoint or OS equivalent). It does not drain the interrupt-endpoint queue that streaming devices fill, and in practice many devices either don't implementGET_REPORTfor input reports or respond incorrectly. The two APIs use different USB transfer mechanisms (interrupt endpoint vs. control endpoint); this PR fixes the interrupt-streaming path.References
HidD_SetNumInputBuffersfunctionality to callersCI equivalent status
All upstream CI equivalents tested locally:
-Wall -Wextra -pedantic -Werror -Wformat-signednessHIDAPI_ENABLE_ASAN=ON-Wall -Wextra -pedantic -Werror/W4 /WXZero warnings on all platforms. Symbol verified exported in all built artifacts.