Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

hid_enumerate() sometimes causes game to freeze for a few seconds #3071

SDLBugzilla opened this issue Feb 11, 2021 · 0 comments

hid_enumerate() sometimes causes game to freeze for a few seconds #3071

SDLBugzilla opened this issue Feb 11, 2021 · 0 comments


Copy link

@SDLBugzilla SDLBugzilla commented Feb 11, 2021

This bug report was migrated from our old Bugzilla tracker.

Reported in version: 2.0.9
Reported for operating system, platform: Windows 7, x86_64

Comments on the original bug report:

On 2018-11-19 16:17:37 +0000, Daniel Gibson wrote:

Even though my game (dhewm3) doesn't use SDL_INIT_JOYSTICK, SDL_PumpEvent() calls SDL_JoystickUpdate() which ends up calling hid_enumerate() every three seconds, and sometimes on my Win7 box hid_enumerate() takes about 5 seconds, which causes the whole game to freeze for that time.

If I do use SDL_INIT_JOYSTICK this doesn't happen, because then hid_enumerate() is only called if some device attached/removed event is received (without SDL_INIT_JOYSTICK SDL_HIDAPI_discovery.m_bCanGetNotifications is false, with it it's true, and when it's true hid_enumerate() only happens on startup and on events).

Anyway, I could fix that by modifying SDL_PumpEvents() to only call SDL_JoystickUpdate() if joysticks are actually enabled, like

/* Check for joystick state change */
if (SDL_WasInit(SDL_INIT_JOYSTICK) && (!SDL_disabled_events[SDL_JOYAXISMOTION >> 8] || SDL_JoystickEventState(SDL_QUERY))) {

I wonder if the same should be done a few lines below for the sensors, i.e. adding a SDL_WasInit(SDL_INIT_SENSORS) to the if-condition before SDL_SensorUpdate();

I also don't know if SDL_WasInit() is indeed the best/most efficient way to test this, or if maybe some other flag should be checked at the beginning of SDL_JoystickUpdate() instead (and then return immediately there), but apart from these details, we need to make sure that SDL_JoystickUpdate() doesn't try to enumerate HID devices if joysticks are disabled.

Bug # 4389 seems to be loosely related to this, but it's not the same (there the game locks up forever, not just for a few seconds).

On 2018-11-19 16:29:09 +0000, Daniel Gibson wrote:

BTW, have you considered disabling HIDAPI support completely if SDL_HIDAPI_discovery.m_bCanGetNotifications is false, instead of manually querying every 3 seconds?
No idea why it should be false (or more specifically, why RegisterDeviceNotification( SDL_HIDAPI_discovery.m_hwndMsg, &devBroadcast, DEVICE_NOTIFY_WINDOW_HANDLE | DEVICE_NOTIFY_ALL_INTERFACE_CLASSES ); should fail), but if it does I guess it would be preferable for users to have SDL access their joysticks via DirectInput or whatever else is available, or maybe even not at all, over the game not running smoothly.

On 2018-11-20 05:18:58 +0000, Sam Lantinga wrote:

This should be fixed, thanks!

Your other point about RegisterDeviceNotification() is a good one. We don't just disable HIDAPI, as device notifications can fail on other platforms where it's cheaper (and important) to poll USB devices. Hmmm....

On 2018-11-20 13:26:36 +0000, Daniel Gibson wrote:

Well, you could disable it on Windows only, if it really doesn't cause problems on other platforms.
Instead of disabling it completely you could still use it to query the devices on startup, just not every 3 seconds - that way you'd lose hotplugging support, but that's still better than random freezes that either drop a few frames or even take several seconds (like in my case - I still can't believe how lucky I am that it freezes for 5sec on my machine and not just 100ms like with the people who reported the bug in dhewm3: Figuring it out would have been much harder with 100ms)

Anyway, are you sure it doesn't take as long on other systems?
It seems like it depends on the hardware how long it takes (=> how long the freezes are, if they are noticable at all), so it's possible that Windows queries the values from the hardware directly - what if it's the same on other operating systems?
(TBH that seems pretty stupid, shouldn't the HID driver query all those values once when the device is connected and cache them, so it can return them quickly? They shouldn't change, right?)

On 2019-01-14 11:15:39 +0000, Olav Sørensen wrote:

I know I'm kinda late to reply on this bug, but I just wanted to say that I had to downgrade from SDL 2.0.9 to SDL 2.0.8 because in Windows, my USB keyboard would re-initialize itself in SDL 2.0.9 at random times. Like the status LEDs shutting off, then you notice that Windows is doing some re-init thing, then they come back on. You could not type in the downtime period. This only happened when I had my SDL 2.0.9 program running, so it's not a keyboard fault.

This never happened in SDL 2.0.8 for me, even after downgrading from 2.0.9 again. Makes me wonder if it was related to this bug...

On 2019-04-05 17:23:20 +0000, Daniel Gibson wrote:

*** Bug 4564 has been marked as a duplicate of this bug. ***

On 2019-04-06 00:32:43 +0000, Daniel Gibson wrote:

For sake of completeness, for people who stumble upon the bug and land here:
The workaround (when using 2.0.9) is to add SDL_INIT_JOYSTICK to your call to SDL_Init() - yes, even if you don't want to use any joysticks and don't even have any connected to your PC.

Also, the discourse discussion that lead to this post was (but it happens on Win10 as well, and usually it doesn't freeze for as long as it did for me). has a short explanation of why the bug happened.

On 2019-04-17 02:50:37 +0000, Sam Lantinga wrote:

*** Bug 4588 has been marked as a duplicate of this bug. ***

TheAIBot added a commit to TheAIBot/VoxelWorld that referenced this issue Sep 28, 2021
xyzz added a commit to vial-kb/vial-gui that referenced this issue Apr 17, 2022
running on the main thread locks UI on windows under some conditions
perhaps device enumerate takes too long
it looks like SDL previously ran into a similar issue libsdl-org/SDL#3071
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
None yet
None yet

No branches or pull requests

1 participant