Switching focus from X screen 0 to X screen 1

I’m on an arch linux 6-monitor system run using two cards:

$~ lspci | grep VGA
VGA compatible controller: NVIDIA Corporation TU106 [GeForce RTX 2060 SUPER] (rev a1)
VGA compatible controller: NVIDIA Corporation GK208B [GeForce GT 710] (rev a1)

After having used the nvidia-settings script, I have set up the configuration to run on two X screens (one for each graphics card), managed by two instances of i3wm (after extensive googling, I don’t think these cards are compatible with getting a single X screen using e.g. SLI).

Everything seems to be working well (all screens & monitors are on and working), but I have run into a segfault when trying to automate things.

My main question I really want the answer to is is how to tell the system to switch focus from X screen 0 to X screen 1 without using the mouse. I presume that internally NVIDIA must be reading a DISPLAY variable, but I’m not sure how to communicate this to it.

When I try to automate this using xdotool mouse motions to click on the screens, I run into a semi-reproduceable segfault. I can give you more detail on this if you wish, but if there is a more direct way to change the current X window that is ‘focussed’ that would be preferable.

# nvidia-settings: X configuration file generated by nvidia-settings
# nvidia-settings:  version 465.27

Section "ServerLayout"
    Identifier     "Layout0"
    Screen      0  "Screen0" 0 0
    Screen      1  "Screen1" 0 1080
    InputDevice    "Keyboard0" "CoreKeyboard"
    InputDevice    "Mouse0" "CorePointer"
    Option         "Xinerama" "0"
EndSection

Section "Files"
EndSection

Section "InputDevice"
    # generated from default
    Identifier     "Mouse0"
    Driver         "mouse"
    Option         "Protocol" "auto"
    Option         "Device" "/dev/psaux"
    Option         "Emulate3Buttons" "no"
    Option         "ZAxisMapping" "4 5"
EndSection

Section "InputDevice"
    # generated from default
    Identifier     "Keyboard0"
    Driver         "kbd"
EndSection

Section "Monitor"
    # HorizSync source: edid, VertRefresh source: edid
    Identifier     "Monitor0"
    VendorName     "Unknown"
    ModelName      "DELL P2419H"
    HorizSync       30.0 - 83.0
    VertRefresh     56.0 - 76.0
    Option         "DPMS"
EndSection

Section "Monitor"
    # HorizSync source: edid, VertRefresh source: edid
    Identifier     "Monitor1"
    VendorName     "Unknown"
    ModelName      "DELL P2419H"
    HorizSync       30.0 - 83.0
    VertRefresh     56.0 - 76.0
    Option         "DPMS"
EndSection

Section "Device"
    Identifier     "Device0"
    Driver         "nvidia"
    VendorName     "NVIDIA Corporation"
    BoardName      "NVIDIA GeForce RTX 2060 SUPER"
    BusID          "PCI:1:0:0"
EndSection

Section "Device"
    Identifier     "Device1"
    Driver         "nvidia"
    VendorName     "NVIDIA Corporation"
    BoardName      "NVIDIA GeForce GT 710"
    BusID          "PCI:76:0:0"
EndSection

Section "Screen"
    Identifier     "Screen0"
    Device         "Device0"
    Monitor        "Monitor0"
    DefaultDepth    24
    Option         "Stereo" "0"
    Option         "nvidiaXineramaInfoOrder" "DFP-0"
    Option         "metamodes" "DP-4: nvidia-auto-select +0+0, DP-0: nvidia-auto-select +1920+0, DP-2: nvidia-auto-select +3840+0"
    Option         "SLI" "Off"
    Option         "MultiGPU" "Off"
    Option         "BaseMosaic" "off"
    SubSection     "Display"
        Depth       24
    EndSubSection
EndSection

Section "Screen"
    Identifier     "Screen1"
    Device         "Device1"
    Monitor        "Monitor1"
    DefaultDepth    24
    Option         "Stereo" "0"
    Option         "nvidiaXineramaInfoOrder" "DFP-1"
    Option         "metamodes" "HDMI-0: nvidia-auto-select +3840+0, HDMI-1: nvidia-auto-select +1920+0, HDMI-3: nvidia-auto-select +0+0"
    Option         "SLI" "Off"
    Option         "MultiGPU" "Off"
    Option         "BaseMosaic" "off"
    SubSection     "Display"
        Depth       24
    EndSubSection
