[gtk/wip/chergert/gdk-macos-for-master: 11/11] macos: plug leak of application windows




commit 004f0a65968b79917982a45184b50cb1ca34fbc8
Author: Christian Hergert <chergert redhat com>
Date:   Wed Dec 2 19:42:07 2020 -0800

    macos: plug leak of application windows
    
    This ensures that we don't leak window references inside the action muxer.
    Otherwise, we risk not disposing the windows upon gtk_window_destroy()
    and blocking the main loop from quitting.
    
    Fixes #3419

 gtk/gtkapplication-quartz.c | 26 ++++++++++++++++++++++++++
 1 file changed, 26 insertions(+)
---
diff --git a/gtk/gtkapplication-quartz.c b/gtk/gtkapplication-quartz.c
index a744ebd89e..5472c20641 100644
--- a/gtk/gtkapplication-quartz.c
+++ b/gtk/gtkapplication-quartz.c
@@ -250,12 +250,38 @@ gtk_application_impl_quartz_shutdown (GtkApplicationImpl *impl)
   quartz->inhibitors = NULL;
 }
 
+static void
+on_window_unmap_cb (GtkApplicationImpl *impl,
+                    GtkWindow          *window)
+{
+  GtkApplicationImplQuartz *quartz = (GtkApplicationImplQuartz *) impl;
+
+  if ((GActionGroup *)window == gtk_action_muxer_get_group (quartz->muxer, "win"))
+    gtk_action_muxer_remove (quartz->muxer, "win");
+}
+
 static void
 gtk_application_impl_quartz_active_window_changed (GtkApplicationImpl *impl,
                                                    GtkWindow          *window)
 {
   GtkApplicationImplQuartz *quartz = (GtkApplicationImplQuartz *) impl;
 
+  /* Track unmapping of the window so we can clear the "win" field.
+   * Without this, we might hold on to a reference of the window
+   * preventing it from getting disposed.
+   */
+  if (window != NULL && !g_object_get_data (G_OBJECT (window), "quartz-muxer-umap"))
+    {
+      gulong handler_id = g_signal_connect_object (window,
+                                                   "unmap",
+                                                   G_CALLBACK (on_window_unmap_cb),
+                                                   impl,
+                                                   G_CONNECT_SWAPPED);
+      g_object_set_data (G_OBJECT (window),
+                         "quartz-muxer-unmap",
+                         GSIZE_TO_POINTER (handler_id));
+    }
+
   gtk_action_muxer_remove (quartz->muxer, "win");
 
   if (G_IS_ACTION_GROUP (window))


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]