Skip to content

Instantly share code, notes, and snippets.

@tyalie
Last active May 28, 2025 01:10
Show Gist options
  • Save tyalie/28368a277e79c016802f6032e1b04000 to your computer and use it in GitHub Desktop.
Save tyalie/28368a277e79c016802f6032e1b04000 to your computer and use it in GitHub Desktop.
Making VT switching work in weston using a raw debian 12 installation

Tip

TL;DR: Install polkit. This problem is a permission problem, but good for us that there is no error reporting on this anywhere. yay Generally VT switching using systemd-logind is done over DBus. One can see the error in realtime by monitoring the dbus with sudo dbus-monitor --system

for humorous purposes I'll still proceed to post my notes on this as there are a few interesting tidbits in here

Also this blogpost is really helpful in understanding permissions in dbus: https://venam.net/blog/unix/2020/07/06/dbus-polkit.html

I have the problem that I can't open other VTs when weston is started from one.

steps to reproduce:

  • install debian 12 without GuI
  • apt install weston
  • weston
  • try ctrl+alt+f2 - no worky

the keyboard short seems to be set in weston_setup_vt_switch_bindings so let's try this.

update

weston is not the issue here. the vt switch is being passed to logind over dbus. Specifically this line is being reached:

	b = dbus_message_append_args(m,
				     DBUS_TYPE_UINT32, &vt,
				     DBUS_TYPE_INVALID);
	if (!b) {
		r = -ENOMEM;
		goto err_unref;
	}

->	dbus_connection_send(wl->dbus, m, NULL);

https://github.com/wayland-mirror/weston/blob/2e543aef219b3efc80ce23660fcce64cbcfaed41/libweston/launcher-logind.c#L277

so the issue seems to stem from logind. let's try to build the dbus call for the switch. Maybe we will be able to discover more funky things along the way.

dbus-send --system --print-reply --dest=org.freedesktop.login1 /org/freedesktop/login1/seat/self org.freedesktop.login1.Seat.SwitchTo int32:2

uhhh. it says permission denied, even though my computer has no issues doing this.


oki i'm even deeper now. By attaching my gdb to logind I'm able to directly look into where this error stems from. So:

b method_switch_to

# is being called when weston tries to switch vts - ~but only if I make the call with sudo~
# that was wrong, it is always called, i've no idea tho why gdb does not trigger

So this means that I'm getting blocked faaaar earlier. It seems like that there are configuration files that change the access policies. e.g. under /usr/share/dbus-1/system.d/org.freedesktop.login1.

Okay that section is mostly wrong. I do end up in method_switch_to (i think) at least when watching the systemd dbus with sudo dbus-monitor --system one can see an unsuccessful request to polkit for org.freedesktop.login1.chvt (which is requested in method_switch_to).

So turns out the issue was that polkit was not installed. After installing policykit-1 I can check for this permission with

nas@debian:/usr/share/dbus-1/system.d$ pkaction -a org.freedesktop.login1.chvt -v
org.freedesktop.login1.chvt:
  description:       Change Session
  message:           Authentication is required to change the virtual terminal.
  vendor:            The systemd Project
  vendor_url:        https://systemd.io
  icon:              
  implicit any:      auth_admin_keep
  implicit inactive: yes
  implicit active:   yes

and tada I have it. (how do these policies work thoo you might ask? well. For one dbus has a very raw access policy config in e.g. /usr/share/dbus-1/system.d/org.freedesktop.login1.conf. That is the one I mentioned previously. This one actually gives me the permission to access that interface. But then the call to polkit is being made - which was not installed and in turn would return false. The relevant polkit config can be found in /usr/share/polkit-1/actions/org.freedesktop.login1.policy

<action id="org.freedesktop.login1.chvt">
    <description gettext-domain="systemd">Change Session</description>
    <message gettext-domain="systemd">Authentication is required to change the virtual terminal.</message>
    <defaults>
        <allow_any>auth_admin_keep</allow_any>
        <allow_inactive>yes</allow_inactive>
        <allow_active>yes</allow_active>
    </defaults>
</action>

How could I have been faster?

I think that's generally a good question to ask after debugging an issue and trying out different things. In this case I think I could have spotted the issue incredibly early if I'd have take a look at what's happening on the dbus. I low key forgot that dbus-monitor exists, but the moment I saw that weston is calling dbus in order to communicate the change, I should have used that tool instead of using gdb and everything.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment