FreeBSD.software
Home/Guides/How to Set Up Wayland on FreeBSD with Sway
tutorial·2026-04-09·10 min read

How to Set Up Wayland on FreeBSD with Sway

Complete guide to running Wayland on FreeBSD: Sway compositor installation, XDG configuration, screen sharing, clipboard, application compatibility, and troubleshooting.

How to Set Up Wayland on FreeBSD with Sway

Wayland is the modern replacement for the X Window System. It eliminates the security issues of X11's permissive client model, reduces input latency, and simplifies the display stack. On FreeBSD, Wayland support has matured significantly. Sway, a tiling compositor that is a drop-in replacement for i3, is the most stable and feature-complete Wayland compositor available on FreeBSD today.

This guide covers a complete Wayland desktop setup on FreeBSD 14.x with Sway: driver prerequisites, package installation, configuration, screen sharing, clipboard integration, running X11 applications under XWayland, and troubleshooting common issues.

Prerequisites

Before installing Sway, your system needs working graphics drivers and a few kernel features enabled.

Graphics Drivers

Wayland compositors talk directly to the kernel's DRM (Direct Rendering Manager) subsystem. You need the drm-kmod package for your GPU.

For Intel and AMD GPUs:

sh
pkg install drm-kmod

Load the appropriate kernel module at boot. For Intel:

sh
sysrc kld_list+="i915kms"

For AMD:

sh
sysrc kld_list+="amdgpu"

For NVIDIA GPUs:

NVIDIA Wayland support on FreeBSD is limited. The proprietary nvidia-driver package does not yet support the GBM backend that Sway requires. If you have an NVIDIA GPU, you may need to use X11 instead, or check if the nvidia-drm module has gained GBM support in the latest driver version.

Kernel Configuration

Sway requires the evdev input subsystem. Load it:

sh
kldload evdev sysrc kld_list+="evdev"

Verify DRM is working:

sh
kldstat | grep drm ls /dev/dri/

You should see card0 and renderD128 (or similar) in /dev/dri/.

User Permissions

Your user must be in the video group to access the GPU:

sh
pw groupmod video -m your_username

Also add to the input group for input device access:

sh
pw groupmod input -m your_username

Log out and log back in for group changes to take effect.

Installing Sway and Supporting Packages

Install the Sway compositor and essential Wayland utilities:

sh
pkg install sway swaylock swayidle swaybg waybar \ foot wofi grim slurp wl-clipboard \ xwayland dbus

What each package provides:

  • sway -- the tiling Wayland compositor
  • swaylock -- screen locker
  • swayidle -- idle management (lock screen after inactivity, suspend)
  • swaybg -- wallpaper setter
  • waybar -- status bar (clock, workspaces, system tray, battery, etc.)
  • foot -- Wayland-native terminal emulator (fast and lightweight)
  • wofi -- application launcher (like dmenu/rofi for Wayland)
  • grim -- screenshot tool
  • slurp -- region selection tool (for partial screenshots)
  • wl-clipboard -- command-line clipboard (wl-copy, wl-paste)
  • xwayland -- compatibility layer for running X11 applications

Enable D-Bus, which Sway and many desktop applications require:

sh
sysrc dbus_enable="YES" service dbus start

Environment Variables

Set the required environment variables. Add these to your shell profile:

sh
vi ~/.profile
sh
# Wayland/Sway environment export XDG_RUNTIME_DIR=/tmp/$(id -u)-runtime-dir if [ ! -d "$XDG_RUNTIME_DIR" ]; then mkdir -p "$XDG_RUNTIME_DIR" chmod 0700 "$XDG_RUNTIME_DIR" fi export XDG_SESSION_TYPE=wayland export XDG_CURRENT_DESKTOP=sway export MOZ_ENABLE_WAYLAND=1 export QT_QPA_PLATFORM=wayland export SDL_VIDEODRIVER=wayland export _JAVA_AWT_WM_NONREPARENTING=1 export ELECTRON_OZONE_PLATFORM_HINT=wayland

The XDG_RUNTIME_DIR is critical. Sway will refuse to start without it. The other variables tell applications to prefer Wayland backends.

If you use ~/.shrc or ~/.bashrc instead, add the same lines there.

Starting Sway

From a TTY console (not from within X11), log in and run:

sh
sway

Sway reads its configuration from ~/.config/sway/config. If no config file exists, Sway uses defaults and opens a terminal with Mod4+Return (the Super/Windows key plus Enter).

If Sway starts and you see a blank screen with a cursor, it is working. Press Mod4+Return to open a terminal.

Configuring Sway

Create the configuration directory and file:

sh
mkdir -p ~/.config/sway cp /usr/local/etc/sway/config ~/.config/sway/config

Edit the configuration:

sh
vi ~/.config/sway/config

Key Bindings

The default modifier is Mod4 (Super key). Core bindings:

