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

SDL and Steam fight over state of Switch Pro Controller #3450

Closed
SDLBugzilla opened this issue Feb 11, 2021 · 21 comments
Closed

SDL and Steam fight over state of Switch Pro Controller #3450

SDLBugzilla opened this issue Feb 11, 2021 · 21 comments
Assignees
Labels
waiting Waiting on user response

Comments

@SDLBugzilla
Copy link
Collaborator

This bug report was migrated from our old Bugzilla tracker.

Reported in version: HG 2.1
Reported for operating system, platform: Windows 10, x86

Comments on the original bug report:

On 2019-11-13 22:34:53 +0000, Austin Palmer wrote:

When Steam is running it will try to set the state of a Switch controller in either extended or normal mode based on whether the current focused window is opted in or out of Steam Input. The reason this is done is that over USB the device doesn't send input reports at all until initialized but when the controller is in the extended mode Dinput will be broken and receive lots of random buttons/axis inputs. We want games to be able to read from the device when required without breaking other games by leaving the device in the wrong state.

SDL right now always tries to set the state of the controller to extended mode - which provides gyro and an extended format for the joystick. Since SDL doesn't read the gyro it'd be nice if it detected the state when opening the controller and only ran initialization when required - which to my understanding should only be if the device is connected over USB and not yet initialized by Steam. The shutdown code might also need to conditionally not run if another process is trying to use the controller.

Bug report from dev about Steam/SDL fighting:
https://steamcommunity.com/groups/steamworks/discussions/22/1676938384243676229/

On 2019-11-17 06:53:03 +0000, Sam Lantinga wrote:

Any suggestions on how to detect whether initialization is necessary?

@SDLBugzilla SDLBugzilla added bug waiting Waiting on user response labels Feb 11, 2021
@SortaCore
Copy link

Getting this issue still, with SDL 2.0.20 on Windows. Switch controller is inconsistent in its input - with Steam open, the Switch Pro controller gets input for a couple seconds, loses it for a couple (the input values, like axis freeze), then it gets input back for a couple seconds, repeat.
There doesn't appear to be device add/remove events.
This only affects Switch Pro when it's on USB; Bluetooth works consistently on both Steam and my SDL app.

I can't view the Steam community link above, members only, so I'm not sure what's gone on there.

@slouken slouken removed the bug label May 11, 2022
@icculus
Copy link
Collaborator

icculus commented Jun 14, 2022

Tossing this to Sam for 2.24.0, but feel free to bump this out of the milestone if we don't have time. It's possible we fixed this, too..this seems like it would generate a lot of noise if we hadn't...

@icculus icculus added this to the 2.24.0 milestone Jun 14, 2022
@slouken slouken removed the waiting Waiting on user response label Jul 25, 2022
@slouken
Copy link
Collaborator

slouken commented Jul 25, 2022

Steam and SDL have both made changes to improve this. Are you still seeing this with the latest version of Steam and SDL main code?

@slouken slouken added the waiting Waiting on user response label Jul 25, 2022
@SortaCore
Copy link

SortaCore commented Jul 26, 2022

Yes, seems to still happen using current master 5d85c7d. Steam seems to see the controller connecting and disconnecting, whereas the second SDL app using 5d85c7d keeps it connected, but keeps freezing input in time with Steam's disconnects and reconnects.

screen.mp4

Here's a screen recording demonstrating. If the Steam window doesn't have focus in the controller settings, it will start the bug, regularly freezing input to the other app, although the other app doesn't seem to be seeing a controller disconnect, just an input freeze. The other app is using SDL statically, and doesn't use an SDL window, just the joystick/haptic system.

If neither of the apps have focus, Steam causes the bug as well.
When you exit Steam settings, the bug sticks around, affecting the other app with a regular loss of input.
Once Steam is closed entirely, the other app loses access to the joystick entirely, freezing indefinitely, even though it's using SDL statically and so shouldn't share anything with Steam's SDL.
Restarting the other app restores normal input to its SDL joysticks, but restarting Steam after restarting the other app, causes the bug again, even before you enter Steam settings.

@slouken
Copy link
Collaborator

slouken commented Jul 27, 2022

It looks like this is purely a Steam issue.

If you watch Steam, even with no other programs running, it will occasionally disconnect the controller after alt-tabbing away from the controller settings window. It's being disconnected because it stops receiving reports from the controller.

@SortaCore
Copy link

SortaCore commented Jul 27, 2022

The other program doesn't seem to get controller disconnected events, though, which I would have expected if another SDL program closed it on OS level. What could Steam be doing that will make the other SDL program lose the controllers silently?

If it is Steam, I can't see the discussion, due to the group discussion permissions. Are they any closer to fixing it or do they have any relevant details?

@slouken
Copy link
Collaborator

slouken commented Jul 27, 2022

It seems to be happening when Steam switches the controller to simple report mode. Something about that process seems to occasionally wedge the controller so it doesn't generate inputs until it's reinitialized - either by Steam or by another SDL program opening the controller.

I'll update this bug report when there's a Steam beta client with a fix available.

@slouken slouken removed the waiting Waiting on user response label Jul 27, 2022
@slouken
Copy link
Collaborator

