Skip to content

libusb: make hid.c compile cleanly as C++#811

Merged
Youw merged 1 commit into
masterfrom
fix-cpp-compile
May 20, 2026
Merged

libusb: make hid.c compile cleanly as C++#811
Youw merged 1 commit into
masterfrom
fix-cpp-compile

Conversation

@Youw
Copy link
Copy Markdown
Member

@Youw Youw commented May 20, 2026

Problem

libusb/hid.c doesn't compile cleanly as C++, as reported in #671. Reproduced on current master with g++ -xc++ -Wall -Wextra -c libusb/hid.c:

libusb/hid.c:23: warning: "_GNU_SOURCE" redefined
libusb/hid.c:385:22: error: invalid conversion from 'void*' to 'wchar_t*'
libusb/hid.c:722:49: error: invalid conversion from 'void*' to 'hid_device_info*'
libusb/hid.c:1094:37: error: invalid conversion from 'void*' to 'hid_device*'
libusb/hid.c:1163:27: error: invalid conversion from 'void*' to 'hid_device*'
libusb/hid.c:1639:27: error: invalid conversion from 'void*' to 'hid_device*'
libusb/hid.c:2103:24: error: invalid conversion from 'void*' to 'char*'
libusb/hid.c:349:56: error: invalid conversion from 'int' to 'libusb_error'
libusb/hid.c:605:67: error: invalid conversion from 'int' to 'libusb_error'
... (13 such int → libusb_error sites total)

Three C-only patterns are involved:

  1. Implicit void* to typed pointer conversions from malloc / calloc / pthread-style void *param (6 sites).
  2. Implicit int to enum libusb_error conversions when storing libusb return codes (typed int) into the hidapi_error_ctx fields or passing them to register_libusb_error() (13 sites).
  3. #define _GNU_SOURCE without an #ifndef guard — emits a "_GNU_SOURCE" redefined warning when the macro is also supplied via -D on the command line.

Change

Minimal fix, scoped to libusb/hid.c:

  • Wrap #define _GNU_SOURCE in #ifndef _GNU_SOURCE.
  • Change the internal hidapi_error_ctx struct's error_code / last_error_code_cache and the register_libusb_error() error parameter from enum libusb_error to plain int. The struct is internal (not exported), the stored values are already a mix of libusb error codes and a 1 sentinel from register_string_error(), and using int removes 13 call-site conversions in a single structural change.
  • Add explicit C-style casts on the 6 malloc / calloc / void* sites. This matches the convention already in windows/hid.c and mac/hid.c.
  • Drop a now-redundant (enum libusb_error) cast at libusb_get_device_list's error path.

Net diff: 17 insertions, 10 deletions in one file.

Verification

On WSL Ubuntu (gcc 11.4, libusb-1.0):

build result
g++ -xc++ -Wall -Wextra -c libusb/hid.c clean — was 19 errors + 1 warning
gcc -Wall -Wextra -c libusb/hid.c clean — no change for the C build
full CMake build of the libusb backend (libhidapi-libusb.so, hidtest_libusb) builds and links unchanged

Closes #671.

Drafted with Claude Code.

libusb/hid.c relied on three C-only patterns that produce errors when
the file is built with a C++ compiler (as reported in #671):

  - void* from malloc/calloc/pthread-style params implicitly assigned
    to typed pointers (6 sites);
  - int libusb return codes implicitly stored in `enum libusb_error`
    struct fields and passed to a function taking `enum libusb_error`
    (13 sites);
  - `#define _GNU_SOURCE` without an #ifndef guard, which produces a
    "redefined" warning when the macro is also supplied via -D.

Fix:

  - Guard _GNU_SOURCE with #ifndef.
  - Change `hidapi_error_ctx`'s error_code / last_error_code_cache
    fields and `register_libusb_error()`'s error parameter from
    `enum libusb_error` to plain int. The struct is internal, the
    values stored are already a mix of libusb_error codes and a `1`
    sentinel used by register_string_error(), and int removes the
    13 call-site conversions in one go.
  - Add explicit casts on the 6 malloc/calloc/void* sites, matching
    the convention already used in windows/hid.c and mac/hid.c.
  - Drop a now-redundant `(enum libusb_error)` cast.

After this, `g++ -xc++ -Wall -Wextra -c libusb/hid.c` and the
equivalent gcc invocation both build cleanly, and the full CMake
build of the libusb backend (including hidtest_libusb) links
unchanged.

Closes: #671

Assisted-by: Claude:claude-opus-4.7
@Youw Youw merged commit e8243e1 into master May 20, 2026
23 checks passed
@Youw Youw deleted the fix-cpp-compile branch May 20, 2026 21:14
@mcuee mcuee added the libusb Related to libusb backend label May 20, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

libusb Related to libusb backend

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Warnings

2 participants