wayland: Phase 73 — frame NULL guards in wmspec.c and winmenu.c

Guard wNETFrameExtents (returns early when !dpy || !frame), so it
does not try to set X11 properties or dereference titlebar/resizebar
for Wayland windows.

Guard OpenWindowMenu, execWindowOptionCommand, and updateOptionsMenu
in winmenu.c so that the window menu and its KeepOnTop/KeepAtBottom
stacking callbacks do not crash when wwin->frame is NULL.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
Levi Neely 2026-03-28 09:56:44 +01:00
parent b1cc22ed54
commit f772c79ff5
3 changed files with 16 additions and 3 deletions

View File

@ -144,6 +144,9 @@ static void execWindowOptionCommand(WMenu * menu, WMenuEntry * entry)
/* Parameter not used, but tell the compiler that it is ok */
(void) menu;
if (!wwin->frame)
return; /* Phase 73: Wayland — no frame for stacking level changes */
switch (entry->order) {
case WO_KEEP_ON_TOP:
if (wwin->frame->core->stacking->window_level != WMFloatingLevel)
@ -479,14 +482,14 @@ static void updateOptionsMenu(WMenu * menu, WWindow * wwin)
/* keep on top check */
smenu->entries[WO_KEEP_ON_TOP]->clientdata = wwin;
smenu->entries[WO_KEEP_ON_TOP]->flags.indicator_on =
(wwin->frame->core->stacking->window_level == WMFloatingLevel) ? 1 : 0;
(wwin->frame && wwin->frame->core->stacking->window_level == WMFloatingLevel) ? 1 : 0;
wMenuSetEnabled(smenu, WO_KEEP_ON_TOP, !wwin->flags.miniaturized);
smenu->entries[WO_KEEP_ON_TOP]->rtext = GetShortcutKey(wKeyBindings[WKBD_KEEP_ON_TOP]);
/* keep at bottom check */
smenu->entries[WO_KEEP_AT_BOTTOM]->clientdata = wwin;
smenu->entries[WO_KEEP_AT_BOTTOM]->flags.indicator_on =
(wwin->frame->core->stacking->window_level == WMSunkenLevel) ? 1 : 0;
(wwin->frame && wwin->frame->core->stacking->window_level == WMSunkenLevel) ? 1 : 0;
wMenuSetEnabled(smenu, WO_KEEP_AT_BOTTOM, !wwin->flags.miniaturized);
smenu->entries[WO_KEEP_AT_BOTTOM]->rtext = GetShortcutKey(wKeyBindings[WKBD_KEEP_AT_BOTTOM]);
@ -787,6 +790,9 @@ void OpenWindowMenu(WWindow *wwin, int x, int y, int keyboard)
{
WMenu *menu;
if (!wwin->frame)
return; /* Phase 73: Wayland — no frame for window menu positioning */
menu = open_window_menu_core(wwin);
if (!menu)
return;

View File

@ -2008,6 +2008,9 @@ void wNETFrameExtents(WWindow *wwin)
{
long extents[4] = { 0, 0, 0, 0 };
if (!dpy || !wwin->frame)
return; /* Phase 73: Wayland — no X11 property to set, no frame */
/* The extents array describes dimensions which are not
* part of the client window. In our case that means
* widths of the border and heights of the titlebar and resizebar.

View File

@ -71,12 +71,16 @@
# wMaximizeWindow, wUnmaximizeWindow, wFullscreenWindow, wIconifyWindow,
# wDeiconifyWindow so that Wayland windows (frame==NULL) do not crash
# when these actions are triggered (build-only check).
# 30. (Phase 72) Early-return guards added to keyboard shortcut handlers
# 30. (Phase 72) Early-return guards in keyboard shortcut handlers
# in event.c (WKBD_KEEP_ON_TOP, WKBD_KEEP_AT_BOTTOM, WKBD_RAISE,
# WKBD_LOWER, WKBD_RAISELOWER, WKBD_WINDOWMENU, WKBD_XKB_TOGGLE) and
# to wKeyboardMoveResizeWindow, wMouseMoveWindow, wMouseResizeWindow in
# moveres.c so Wayland windows do not crash on frame->core access
# (build-only check).
# 31. (Phase 73) Frame NULL guards in wmspec.c (wNETFrameExtents) and
# winmenu.c (OpenWindowMenu, execWindowOptionCommand, updateOptionsMenu)
# so Wayland windows do not crash on frame->core stacking access
# (build-only check).
#
# This test grows as wl_backend vtable slots are implemented.
#