Skip to content

Commit 79cbb65

Browse files
committed
Dynamically load libudev in linux-hidraw backend
Signed-off-by: falkTX <falktx@falktx.com>
1 parent 657b9fa commit 79cbb65

3 files changed

Lines changed: 122 additions & 5 deletions

File tree

linux/CMakeLists.txt

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,7 @@ target_link_libraries(hidapi_hidraw PUBLIC hidapi_include)
88

99
find_package(Threads REQUIRED)
1010

11-
include(FindPkgConfig)
12-
pkg_check_modules(libudev REQUIRED IMPORTED_TARGET libudev)
13-
14-
target_link_libraries(hidapi_hidraw PRIVATE PkgConfig::libudev Threads::Threads)
11+
target_link_libraries(hidapi_hidraw PRIVATE Threads::Threads dl)
1512

1613
set_target_properties(hidapi_hidraw
1714
PROPERTIES

linux/hid.c

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,9 @@
4040
#include <linux/hidraw.h>
4141
#include <linux/version.h>
4242
#include <linux/input.h>
43-
#include <libudev.h>
43+
44+
/* falkTX: replaced by local file for dynamic loading */
45+
#include "libudev.c"
4446

4547
#include "hidapi.h"
4648

linux/libudev.c

Lines changed: 118 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,118 @@
1+
/* SPDX-FileCopyrightText: 2026 Filipe Coelho <falktx@falktx.com> */
2+
/* SPDX-License-Identifier: LGPL-2.1-or-later */
3+
4+
#include <dlfcn.h>
5+
#include <stdarg.h>
6+
#include <stddef.h>
7+
8+
#define C(FN) static typeof(FN)* FN; { if (FN == NULL) FN = dlsym(NULL, #FN); }
9+
10+
#define udev_list_entry_foreach(varname, front) \
11+
for (varname = front; varname != NULL; varname = udev_list_entry_get_next(varname))
12+
13+
struct udev *udev_new(void)
14+
{
15+
static void* _lib;
16+
if (_lib == NULL)
17+
{
18+
_lib = dlopen("libudev.so.1", RTLD_NOW | RTLD_GLOBAL);
19+
if (_lib == NULL)
20+
return NULL;
21+
}
22+
23+
C(udev_new);
24+
return udev_new();
25+
}
26+
27+
struct udev *udev_unref(struct udev *udev)
28+
{
29+
C(udev_unref);
30+
return udev_unref(udev);
31+
}
32+
33+
struct udev_device *udev_device_new_from_devnum(struct udev *udev, char type, dev_t devnum)
34+
{
35+
C(udev_device_new_from_devnum);
36+
return udev_device_new_from_devnum(udev, type, devnum);
37+
}
38+
39+
struct udev_device *udev_device_new_from_syspath(struct udev *udev, const char *syspath)
40+
{
41+
C(udev_device_new_from_syspath);
42+
return udev_device_new_from_syspath(udev, syspath);
43+
}
44+
45+
struct udev_device *udev_device_unref(struct udev_device *udev_device)
46+
{
47+
C(udev_device_unref);
48+
return udev_device_unref(udev_device);
49+
}
50+
51+
struct udev_device *udev_device_get_parent_with_subsystem_devtype(struct udev_device *udev_device,
52+
const char *subsystem, const char *devtype)
53+
{
54+
C(udev_device_get_parent_with_subsystem_devtype);
55+
return udev_device_get_parent_with_subsystem_devtype(udev_device, subsystem, devtype);
56+
}
57+
58+
const char* udev_device_get_syspath(struct udev_device *udev_device)
59+
{
60+
C(udev_device_get_syspath);
61+
return udev_device_get_syspath(udev_device);
62+
}
63+
64+
const char* udev_device_get_devnode(struct udev_device *udev_device)
65+
{
66+
C(udev_device_get_devnode);
67+
return udev_device_get_devnode(udev_device);
68+
}
69+
70+
const char* udev_device_get_sysattr_value(struct udev_device *udev_device, const char *sysattr)
71+
{
72+
C(udev_device_get_sysattr_value);
73+
return udev_device_get_sysattr_value(udev_device, sysattr);
74+
}
75+
76+
struct udev_enumerate *udev_enumerate_new(struct udev *udev)
77+
{
78+
C(udev_enumerate_new);
79+
return udev_enumerate_new(udev);
80+
}
81+
82+
struct udev_enumerate *udev_enumerate_unref(struct udev_enumerate *udev_enumerate)
83+
{
84+
C(udev_enumerate_unref);
85+
return udev_enumerate_unref(udev_enumerate);
86+
}
87+
88+
int udev_enumerate_add_match_subsystem(struct udev_enumerate *udev_enumerate, const char *subsystem)
89+
{
90+
C(udev_enumerate_add_match_subsystem);
91+
return udev_enumerate_add_match_subsystem(udev_enumerate, subsystem);
92+
}
93+
94+
int udev_enumerate_scan_devices(struct udev_enumerate *udev_enumerate)
95+
{
96+
C(udev_enumerate_scan_devices);
97+
return udev_enumerate_scan_devices(udev_enumerate);
98+
}
99+
100+
struct udev_list_entry *udev_enumerate_get_list_entry(struct udev_enumerate *udev_enumerate)
101+
{
102+
C(udev_enumerate_get_list_entry);
103+
return udev_enumerate_get_list_entry(udev_enumerate);
104+
}
105+
106+
struct udev_list_entry *udev_list_entry_get_next(struct udev_list_entry *list_entry)
107+
{
108+
C(udev_list_entry_get_next);
109+
return udev_list_entry_get_next(list_entry);
110+
}
111+
112+
const char* udev_list_entry_get_name(struct udev_list_entry *list_entry)
113+
{
114+
C(udev_list_entry_get_name);
115+
return udev_list_entry_get_name(list_entry);
116+
}
117+
118+
#undef C

0 commit comments

Comments
 (0)