We are currently migrating Bugzilla to GitHub issues.
Any changes made to the bug tracker now will be lost, so please do not post new bugs or make changes to them.
When we're done, all bug URLs will redirect to their equivalent location on the new bug tracker.

Bug 5327

Summary: When direct input fails to load, but a controlller is plugged in through another api, an access violation happens.
Product: SDL Reporter: Bart van der Werf <bart>
Component: joystickAssignee: Sam Lantinga <slouken>
Status: RESOLVED FIXED QA Contact: Sam Lantinga <slouken>
Severity: major    
Priority: P2 CC: huseyincaliskan32
Version: HG 2.0   
Hardware: All   
OS: Windows 10   

Description Bart van der Werf 2020-10-22 21:45:19 UTC
When directinput fails to load, but a controlller is plugged in, an access violation happens.
This is due to IEventHandler_CRawGameControllerVtbl_InvokeAdded calling SDL_DINPUT_JoystickPresent which does not check if dinput is assigned signalling initialization of directinput.



diff -r 69e84b7a2d21 src/joystick/windows/SDL_dinputjoystick.c
--- a/src/joystick/windows/SDL_dinputjoystick.c        Wed Oct 21 23:28:02 2020 +0300
+++ b/src/joystick/windows/SDL_dinputjoystick.c        Thu Oct 22 23:41:25 2020 +0200
@@ -514,11 +514,15 @@
     /* Because we used CoCreateInstance, we need to Initialize it, first. */
     instance = GetModuleHandle(NULL);
     if (instance == NULL) {
+        IDirectInput8_Release(dinput);
+        dinput = NULL;
         return SDL_SetError("GetModuleHandle() failed with error code %lu.", GetLastError());
     }
     result = IDirectInput8_Initialize(dinput, instance, DIRECTINPUT_VERSION);

     if (FAILED(result)) {
+        IDirectInput8_Release(dinput);
+        dinput = NULL;
         return SetDIerror("IDirectInput::Initialize", result);
     }
     return 0;
@@ -724,6 +728,11 @@
 SDL_bool
 SDL_DINPUT_JoystickPresent(Uint16 vendor, Uint16 product, Uint16 version)
 {
+    if (dinput == NULL)
+    {
+            return SDL_FALSE;
+    }
+
     EnumJoystickPresentData data;

     data.vendor = vendor;
Comment 1 Sam Lantinga 2020-11-12 03:43:23 UTC
Fixed, thanks!
https://hg.libsdl.org/SDL/rev/ab65db97097d
Comment 2 Huseyin Caliskan 2020-11-12 16:14:45 UTC
(In reply to Sam Lantinga from comment #1)
> Fixed, thanks!
> https://hg.libsdl.org/SDL/rev/ab65db97097d

This fix causes a compile error on my latest version of Windows MinGW compiler:

C:\Users\husey\Desktop\engine\Libraries\SDL\src\joystick\windows\SDL_dinputjoystick.c: In function 'SDL_DINPUT_JoystickPresent':
C:\Users\husey\Desktop\engine\Libraries\SDL\src\joystick\windows\SDL_dinputjoystick.c:736:5: error: ISO C90 forbids mixed declarations and code [-Werror=declaration-after-statement]
  736 |     EnumJoystickPresentData data;
      |     ^~~~~~~~~~~~~~~~~~~~~~~
cc1.exe: some warnings being treated as errors
mingw32-make[3]: *** [build\sdl\CMakeFiles\SDL2.dir\build.make:2225: build/sdl/CMakeFiles/SDL2.dir/src/joystick/windows/SDL_dinputjoystick.c.obj] Error 1
mingw32-make[2]: *** [CMakeFiles\Makefile2:448: build/sdl/CMakeFiles/SDL2.dir/all] Error 2
mingw32-make[1]: *** [CMakeFiles\Makefile2:374: CMakeFiles/NightByte.dir/rule] Error 2
mingw32-make: *** [Makefile:183: NightByte] Error 2

Putting the data before the if statements fixed the issue for me
Comment 3 Huseyin Caliskan 2020-11-12 16:18:23 UTC
Reopening this bug since it has caused compile errors on multiple systems:
https://bugzilla.libsdl.org/show_bug.cgi?id=5327#c2
Comment 4 Huseyin Caliskan 2020-11-14 14:37:51 UTC
Took the latest commit of SDL and it compiles now.