[gdm/benzea/wait-seat-graphical: 54/54] local-display-factory: Wait for seats to become graphical
- From: Benjamin Berg <bberg src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gdm/benzea/wait-seat-graphical: 54/54] local-display-factory: Wait for seats to become graphical
- Date: Tue, 9 Feb 2021 15:05:37 +0000 (UTC)
commit 660a3e97d6847dd2801ba0a086852d2835606c12
Author: Benjamin Berg <bberg redhat com>
Date: Tue Feb 9 15:43:05 2021 +0100
local-display-factory: Wait for seats to become graphical
It may happen that seats are not graphical initially because the DRM
device is not ready yet. In that case, ignore the seat and wait for the
CanGraphical property notification in order to add it at that point.
Fixes: #662
daemon/gdm-local-display-factory.c | 59 ++++++++++++++++++++++++++++++++++++++
1 file changed, 59 insertions(+)
---
diff --git a/daemon/gdm-local-display-factory.c b/daemon/gdm-local-display-factory.c
index e7cafeb10..bfb472088 100644
--- a/daemon/gdm-local-display-factory.c
+++ b/daemon/gdm-local-display-factory.c
@@ -62,6 +62,7 @@ struct _GdmLocalDisplayFactory
guint seat_new_id;
guint seat_removed_id;
+ guint seat_prop_changed_id;
#if defined(ENABLE_USER_DISPLAY_SERVER)
unsigned int active_vt;
@@ -610,6 +611,11 @@ on_seat_new (GDBusConnection *connection,
const char *seat;
g_variant_get (parameters, "(&s&o)", &seat, NULL);
+
+ /* We retry adding it if the CanGraphical value changes. */
+ if (!sd_seat_can_graphical (seat))
+ return;
+
create_display (GDM_LOCAL_DISPLAY_FACTORY (user_data), seat, NULL, FALSE);
}
@@ -628,6 +634,44 @@ on_seat_removed (GDBusConnection *connection,
delete_display (GDM_LOCAL_DISPLAY_FACTORY (user_data), seat);
}
+static void
+on_seat_prop_changed (GDBusConnection *connection,
+ const gchar *sender_name,
+ const gchar *object_path,
+ const gchar *interface_name,
+ const gchar *signal_name,
+ GVariant *parameters,
+ gpointer user_data)
+{
+ const gchar *seat = NULL;
+ g_autoptr(GVariant) changed_props = NULL;
+ g_autoptr(GVariant) changed_prop = NULL;
+ g_autofree gchar **invalidated_props = NULL;
+ gboolean changed = FALSE;
+
+ /* Extract seat id, i.e. the last element of the object path. */
+ seat = strrchr (object_path, '/');
+ if (seat == NULL)
+ return;
+ seat += 1;
+
+ g_variant_get (parameters, "(s@a{sv}^a&s)", NULL, &changed_props, &invalidated_props);
+
+ changed_prop = g_variant_lookup_value (changed_props, "CanGraphical", NULL);
+ if (changed_prop)
+ changed = TRUE;
+ if (!changed && g_strv_contains (invalidated_props, "CanGraphical"))
+ changed = TRUE;
+
+ if (!changed)
+ return;
+
+ if (sd_seat_can_graphical (seat))
+ create_display (GDM_LOCAL_DISPLAY_FACTORY (user_data), seat, NULL, FALSE);
+ else
+ delete_display (GDM_LOCAL_DISPLAY_FACTORY (user_data), seat);
+}
+
static gboolean
lookup_by_session_id (const char *id,
GdmDisplay *display,
@@ -866,6 +910,16 @@ gdm_local_display_factory_start_monitor (GdmLocalDisplayFactory *factory)
on_seat_removed,
g_object_ref (factory),
g_object_unref);
+ factory->seat_prop_changed_id = g_dbus_connection_signal_subscribe (factory->connection,
+ "org.freedesktop.login1",
+
"org.freedesktop.DBus.Properties",
+ "PropertiesChanged",
+ NULL,
+ "org.freedesktop.login1.Seat",
+
G_DBUS_SIGNAL_FLAGS_MATCH_ARG0_NAMESPACE,
+ on_seat_prop_changed,
+ g_object_ref (factory),
+ g_object_unref);
#if defined(ENABLE_USER_DISPLAY_SERVER)
io_channel = g_io_channel_new_file ("/sys/class/tty/tty0/active", "r", NULL);
@@ -894,6 +948,11 @@ gdm_local_display_factory_stop_monitor (GdmLocalDisplayFactory *factory)
factory->seat_removed_id);
factory->seat_removed_id = 0;
}
+ if (factory->seat_prop_changed_id) {
+ g_dbus_connection_signal_unsubscribe (factory->connection,
+ factory->seat_prop_changed_id);
+ factory->seat_prop_changed_id = 0;
+ }
#if defined(ENABLE_USER_DISPLAY_SERVER)
if (factory->active_vt_watch_id) {
g_source_remove (factory->active_vt_watch_id);
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]