shell
set $mod Mod4 set $term foot set $menu wofi --show drun # Start terminal bindsym $mod+Return exec $term # Kill focused window bindsym $mod+Shift+q kill # Application launcher bindsym $mod+d exec $menu # Screenshot (full screen) bindsym Print exec grim ~/screenshots/$(date +%Y%m%d-%H%M%S).png # Screenshot (selected region) bindsym $mod+Shift+s exec grim -g "$(slurp)" ~/screenshots/$(date +%Y%m%d-%H%M%S).png # Lock screen bindsym $mod+l exec swaylock -c 000000 # Reload config bindsym $mod+Shift+c reload # Exit Sway bindsym $mod+Shift+e exec swaynag -t warning -m 'Exit Sway?' -b 'Yes' 'swaymsg exit'

Output Configuration

List connected displays:

sh
swaymsg -t get_outputs

Configure displays in your Sway config:

shell
# Set resolution and position output HDMI-A-1 resolution 1920x1080 position 0,0 output DP-1 resolution 2560x1440 position 1920,0 # Set wallpaper output * bg ~/wallpaper.jpg fill

Input Configuration

List input devices:

sh
swaymsg -t get_inputs

Configure keyboard layout and touchpad:

shell
input type:keyboard { xkb_layout us xkb_options caps:escape repeat_delay 200 repeat_rate 40 } input type:touchpad { tap enabled natural_scroll enabled scroll_method two_finger }

Idle and Lock

Configure automatic screen locking:

shell
exec swayidle -w \ timeout 300 'swaylock -f -c 000000' \ timeout 600 'swaymsg "output * dpms off"' \ resume 'swaymsg "output * dpms on"' \ before-sleep 'swaylock -f -c 000000'

This locks the screen after 5 minutes of inactivity and turns off displays after 10 minutes.

Configuring Waybar

Waybar is the status bar for Sway. Create its configuration:

sh
mkdir -p ~/.config/waybar vi ~/.config/waybar/config
json
{ "layer": "top", "position": "top", "height": 30, "modules-left": ["sway/workspaces", "sway/mode"], "modules-center": ["clock"], "modules-right": ["cpu", "memory", "disk", "network", "pulseaudio", "tray"], "clock": { "format": "{:%Y-%m-%d %H:%M}", "tooltip-format": "{:%A, %B %d, %Y}" }, "cpu": { "format": "CPU {usage}%", "interval": 5 }, "memory": { "format": "MEM {}%", "interval": 5 }, "disk": { "format": "DISK {percentage_used}%", "path": "/" }, "network": { "format-wifi": "{essid} ({signalStrength}%)", "format-ethernet": "{ifname}: {ipaddr}", "format-disconnected": "disconnected" }, "tray": { "spacing": 10 } }

Add to your Sway config:

shell
bar { swaybar_command waybar }

Style Waybar with CSS:

sh
vi ~/.config/waybar/style.css
css
* { font-family: monospace; font-size: 13px; } window#waybar { background-color: rgba(0, 0, 0, 0.9); color: #cccccc; } #workspaces button.focused { background-color: #333333; color: #ffffff; } #cpu, #memory, #disk, #network, #clock { padding: 0 10px; }

Running X11 Applications

XWayland provides backward compatibility for X11 applications that do not yet support Wayland natively. It is enabled by default in Sway.

Verify XWayland is enabled in your Sway config:

shell
xwayland enable

Most X11 applications work transparently under XWayland. To check if an application is running natively on Wayland or through XWayland:

sh
xprop

Click on a window. If xprop can read its properties, it is running under XWayland. Wayland-native windows will not respond to xprop.

Applications with known Wayland support on FreeBSD:

  • Firefox: native with MOZ_ENABLE_WAYLAND=1
  • Chromium: native with --ozone-platform=wayland
  • foot, alacritty: native terminal emulators
  • LibreOffice: native since 7.x
  • mpv: native with --gpu-context=waylandvk
  • GIMP: XWayland (Wayland support in progress)

Clipboard

The wl-clipboard package provides wl-copy and wl-paste for command-line clipboard operations:

sh
# Copy text to clipboard echo "hello" | wl-copy # Paste from clipboard wl-paste # Copy file contents wl-copy < /etc/motd # Copy screenshot to clipboard grim - | wl-copy -t image/png

Clipboard works between Wayland-native applications and XWayland applications seamlessly.

Screen Sharing

Screen sharing on Wayland requires PipeWire and the xdg-desktop-portal stack.

Install the required packages:

sh
pkg install pipewire xdg-desktop-portal xdg-desktop-portal-wlr

Enable PipeWire. Add to your Sway config or shell profile:

sh
vi ~/.config/sway/config
shell
exec pipewire exec pipewire-pulse exec wireplumber

Ensure the portal environment variable is set (already in our .profile if XDG_CURRENT_DESKTOP=sway is set).

Test screen sharing in Firefox by joining a test video call or using a screen sharing test page. Firefox uses xdg-desktop-portal-wlr to capture the Sway output.

For OBS Studio, install it and configure it to use the PipeWire source:

sh
pkg install obs-studio

Notifications

Install mako, a Wayland notification daemon:

sh
pkg install mako

Add to your Sway config:

shell
exec mako

Configure mako:

sh
mkdir -p ~/.config/mako vi ~/.config/mako/config
ini
default-timeout=5000 font=monospace 12 background-color=#1a1a1aee text-color=#cccccc border-color=#333333 border-size=2

Test notifications:

sh
notify-send "Test" "This is a test notification"

File Manager and GTK Theming

Install a file manager and set GTK themes for a consistent look:

sh
pkg install thunar adwaita-icon-theme

Configure GTK for Wayland:

sh
mkdir -p ~/.config/gtk-3.0 vi ~/.config/gtk-3.0/settings.ini
ini
[Settings] gtk-theme-name=Adwaita gtk-icon-theme-name=Adwaita gtk-font-name=Sans 11 gtk-cursor-theme-name=Adwaita gtk-cursor-theme-size=24

For cursor theme in Sway, add to your config:

shell
seat * xcursor_theme Adwaita 24

Auto-Starting Sway on Login

To start Sway automatically when you log into TTY1, add to the end of your ~/.profile:

sh
# Auto-start Sway on TTY1 if [ "$(tty)" = "/dev/ttyv0" ]; then exec sway fi

Performance Tuning

Reduce compositor latency. Add to Sway config:

shell
# Disable vsync for lower input latency (may cause tearing) # output * adaptive_sync on

Hardware video acceleration. Install VA-API support:

sh
pkg install libva-intel-driver

Or for AMD:

sh
pkg install libva-mesa-driver mesa-gallium-va

Verify VA-API:

sh
vainfo

Font rendering. Install good fonts:

sh
pkg install noto dejavu sourcecodepro-ttf

Configure fontconfig:

sh
mkdir -p ~/.config/fontconfig vi ~/.config/fontconfig/fonts.conf
xml
<?xml version="1.0"?> <!DOCTYPE fontconfig SYSTEM "urn:fontconfig:fonts.dtd"> <fontconfig> <match target="font"> <edit name="antialias" mode="assign"><bool>true</bool></edit> <edit name="hinting" mode="assign"><bool>true</bool></edit> <edit name="hintstyle" mode="assign"><const>hintslight</const></edit> <edit name="rgba" mode="assign"><const>rgb</const></edit> <edit name="lcdfilter" mode="assign"><const>lcddefault</const></edit> </match> </fontconfig>

Troubleshooting

Sway fails to start with "Failed to open DRM device":

Check GPU driver is loaded:

sh
kldstat | grep -E "(i915|amdgpu|radeon)"

Check device permissions:

sh
ls -la /dev/dri/

Ensure your user is in the video group:

sh
groups your_username

Black screen after starting Sway:

Press Mod4+Return to open a terminal. If nothing happens, check the Sway log:

sh
sway -d 2> /tmp/sway.log

Review /tmp/sway.log for errors.

XWayland applications look blurry on HiDPI:

XWayland does not handle fractional scaling well. Force integer scaling in Sway:

shell
output * scale 2

Or set per-application scaling with GDK_SCALE=2 or QT_SCALE_FACTOR=2.

No sound:

Install and configure PipeWire:

sh
pkg install pipewire wireplumber

Ensure PipeWire is started in your Sway config:

shell
exec pipewire exec wireplumber

Check audio devices:

sh
pw-cli list-objects | grep -i audio

Firefox does not use Wayland natively:

Verify the environment variable:

sh
echo $MOZ_ENABLE_WAYLAND

It must be 1. Check with:

sh
MOZ_ENABLE_WAYLAND=1 firefox &

In about:support, the "Window Protocol" field should say "wayland".

FAQ

Is Wayland stable enough for daily use on FreeBSD?

Yes, for most workflows. Sway is production-quality. The main gaps are in application support (some older GTK2 and Qt4 apps need XWayland) and in screen recording/sharing (which requires PipeWire). If you run a tiling workflow with terminals, a browser, and standard productivity tools, Wayland on FreeBSD works well.

Can I run GNOME or KDE on Wayland on FreeBSD?

GNOME on Wayland has experimental support on FreeBSD but is less stable than Sway. KDE Plasma Wayland support is in progress. Sway is the most mature Wayland compositor on FreeBSD currently.

Does multi-monitor work?

Yes. Sway handles multi-monitor setups natively. Use swaymsg -t get_outputs to list displays and configure them in your Sway config with resolution, position, and scale settings.

Can I use Sway with a floating window layout instead of tiling?

Yes. Sway supports floating windows. Press Mod4+Shift+Space to toggle a window between tiled and floating. You can set specific applications to always float with window rules in the config.

How do I switch back to X11 if Wayland does not work?

Install Xorg and a window manager, then start X11 from the console instead of Sway. Both can coexist. You choose which to start at login.

What about gaming on Wayland?

Games using SDL2 or Vulkan generally work. OpenGL games may need XWayland. Steam runs under XWayland. Performance is comparable to X11 for most titles. Set SDL_VIDEODRIVER=wayland for native Wayland support in SDL2 games.

Get more FreeBSD guides

Weekly tutorials, security advisories, and package updates. No spam.