slouken commented Jul 27, 2022

Actually Steam is just disabling reports entirely so DirectInput and WGI games don't get spammed with garbage input. Fortunately, this is easy to fix for SDL applications.

@SortaCore
Copy link

Actually Steam is just disabling reports entirely so DirectInput and WGI games don't get spammed with garbage input. Fortunately, this is easy to fix for SDL applications.

Latest commit, if Steam is open, now sends no input at all - is that what you meant?

@slouken
Copy link
Collaborator

slouken commented Jul 27, 2022

Nope, it's working here. Are you able to repro with testgamecontroller? That's what I've been testing.

@SortaCore
Copy link

SortaCore commented Jul 29, 2022

testgamecontroller works great, but in my app, both the Joystick and GameController interfaces are either working fine, or no input through when Steam is open, although they recognise the controller is connected and can get the controller name, number of buttons and axes, and so on; but they can't get any button states, axis states, etc.
At one point, was working fine, I switched windows around (without switching to Steam), and it lost input. testgamecontroller was unaffected.

@slouken
Copy link
Collaborator

slouken commented Jul 29, 2022

Can you debug and see why testgamecontroller works and your app doesn't?

@slouken slouken reopened this Jul 29, 2022
@slouken slouken added the waiting Waiting on user response label Aug 1, 2022
@slouken
Copy link
Collaborator

slouken commented Aug 5, 2022

Is this still an issue with the Steam beta update dated 8/4 or newer?

@SortaCore
Copy link

SortaCore commented Aug 6, 2022

(Sorry, my attention's been pulled by other projects.)

Yes, still an issue with 5th Aug build. The statistics are available, everything else missing.

When Switch was connected, there's a small freeze, it sends statistics like num of axis, and sometimes the initial values of the sticks. Curiously, controller disconnect gets a much longer freeze, on deleting the device, main thread waiting on rumble thread, and rumble thread stuck with a high request->device->rumble_pending (34k rumble_pending on one test), even though no rumble is sent by my app, and the request->device->dev is null.

@slouken
Copy link
Collaborator

slouken commented Aug 6, 2022

Can you debug why it's an issue in your application and not in testgamecontroller?

@SortaCore
Copy link

SortaCore commented Aug 8, 2022

I will look into it, but it may be a couple months before I can. I have limited access to my dev environment for the next couple of weeks.

I'm using SDL static, and disabling some SDL features with CMake, since the plan is only using joystick related features. I think I was pretty safe with my choices, but is there any that may be needed for this to work properly?
https://github.com/SortaCore/SDLJoystick-priv/ has my configuration for a previous SDL in the README.

@slouken
Copy link
Collaborator

slouken commented Aug 8, 2022

Threads are the only thing off the top of my head that are needed, but it looks like you have those enabled.

By the way, I highly recommend shipping SDL2.dll as it will allow developers and end users to easily update the SDK with future SDL controller support. For example, we're about to add Joy-Con support, and if a developer has statically linked SDL, customers won't be able to take advantage of that when the developer has moved on to other projects.

@slouken
Copy link
Collaborator

slouken commented Aug 9, 2022

I'm bumping this out of the current milestone so you have time to investigate in more detail.

@slouken slouken removed this from the 2.24.0 milestone Aug 9, 2022
@slouken slouken added this to the 2.26.0 milestone Aug 9, 2022
@slouken slouken removed this from the 2.26.0 milestone Nov 11, 2022
@SortaCore
Copy link

SortaCore commented Feb 8, 2023

@slouken Just used SDL3, and while the new commit bb5b130 doesn't fix it, it's very close.
The only issue is async write to change the reporting mode doesn't go through; the Rumble thread doesn't seem to send the request, but just queues indefinitely. This also makes the Switch freeze the application on joystick close, while the rumble_pending count is slowly decremented by rumble thread, while main thread waits for it.

I found a fix for it by adding some lines around the ForceUSB to make it always switch on main thread:

/* Steam may have put the controller back into non-reporting mode */
SDL_bool oldSyncWrite = ctx->m_bSyncWrite;
ctx->m_bSyncWrite = SDL_TRUE;
WriteProprietary(ctx, k_eSwitchProprietaryCommandIDs_ForceUSB, NULL, 0, SDL_FALSE);
ctx->m_bSyncWrite = oldSyncWrite;

Then that seems to fix it for both disconnects and connects.

@slouken slouken closed this as completed in b7c6fec Feb 8, 2023
@slouken
Copy link
Collaborator

slouken commented Feb 8, 2023

Great, thanks!

slouken added a commit that referenced this issue Feb 8, 2023
@Squall-Leonhart
Copy link

Squall-Leonhart commented Feb 27, 2024

Steam and SDL have both made changes to improve this. Are you still seeing this with the latest version of Steam and SDL main code?

I can still replicate this issue with Cemu, built with SDL 2.30

Cemu started while Steam is running will show the Switch Pro controller for a second and then the list of controllers blanks and no longer picks it up, kill steam and load cemu back up and the control is fine, even if you open steam back up.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
waiting Waiting on user response
Projects
None yet
Development

No branches or pull requests

5 participants