EndSection

The NVIDIA driver running in the X server doesn’t do anything with input focus, it just processes rendering requests on whichever screen the request is for.

On the client side, some NVIDIA driver components will talk to the X server but it’s generally up to the application to choose which screen it wants to use.

Can you elaborate on the crash? I’m interested to know whether the NVIDIA driver components are involved.

X11 has a XSetInputFocus request that can be used to change the input focus, but be aware that window managers are also involved in managing input focus and may get in your way.

Many thanks @aplattner.

The crash occurs when I try to use this script:

#!/bin/bash
xdotool mousemove --sync --screen=$1 960 1080 
xdotool click 1 
xdotool mousemove --sync --screen=$1 2880 1080 
xdotool click 1 
xdotool mousemove --sync --screen=$1 4800 1080 
xdotool click 1

i.e. to click across all three monitors on a given screen number to ensure that the focus is changed (so it would be called as focus_screen 0). I find the same error occurs if I try a similar thing with wmctl, and all I have to go on at the moment is a rather uninformative portion of the Xorg.0.log (the timestamps indicate a large gap from the last start-up):

[  2355.604] (EE) 
[  2355.604] (EE) Backtrace:
[  2355.604] (EE) 0: /usr/lib/Xorg (xorg_backtrace+0x53) [0x56072bdb8fd3]
[  2355.604] (EE) 1: /usr/lib/Xorg (0x56072bc72000+0x151df5) [0x56072bdc3df5]
[  2355.604] (EE) 2: /usr/lib/libc.so.6 (0x7fd2bdbaa000+0x3cda0) [0x7fd2bdbe6da0]
[  2355.604] (EE) 3: /usr/lib/Xorg (0x56072bc72000+0xc0d5f) [0x56072bd32d5f]
[  2355.604] (EE) 4: /usr/lib/Xorg (0x56072bc72000+0x1429f0) [0x56072bdb49f0]
[  2355.604] (EE) 5: /usr/lib/Xorg (WaitForSomething+0x1ea) [0x56072bdb7c1a]
[  2355.604] (EE) 6: /usr/lib/Xorg (0x56072bc72000+0x39914) [0x56072bcab914]
[  2355.604] (EE) 7: /usr/lib/libc.so.6 (__libc_start_main+0xd5) [0x7fd2bdbd1b25]
[  2355.604] (EE) 8: /usr/lib/Xorg (_start+0x2e) [0x56072bcac5de]
[  2355.604] (EE) 
[  2355.604] (EE) Segmentation fault at address 0x3d0
[  2355.604] (EE) 
Fatal server error:
[  2355.604] (EE) Caught signal 11 (Segmentation fault). Server aborting
[  2355.604] (EE) 
[  2355.604] (EE) 

For trying to get the window manager to do this, it is likely that this may be part of a solution, although it doesn’t explain why my in theory harmless hack is causing an Xorg segfault.

Is there anything else which I could provide which could help to determine whether this is an nvidia-specific issue? I can now reliably reproduce the segfault by running the command using an i3 key binding starting from an empty desktop.

Interesting, thanks for that. While generally unhelpful, this backtrace code is pretty good about at least identifying which file the crash was in. Since nvidia_drv.so and libglx_nvidia.so are not listed here it’s a good indication that the driver was not involved.

Can you please try running coredumpctl gdb Xorg and if that manages to load a core file, run backtrace full?

I don’t think it’s able to load the corefile:

