mirror of
https://github.com/kuhyx/screen-locker.git
synced 2026-11-11 13:07:43 +01:00
Both previous escapes were unreachable, for the same underlying reason stated two different ways. A Tk key binding cannot fire, because once the workout app takes its seat grab X delivers every keystroke to that app alone. And "run touch from another terminal" cannot be done, because the app covers the screen with an override-redirect fullscreen window -- there is no other terminal to reach. An escape has to be handled INSIDE the grab, by the app itself, or it is not an escape. So --demo-escape arms a key handler in the runner: Ctrl+Shift+Q ungrabs the seat and closes the window. The grab, the override-redirect window and the handoff are all unchanged, so the demo exercises the real locking mechanism rather than a softened copy of it, and the hatch is the one deliberate way out. The handler ungrabs before closing. Destroying a window that still holds the seat can leave the pointer and keyboard grabbed with nothing left to release them, which needs exactly the reboot this hatch exists to prevent. Not Escape, which the Dart side already binds for in-app navigation; shadowing it would change the behaviour under test. Verified in both directions against the real debug bundle, each under its own Xvfb display: with the flag, the app exits on Ctrl+Shift+Q while holding the grab and the lock takes the screen back; without it, the identical keystroke does nothing and the app keeps the screen. A test asserts the production path never passes the flag. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01DfJC1Wu1SEgJ6X49k5Jqtg
23 lines
928 B
C
23 lines
928 B
C
// Demo-only escape hatch for the lock-mode window.
|
|
//
|
|
// In lock mode the app takes an exclusive seat grab and never releases it, so
|
|
// while it is up X delivers every keystroke to this app and to nothing else.
|
|
// That is the point in production -- but it also means a human testing the
|
|
// handoff cannot reach a terminal, a VT, or the supervisor's own key bindings
|
|
// to get out. An escape has to be handled INSIDE the grab, by this app, or it
|
|
// cannot be reached at all.
|
|
//
|
|
// Enabled only by --demo-escape, which the demo harness passes and the
|
|
// production supervisor never does. The grab itself is unchanged, so the
|
|
// locking mechanism under test is the real one.
|
|
|
|
#ifndef RUNNER_DEMO_ESCAPE_H_
|
|
#define RUNNER_DEMO_ESCAPE_H_
|
|
|
|
#include <gtk/gtk.h>
|
|
|
|
// Installs the Ctrl+Shift+Q handler on `window`. No-op unless `enabled`.
|
|
void demo_escape_install(GtkWidget* window, gboolean enabled);
|
|
|
|
#endif // RUNNER_DEMO_ESCAPE_H_
|