Automatic login with startx and systemd
Vincent Bernat
If your workstation is using full-disk encryption, you may want to jump directly to your desktop environment after entering the passphrase to decrypt the disk. Many display managers like GDM and LightDM have an autologin feature. However, only GDM can run Xorg with standard user privileges.
Here is an alternative using startx
and a systemd service:
[Unit] Description=X11 session for bernat After=graphical.target systemd-user-sessions.service [Service] User=bernat WorkingDirectory=~ PAMName=login Environment=XDG_SESSION_TYPE=x11 TTYPath=/dev/tty8 StandardInput=tty UnsetEnvironment=TERM UtmpIdentifier=tty8 UtmpMode=user StandardOutput=journal ExecStartPre=/usr/bin/chvt 8 ExecStart=/usr/bin/startx -- vt8 -keeptty -verbose 3 -logfile /dev/null Restart=no [Install] WantedBy=graphical.target
Let me explain each block:
-
The unit starts after
systemd-user-sessions.service
, which enables user logins after boot by removing the/run/nologin
file. -
With
User=bernat
, the unit is started with the identity of the specified user. This implies thatXorg
does not run with elevated privileges. -
With
PAMName=login
, the executed process is registered as a PAM session for thelogin
service, which includes pam_systemd. This module registers the session to the systemd login manager. To be effective, we also need to allocate a TTY withTTYPath=/dev/tty8
. When the TTY is active, the user is granted additional access to local devices—notably display, sound, keyboard, mouse. These additional rights are needed to get Xorg working rootless.1 TheTERM
environment variable is unset because it would be set tolinux
by systemd as a result of attaching the standard input to the TTY. Moreover, we informpam_systemd
we want an X11 session withEnvironment=XDG_SESSION_TYPE=x11
. Otherwise,logind
considers the session idle unless it receives input on the TTY. Software relying on the idle hint fromlogind
would be ineffective.2 -
The
UtmpIdentifier=tty8
andUtmpMode=user
directives are just a nice addition to register the session in/var/run/utmp
. -
The last step is to execute
Xorg
throughstartx
. Forlogind
to allowXorg
to take control of the local devices,chvt 8
switches to the allocated TTY.3StandardOutput=journal
, combined with the-verbose 3 -logfile /dev/null
flags forXorg
, puts the logs from the X server into the journal instead of using a file. While equal to the default value, theRestart=no
directive highlights we do not want this unit to be restarted. This ensures the loginless session is only available on boot. By default,startx
runsxinitrc
. If you want to run Kodi instead, add/usr/bin/kodi-standalone
betweenstartx
and--
.
Drop this unit in /etc/systemd/system/x11-autologin.service
and
enable it with systemctl enable x11-autologin.service
. Xorg is now
running rootless and logging into the journal. After using it for a
few months, I didn’t notice any regression compared to LightDM with
autologin.
-
For more information on how
logind
provides access to devices, see this blog post. The method names do not match the current implementation, but the concepts are still correct.Xorg
takes control of the session when the TTY is active. ↩︎ -
Xorg could change the type of the session itself after taking control of it, but it does not. ↩︎
-
There is some code in Xorg to do that, but it is executed too late and fails with:
xf86OpenConsole: VT_ACTIVATE failed: Operation not permitted
. ↩︎