diff options
-rw-r--r-- | configure.ac | 2 | ||||
-rw-r--r-- | debian/changelog | 6 | ||||
-rw-r--r-- | debian/liblightdm-gobject-1-0.symbols | 1 | ||||
-rw-r--r-- | liblightdm-gobject/greeter.c | 99 | ||||
-rw-r--r-- | liblightdm-gobject/lightdm/greeter.h | 6 | ||||
-rw-r--r-- | liblightdm-qt/QLightDM/greeter.h | 3 | ||||
-rw-r--r-- | liblightdm-qt/greeter.cpp | 24 | ||||
-rw-r--r-- | src/greeter.c | 53 | ||||
-rw-r--r-- | src/greeter.h | 8 | ||||
-rw-r--r-- | src/seat.c | 194 | ||||
-rw-r--r-- | tests/src/test-gobject-greeter.c | 54 | ||||
-rwxr-xr-x | tests/src/test-python-greeter | 46 | ||||
-rw-r--r-- | tests/src/test-qt-greeter.cpp | 52 | ||||
-rw-r--r-- | tests/src/test-qt-greeter.h | 4 |
14 files changed, 447 insertions, 105 deletions
diff --git a/configure.ac b/configure.ac index 9ded6cad..0de08ad3 100644 --- a/configure.ac +++ b/configure.ac @@ -1,6 +1,6 @@ dnl Process this file with autoconf to produce a configure script. -AC_INIT(lightdm, 1.10.0) +AC_INIT(lightdm, 1.10.1) AC_CONFIG_MACRO_DIR(m4) AC_CONFIG_HEADER(config.h) AM_INIT_AUTOMAKE([1.11 no-dist-gzip dist-xz foreign]) diff --git a/debian/changelog b/debian/changelog index f8c1d2e0..c558ccf9 100644 --- a/debian/changelog +++ b/debian/changelog @@ -1,3 +1,9 @@ +lightdm (1.10.1-0ubuntu1) UNRELEASED; urgency=medium + + * Add lightdm_greeter_set_resettable + + -- Michael Terry <mterry@ubuntu.com> Wed, 23 Apr 2014 19:21:30 -0400 + lightdm (1.10.0-0ubuntu3) trusty; urgency=medium * debian/patches/06_apparmor_chromium_updates.patch: allow oxide based diff --git a/debian/liblightdm-gobject-1-0.symbols b/debian/liblightdm-gobject-1-0.symbols index e9afdffa..770e824e 100644 --- a/debian/liblightdm-gobject-1-0.symbols +++ b/debian/liblightdm-gobject-1-0.symbols @@ -37,6 +37,7 @@ liblightdm-gobject-1.so.0 liblightdm-gobject-1-0 #MINVER# lightdm_greeter_new@Base 0.9.2 lightdm_greeter_respond@Base 0.9.2 lightdm_greeter_set_language@Base 0.9.8 + lightdm_greeter_set_resettable@Base 1.10.1 lightdm_greeter_start_session_sync@Base 0.9.2 lightdm_hibernate@Base 0.9.2 lightdm_language_get_code@Base 0.9.2 diff --git a/liblightdm-gobject/greeter.c b/liblightdm-gobject/greeter.c index c02f73ef..2f28464b 100644 --- a/liblightdm-gobject/greeter.c +++ b/liblightdm-gobject/greeter.c @@ -39,6 +39,8 @@ enum { SHOW_MESSAGE, AUTHENTICATION_COMPLETE, AUTOLOGIN_TIMER_EXPIRED, + IDLE, + RESET, LAST_SIGNAL }; static guint signals[LAST_SIGNAL] = { 0 }; @@ -83,6 +85,7 @@ typedef enum GREETER_MESSAGE_SET_LANGUAGE, GREETER_MESSAGE_AUTHENTICATE_REMOTE, GREETER_MESSAGE_ENSURE_SHARED_DIR, + GREETER_MESSAGE_SET_RESETTABLE, } GreeterMessage; /* Messages from the server to the greeter */ @@ -93,6 +96,8 @@ typedef enum SERVER_MESSAGE_END_AUTHENTICATION, SERVER_MESSAGE_SESSION_RESULT, SERVER_MESSAGE_SHARED_DIR_RESULT, + SERVER_MESSAGE_IDLE, + SERVER_MESSAGE_RESET, } ServerMessage; /** @@ -381,6 +386,31 @@ handle_end_authentication (LightDMGreeter *greeter, guint8 *message, gsize messa g_signal_emit (G_OBJECT (greeter), signals[AUTHENTICATION_COMPLETE], 0); } +static void +handle_reset (LightDMGreeter *greeter, guint8 *message, gsize message_length, gsize *offset) +{ + LightDMGreeterPrivate *priv = GET_PRIVATE (greeter); + GString *hint_string; + + g_hash_table_remove_all (priv->hints); + + hint_string = g_string_new (""); + while (*offset < message_length) + { + gchar *name, *value; + + name = read_string (message, message_length, offset); + value = read_string (message, message_length, offset); + g_hash_table_insert (priv->hints, name, value); + g_string_append_printf (hint_string, " %s=%s", name, value); + } + + g_debug ("Reset%s", hint_string->str); + g_string_free (hint_string, TRUE); + + g_signal_emit (G_OBJECT (greeter), signals[RESET], 0); +} + static guint8 * read_message (LightDMGreeter *greeter, gsize *length, gboolean block) { @@ -460,6 +490,12 @@ from_server_cb (GIOChannel *source, GIOCondition condition, gpointer data) case SERVER_MESSAGE_END_AUTHENTICATION: handle_end_authentication (greeter, message, message_length, &offset); break; + case SERVER_MESSAGE_IDLE: + g_signal_emit (G_OBJECT (greeter), signals[IDLE], 0); + break; + case SERVER_MESSAGE_RESET: + handle_reset (greeter, message, message_length, &offset); + break; default: g_warning ("Unknown message from server: %d", id); break; @@ -1057,6 +1093,31 @@ lightdm_greeter_set_language (LightDMGreeter *greeter, const gchar *language) } /** + * lightdm_greeter_set_resettable: + * @greeter: A #LightDMGreeter + * @resettable: Whether the greeter wants to be reset instead of killed after the user logs in + * + * Set whether the greeter will be reset instead of killed after the user logs in. + **/ +void +lightdm_greeter_set_resettable (LightDMGreeter *greeter, gboolean resettable) +{ + LightDMGreeterPrivate *priv; + guint8 message[MAX_MESSAGE_LENGTH]; + gsize offset = 0; + + g_return_if_fail (LIGHTDM_IS_GREETER (greeter)); + + priv = GET_PRIVATE (greeter); + + g_return_if_fail (priv->connected); + + write_header (message, MAX_MESSAGE_LENGTH, GREETER_MESSAGE_SET_RESETTABLE, int_length (), &offset); + write_int (message, MAX_MESSAGE_LENGTH, resettable ? 1 : 0, &offset); + write_message (greeter, message, offset); +} + +/** * lightdm_greeter_start_session_sync: * @greeter: A #LightDMGreeter * @session: (allow-none): The session to log into or #NULL to use the default. @@ -1460,4 +1521,42 @@ lightdm_greeter_class_init (LightDMGreeterClass *klass) NULL, NULL, NULL, G_TYPE_NONE, 0); + + /** + * LightDMGreeter::idle: + * @greeter: A #LightDMGreeter + * + * The ::idle signal gets emitted when the user has logged in and the + * greeter is no longer needed. + * + * This signal only matters if the greeter has marked itself as + * resettable using lightdm_greeter_set_resettable(). + **/ + signals[IDLE] = + g_signal_new ("idle", + G_TYPE_FROM_CLASS (klass), + G_SIGNAL_RUN_LAST, + G_STRUCT_OFFSET (LightDMGreeterClass, idle), + NULL, NULL, + NULL, + G_TYPE_NONE, 0); + + /** + * LightDMGreeter::reset: + * @greeter: A #LightDMGreeter + * + * The ::reset signal gets emitted when the user is returning to a greeter + * that was previously marked idle. + * + * This signal only matters if the greeter has marked itself as + * resettable using lightdm_greeter_set_resettable(). + **/ + signals[RESET] = + g_signal_new ("reset", + G_TYPE_FROM_CLASS (klass), + G_SIGNAL_RUN_LAST, + G_STRUCT_OFFSET (LightDMGreeterClass, reset), + NULL, NULL, + NULL, + G_TYPE_NONE, 0); } diff --git a/liblightdm-gobject/lightdm/greeter.h b/liblightdm-gobject/lightdm/greeter.h index ca1b26fb..438fb755 100644 --- a/liblightdm-gobject/lightdm/greeter.h +++ b/liblightdm-gobject/lightdm/greeter.h @@ -57,14 +57,14 @@ typedef struct void (*show_prompt)(LightDMGreeter *greeter, const gchar *text, LightDMPromptType type); void (*authentication_complete)(LightDMGreeter *greeter); void (*autologin_timer_expired)(LightDMGreeter *greeter); + void (*idle)(LightDMGreeter *greeter); + void (*reset)(LightDMGreeter *greeter); /* Reserved */ void (*reserved1) (void); void (*reserved2) (void); void (*reserved3) (void); void (*reserved4) (void); - void (*reserved5) (void); - void (*reserved6) (void); } LightDMGreeterClass; GType lightdm_greeter_get_type (void); @@ -119,6 +119,8 @@ const gchar *lightdm_greeter_get_authentication_user (LightDMGreeter *greeter); void lightdm_greeter_set_language (LightDMGreeter *greeter, const gchar *language); +void lightdm_greeter_set_resettable (LightDMGreeter *greeter, gboolean resettable); + gboolean lightdm_greeter_start_session_sync (LightDMGreeter *greeter, const gchar *session, GError **error); gchar *lightdm_greeter_ensure_shared_data_dir_sync (LightDMGreeter *greeter, const gchar *username); diff --git a/liblightdm-qt/QLightDM/greeter.h b/liblightdm-qt/QLightDM/greeter.h index 82916d00..8abf5e92 100644 --- a/liblightdm-qt/QLightDM/greeter.h +++ b/liblightdm-qt/QLightDM/greeter.h @@ -79,6 +79,7 @@ public Q_SLOTS: void respond(const QString &response); void cancelAuthentication(); void setLanguage (const QString &language); + void setResettable (bool resettable); bool startSessionSync(const QString &session=QString()); QString ensureSharedDataDirSync(const QString &username); @@ -87,6 +88,8 @@ Q_SIGNALS: void showPrompt(QString text, QLightDM::Greeter::PromptType type); void authenticationComplete(); void autologinTimerExpired(); + void idle(); + void reset(); private: GreeterPrivate *d_ptr; diff --git a/liblightdm-qt/greeter.cpp b/liblightdm-qt/greeter.cpp index 12e2db4c..406a6321 100644 --- a/liblightdm-qt/greeter.cpp +++ b/liblightdm-qt/greeter.cpp @@ -33,6 +33,8 @@ protected: static void cb_showMessage(LightDMGreeter *greeter, const gchar *text, LightDMMessageType type, gpointer data); static void cb_authenticationComplete(LightDMGreeter *greeter, gpointer data); static void cb_autoLoginExpired(LightDMGreeter *greeter, gpointer data); + static void cb_idle(LightDMGreeter *greeter, gpointer data); + static void cb_reset(LightDMGreeter *greeter, gpointer data); private: Q_DECLARE_PUBLIC(Greeter) @@ -50,6 +52,8 @@ GreeterPrivate::GreeterPrivate(Greeter *parent) : g_signal_connect (ldmGreeter, "show-message", G_CALLBACK (cb_showMessage), this); g_signal_connect (ldmGreeter, "authentication-complete", G_CALLBACK (cb_authenticationComplete), this); g_signal_connect (ldmGreeter, "autologin-timer-expired", G_CALLBACK (cb_autoLoginExpired), this); + g_signal_connect (ldmGreeter, "idle", G_CALLBACK (cb_idle), this); + g_signal_connect (ldmGreeter, "reset", G_CALLBACK (cb_reset), this); } void GreeterPrivate::cb_showPrompt(LightDMGreeter *greeter, const gchar *text, LightDMPromptType type, gpointer data) @@ -88,6 +92,20 @@ void GreeterPrivate::cb_autoLoginExpired(LightDMGreeter *greeter, gpointer data) Q_EMIT that->q_func()->autologinTimerExpired(); } +void GreeterPrivate::cb_idle(LightDMGreeter *greeter, gpointer data) +{ + Q_UNUSED(greeter); + GreeterPrivate *that = static_cast<GreeterPrivate*>(data); + Q_EMIT that->q_func()->idle(); +} + +void GreeterPrivate::cb_reset(LightDMGreeter *greeter, gpointer data) +{ + Q_UNUSED(greeter); + GreeterPrivate *that = static_cast<GreeterPrivate*>(data); + Q_EMIT that->q_func()->reset(); +} + Greeter::Greeter(QObject *parent) : QObject(parent), d_ptr(new GreeterPrivate(this)) @@ -166,6 +184,12 @@ void Greeter::setLanguage (const QString &language) lightdm_greeter_set_language(d->ldmGreeter, language.toLocal8Bit().constData()); } +void Greeter::setResettable (bool resettable) +{ + Q_D(Greeter); + lightdm_greeter_set_resettable(d->ldmGreeter, resettable); +} + bool Greeter::startSessionSync(const QString &session) { Q_D(Greeter); diff --git a/src/greeter.c b/src/greeter.c index 9c68556a..7643fb53 100644 --- a/src/greeter.c +++ b/src/greeter.c @@ -63,6 +63,9 @@ struct GreeterPrivate /* PAM session being constructed by the greeter */ Session *authentication_session; + /* TRUE if a the greeter can handle a reset; else we will just kill it instead */ + gboolean resettable; + /* TRUE if a user has been authenticated and the session requested to start */ gboolean start_session; @@ -92,6 +95,7 @@ typedef enum GREETER_MESSAGE_SET_LANGUAGE, GREETER_MESSAGE_AUTHENTICATE_REMOTE, GREETER_MESSAGE_ENSURE_SHARED_DIR, + GREETER_MESSAGE_SET_RESETTABLE, } GreeterMessage; /* Messages from the server to the greeter */ @@ -102,6 +106,8 @@ typedef enum SERVER_MESSAGE_END_AUTHENTICATION, SERVER_MESSAGE_SESSION_RESULT, SERVER_MESSAGE_SHARED_DIR_RESULT, + SERVER_MESSAGE_IDLE, + SERVER_MESSAGE_RESET, } ServerMessage; static gboolean read_cb (GIOChannel *source, GIOCondition condition, gpointer data); @@ -128,6 +134,12 @@ greeter_set_allow_guest (Greeter *greeter, gboolean allow_guest) } void +greeter_clear_hints (Greeter *greeter) +{ + g_hash_table_remove_all (greeter->priv->hints); +} + +void greeter_set_hint (Greeter *greeter, const gchar *name, const gchar *value) { g_hash_table_insert (greeter->priv->hints, g_strdup (name), g_strdup (value)); @@ -315,6 +327,37 @@ send_end_authentication (Greeter *greeter, guint32 sequence_number, const gchar write_message (greeter, message, offset); } +void greeter_idle (Greeter *greeter) +{ + guint8 message[MAX_MESSAGE_LENGTH]; + gsize offset = 0; + + write_header (message, MAX_MESSAGE_LENGTH, SERVER_MESSAGE_IDLE, 0, &offset); + write_message (greeter, message, offset); +} + +void greeter_reset (Greeter *greeter) +{ + guint8 message[MAX_MESSAGE_LENGTH]; + gsize offset = 0; + guint32 length = 0; + GHashTableIter iter; + gpointer key, value; + + g_hash_table_iter_init (&iter, greeter->priv->hints); + while (g_hash_table_iter_next (&iter, &key, &value)) + length += string_length (key) + string_length (value); + + write_header (message, MAX_MESSAGE_LENGTH, SERVER_MESSAGE_RESET, length, &offset); + g_hash_table_iter_init (&iter, greeter->priv->hints); + while (g_hash_table_iter_next (&iter, &key, &value)) + { + write_string (message, MAX_MESSAGE_LENGTH, key, &offset); + write_string (message, MAX_MESSAGE_LENGTH, value, &offset); + } + write_message (greeter, message, offset); +} + static void authentication_complete_cb (Session *session, Greeter *greeter) { @@ -837,6 +880,9 @@ read_cb (GIOChannel *source, GIOCondition condition, gpointer data) handle_ensure_shared_dir (greeter, username); g_free (username); break; + case GREETER_MESSAGE_SET_RESETTABLE: + greeter->priv->resettable = read_int (greeter, &offset); + break; default: l_warning (greeter, "Unknown message from greeter: %d", id); break; @@ -862,6 +908,13 @@ greeter_get_authentication_session (Greeter *greeter) } gboolean +greeter_get_resettable (Greeter *greeter) +{ + g_return_val_if_fail (greeter != NULL, FALSE); + return greeter->priv->resettable; +} + +gboolean greeter_get_start_session (Greeter *greeter) { g_return_val_if_fail (greeter != NULL, FALSE); diff --git a/src/greeter.h b/src/greeter.h index 5fae00e4..3aa126d6 100644 --- a/src/greeter.h +++ b/src/greeter.h @@ -46,14 +46,22 @@ void greeter_set_pam_services (Greeter *greeter, const gchar *pam_service, const void greeter_set_allow_guest (Greeter *greeter, gboolean allow_guest); +void greeter_clear_hints (Greeter *greeter); + void greeter_set_hint (Greeter *greeter, const gchar *name, const gchar *value); +void greeter_idle (Greeter *greeter); + +void greeter_reset (Greeter *greeter); + gboolean greeter_get_guest_authenticated (Greeter *greeter); Session *greeter_get_authentication_session (Greeter *greeter); gboolean greeter_get_start_session (Greeter *greeter); +gboolean greeter_get_resettable (Greeter *greeter); + const gchar *greeter_get_active_username (Greeter *greeter); G_END_DECLS @@ -220,8 +220,17 @@ seat_set_active_session (Seat *seat, Session *session) if (IS_GREETER (s)) { - l_debug (seat, "Stopping greeter"); - session_stop (s); + Greeter *greeter = GREETER (s); + if (greeter_get_resettable (greeter)) + { + l_debug (seat, "Idling greeter"); + greeter_idle (greeter); + } + else + { + l_debug (seat, "Stopping greeter"); + session_stop (s); + } } } @@ -430,36 +439,84 @@ can_share_display_server (Seat *seat, DisplayServer *display_server) return seat->priv->share_display_server && display_server_get_can_share (display_server); } +static Greeter * +find_greeter_session (Seat *seat) +{ + GList *link; + + for (link = seat->priv->sessions; link; link = link->next) + { + Session *session = link->data; + if (!session_get_is_stopping (session) && IS_GREETER (session)) + return GREETER (session); + } + + return NULL; +} + +static void +reset_greeter_hints (Seat *seat, Greeter *greeter_session) +{ + greeter_clear_hints (greeter_session); + greeter_set_hint (greeter_session, "default-session", seat_get_string_property (seat, "user-session")); + greeter_set_hint (greeter_session, "hide-users", seat_get_boolean_property (seat, "greeter-hide-users") ? "true" : "false"); + greeter_set_hint (greeter_session, "show-manual-login", seat_get_boolean_property (seat, "greeter-show-manual-login") ? "true" : "false"); + greeter_set_hint (greeter_session, "show-remote-login", seat_get_boolean_property (seat, "greeter-show-remote-login") ? "true" : "false"); + greeter_set_hint (greeter_session, "has-guest-account", seat_get_allow_guest (seat) && seat_get_boolean_property (seat, "greeter-allow-guest") ? "true" : "false"); +} + static void switch_to_greeter_from_failed_session (Seat *seat, Session *session) { Greeter *greeter_session; + gboolean existing = FALSE; + + /* Switch to greeter if one open */ + greeter_session = find_greeter_session (seat); + if (greeter_session) + { + l_debug (seat, "Switching to existing greeter"); + reset_greeter_hints (seat, greeter_session); + existing = TRUE; + } + else + { + greeter_session = create_greeter_session (seat); + } - greeter_session = create_greeter_session (seat); if (session_get_is_guest (session)) greeter_set_hint (greeter_session, "select-guest", "true"); else greeter_set_hint (greeter_session, "select-user", session_get_username (session)); - if (seat->priv->session_to_activate) - g_object_unref (seat->priv->session_to_activate); - seat->priv->session_to_activate = g_object_ref (greeter_session); - if (can_share_display_server (seat, session_get_display_server (session))) - session_set_display_server (SESSION (greeter_session), session_get_display_server (session)); + if (existing) + { + greeter_reset (greeter_session); + seat_set_active_session (seat, SESSION (greeter_session)); + } else { - DisplayServer *display_server; + if (seat->priv->session_to_activate) + g_object_unref (seat->priv->session_to_activate); + seat->priv->session_to_activate = g_object_ref (greeter_session); - display_server = create_display_server (seat, session_get_session_type (session)); - session_set_display_server (session, display_server); - if (!display_server_start (display_server)) + if (can_share_display_server (seat, session_get_display_server (session))) + session_set_display_server (SESSION (greeter_session), session_get_display_server (session)); + else { - l_debug (seat, "Failed to start display server for greeter"); - seat_stop (seat); + DisplayServer *display_server; + + display_server = create_display_server (seat, session_get_session_type (session)); + session_set_display_server (session, display_server); + if (!display_server_start (display_server)) + { + l_debug (seat, "Failed to start display server for greeter"); + seat_stop (seat); + } } - } - start_session (seat, SESSION (greeter_session)); + start_session (seat, SESSION (greeter_session)); + } /* Stop failed session */ session_stop (session); @@ -1160,12 +1217,8 @@ create_greeter_session (Seat *seat) g_signal_connect (greeter_session, "start-session", G_CALLBACK (greeter_start_session_cb), seat); /* Set hints to greeter */ - greeter_set_hint (greeter_session, "default-session", seat_get_string_property (seat, "user-session")); greeter_set_allow_guest (greeter_session, seat_get_allow_guest (seat)); - greeter_set_hint (greeter_session, "hide-users", seat_get_boolean_property (seat, "greeter-hide-users") ? "true" : "false"); - greeter_set_hint (greeter_session, "show-manual-login", seat_get_boolean_property (seat, "greeter-show-manual-login") ? "true" : "false"); - greeter_set_hint (greeter_session, "show-remote-login", seat_get_boolean_property (seat, "greeter-show-remote-login") ? "true" : "false"); - greeter_set_hint (greeter_session, "has-guest-account", seat_get_allow_guest (seat) && seat_get_boolean_property (seat, "greeter-allow-guest") ? "true" : "false"); + reset_greeter_hints (seat, greeter_session); g_object_unref (session_config); @@ -1248,21 +1301,6 @@ create_display_server (Seat *seat, const gchar *session_type) return display_server; } -static Greeter * -find_greeter_session (Seat *seat) -{ - GList *link; - - for (link = seat->priv->sessions; link; link = link->next) - { - Session *session = link->data; - if (!session_get_is_stopping (session) && IS_GREETER (session)) - return GREETER (session); - } - - return NULL; -} - gboolean seat_switch_to_greeter (Seat *seat) { @@ -1274,7 +1312,7 @@ seat_switch_to_greeter (Seat *seat) if (!seat->priv->can_switch) return FALSE; - /* Switch to greeter if one open (shouldn't be though) */ + /* Switch to greeter if one open */ greeter_session = find_greeter_session (seat); if (greeter_session) { @@ -1304,6 +1342,7 @@ switch_authentication_complete_cb (Session *session, Seat *seat) { Greeter *greeter_session; DisplayServer *display_server; + gboolean existing = FALSE; /* If authenticated, then unlock existing session or start new one */ if (session_get_is_authenticated (session)) @@ -1332,22 +1371,44 @@ switch_authentication_complete_cb (Session *session, Seat *seat) return; } - l_debug (seat, "Switching to greeter to authenticate session"); - session_stop (session); - greeter_session = create_greeter_session (seat); + /* See if we already have a greeter up and reuse it if so. Which will only + happen if the greeter marked itself as resettable and we thus didn't + kill it when a user session started */ + greeter_session = find_greeter_session (seat); + if (greeter_session) + { + l_debug (seat, "Switching to existing greeter to authenticate session"); + reset_greeter_hints (seat, greeter_session); + existing = TRUE; + } + else + { + l_debug (seat, "Starting greeter to authenticate session"); + greeter_session = create_greeter_session (seat); + } + if (session_get_is_guest (session)) greeter_set_hint (greeter_session, "select-guest", "true"); else greeter_set_hint (greeter_session, "select-user", session_get_username (session)); - if (seat->priv->session_to_activate) - g_object_unref (seat->priv->session_to_activate); - seat->priv->session_to_activate = g_object_ref (greeter_session); - display_server = create_display_server (seat, session_get_session_type (SESSION (greeter_session))); - session_set_display_server (SESSION (greeter_session), display_server); - display_server_start (display_server); + if (existing) + { + greeter_reset (greeter_session); + seat_set_active_session (seat, SESSION (greeter_session)); + } + else + { + if (seat->priv->session_to_activate) + g_object_unref (seat->priv->session_to_activate); + seat->priv->session_to_activate = g_object_ref (greeter_session); + + display_server = create_display_server (seat, session_get_session_type (SESSION (greeter_session))); + session_set_display_server (SESSION (greeter_session), display_server); + display_server_start (display_server); + } } gboolean @@ -1432,6 +1493,7 @@ seat_lock (Seat *seat, const gchar *username) { Greeter *greeter_session; DisplayServer *display_server; + gboolean existing = FALSE; g_return_val_if_fail (seat != NULL, FALSE); @@ -1440,30 +1502,42 @@ seat_lock (Seat *seat, const gchar *username) l_debug (seat, "Locking"); - /* Switch to greeter if one open (shouldn't be though) */ + /* Switch to greeter if one open (only true if it's a resettable greeter) */ greeter_session = find_greeter_session (seat); if (greeter_session) { l_debug (seat, "Switching to existing greeter"); - seat_set_active_session (seat, SESSION (greeter_session)); - return TRUE; + reset_greeter_hints (seat, greeter_session); + existing = TRUE; + } + else + { + greeter_session = create_greeter_session (seat); + if (!greeter_session) + return FALSE; } - greeter_session = create_greeter_session (seat); - if (!greeter_session) - return FALSE; - - display_server = create_display_server (seat, session_get_session_type (SESSION (greeter_session))); - - if (seat->priv->session_to_activate) - g_object_unref (seat->priv->session_to_activate); - seat->priv->session_to_activate = g_object_ref (greeter_session); greeter_set_hint (greeter_session, "lock-screen", "true"); if (username) greeter_set_hint (greeter_session, "select-user", username); - session_set_display_server (SESSION (greeter_session), display_server); - return display_server_start (display_server); + if (existing) + { + greeter_reset (greeter_session); + seat_set_active_session (seat, SESSION (greeter_session)); + return TRUE; + } + else + { + display_server = create_display_server (seat, session_get_session_type (SESSION (greeter_session))); + + if (seat->priv->session_to_activate) + g_object_unref (seat->priv->session_to_activate); + seat->priv->session_to_activate = g_object_ref (greeter_session); + session_set_display_server (SESSION (greeter_session), display_server); + + return display_server_start (display_server); + } } void diff --git a/tests/src/test-gobject-greeter.c b/tests/src/test-gobject-greeter.c index 233df5c0..0be56c0b 100644 --- a/tests/src/test-gobject-greeter.c +++ b/tests/src/test-gobject-greeter.c @@ -65,6 +65,38 @@ sigterm_cb (gpointer user_data) } static void +print_hints (LightDMGreeter *greeter) +{ + if (lightdm_greeter_get_select_user_hint (greeter)) + status_notify ("%s SELECT-USER-HINT USERNAME=%s", greeter_id, lightdm_greeter_get_select_user_hint (greeter)); + if (lightdm_greeter_get_select_guest_hint (greeter)) + status_notify ("%s SELECT-GUEST-HINT", greeter_id); + if (lightdm_greeter_get_lock_hint (greeter)) + status_notify ("%s LOCK-HINT", greeter_id); + if (!lightdm_greeter_get_has_guest_account_hint (greeter)) + status_notify ("%s HAS-GUEST-ACCOUNT-HINT=FALSE", greeter_id); + if (lightdm_greeter_get_hide_users_hint (greeter)) + status_notify ("%s HIDE-USERS-HINT", greeter_id); + if (lightdm_greeter_get_show_manual_login_hint (greeter)) + status_notify ("%s SHOW-MANUAL-LOGIN-HINT", greeter_id); + if (!lightdm_greeter_get_show_remote_login_hint (greeter)) + status_notify ("%s SHOW-REMOTE-LOGIN-HINT=FALSE", greeter_id); +} + +static void +idle_cb (LightDMGreeter *greeter) +{ + status_notify ("%s IDLE", greeter_id); +} + +static void +reset_cb (LightDMGreeter *greeter) +{ + status_notify ("%s RESET", greeter_id); + print_hints (greeter); +} + +static void user_changed_cb (LightDMUser *user) { status_notify ("%s USER-CHANGED USERNAME=%s", greeter_id, lightdm_user_get_name (user)); @@ -405,6 +437,13 @@ main (int argc, char **argv) g_signal_connect (lightdm_user_list_get_instance (), "user-removed", G_CALLBACK (user_removed_cb), NULL); } + if (g_key_file_get_boolean (config, "test-greeter-config", "resettable", NULL)) + { + lightdm_greeter_set_resettable (greeter, TRUE); + g_signal_connect (greeter, "idle", G_CALLBACK (idle_cb), NULL); + g_signal_connect (greeter, "reset", G_CALLBACK (reset_cb), NULL); + } + status_notify ("%s CONNECT-TO-DAEMON", greeter_id); if (!lightdm_greeter_connect_sync (greeter, NULL)) { @@ -414,20 +453,7 @@ main (int argc, char **argv) status_notify ("%s CONNECTED-TO-DAEMON", greeter_id); - if (lightdm_greeter_get_select_user_hint (greeter)) - status_notify ("%s SELECT-USER-HINT USERNAME=%s", greeter_id, lightdm_greeter_get_select_user_hint (greeter)); - if (lightdm_greeter_get_select_guest_hint (greeter)) - status_notify ("%s SELECT-GUEST-HINT", greeter_id); - if (lightdm_greeter_get_lock_hint (greeter)) - status_notify ("%s LOCK-HINT", greeter_id); - if (!lightdm_greeter_get_has_guest_account_hint (greeter)) - status_notify ("%s HAS-GUEST-ACCOUNT-HINT=FALSE", greeter_id); - if (lightdm_greeter_get_hide_users_hint (greeter)) - status_notify ("%s HIDE-USERS-HINT", greeter_id); - if (lightdm_greeter_get_show_manual_login_hint (greeter)) - status_notify ("%s SHOW-MANUAL-LOGIN-HINT", greeter_id); - if (!lightdm_greeter_get_show_remote_login_hint (greeter)) - status_notify ("%s SHOW-REMOTE-LOGIN-HINT=FALSE", greeter_id); + print_hints (greeter); g_main_loop_run (loop); diff --git a/tests/src/test-python-greeter b/tests/src/test-python-greeter index f8e5c373..2bc80e3e 100755 --- a/tests/src/test-python-greeter +++ b/tests/src/test-python-greeter @@ -185,6 +185,22 @@ def request_cb (channel, condition): return True +def print_hints (greeter): + if greeter.get_select_user_hint () is not None: + status_notify ('%s SELECT-USER-HINT USERNAME=%s' % (greeter_id, greeter.get_select_user_hint ())) + if greeter.get_select_guest_hint (): + status_notify ('%s SELECT-GUEST-HINT' % greeter_id) + if greeter.get_lock_hint (): + status_notify ('%s LOCK-HINT' % greeter_id) + if not greeter.get_has_guest_account_hint (): + status_notify ('%s HAS-GUEST-ACCOUNT-HINT=FALSE' % greeter_id) + if greeter.get_hide_users_hint (): + status_notify ('%s HIDE-USERS-HINT' % greeter_id) + if greeter.get_show_manual_login_hint (): + status_notify ('%s SHOW-MANUAL-LOGIN-HINT' % greeter_id) + if not greeter.get_show_remote_login_hint (): + status_notify ('%s SHOW-REMOTE-LOGIN-HINT=FALSE' % greeter_id) + path = os.getenv ('LIGHTDM_TEST_ROOT') + '/.s' status_socket = socket.socket (socket.AF_UNIX, socket.SOCK_STREAM) status_socket.connect (path) @@ -254,6 +270,21 @@ if log_user_changes: LightDM.UserList.get_instance ().connect ('user-added', user_added_cb) LightDM.UserList.get_instance ().connect ('user-removed', user_removed_cb) +def idle_cb (greeter): + status_notify ('%s IDLE' % (greeter_id)) +def reset_cb (greeter): + status_notify ('%s RESET' % (greeter_id)) + print_hints (greeter) +resettable = False +try: + resettable = config.get_boolean ('test-greeter-config', 'resettable') +except: + pass +if resettable: + LightDM.Greeter.get_instance ().set_resettable (True) + LightDM.Greeter.get_instance ().connect ('idle', idle_cb) + LightDM.Greeter.get_instance ().connect ('reset', reset_cb) + status_notify ('%s CONNECT-TO-DAEMON' % greeter_id) if not greeter.connect_sync (): status_notify ('%s FAIL-CONNECT-DAEMON' % greeter_id) @@ -261,19 +292,6 @@ if not greeter.connect_sync (): status_notify ('%s CONNECTED-TO-DAEMON' % greeter_id) -if greeter.get_select_user_hint () is not None: - status_notify ('%s SELECT-USER-HINT USERNAME=%s' % (greeter_id, greeter.get_select_user_hint ())) -if greeter.get_select_guest_hint (): - status_notify ('%s SELECT-GUEST-HINT' % greeter_id) -if greeter.get_lock_hint (): - status_notify ('%s LOCK-HINT' % greeter_id) -if not greeter.get_has_guest_account_hint (): - status_notify ('%s HAS-GUEST-ACCOUNT-HINT=FALSE' % greeter_id) -if greeter.get_hide_users_hint (): - status_notify ('%s HIDE-USERS-HINT' % greeter_id) -if greeter.get_show_manual_login_hint (): - status_notify ('%s SHOW-MANUAL-LOGIN-HINT' % greeter_id) -if not greeter.get_show_remote_login_hint (): - status_notify ('%s SHOW-REMOTE-LOGIN-HINT=FALSE' % greeter_id) +print_hints (greeter) loop.run () diff --git a/tests/src/test-qt-greeter.cpp b/tests/src/test-qt-greeter.cpp index 29434c7b..bac1fea8 100644 --- a/tests/src/test-qt-greeter.cpp +++ b/tests/src/test-qt-greeter.cpp @@ -54,6 +54,36 @@ void TestGreeter::autologinTimerExpired () status_notify ("%s AUTOLOGIN-TIMER-EXPIRED", greeter_id); } +void TestGreeter::printHints () +{ + if (selectUserHint() != "") + status_notify ("%s SELECT-USER-HINT USERNAME=%s", greeter_id, greeter->selectUserHint ().toAscii ().constData ()); + if (selectGuestHint()) + status_notify ("%s SELECT-GUEST-HINT", greeter_id); + if (lockHint()) + status_notify ("%s LOCK-HINT", greeter_id); + if (!hasGuestAccountHint ()) + status_notify ("%s HAS-GUEST-ACCOUNT-HINT=FALSE", greeter_id); + if (hideUsersHint ()) + status_notify ("%s HIDE-USERS-HINT", greeter_id); + if (showManualLoginHint ()) + status_notify ("%s SHOW-MANUAL-LOGIN-HINT", greeter_id); + if (!showRemoteLoginHint ()) + status_notify ("%s SHOW-REMOTE-LOGIN-HINT=FALSE", greeter_id); + +} + +void TestGreeter::idle () +{ + status_notify ("%s IDLE", greeter_id); +} + +void TestGreeter::reset () +{ + status_notify ("%s RESET", greeter_id); + printHints (); +} + void TestGreeter::userRowsInserted (const QModelIndex & parent, int start, int end) { for (int i = start; i <= end; i++) @@ -268,6 +298,13 @@ main(int argc, char *argv[]) QObject::connect (users_model, SIGNAL(rowsAboutToBeRemoved(const QModelIndex&, int, int)), greeter, SLOT(userRowsRemoved(const QModelIndex&, int, int))); } + if (config->value ("test-greeter-config/resettable", "false") == "true") + { + greeter->setResettable (true); + QObject::connect (greeter, SIGNAL(idle()), greeter, SLOT(idle())); + QObject::connect (greeter, SIGNAL(reset()), greeter, SLOT(reset())); + } + status_notify ("%s CONNECT-TO-DAEMON", greeter_id); if (!greeter->connectSync()) { @@ -277,20 +314,7 @@ main(int argc, char *argv[]) status_notify ("%s CONNECTED-TO-DAEMON", greeter_id); - if (greeter->selectUserHint() != "") - status_notify ("%s SELECT-USER-HINT USERNAME=%s", greeter_id, greeter->selectUserHint ().toAscii ().constData ()); - if (greeter->selectGuestHint()) - status_notify ("%s SELECT-GUEST-HINT", greeter_id); - if (greeter->lockHint()) - status_notify ("%s LOCK-HINT", greeter_id); - if (!greeter->hasGuestAccountHint ()) - status_notify ("%s HAS-GUEST-ACCOUNT-HINT=FALSE", greeter_id); - if (greeter->hideUsersHint ()) - status_notify ("%s HIDE-USERS-HINT", greeter_id); - if (greeter->showManualLoginHint ()) - status_notify ("%s SHOW-MANUAL-LOGIN-HINT", greeter_id); - if (!greeter->showRemoteLoginHint ()) - status_notify ("%s SHOW-REMOTE-LOGIN-HINT=FALSE", greeter_id); + greeter->printHints(); return app->exec(); } diff --git a/tests/src/test-qt-greeter.h b/tests/src/test-qt-greeter.h index 10a10db0..b6ff1270 100644 --- a/tests/src/test-qt-greeter.h +++ b/tests/src/test-qt-greeter.h @@ -8,6 +8,8 @@ class TestGreeter : public QLightDM::Greeter public: TestGreeter (); + void printHints(); + private Q_SLOTS: void showMessage(QString text, QLightDM::Greeter::MessageType type); void showPrompt(QString text, QLightDM::Greeter::PromptType type); @@ -15,4 +17,6 @@ private Q_SLOTS: void autologinTimerExpired(); void userRowsInserted(const QModelIndex & parent, int start, int end); void userRowsRemoved(const QModelIndex & parent, int start, int end); + void idle(); + void reset(); }; |