As we are going to reuse the same device id when re-plugging a previously plugged SDL controller, the device interfaces are still present in the tree and IoRegisterDeviceInterface was not updating the device pointer.
Signed-off-by: Rémi Bernon rbernon@codeweavers.com --- dlls/ntoskrnl.exe/pnp.c | 25 ++++++++++++++++++++----- 1 file changed, 20 insertions(+), 5 deletions(-)
diff --git a/dlls/ntoskrnl.exe/pnp.c b/dlls/ntoskrnl.exe/pnp.c index 30865a05dcb..79aa343c1b2 100644 --- a/dlls/ntoskrnl.exe/pnp.c +++ b/dlls/ntoskrnl.exe/pnp.c @@ -622,7 +622,9 @@ NTSTATUS WINAPI IoRegisterDeviceInterface(DEVICE_OBJECT *device, const GUID *cla WCHAR device_instance_id[MAX_DEVICE_ID_LEN]; SP_DEVICE_INTERFACE_DETAIL_DATA_W *data; NTSTATUS status = STATUS_SUCCESS; + UNICODE_STRING device_path; struct device_interface *iface; + struct wine_rb_entry *entry; DWORD required; HDEVINFO set;
@@ -660,19 +662,32 @@ NTSTATUS WINAPI IoRegisterDeviceInterface(DEVICE_OBJECT *device, const GUID *cla
data->DevicePath[1] = '?'; TRACE("Returning path %s.\n", debugstr_w(data->DevicePath)); + RtlCreateUnicodeString( &device_path, data->DevicePath); + + entry = wine_rb_get( &device_interfaces, &device_path ); + if (entry) + { + iface = WINE_RB_ENTRY_VALUE( entry, struct device_interface, entry ); + if (iface->enabled) + ERR("Device interface %s is still enabled.\n", debugstr_us(&iface->symbolic_link)); + } + else + { + iface = heap_alloc_zero( sizeof(struct device_interface) ); + RtlCreateUnicodeString(&iface->symbolic_link, data->DevicePath); + if (wine_rb_put( &device_interfaces, &iface->symbolic_link, &iface->entry )) + ERR("Failed to insert interface %s into tree.\n", debugstr_us(&iface->symbolic_link)); + }
- iface = heap_alloc_zero( sizeof(struct device_interface) ); iface->device = device; iface->interface_class = *class_guid; - RtlCreateUnicodeString(&iface->symbolic_link, data->DevicePath); if (symbolic_link) RtlCreateUnicodeString( symbolic_link, data->DevicePath);
- if (wine_rb_put( &device_interfaces, &iface->symbolic_link, &iface->entry )) - ERR("Failed to insert interface %s into tree.\n", debugstr_us(&iface->symbolic_link)); - HeapFree( GetProcessHeap(), 0, data );
+ RtlFreeUnicodeString( &device_path ); + return status; }
Some games are using the HID device id as the gamepad index for xinput API. When hotplugging devices, SDL increases its instances id and it doesn't match anymore with xinput gamepad numbers.
Signed-off-by: Rémi Bernon rbernon@codeweavers.com --- dlls/winebus.sys/bus_sdl.c | 26 +++++++++++++++----------- 1 file changed, 15 insertions(+), 11 deletions(-)
diff --git a/dlls/winebus.sys/bus_sdl.c b/dlls/winebus.sys/bus_sdl.c index d24e21cff83..7bd4a13b14c 100644 --- a/dlls/winebus.sys/bus_sdl.c +++ b/dlls/winebus.sys/bus_sdl.c @@ -744,17 +744,21 @@ static const platform_vtbl sdl_vtbl = set_feature_report, };
+static int compare_joystick_id(DEVICE_OBJECT *device, void* context) +{ + return impl_from_DEVICE_OBJECT(device)->id - PtrToUlong(context); +} + static BOOL set_report_from_event(SDL_Event *event) { DEVICE_OBJECT *device; struct platform_private *private; /* All the events coming in will have 'which' as a 3rd field */ - SDL_JoystickID index = ((SDL_JoyButtonEvent*)event)->which; - - device = bus_find_hid_device(&sdl_vtbl, ULongToPtr(index)); + SDL_JoystickID id = ((SDL_JoyButtonEvent*)event)->which; + device = bus_enumerate_hid_devices(&sdl_vtbl, compare_joystick_id, ULongToPtr(id)); if (!device) { - ERR("Failed to find device at index %i\n",index); + ERR("Failed to find device at index %i\n",id); return FALSE; } private = impl_from_DEVICE_OBJECT(device); @@ -814,11 +818,11 @@ static BOOL set_mapped_report_from_event(SDL_Event *event) DEVICE_OBJECT *device; struct platform_private *private; /* All the events coming in will have 'which' as a 3rd field */ - int index = ((SDL_ControllerButtonEvent*)event)->which; - device = bus_find_hid_device(&sdl_vtbl, ULongToPtr(index)); + SDL_JoystickID id = ((SDL_ControllerButtonEvent*)event)->which; + device = bus_enumerate_hid_devices(&sdl_vtbl, compare_joystick_id, ULongToPtr(id)); if (!device) { - ERR("Failed to find device at index %i\n",index); + ERR("Failed to find device at index %i\n",id); return FALSE; } private = impl_from_DEVICE_OBJECT(device); @@ -878,7 +882,7 @@ static BOOL set_mapped_report_from_event(SDL_Event *event) return FALSE; }
-static void try_remove_device(SDL_JoystickID index) +static void try_remove_device(SDL_JoystickID id) { DEVICE_OBJECT *device = NULL; struct platform_private *private; @@ -886,7 +890,7 @@ static void try_remove_device(SDL_JoystickID index) SDL_GameController *sdl_controller; SDL_Haptic *sdl_haptic;
- device = bus_find_hid_device(&sdl_vtbl, ULongToPtr(index)); + device = bus_enumerate_hid_devices(&sdl_vtbl, compare_joystick_id, ULongToPtr(id)); if (!device) return;
private = impl_from_DEVICE_OBJECT(device); @@ -905,7 +909,7 @@ static void try_remove_device(SDL_JoystickID index) pSDL_HapticClose(sdl_haptic); }
-static void try_add_device(SDL_JoystickID index) +static void try_add_device(unsigned int index) { DWORD vid = 0, pid = 0, version = 0; DEVICE_OBJECT *device = NULL; @@ -967,7 +971,7 @@ static void try_add_device(SDL_JoystickID index) input = 0;
device = bus_create_hid_device(sdl_busidW, vid, pid, - input, version, id, serial, is_xbox_gamepad, &GUID_DEVCLASS_SDL, + input, version, index, serial, is_xbox_gamepad, &GUID_DEVCLASS_SDL, &sdl_vtbl, sizeof(struct platform_private));
if (device)
Hi,
While running your changed tests, I think I found new failures. Being a bot and all I'm not very good at pattern recognition, so I might be wrong, but could you please double-check?
Full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=54882
Your paranoid android.
=== debian10 (32 bit report) ===
Report errors: ntoskrnl.exe:ntoskrnl contains a misplaced todo message for driver
=== debian10 (32 bit Chinese:China report) ===
Report errors: ntoskrnl.exe:ntoskrnl contains a misplaced todo message for driver
=== debian10 (32 bit WoW report) ===
Report errors: ntoskrnl.exe:ntoskrnl contains a misplaced todo message for driver
=== debian10 (64 bit WoW report) ===
Report errors: ntoskrnl.exe:ntoskrnl contains a misplaced todo message for driver
Hi,
While running your changed tests, I think I found new failures. Being a bot and all I'm not very good at pattern recognition, so I might be wrong, but could you please double-check?
Full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=54881
Your paranoid android.
=== debian10 (32 bit report) ===
Report errors: ntoskrnl.exe:ntoskrnl contains a misplaced todo message for driver
=== debian10 (32 bit Chinese:China report) ===
Report errors: ntoskrnl.exe:ntoskrnl contains a misplaced todo message for driver
=== debian10 (32 bit WoW report) ===
Report errors: ntoskrnl.exe:ntoskrnl contains a misplaced todo message for driver
=== debian10 (64 bit WoW report) ===
Report errors: ntoskrnl.exe:ntoskrnl contains a misplaced todo message for driver