On Sun, 28 May 2023 at 00:15:26 +0100, Simon McVittie wrote: > [x] attach debdiff against the package in [bookworm]
Sorry, here's the diff. The attached diff is between patched trees, excluding the patches themselves to avoid duplicating the changes, and is lightly filtered to ignore translations (very verbose). I normally upload using dgit, so if I'm the uploader, the uploaded .dsc will be checked for an exact match to what's in git. GNOME team (particularly Jeremy and Marco): This and the accompanying gnome-shell update are particularly high-visibility and important to get right, and the finer points of compositor behaviour are not my strong point, so please check this. I have uploaded prerelease packages to <https://people.debian.org/~smcv/12.1/> and will upload to unstable if given permission. If someone with more compositor expertise wants to take these over, they are very welcome to do so. smcv
git diff patch-queue/43.4.. | filterdiff -p1 -x'debian/patches/*.patch' -x'po/*.po' diff --git a/NEWS b/NEWS index 65e5d1cf8..27862914b 100644 --- a/NEWS +++ b/NEWS @@ -1,3 +1,15 @@ +43.5 +==== +* Fix recording windows on non-active workspaces [Robert; !2789] +* Fixed crashes [Colin, Sebastian, Jonas; !2917, !2955, !2969] +* Misc. bug fixes and cleanups [Ivan; !2928] + +Contributors: + Jonas Ã…dahl, Sebastian Keller, Colin Kinloch, Robert Mader, Ivan Molodetskikh + +Translators: + Nart Tlisha [ab] + 43.4 ==== * Do not overwrite previously set offsets on attach [Matthias; !2843] diff --git a/debian/changelog b/debian/changelog index d7daed123..1440b273e 100644 --- a/debian/changelog +++ b/debian/changelog @@ -1,3 +1,27 @@ +mutter (43.5-0+deb12u1) UNRELEASED; urgency=medium + + * New upstream stable release + - Always update surfaces belonging to a window that is being recorded + or included in a screencast, even if the window is not visible + on a local display (mutter#2538, mutter!2789) + - Export previously-private meta_window_has_pointer(), needed by + screenshot UI fixes in gnome-shell 43.5 (mutter!2928) + + d/libmutter-11-0.symbols: Update to add that symbol + - All other changes were already present in 43.4-2 + * d/patches: Drop patches that were applied upstream + * d/patches: Update to upstream gnome-43 branch commit 43.5-2-g8d7e958b8 + for additional post-release fixes + - d/p/compositor-view-Chain-up-finalize.patch: + Fix a resource leak when a compositor view is destroyed (mutter!2991) + - d/p/wayland-xdg-shell-Dismiss-instead-of-destroy-invalid-popu.patch: + Update metadata to reflect upstream backport, no functional change + * d/p/wayland-outputs-Fix-potential-crash-when-output-has-no-mo.patch: + Backport patch from 44~beta to fix a crash during suspend/resume in + some circumstances (mutter#2570, potentially also resolves + #1010478 and #1036268) + + -- Simon McVittie <s...@debian.org> Sat, 27 May 2023 15:46:33 +0100 + mutter (43.4-2) unstable; urgency=medium * Team upload diff --git a/debian/libmutter-11-0.symbols b/debian/libmutter-11-0.symbols index 1128f2ab3..f3b181d85 100644 --- a/debian/libmutter-11-0.symbols +++ b/debian/libmutter-11-0.symbols @@ -780,6 +780,7 @@ libmutter-11.so.0 libmutter-11-0 #MINVER# meta_window_group_leader_changed@Base 43.0 meta_window_has_attached_dialogs@Base 43.0 meta_window_has_focus@Base 43.0 + meta_window_has_pointer@Base 43.5 meta_window_is_above@Base 43.0 meta_window_is_always_on_all_workspaces@Base 43.0 meta_window_is_ancestor_of_transient@Base 43.0 diff --git a/debian/patches/compositor-view-Chain-up-finalize.patch b/debian/patches/compositor-view-Chain-up-finalize.patch new file mode 100644 index 000000000..383a1065d diff --git a/debian/patches/series b/debian/patches/series index 8be32b377..3068ed91d 100644 --- a/debian/patches/series +++ b/debian/patches/series @@ -1,9 +1,6 @@ -wayland-Skip-subsurface-desync-if-parent-is-NULL.patch -Update-Abkhazian-translation.patch -clutter-actor-Get-next-action-from-list-before-handling-c.patch -cursor-tracker-Don-t-leak-window-cursor-on-exit.patch -wayland-cursor-surface-Update-cursor-on-dispose.patch +compositor-view-Chain-up-finalize.patch wayland-xdg-shell-Dismiss-instead-of-destroy-invalid-popu.patch +wayland-outputs-Fix-potential-crash-when-output-has-no-mo.patch tests-Break-up-stacking-installed-tests-into-more-smaller.patch tests-Use-a-more-interoperable-path-to-bash.patch meson-add-back-default_driver-option.patch diff --git a/debian/patches/wayland-outputs-Fix-potential-crash-when-output-has-no-mo.patch b/debian/patches/wayland-outputs-Fix-potential-crash-when-output-has-no-mo.patch new file mode 100644 index 000000000..afcde4c38 diff --git a/meson.build b/meson.build index ba881c36f..f307a4736 100644 --- a/meson.build +++ b/meson.build @@ -1,5 +1,5 @@ project('mutter', 'c', - version: '43.4', + version: '43.5', meson_version: '>= 0.55.0', license: 'GPLv2+' ) diff --git a/src/backends/meta-screen-cast-window-stream.c b/src/backends/meta-screen-cast-window-stream.c index 6f42a446e..d678d4f61 100644 --- a/src/backends/meta-screen-cast-window-stream.c +++ b/src/backends/meta-screen-cast-window-stream.c @@ -197,6 +197,16 @@ meta_screen_cast_window_stream_finalize (GObject *object) { MetaScreenCastWindowStream *window_stream = META_SCREEN_CAST_WINDOW_STREAM (object); + MetaWindowActor *window_actor; + + window_actor = meta_window_actor_from_window (window_stream->window); + if (window_actor) + { + MetaScreenCastWindow *screen_cast_window; + + screen_cast_window = META_SCREEN_CAST_WINDOW (window_actor); + meta_screen_cast_window_dec_usage (screen_cast_window); + } g_clear_signal_handler (&window_stream->window_unmanaged_handler_id, window_stream->window); @@ -212,6 +222,8 @@ meta_screen_cast_window_stream_initable_init (GInitable *initable, MetaScreenCastWindowStream *window_stream = META_SCREEN_CAST_WINDOW_STREAM (initable); MetaWindow *window = window_stream->window; + MetaScreenCastWindow *screen_cast_window = + META_SCREEN_CAST_WINDOW (meta_window_actor_from_window (window)); MetaLogicalMonitor *logical_monitor; int scale; @@ -242,6 +254,8 @@ meta_screen_cast_window_stream_initable_init (GInitable *initable, window_stream->stream_width = logical_monitor->rect.width * scale; window_stream->stream_height = logical_monitor->rect.height * scale; + meta_screen_cast_window_inc_usage (screen_cast_window); + return initable_parent_iface->init (initable, cancellable, error); } diff --git a/src/backends/meta-screen-cast-window.c b/src/backends/meta-screen-cast-window.c index b9c0df867..b36f9e16f 100644 --- a/src/backends/meta-screen-cast-window.c +++ b/src/backends/meta-screen-cast-window.c @@ -99,3 +99,15 @@ meta_screen_cast_window_has_damage (MetaScreenCastWindow *screen_cast_window) return iface->has_damage (screen_cast_window); } + +void +meta_screen_cast_window_inc_usage (MetaScreenCastWindow *screen_cast_window) +{ + META_SCREEN_CAST_WINDOW_GET_IFACE (screen_cast_window)->inc_usage (screen_cast_window); +} + +void +meta_screen_cast_window_dec_usage (MetaScreenCastWindow *screen_cast_window) +{ + META_SCREEN_CAST_WINDOW_GET_IFACE (screen_cast_window)->dec_usage (screen_cast_window); +} diff --git a/src/backends/meta-screen-cast-window.h b/src/backends/meta-screen-cast-window.h index d170d92ae..a2cc4cd40 100644 --- a/src/backends/meta-screen-cast-window.h +++ b/src/backends/meta-screen-cast-window.h @@ -62,6 +62,9 @@ struct _MetaScreenCastWindowInterface CoglFramebuffer *framebuffer); gboolean (*has_damage) (MetaScreenCastWindow *screen_cast_window); + + void (*inc_usage) (MetaScreenCastWindow *screen_cast_window); + void (*dec_usage) (MetaScreenCastWindow *screen_cast_window); }; void meta_screen_cast_window_get_buffer_bounds (MetaScreenCastWindow *screen_cast_window, @@ -90,6 +93,9 @@ gboolean meta_screen_cast_window_blit_to_framebuffer (MetaScreenCastWindow *scre gboolean meta_screen_cast_window_has_damage (MetaScreenCastWindow *screen_cast_window); +void meta_screen_cast_window_inc_usage (MetaScreenCastWindow *screen_cast_window); +void meta_screen_cast_window_dec_usage (MetaScreenCastWindow *screen_cast_window); + G_END_DECLS #endif /* META_SCREEN_CAST_WINDOW_H */ diff --git a/src/compositor/meta-compositor-view.c b/src/compositor/meta-compositor-view.c index b95cec7e8..6ce622424 100644 --- a/src/compositor/meta-compositor-view.c +++ b/src/compositor/meta-compositor-view.c @@ -170,6 +170,8 @@ meta_compositor_view_finalize (GObject *object) meta_compositor_view_get_instance_private (compositor_view); g_clear_weak_pointer (&priv->top_window_actor); + + G_OBJECT_CLASS (meta_compositor_view_parent_class)->finalize (object); } static void diff --git a/src/compositor/meta-surface-actor-wayland.c b/src/compositor/meta-surface-actor-wayland.c index b8d354627..a9e5ea3d9 100644 --- a/src/compositor/meta-surface-actor-wayland.c +++ b/src/compositor/meta-surface-actor-wayland.c @@ -30,7 +30,9 @@ #include "backends/meta-backend-private.h" #include "backends/meta-logical-monitor.h" +#include "backends/meta-screen-cast-window.h" #include "compositor/meta-shaped-texture-private.h" +#include "compositor/meta-window-actor-private.h" #include "compositor/region-utils.h" #include "wayland/meta-wayland-buffer.h" #include "wayland/meta-wayland-private.h" @@ -74,15 +76,19 @@ meta_surface_actor_wayland_is_view_primary (MetaSurfaceActor *actor, ClutterStageView *current_primary_view = NULL; float highest_refresh_rate = 0.f; float biggest_unobscurred_fraction = 0.f; + MetaWindowActor *window_actor; + gboolean is_streaming = FALSE; GList *l; - if (!clutter_actor_is_effectively_on_stage_view (CLUTTER_ACTOR (actor), - stage_view)) - return FALSE; + window_actor = meta_window_actor_from_actor (CLUTTER_ACTOR (actor)); + if (window_actor) + is_streaming = meta_window_actor_is_streaming (window_actor); - if (clutter_actor_has_mapped_clones (CLUTTER_ACTOR (actor))) + if (clutter_actor_has_mapped_clones (CLUTTER_ACTOR (actor)) || is_streaming) { ClutterStage *stage; + ClutterStageView *fallback_view = NULL; + float fallback_refresh_rate = 0.0; stage = CLUTTER_STAGE (clutter_actor_get_stage (CLUTTER_ACTOR (actor))); for (l = clutter_stage_peek_stage_views (stage); l; l = l->next) @@ -90,28 +96,42 @@ meta_surface_actor_wayland_is_view_primary (MetaSurfaceActor *actor, ClutterStageView *view = l->data; float refresh_rate; - if (!clutter_actor_is_effectively_on_stage_view (CLUTTER_ACTOR (actor), - view)) - continue; - refresh_rate = clutter_stage_view_get_refresh_rate (view); - if (refresh_rate > highest_refresh_rate) + + if (clutter_actor_is_effectively_on_stage_view (CLUTTER_ACTOR (actor), + view)) { - current_primary_view = view; - highest_refresh_rate = refresh_rate; + if (refresh_rate > highest_refresh_rate) + { + current_primary_view = view; + highest_refresh_rate = refresh_rate; + } + } + else + { + if (refresh_rate > fallback_refresh_rate) + { + fallback_view = view; + fallback_refresh_rate = refresh_rate; + } } } - return current_primary_view == stage_view; + if (current_primary_view) + return current_primary_view == stage_view; + else if (is_streaming) + return fallback_view == stage_view; } l = clutter_actor_peek_stage_views (CLUTTER_ACTOR (actor)); - g_return_val_if_fail (l, FALSE); + if (!l) + return FALSE; if (!l->next) { - g_return_val_if_fail (l->data == stage_view, FALSE); - return !meta_surface_actor_is_obscured (actor); + return !meta_surface_actor_is_obscured_on_stage_view (actor, + stage_view, + NULL); } for (; l; l = l->next) diff --git a/src/compositor/meta-window-actor-private.h b/src/compositor/meta-window-actor-private.h index 477d0b3a5..c1f46d590 100644 --- a/src/compositor/meta-window-actor-private.h +++ b/src/compositor/meta-window-actor-private.h @@ -101,6 +101,8 @@ void meta_window_actor_set_geometry_scale (MetaWindowActor *window_actor, int meta_window_actor_get_geometry_scale (MetaWindowActor *window_actor); +gboolean meta_window_actor_is_streaming (MetaWindowActor *window_actor); + void meta_window_actor_notify_damaged (MetaWindowActor *window_actor); gboolean meta_window_actor_is_frozen (MetaWindowActor *self); diff --git a/src/compositor/meta-window-actor.c b/src/compositor/meta-window-actor.c index 02e81f0aa..943343c14 100644 --- a/src/compositor/meta-window-actor.c +++ b/src/compositor/meta-window-actor.c @@ -70,6 +70,7 @@ typedef struct _MetaWindowActorPrivate gint destroy_in_progress; guint freeze_count; + guint screen_cast_usage_count; guint visible : 1; guint disposed : 1; @@ -1392,6 +1393,26 @@ meta_window_actor_has_damage (MetaScreenCastWindow *screen_cast_window) return clutter_actor_has_damage (CLUTTER_ACTOR (screen_cast_window)); } +static void +meta_window_actor_inc_screen_cast_usage (MetaScreenCastWindow *screen_cast_window) +{ + MetaWindowActor *window_actor = META_WINDOW_ACTOR (screen_cast_window); + MetaWindowActorPrivate *priv = + meta_window_actor_get_instance_private (window_actor); + + priv->screen_cast_usage_count++; +} + +static void +meta_window_actor_dec_screen_cast_usage (MetaScreenCastWindow *screen_cast_window) +{ + MetaWindowActor *window_actor = META_WINDOW_ACTOR (screen_cast_window); + MetaWindowActorPrivate *priv = + meta_window_actor_get_instance_private (window_actor); + + priv->screen_cast_usage_count--; +} + static void screen_cast_window_iface_init (MetaScreenCastWindowInterface *iface) { @@ -1401,6 +1422,17 @@ screen_cast_window_iface_init (MetaScreenCastWindowInterface *iface) iface->capture_into = meta_window_actor_capture_into; iface->blit_to_framebuffer = meta_window_actor_blit_to_framebuffer; iface->has_damage = meta_window_actor_has_damage; + iface->inc_usage = meta_window_actor_inc_screen_cast_usage; + iface->dec_usage = meta_window_actor_dec_screen_cast_usage; +} + +gboolean +meta_window_actor_is_streaming (MetaWindowActor *window_actor) +{ + MetaWindowActorPrivate *priv = + meta_window_actor_get_instance_private (window_actor); + + return priv->screen_cast_usage_count > 0; } MetaWindowActor * diff --git a/src/core/window-private.h b/src/core/window-private.h index 2f3e1e6d4..188b21468 100644 --- a/src/core/window-private.h +++ b/src/core/window-private.h @@ -888,8 +888,6 @@ void meta_window_show_close_dialog (MetaWindow *window); void meta_window_hide_close_dialog (MetaWindow *window); void meta_window_ensure_close_dialog_timeout (MetaWindow *window); -gboolean meta_window_has_pointer (MetaWindow *window); - void meta_window_emit_size_changed (MetaWindow *window); MetaPlacementRule *meta_window_get_placement_rule (MetaWindow *window); diff --git a/src/meta/window.h b/src/meta/window.h index d5d07a061..d4ba4966b 100644 --- a/src/meta/window.h +++ b/src/meta/window.h @@ -453,4 +453,7 @@ uint64_t meta_window_get_id (MetaWindow *window); META_EXPORT MetaWindowClientType meta_window_get_client_type (MetaWindow *window); +META_EXPORT +gboolean meta_window_has_pointer (MetaWindow *window); + #endif diff --git a/src/wayland/meta-wayland-actor-surface.c b/src/wayland/meta-wayland-actor-surface.c index 2b76d943a..ca4b0d7c8 100644 --- a/src/wayland/meta-wayland-actor-surface.c +++ b/src/wayland/meta-wayland-actor-surface.c @@ -300,19 +300,14 @@ meta_wayland_actor_surface_apply_state (MetaWaylandSurfaceRole *surface_role, MetaWaylandActorSurfacePrivate *priv = meta_wayland_actor_surface_get_instance_private (actor_surface); - if (!wl_list_empty (&pending->frame_callback_list) && - priv->actor && - !meta_surface_actor_is_obscured (priv->actor)) + if (priv->actor && !wl_list_empty (&pending->frame_callback_list)) { - GList *l; + ClutterStage *stage; - for (l = clutter_actor_peek_stage_views (CLUTTER_ACTOR (priv->actor)); l; - l = l->next) - { - ClutterStageView *view = l->data; - - clutter_stage_view_schedule_update (view); - } + stage = + CLUTTER_STAGE (clutter_actor_get_stage (CLUTTER_ACTOR (priv->actor))); + if (stage) + clutter_stage_schedule_update (stage); } meta_wayland_actor_surface_queue_frame_callbacks (actor_surface, pending); diff --git a/src/wayland/meta-wayland-outputs.c b/src/wayland/meta-wayland-outputs.c index bdce99c6c..3c0861622 100644 --- a/src/wayland/meta-wayland-outputs.c +++ b/src/wayland/meta-wayland-outputs.c @@ -299,7 +299,12 @@ bind_output (struct wl_client *client, monitor = wayland_output->monitor; if (!monitor) - return; + { + wl_resource_set_implementation (resource, + &meta_wl_output_interface, + NULL, NULL); + return; + } wayland_output->resources = g_list_prepend (wayland_output->resources, resource);