From a789abc09f528ea37bf1deb54ebbe11fdb0d8e25 Mon Sep 17 00:00:00 2001 From: Window Maker Date: Sun, 24 May 2026 08:40:38 +0200 Subject: [PATCH] arch: eliminate last _x11_raw escape from src/ (winspector) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The Window Inspector's 'select window' feature grabbed the pointer on the root window then read XEvent.xbutton.subwindow to learn which window was clicked. This was the last access to _x11_raw in shared src/ code. Add a subwindow field to WMEButton. The X11 backend's WMEvent translation populates it from xbutton.subwindow. The Wayland backend leaves it 0 (Wayland has no equivalent grab semantic — the click reports the actual frame as event.window directly). winspector.c now uses event.u.button.subwindow with fallback to event.u.button.window, working on both backends. Net: src/ has zero _x11_raw escapes from shared code. Remaining references are inside the X11 backend (legitimately consuming the field set by its own event translator). --- WINGs/WINGs/WMEvent.h | 1 + WINGs/wevent_x11.c | 1 + src/winspector.c | 9 +++++++-- 3 files changed, 9 insertions(+), 2 deletions(-) diff --git a/WINGs/WINGs/WMEvent.h b/WINGs/WINGs/WMEvent.h index a96d2c7..ff9b100 100644 --- a/WINGs/WINGs/WMEvent.h +++ b/WINGs/WINGs/WMEvent.h @@ -82,6 +82,7 @@ typedef struct { typedef struct { WNativeWindow window; + WNativeWindow subwindow; /* deepest child under pointer at click time */ unsigned int button; /* 1=left, 2=middle, 3=right, 4+=extra */ unsigned int state; /* modifier mask */ int x, y; diff --git a/WINGs/wevent_x11.c b/WINGs/wevent_x11.c index 8996de9..3445442 100644 --- a/WINGs/wevent_x11.c +++ b/WINGs/wevent_x11.c @@ -40,6 +40,7 @@ xev_to_wme(const XEvent *xev, WMEvent *out) case ButtonRelease: out->type = (xev->type == ButtonPress) ? WME_BUTTON_PRESS : WME_BUTTON_RELEASE; out->u.button.window = (WNativeWindow)xev->xbutton.window; + out->u.button.subwindow = (WNativeWindow)xev->xbutton.subwindow; out->u.button.button = xev->xbutton.button; out->u.button.state = xev->xbutton.state; out->u.button.x = xev->xbutton.x; diff --git a/src/winspector.c b/src/winspector.c index 664fddc..524561e 100644 --- a/src/winspector.c +++ b/src/winspector.c @@ -1035,8 +1035,13 @@ static void selectWindow(WMWidget *bPtr, void *data) wm_backend->pointer_ungrab(0); { - XEvent *_xev = (XEvent *)event._x11_raw; - iwin = _xev ? wWindowFor(_xev->xbutton.subwindow) : NULL; + /* On X11 with the pointer grabbed on root_win, the click reports + * window=root and subwindow=clicked window. On Wayland there + * is no such grab semantic; the event reports window=clicked + * window directly with subwindow==0. Prefer subwindow when set. */ + WNativeWindow target = event.u.button.subwindow ? + event.u.button.subwindow : event.u.button.window; + iwin = wWindowFor(target); } if (iwin && !iwin->flags.internal_window && iwin != wwin && !iwin->flags.inspector_open) { iwin->flags.inspector_open = 1;