Making X11 applications talk Wayland

Why make X11 applications talk Wayland?

I’m not going to repeat the reasons for considering Wayland a more secure protocol than X11. Suffice it to say that mir-kiosk on Ubuntu Core expects applications to connect using Wayland. Even on the desktop, it can be desirable to isolate X11 applications from the Xorg server.

In the following I’m going to show how Mir can be used to confine an X11 based application in a snap that has no access to X11. This approach can be used both for “X11 Kiosk Snaps” or for isolating an application on the desktop.

A simple Mir server to support X11 apps

Mir (like other Wayland compositors) supports X11 applications using Xwayland, for this article I’ve written a simple server mir_kiosk_x11 that is intended to run a single X11 application fullscreen. I won’t list the code here (you can find it on Github), but there’s not a frightening amount of it:

$ wc -l *.sh *.cpp *.h
  18 x11_kiosk_launch.sh
  43 x11_kiosk_main.cpp
 127 x11_kiosk_window_manager.cpp
  50 x11_kiosk_window_manager.h
 238 total

An example snap using mir_kiosk_x11

The example snap uses this server and adds an X11 based application (Zoom) that will packaged with mir_kiosk_x11 and the whole snap confined so that it has no X11 access to the system.

These are the interfaces from the snapcraft.yaml:

plugs:
  opengl:         # For Mir
  wayland:        # For Mir
  network-bind:   # For Mir (to serve X11)
  camera:         # For Zoom
  audio-playback: # For Zoom
  audio-record:   # For Zoom

I won’t repeat all the snapcraft.yaml (it is on Github), but the main thing of interest is the apps: stanza:

apps:
  mir-kiosk-x11-example:
#    daemon: simple
#    restart-condition: always
    command-chain:
      - env-setup
    command: usr/local/bin/x11_kiosk_launch $SNAP/usr/bin/zoom

This is the setup for running on the desktop, the comments indicate the changes needed to adapt for use as “kiosk” daemon. Obviously, if snapping a different application, it is necessary to change $SNAP/usr/bin/zoom to the corresponding app launch command.

The x11_kiosk_launch command comes from the mir_kiosk_x11 project. It starts the Mir server, waits for it to “come up” and starts the application, it looks like this:

#!/bin/sh

bindir=$(dirname "$0")

if [ "${bindir}" != "" ]; then bindir="${bindir}/"; fi

unset WAYLAND_DISPLAY

# ${x11_display_file} will contain the X11 display
x11_display_file=$(mktemp)

MIR_SERVER_ENABLE_X11=1 "${bindir}"mir_kiosk_x11 --x11-displayfd 5 5>"${x11_display_file}"&

inotifywait --event close_write "${x11_display_file}"
export DISPLAY
DISPLAY=:$(cat "${x11_display_file}")
rm "${x11_display_file}"
XDG_SESSION_TYPE=mir GDK_BACKEND=x11 QT_QPA_PLATFORM=xcb SDL_VIDEODRIVER=x11 NO_AT_BRIDGE=1 exec "$@"

Running the example

You can build and install this snap locally in the same way as any other snap.

Once it is built, you can run the example on your desktop provided there is a Wayland server available. If your desktop doesn’t already support Wayland, then you can install and run mir-kiosk to provide one:

$ snap install mir-kiosk
$ mir-kiosk&

This will provide a “Mir-on-X” window that Wayland applications (like the example snap) will appear on. After this you can start the example (if you’ve not done so already, connect the interfaces as shown):

$ snap connect mir-kiosk-x11-example:wayland 
$ snap connect mir-kiosk-x11-example:camera 
$ snap connect mir-kiosk-x11-example:audio-record 
$ mir-kiosk-x11-example

What is this useful for?

From a privacy perspective, I’ve shown a way to take an application that you might not trust entirely and run it, not only in strict snap confinement, but also without giving it X11 access to your desktop. (X11 applications can monitor the input and output of other applications and track which window is “active”.)

From the perspective of packaging snaps for use on Ubuntu Core, this provides an alternative for the packager to the previous approach of manually bundling Xwayland and a window manager such as i3 and configuring these to fullscreen the application.

For more: Make a X11-based Kiosk Snap


Note: You can also use this technique of running mir-kiosk as the server if your desktop already supports Wayland, just be sure that the example snap connects to the right WAYLAND_DISPLAY).

1 Like