From 47a67252078ba5c78ec5e17dae5e32bf91c8da08 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jonas=20=C3=85dahl?= Date: Wed, 27 Jan 2021 23:16:05 +0100 Subject: [PATCH] monitor: Unset output monitor when disposing When rebuilding the monitors (e.g. during hotplug), make sure to detach the disposed monitors from any outputs before creating the new monitors. While this isn't currently needed, as outputs are too being recreated, with the to be introduced virtual outputs that are created for virtual monitors, this is not always the case anymore, as these virtual outputs are not regenerated each time anything changes. Prepare for this by making sure that cleaning up disposed monitors detach themself properly from the outputs, so new ones can attach themself to outputs without running into conflicts. Part-of: --- src/backends/meta-monitor-manager.c | 9 ++++++++- src/backends/meta-monitor.c | 1 + src/backends/meta-output.c | 10 ++++++++++ src/backends/meta-output.h | 2 ++ 4 files changed, 21 insertions(+), 1 deletion(-) diff --git a/src/backends/meta-monitor-manager.c b/src/backends/meta-monitor-manager.c index 620b60d0a..8744d729e 100644 --- a/src/backends/meta-monitor-manager.c +++ b/src/backends/meta-monitor-manager.c @@ -2843,6 +2843,13 @@ meta_monitor_manager_get_power_save_mode (MetaMonitorManager *manager) return priv->power_save_mode; } +static void +destroy_monitor (MetaMonitor *monitor) +{ + g_object_run_dispose (G_OBJECT (monitor)); + g_object_unref (monitor); +} + static void rebuild_monitors (MetaMonitorManager *manager) { @@ -2851,7 +2858,7 @@ rebuild_monitors (MetaMonitorManager *manager) if (manager->monitors) { - g_list_free_full (manager->monitors, g_object_unref); + g_list_free_full (manager->monitors, (GDestroyNotify) destroy_monitor); manager->monitors = NULL; } diff --git a/src/backends/meta-monitor.c b/src/backends/meta-monitor.c index 8f147b70c..e02f8ed45 100644 --- a/src/backends/meta-monitor.c +++ b/src/backends/meta-monitor.c @@ -486,6 +486,7 @@ meta_monitor_dispose (GObject *object) if (priv->outputs) { + g_list_foreach (priv->outputs, (GFunc) meta_output_unset_monitor, NULL); g_list_free_full (priv->outputs, g_object_unref); priv->outputs = NULL; } diff --git a/src/backends/meta-output.c b/src/backends/meta-output.c index c903110a6..432697d6d 100644 --- a/src/backends/meta-output.c +++ b/src/backends/meta-output.c @@ -135,6 +135,16 @@ meta_output_set_monitor (MetaOutput *output, priv->monitor = monitor; } +void +meta_output_unset_monitor (MetaOutput *output) +{ + MetaOutputPrivate *priv = meta_output_get_instance_private (output); + + g_warn_if_fail (priv->monitor); + + priv->monitor = NULL; +} + const char * meta_output_get_name (MetaOutput *output) { diff --git a/src/backends/meta-output.h b/src/backends/meta-output.h index bed199662..3c4431c4d 100644 --- a/src/backends/meta-output.h +++ b/src/backends/meta-output.h @@ -145,6 +145,8 @@ MetaMonitor * meta_output_get_monitor (MetaOutput *output); void meta_output_set_monitor (MetaOutput *output, MetaMonitor *monitor); +void meta_output_unset_monitor (MetaOutput *output); + const char * meta_output_get_name (MetaOutput *output); META_EXPORT_TEST