dbus: Fix deadlock in a11y keyboard monitor

A11yKeyboardMonitorState::key_event calls self.has_key_grab() inside
self.clients guard loop.

A "well-behaved" a11y client calls `WatchKeyboard` before `SetKeyGrabs`.

If WatchKeyboard is not called first, the `!client.watched` guard does
not short-circuit, so `has_key_grab()` runs and locks `self.clients` again.

This causes a deadlock and the compositor freezes, requiring a hard reboot.

This commit moves the `self.has_key_grab()` before the guard to
prevent a double lock.
This commit is contained in:
Tom Grushka 2026-07-23 22:43:56 -06:00 • committed by Victoria Brekenfeld
parent 6108cef8b3
commit 44de3063ee

View file

@ -150,9 +150,10 @@ impl A11yKeyboardMonitorState {
}
pub fn key_event(&self, modifiers: &ModifiersState, keysym: &KeysymHandle, state: KeyState) {
let has_key_grab = self.has_key_grab(modifiers, keysym.modified_sym());
let clients = self.clients.lock().unwrap();
for (unique_name, client) in clients.0.iter() {
if !client.watched && !self.has_key_grab(modifiers, keysym.modified_sym()) {
if !client.watched && !has_key_grab {
continue;
}