wayland: Phase 67 — WWindow.workspace; safe workspace switching without frame
Add int workspace to WWindow so Wayland-managed windows (which have no WFrameWindow and therefore no frame->workspace slot) can track their workspace assignment. Set wwin->workspace = workspace in the Wayland branch of wManageWindow alongside the existing geometry recording. Guard wWorkspaceForceChange against NULL frame dereferences: introduce a tmp_workspace local that falls back to tmp->workspace when frame is NULL, and protect the omnipresent workspace assignment the same way. Also add a NULL guard for tmp->icon->core in the miniwindow-unmap path. This prevents NULL dereferences if workspace switching is triggered (e.g., via a root-menu action) while Wayland windows are managed. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
a2571be53e
commit
e60dff8ffd
|
|
@ -1171,13 +1171,17 @@ WWindow *wManageWindow(WScreen *scr, WNativeWindow window)
|
|||
/* to make sure the window receives it's new position after reparenting */
|
||||
wWindowSynthConfigureNotify(wwin);
|
||||
} else {
|
||||
/* Wayland: record geometry from normal hints; frame stays NULL */
|
||||
/* Wayland: record geometry from normal hints; frame stays NULL.
|
||||
* Phase 67: store workspace in wwin->workspace since there is no
|
||||
* frame->workspace slot; wWorkspaceForceChange uses this field
|
||||
* when frame is NULL to avoid NULL dereferences on WS switch. */
|
||||
wwin->client.x = x;
|
||||
wwin->client.y = y;
|
||||
wwin->client.width = width;
|
||||
wwin->client.height = height;
|
||||
wwin->frame_x = x;
|
||||
wwin->frame_y = y;
|
||||
wwin->workspace = workspace;
|
||||
}
|
||||
|
||||
/* Setup descriptors and save window to internal lists */
|
||||
|
|
|
|||
|
|
@ -294,6 +294,10 @@ typedef struct WWindow {
|
|||
int icon_w, icon_h;
|
||||
RImage *net_icon_image; /* Window Image */
|
||||
WNETWindowType window_type; /* _NET_WM_WINDOW_TYPE (WNW_TYPE_*) */
|
||||
/* Phase 67: workspace slot for Wayland path (frame is NULL, so
|
||||
* frame->workspace is unavailable; workspace operations use this
|
||||
* field instead when !frame). */
|
||||
int workspace;
|
||||
} WWindow;
|
||||
|
||||
#define HAS_TITLEBAR(w) (!(WFLAGP((w), no_titlebar) || (w)->flags.fullscreen))
|
||||
|
|
|
|||
|
|
@ -467,7 +467,10 @@ void wWorkspaceForceChange(WScreen * scr, int workspace)
|
|||
* but will create annoyance for every other application
|
||||
*/
|
||||
while (tmp) {
|
||||
if (tmp->frame->workspace != workspace && !tmp->flags.selected) {
|
||||
/* Phase 67: Wayland windows have no frame; use wwin->workspace
|
||||
* as the workspace slot when frame is NULL. */
|
||||
int tmp_workspace = tmp->frame ? tmp->frame->workspace : tmp->workspace;
|
||||
if (tmp_workspace != workspace && !tmp->flags.selected) {
|
||||
/* unmap windows not on this workspace */
|
||||
if ((tmp->flags.mapped || tmp->flags.shaded) &&
|
||||
!IS_OMNIPRESENT(tmp) && !tmp->flags.changing_workspace) {
|
||||
|
|
@ -480,7 +483,7 @@ void wWorkspaceForceChange(WScreen * scr, int workspace)
|
|||
}
|
||||
/* also unmap miniwindows not on this workspace */
|
||||
if (!wPreferences.sticky_icons && tmp->flags.miniaturized &&
|
||||
tmp->icon && !IS_OMNIPRESENT(tmp)) {
|
||||
tmp->icon && !IS_OMNIPRESENT(tmp) && tmp->icon->core) {
|
||||
wm_backend->window_unmap(tmp->icon->core->window);
|
||||
tmp->icon->mapped = 0;
|
||||
}
|
||||
|
|
@ -488,7 +491,10 @@ void wWorkspaceForceChange(WScreen * scr, int workspace)
|
|||
if (IS_OMNIPRESENT(tmp)) {
|
||||
WApplication *wapp = wApplicationOf(tmp->main_window);
|
||||
|
||||
tmp->frame->workspace = workspace;
|
||||
if (tmp->frame)
|
||||
tmp->frame->workspace = workspace;
|
||||
else
|
||||
tmp->workspace = workspace;
|
||||
|
||||
if (wapp) {
|
||||
wapp->last_workspace = workspace;
|
||||
|
|
|
|||
|
|
@ -55,6 +55,9 @@
|
|||
# 24. (Phase 66) XDG popup initial configure scheduled so context menus and
|
||||
# autocomplete dropdowns can commit first buffer without stalling
|
||||
# (build-only check — weston-simple-shm creates no popups).
|
||||
# 25. (Phase 67) WWindow.workspace added; wWorkspaceForceChange uses it as
|
||||
# fallback when frame==NULL so workspace switching is safe in Wayland
|
||||
# (build-only check — workspace switch requires keyboard shortcuts).
|
||||
#
|
||||
# This test grows as wl_backend vtable slots are implemented.
|
||||
#
|
||||
|
|
|
|||
Loading…
Reference in New Issue