Enable G-Sync

G-Sync is a variable refresh rate technology from Nvidia. It allows a display to synchronize its refresh rate with the rate at which a computer’s GPU is generating frames. This prevents “screen tearing” — visual artifacts that occur when these rates are out of sync and the monitor attempts to draw multiple frames at once. These artifacts are particularly noticeable in fast-paced games with lots of lateral screen movement.

Screen Tearing in Portal

Using G-Sync requires a compatible GPU and display. At the time of writing I had an Nvidia GeForce RTX 3090 and a first generation Acer X34 Predator monitor which both support G-Sync.

I’m using the proprietary Nvidia driver (v455.38) since it is the only real driver choice for Nvidia hardware on Linux in my opinion. The open source drivers are just too far behind in performance and features for my purposes.

Nvidia Driver Version

The first step is to enable G-Sync in NVIDIA X Server Settings under OpenGL Settings for the G-Sync compatible display. This is done by checking these options:

  • Allow G-SYNC/G-SYNC Compatible
  • Enable G-SYNC/G-SYNC Compatible Visual Indicator

NVIDIA X Server OpenGL Settings

In my experience, there are a couple reasons for why these settings might not be visible under OpenGL Settings:

  • The graphics driver has been updated and the computer needs a reboot
  • The cable connecting the GPU to the display is incompatible/bad (e.g., HDMI when DisplayPort is required)

The “Enable G-SYNC/G-SYNC Compatible Visual Indicator” option adds a visual to the upper right corner of a window indicating whether G-Sync is working. If it is not working for some reason it will read “Normal”. This is useful for testing but you’ll probably want to disable this once everything is set up unless you don’t mind seeing the overlay all the time.

G-Sync On G-Sync Off

In many desktop environments, this would be enough to enjoy smooth frame pacing with G-Sync, but it is not enough in Cinnamon. For years I simply accepted that I would not be able to use G-Sync with my hardware unless I switched to a different desktop environment such as MATE.

That is until I learned a bit about Cinnamon’s window compositor.

Disable Cinnamon Window Compositor

Cinnamon’s window compositor forces vertical synchronization in all windows to avoid screen tearing on the desktop. However, this behavior overrides any G-Sync settings, but there is an option to disable compositing for full-screen windows, which is how I play most games. This option is under System Settings > General > Disable compositing for full-screen windows.

Linux Mint General Settings

After toggling this option on and restarting Cinnamon (Alt+F2 then r) G-Sync will be working in Linux games!

Linux Mint General Settings

That said, there is an apparent bug in Cinnamon where the “Disable compositing for full-screen windows” setting will not persist across reboots. I opened an issue on GitHub for this, but found a workaround in the meantime:

  1. After rebooting, toggle “Disable compositing for full-screen windows” off and back on again.
  2. Restart Cinnamon (Alt+F2 then r)
  3. G-Sync should be working again

This only works for native Linux games, which I confirmed with Total War: WARHAMMER II and Shadow of the Tomb Raider. Non-native games such as Control (Windows-only) that run via the Proton/Wine compatibility layer need a bit more effort to get G-Sync working.

Proton/Wine: Emulate a Virtual Desktop

I came across this open muffin issue which mentions that the “Disable compositing for full-screen windows” setting does not work with full-screen games running through Wine, but does when emulating a virtual desktop.

Linux has been my primary desktop OS for the last four years, and I’ve learned a lot, but my experience with Valve’s Proton (and Wine) is limited. So, it took some tinkering to figure out what “emulating a virtual desktop” actually means and how to do it. After reading through some related threads[1, 2] I found that this works:

  1. Install (and run at least once) a game with Steam that will run via Proton.

  2. In a terminal, navigate to the game’s pfx directory. Unless you’ve changed the path, this is probably:

    ~/.steam/steam/steamapps/compatdata/<App ID>/pfx
    

    You’ll need the game’s App ID, which you can find in the game’s properties dialog or by using a tool like https://steamdb.info.

    For example, the App ID for Control is 870780.

    CONTROL Game Properties

  3. Open the Wine configuration dialog for the game:

    cd ~/.steam/steam/steamapps/compatdata/870780/pfx
    env WINEPREFIX="$PWD" winecfg
    

    Note: If you are running a game through a system installation of Wine directly (no Proton), you can simply run winecfg which will open the system-wide Wine configuration dialog rather than the game-specific specific configuration dialog.

  4. In the Wine configuration dialog, go to the Graphics tab and check Emulate a virtual desktop. Set the desktop size to your monitor resolution (in my case, 3440x1440). Click OK.

    Wine Configuration

G-Sync will now work in non-native Linux games!

Note: You may need to perform these steps again if the game is updated/reinstalled or if a different version of Proton is installed later.

Summary

Enabling Nvidia G-Sync on Linux Mint with the Cinnamon desktop environment is possible, but requires a bit of work to:

  1. Enable G-Sync in the NVIDIA X Server Settings
  2. Disable the Cinnamon window compositor (and work around a persistence bug)
  3. Emulate a Virtual Desktop (for Proton/Wine games)

Now I can enjoy that buttery smooth frame pacing in Windows-only games like Control :)

Control Gameplay

In the end, I couldn’t figure out a way to make the virtual desktop configuration change apply to all Proton games instead of just one at a time. I did learn that there is a default proton prefix located here:

~/.steam/steam/steamapps/common/Proton <VERSION>/dist/share/default_pfx

But when I made configuration changes here they didn’t seem to stick, even if I forced a particular version of Proton. If you have any insight, please let me know!