Use the active contents lock and safe list iteration within the linux usbfs code
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39
diff --git a/compat/libusb-1.0/libusb/os/linux_usbfs.c b/compat/libusb-1.0/libusb/os/linux_usbfs.c
index 57603e6..bd847c2 100644
--- a/compat/libusb-1.0/libusb/os/linux_usbfs.c
+++ b/compat/libusb-1.0/libusb/os/linux_usbfs.c
@@ -1144,6 +1144,7 @@ void linux_hotplug_enumerate(uint8_t busnum, uint8_t devaddr, const char *sys_na
{
struct libusb_context *ctx;
+ usbi_mutex_lock(&active_contexts_lock);
list_for_each_entry(ctx, &active_contexts_list, list, struct libusb_context) {
if (usbi_get_device_by_session_id(ctx, busnum << 8 | devaddr)) {
/* device already exists in the context */
@@ -1153,14 +1154,16 @@ void linux_hotplug_enumerate(uint8_t busnum, uint8_t devaddr, const char *sys_na
linux_enumerate_device(ctx, busnum, devaddr, sys_name);
}
+ usbi_mutex_unlock(&active_contexts_lock);
}
void linux_hotplug_disconnected(uint8_t busnum, uint8_t devaddr, const char *sys_name)
{
- struct libusb_context *ctx;
+ struct libusb_context *ctx, *tmp;
struct libusb_device *dev;
- list_for_each_entry(ctx, &active_contexts_list, list, struct libusb_context) {
+ usbi_mutex_lock(&active_contexts_lock);
+ list_for_each_entry_safe(ctx, tmp, &active_contexts_list, list, struct libusb_context) {
dev = usbi_get_device_by_session_id (ctx, busnum << 8 | devaddr);
if (NULL != dev) {
usbi_disconnect_device (dev);
@@ -1168,6 +1171,7 @@ void linux_hotplug_disconnected(uint8_t busnum, uint8_t devaddr, const char *sys
usbi_err(ctx, "device not found for session %x %s", busnum << 8 | devaddr, sys_name);
}
}
+ usbi_mutex_unlock(&active_contexts_lock);
}
#if !defined(USE_UDEV)