~$ coredumpctl gdb Xorg
           PID: 448978 (Xorg)
           UID: 1000 (will)
           GID: 1000 (will)
        Signal: 6 (ABRT)
     Timestamp: Fri 2021-05-28 14:07:44 BST (4min 43s ago)
  Command Line: /usr/lib/Xorg -nolisten tcp :0 vt1 -keeptty -auth /tmp/serverauth.qfTJS9fjfz
    Executable: /usr/lib/Xorg
 Control Group: /user.slice/user-1000.slice/session-1.scope
          Unit: session-1.scope
         Slice: user-1000.slice
       Session: 1
     Owner UID: 1000 (will)
       Boot ID: 7b1a35b6f34c48e3ae7f48d0cd46186b
    Machine ID: 99edaae67c3745f9882361b5bf95bb86
      Hostname: newton
       Storage: /var/lib/systemd/coredump/core.Xorg.1000.7b1a35b6f34c48e3ae7f48d0cd46186b.448978.1622207264000000.zst (present)
     Disk Size: 2.8M
       Message: Process 448978 (Xorg) of user 1000 dumped core.
                
                Stack trace of thread 448978:
                #0  0x00007f8429c27d22 raise (libc.so.6 + 0x3cd22)
                #1  0x00007f8429c11862 abort (libc.so.6 + 0x26862)
                #2  0x000055a94b83775a OsAbort (Xorg + 0x14a75a)
                #3  0x000055a94b839221 FatalError (Xorg + 0x14c221)
                #4  0x000055a94b83ee59 n/a (Xorg + 0x151e59)
                #5  0x00007f8429c27da0 __restore_rt (libc.so.6 + 0x3cda0)
                #6  0x000055a94b8a2134 n/a (Xorg + 0x1b5134)
                #7  0x000055a94b73f258 n/a (Xorg + 0x52258)
                #8  0x000055a94b73f506 n/a (Xorg + 0x52506)
                #9  0x000055a94b7ea35b n/a (Xorg + 0xfd35b)
                #10 0x000055a94b7addb3 n/a (Xorg + 0xc0db3)
                #11 0x000055a94b82f9f0 n/a (Xorg + 0x1429f0)
                #12 0x000055a94b832c1a WaitForSomething (Xorg + 0x145c1a)
                #13 0x000055a94b726914 n/a (Xorg + 0x39914)
                #14 0x00007f8429c12b25 __libc_start_main (libc.so.6 + 0x27b25)
                #15 0x000055a94b7275de _start (Xorg + 0x3a5de)

GNU gdb (GDB) 10.2
Copyright (C) 2021 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
Type "show copying" and "show warranty" for details.
This GDB was configured as "x86_64-pc-linux-gnu".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<https://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
    <http://www.gnu.org/software/gdb/documentation/>.

For help, type "help".
Type "apropos word" to search for commands related to "word"...
Reading symbols from /usr/lib/Xorg...
(No debugging symbols found in /usr/lib/Xorg)

warning: Can't open file /SYSV00000000 (deleted) during file-backed mapping note processing

warning: Can't open file /memfd:/.nvidia_drv.XXXXXX (deleted) during file-backed mapping note processing
[New LWP 448978]
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/usr/lib/libthread_db.so.1".
Core was generated by `/usr/lib/Xorg -nolisten tcp :0 vt1 -keeptty -auth /tmp/serverauth.qfTJS9fjfz'.
Program terminated with signal SIGABRT, Aborted.
#0  0x00007f8429c27d22 in raise () from /usr/lib/libc.so.6
(gdb) backtrace full
#0  0x00007f8429c27d22 in raise () at /usr/lib/libc.so.6
#1  0x00007f8429c11862 in abort () at /usr/lib/libc.so.6
#2  0x000055a94b83775a in  ()
#3  0x000055a94b839221 in FatalError ()
#4  0x000055a94b83ee59 in  ()
#5  0x00007f8429c27da0 in <signal handler called> () at /usr/lib/libc.so.6
#6  0x000055a94b8a2134 in  ()
#7  0x000055a94b73f258 in  ()
#8  0x000055a94b73f506 in  ()
#9  0x000055a94b7ea35b in  ()
#10 0x000055a94b7addb3 in  ()
#11 0x000055a94b82f9f0 in  ()
#12 0x000055a94b832c1a in WaitForSomething ()
#13 0x000055a94b726914 in  ()
#14 0x00007f8429c12b25 in __libc_start_main () at /usr/lib/libc.so.6
#15 0x000055a94b7275de in _start ()
(gdb) 

There is a brief mention of warning: Can't open file /memfd:/.nvidia_drv.XXXXXX (deleted) during file-backed mapping note processing but I’m not sure this is relevant.

Hmm, too bad. Yeah, that memfd thing is irrelevant – it’s just a shared memory file that the NVIDIA X driver uses to communicate with its client-side graphics libraries.

It’s strange that gdb wasn’t able to get any useful information at all. But given that the backtrace seems to be entirely inside the Xorg process you might need to rebuild the xorg-server package with debug information.