backend/native: Split up KMS shutdown in two phases
The first phase happens early, which discards pending page flips, meaning the references held by those page flip closures are released. The second phase happens late, after other units depending on the KMS abstraction, have been cleaned up. Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1822>
This commit is contained in:
parent
1af874fca6
commit
22417b8a94
9 changed files with 82 additions and 9 deletions
|
@ -112,11 +112,13 @@ meta_backend_native_dispose (GObject *object)
|
|||
native->udev_device_added_handler_id = 0;
|
||||
}
|
||||
|
||||
g_clear_object (&native->kms);
|
||||
g_clear_object (&native->udev);
|
||||
if (native->kms)
|
||||
meta_kms_prepare_shutdown (native->kms);
|
||||
|
||||
G_OBJECT_CLASS (meta_backend_native_parent_class)->dispose (object);
|
||||
|
||||
g_clear_object (&native->kms);
|
||||
g_clear_object (&native->udev);
|
||||
g_clear_pointer (&native->launcher, meta_launcher_free);
|
||||
}
|
||||
|
||||
|
|
|
@ -1011,15 +1011,24 @@ dispose_page_flip_data (gpointer key,
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
meta_kms_impl_device_atomic_prepare_shutdown (MetaKmsImplDevice *impl_device)
|
||||
{
|
||||
MetaKmsImplDeviceAtomic *impl_device_atomic =
|
||||
META_KMS_IMPL_DEVICE_ATOMIC (impl_device);
|
||||
|
||||
g_hash_table_foreach_remove (impl_device_atomic->page_flip_datas,
|
||||
dispose_page_flip_data,
|
||||
NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
meta_kms_impl_device_atomic_finalize (GObject *object)
|
||||
{
|
||||
MetaKmsImplDeviceAtomic *impl_device_atomic =
|
||||
META_KMS_IMPL_DEVICE_ATOMIC (object);
|
||||
|
||||
g_hash_table_foreach_remove (impl_device_atomic->page_flip_datas,
|
||||
dispose_page_flip_data,
|
||||
NULL);
|
||||
g_assert (g_hash_table_size (impl_device_atomic->page_flip_datas) == 0);
|
||||
|
||||
g_hash_table_unref (impl_device_atomic->page_flip_datas);
|
||||
|
||||
|
@ -1039,10 +1048,7 @@ meta_kms_impl_device_atomic_initable_init (GInitable *initable,
|
|||
static void
|
||||
meta_kms_impl_device_atomic_init (MetaKmsImplDeviceAtomic *impl_device_atomic)
|
||||
{
|
||||
impl_device_atomic->page_flip_datas =
|
||||
g_hash_table_new_full (NULL, NULL,
|
||||
NULL,
|
||||
(GDestroyNotify) meta_kms_page_flip_data_unref);
|
||||
impl_device_atomic->page_flip_datas = g_hash_table_new (NULL, NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -1068,4 +1074,6 @@ meta_kms_impl_device_atomic_class_init (MetaKmsImplDeviceAtomicClass *klass)
|
|||
meta_kms_impl_device_atomic_handle_page_flip_callback;
|
||||
impl_device_class->discard_pending_page_flips =
|
||||
meta_kms_impl_device_atomic_discard_pending_page_flips;
|
||||
impl_device_class->prepare_shutdown =
|
||||
meta_kms_impl_device_atomic_prepare_shutdown;
|
||||
}
|
||||
|
|
|
@ -1488,6 +1488,18 @@ meta_kms_impl_device_simple_discard_pending_page_flips (MetaKmsImplDevice *impl_
|
|||
g_source_destroy);
|
||||
}
|
||||
|
||||
static void
|
||||
meta_kms_impl_device_simple_prepare_shutdown (MetaKmsImplDevice *impl_device)
|
||||
{
|
||||
MetaKmsImplDeviceSimple *impl_device_simple =
|
||||
META_KMS_IMPL_DEVICE_SIMPLE (impl_device);
|
||||
|
||||
g_list_foreach (impl_device_simple->posted_page_flip_datas,
|
||||
(GFunc) meta_kms_page_flip_data_discard_in_impl,
|
||||
impl_device);
|
||||
g_clear_list (&impl_device_simple->posted_page_flip_datas, NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
meta_kms_impl_device_simple_finalize (GObject *object)
|
||||
{
|
||||
|
@ -1506,6 +1518,8 @@ meta_kms_impl_device_simple_finalize (GObject *object)
|
|||
(GFunc) meta_kms_page_flip_data_discard_in_impl,
|
||||
NULL);
|
||||
|
||||
g_assert (!impl_device_simple->posted_page_flip_datas);
|
||||
|
||||
g_clear_pointer (&impl_device_simple->mode_set_fallback_feedback_source,
|
||||
g_source_destroy);
|
||||
g_hash_table_destroy (impl_device_simple->cached_mode_sets);
|
||||
|
@ -1583,4 +1597,6 @@ meta_kms_impl_device_simple_class_init (MetaKmsImplDeviceSimpleClass *klass)
|
|||
meta_kms_impl_device_simple_handle_page_flip_callback;
|
||||
impl_device_class->discard_pending_page_flips =
|
||||
meta_kms_impl_device_simple_discard_pending_page_flips;
|
||||
impl_device_class->prepare_shutdown =
|
||||
meta_kms_impl_device_simple_prepare_shutdown;
|
||||
}
|
||||
|
|
|
@ -836,6 +836,15 @@ meta_kms_impl_device_init_mode_setting (MetaKmsImplDevice *impl_device,
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
void
|
||||
meta_kms_impl_device_prepare_shutdown (MetaKmsImplDevice *impl_device)
|
||||
{
|
||||
MetaKmsImplDeviceClass *klass = META_KMS_IMPL_DEVICE_GET_CLASS (impl_device);
|
||||
|
||||
if (klass->prepare_shutdown)
|
||||
klass->prepare_shutdown (impl_device);
|
||||
}
|
||||
|
||||
static void
|
||||
meta_kms_impl_device_init (MetaKmsImplDevice *impl_device)
|
||||
{
|
||||
|
|
|
@ -68,6 +68,7 @@ struct _MetaKmsImplDeviceClass
|
|||
void (* handle_page_flip_callback) (MetaKmsImplDevice *impl_device,
|
||||
MetaKmsPageFlipData *page_flip_data);
|
||||
void (* discard_pending_page_flips) (MetaKmsImplDevice *impl_device);
|
||||
void (* prepare_shutdown) (MetaKmsImplDevice *impl_device);
|
||||
};
|
||||
|
||||
MetaKmsDevice * meta_kms_impl_device_get_device (MetaKmsImplDevice *impl_device);
|
||||
|
@ -143,4 +144,6 @@ int meta_kms_impl_device_close (MetaKmsImplDevice *impl_device);
|
|||
gboolean meta_kms_impl_device_init_mode_setting (MetaKmsImplDevice *impl_device,
|
||||
GError **error);
|
||||
|
||||
void meta_kms_impl_device_prepare_shutdown (MetaKmsImplDevice *impl_device);
|
||||
|
||||
#endif /* META_KMS_IMPL_DEVICE_H */
|
||||
|
|
|
@ -103,6 +103,21 @@ meta_kms_impl_discard_pending_page_flips (MetaKmsImpl *impl)
|
|||
NULL);
|
||||
}
|
||||
|
||||
void
|
||||
meta_kms_impl_prepare_shutdown (MetaKmsImpl *impl)
|
||||
{
|
||||
MetaKmsImplPrivate *priv = meta_kms_impl_get_instance_private (impl);
|
||||
GList *l;
|
||||
|
||||
for (l = priv->impl_devices; l; l = l->next)
|
||||
{
|
||||
MetaKmsImplDevice *impl_device = l->data;
|
||||
|
||||
meta_kms_impl_device_discard_pending_page_flips (impl_device);
|
||||
meta_kms_impl_device_prepare_shutdown (impl_device);
|
||||
}
|
||||
}
|
||||
|
||||
MetaKmsImpl *
|
||||
meta_kms_impl_new (MetaKms *kms)
|
||||
{
|
||||
|
|
|
@ -42,6 +42,8 @@ void meta_kms_impl_remove_impl_device (MetaKmsImpl *impl,
|
|||
|
||||
void meta_kms_impl_discard_pending_page_flips (MetaKmsImpl *impl);
|
||||
|
||||
void meta_kms_impl_prepare_shutdown (MetaKmsImpl *impl);
|
||||
|
||||
MetaKmsImpl * meta_kms_impl_new (MetaKms *kms);
|
||||
|
||||
#endif /* META_KMS_IMPL_H */
|
||||
|
|
|
@ -662,6 +662,22 @@ meta_kms_new (MetaBackend *backend,
|
|||
return kms;
|
||||
}
|
||||
|
||||
static gpointer
|
||||
prepare_shutdown_in_impl (MetaKmsImpl *impl,
|
||||
gpointer user_data,
|
||||
GError **error)
|
||||
{
|
||||
meta_kms_impl_prepare_shutdown (impl);
|
||||
return GINT_TO_POINTER (TRUE);
|
||||
}
|
||||
|
||||
void
|
||||
meta_kms_prepare_shutdown (MetaKms *kms)
|
||||
{
|
||||
meta_kms_run_impl_task_sync (kms, prepare_shutdown_in_impl, NULL, NULL);
|
||||
flush_callbacks (kms);
|
||||
}
|
||||
|
||||
static void
|
||||
meta_kms_finalize (GObject *object)
|
||||
{
|
||||
|
|
|
@ -63,6 +63,8 @@ MetaKmsDevice * meta_kms_create_device (MetaKms *kms,
|
|||
MetaKmsDeviceFlag flags,
|
||||
GError **error);
|
||||
|
||||
void meta_kms_prepare_shutdown (MetaKms *kms);
|
||||
|
||||
MetaKms * meta_kms_new (MetaBackend *backend,
|
||||
MetaKmsFlags flags,
|
||||
GError **error);
|
||||
|
|
Loading…
Reference in a new issue