[gdm/multi-stack: 6/32] Propagate service name to more layers



commit a7d9baab98651d5a36b674c5dd5745bdd980918d
Author: Ray Strode <rstrode redhat com>
Date:   Thu Jan 22 08:52:01 2009 -0500

    Propagate service name to more layers
    
    This is more prep work to get multiple concurrent
    PAM stacks going.

 daemon/gdm-factory-slave.c               |   63 +++--
 daemon/gdm-greeter-server.c              |  120 ++++++--
 daemon/gdm-greeter-server.h              |   17 +-
 daemon/gdm-product-slave.c               |  233 ++++++++++++---
 daemon/gdm-session-direct.c              |  472 +++++++++++++++++-------------
 daemon/gdm-session-private.h             |   22 ++-
 daemon/gdm-session-relay.c               |  122 ++++++--
 daemon/gdm-session-worker.c              |   27 ++
 daemon/gdm-session.c                     |  151 ++++++----
 daemon/gdm-session.h                     |   44 +++-
 daemon/gdm-simple-slave.c                |   70 ++++--
 daemon/test-session.c                    |   22 +-
 gui/simple-greeter/gdm-greeter-client.c  |  188 ++++++++++---
 gui/simple-greeter/gdm-greeter-client.h  |   16 +-
 gui/simple-greeter/gdm-greeter-session.c |   11 +-
 15 files changed, 1125 insertions(+), 453 deletions(-)
---
diff --git a/daemon/gdm-factory-slave.c b/daemon/gdm-factory-slave.c
index d1bb5dd..826612e 100644
--- a/daemon/gdm-factory-slave.c
+++ b/daemon/gdm-factory-slave.c
@@ -144,45 +144,49 @@ on_greeter_session_died (GdmGreeterSession    *greeter,
 
 static void
 on_session_info (GdmSession      *session,
+                 const char      *service_name,
                  const char      *text,
                  GdmFactorySlave *slave)
 {
         g_debug ("GdmFactorySlave: Info: %s", text);
-        gdm_greeter_server_info (slave->priv->greeter_server, text);
+        gdm_greeter_server_info (slave->priv->greeter_server, service_name, text);
 }
 
 static void
 on_session_problem (GdmSession      *session,
+                    const char      *service_name,
                     const char      *text,
                     GdmFactorySlave *slave)
 {
         g_debug ("GdmFactorySlave: Problem: %s", text);
-        gdm_greeter_server_problem (slave->priv->greeter_server, text);
+        gdm_greeter_server_problem (slave->priv->greeter_server, service_name, text);
 }
 
 static void
 on_session_info_query (GdmSession      *session,
+                       const char      *service_name,
                        const char      *text,
                        GdmFactorySlave *slave)
 {
 
         g_debug ("GdmFactorySlave: Info query: %s", text);
-        gdm_greeter_server_info_query (slave->priv->greeter_server, text);
+        gdm_greeter_server_info_query (slave->priv->greeter_server, service_name, text);
 }
 
 static void
 on_session_secret_info_query (GdmSession      *session,
+                              const char      *service_name,
                               const char      *text,
                               GdmFactorySlave *slave)
 {
         g_debug ("GdmFactorySlave: Secret info query: %s", text);
-        gdm_greeter_server_secret_info_query (slave->priv->greeter_server, text);
+        gdm_greeter_server_secret_info_query (slave->priv->greeter_server, service_name, text);
 }
 
 static void
 on_session_conversation_started (GdmSession      *session,
-                                 GdmFactorySlave *slave,
-                                 const char      *service_name)
+                                 const char      *service_name,
+                                 GdmFactorySlave *slave)
 {
         g_debug ("GdmFactorySlave:  session conversation started");
 
@@ -192,17 +196,19 @@ on_session_conversation_started (GdmSession      *session,
 
 static void
 on_session_setup_complete (GdmSession      *session,
+                           const char      *service_name,
                            GdmFactorySlave *slave)
 {
-        gdm_session_authenticate (session);
+        gdm_session_authenticate (session, service_name);
 }
 
 static void
 on_session_setup_failed (GdmSession      *session,
+                         const char      *service_name,
                          const char      *message,
                          GdmFactorySlave *slave)
 {
-        gdm_greeter_server_problem (slave->priv->greeter_server, _("Unable to initialize login system"));
+        gdm_greeter_server_problem (slave->priv->greeter_server, service_name, _("Unable to initialize login system"));
 
         queue_greeter_reset (slave);
 }
@@ -224,23 +230,26 @@ on_session_reset_failed (GdmSession      *session,
 
 static void
 on_session_authenticated (GdmSession      *session,
+                          const char      *service_name,
                           GdmFactorySlave *slave)
 {
-        gdm_session_authorize (session);
+        gdm_session_authorize (session, service_name);
 }
 
 static void
 on_session_authentication_failed (GdmSession      *session,
+                                  const char      *service_name,
                                   const char      *message,
                                   GdmFactorySlave *slave)
 {
-        gdm_greeter_server_problem (slave->priv->greeter_server, _("Unable to authenticate user"));
+        gdm_greeter_server_problem (slave->priv->greeter_server, service_name, _("Unable to authenticate user"));
 
         queue_greeter_reset (slave);
 }
 
 static void
 on_session_authorized (GdmSession      *session,
+                       const char      *service_name,
                        GdmFactorySlave *slave)
 {
         int flag;
@@ -248,39 +257,42 @@ on_session_authorized (GdmSession      *session,
         /* FIXME: check for migration? */
         flag = GDM_SESSION_CRED_ESTABLISH;
 
-        gdm_session_accredit (session, flag);
+        gdm_session_accredit (session, service_name, flag);
 }
 
 static void
 on_session_authorization_failed (GdmSession      *session,
+                                 const char      *service_name,
                                  const char      *message,
                                  GdmFactorySlave *slave)
 {
-        gdm_greeter_server_problem (slave->priv->greeter_server, _("Unable to authorize user"));
+        gdm_greeter_server_problem (slave->priv->greeter_server, service_name, _("Unable to authorize user"));
 
         queue_greeter_reset (slave);
 }
 
 static void
 on_session_accredited (GdmSession      *session,
+                       const char      *service_name,
                        GdmFactorySlave *slave)
 {
         g_debug ("GdmFactorySlave:  session user verified");
 
-        gdm_session_start_session (session);
+        gdm_session_start_session (session, service_name);
 
         gdm_greeter_server_reset (slave->priv->greeter_server);
 }
 
 static void
 on_session_accreditation_failed (GdmSession      *session,
+                                 const char      *service_name,
                                  const char      *message,
                                  GdmFactorySlave *slave)
 {
         g_debug ("GdmFactorySlave: could not successfully authenticate user: %s",
                  message);
 
-        gdm_greeter_server_problem (slave->priv->greeter_server, _("Unable to establish credentials"));
+        gdm_greeter_server_problem (slave->priv->greeter_server, service_name, _("Unable to establish credentials"));
 
         queue_greeter_reset (slave);
 }
@@ -368,37 +380,48 @@ on_session_relay_connected (GdmSessionRelay *session,
                             GdmFactorySlave *slave)
 {
         g_debug ("GdmFactorySlave: Relay Connected");
+}
+
+static void
+on_greeter_start_conversation (GdmGreeterServer *greeter_server,
+                               const char       *service_name,
+                               GdmFactorySlave  *slave)
+{
+        g_debug ("GdmFactorySlave: start conversation");
 
-        gdm_session_start_conversation (GDM_SESSION (slave->priv->session), "gdm");
+        gdm_session_start_conversation (GDM_SESSION (slave->priv->session), service_name);
 }
 
 static void
 on_greeter_begin_verification (GdmGreeterServer *greeter_server,
+                               const char       *service_name,
                                GdmFactorySlave  *slave)
 {
         g_debug ("GdmFactorySlave: begin verification");
         gdm_session_setup (GDM_SESSION (slave->priv->session),
-                           "gdm");
+                           service_name);
 }
 
 static void
 on_greeter_begin_verification_for_user (GdmGreeterServer *greeter_server,
+                                        const char       *service_name,
                                         const char       *username,
                                         GdmFactorySlave  *slave)
 {
         g_debug ("GdmFactorySlave: begin verification for user");
         gdm_session_setup_for_user (GDM_SESSION (slave->priv->session),
-                                    "gdm",
+                                    service_name,
                                     username);
 }
 
 static void
 on_greeter_answer (GdmGreeterServer *greeter_server,
+                   const char       *service_name,
                    const char       *text,
                    GdmFactorySlave  *slave)
 {
         g_debug ("GdmFactorySlave: Greeter answer");
-        gdm_session_answer_query (GDM_SESSION (slave->priv->session), text);
+        gdm_session_answer_query (GDM_SESSION (slave->priv->session), service_name, text);
 }
 
 static void
@@ -495,6 +518,10 @@ run_greeter (GdmFactorySlave *slave)
 
         slave->priv->greeter_server = gdm_greeter_server_new (display_id);
         g_signal_connect (slave->priv->greeter_server,
+                          "start-conversation",
+                          G_CALLBACK (on_greeter_start_conversation),
+                          slave);
+        g_signal_connect (slave->priv->greeter_server,
                           "begin-verification",
                           G_CALLBACK (on_greeter_begin_verification),
                           slave);
diff --git a/daemon/gdm-greeter-server.c b/daemon/gdm-greeter-server.c
index ffca7ec..dae34c5 100644
--- a/daemon/gdm-greeter-server.c
+++ b/daemon/gdm-greeter-server.c
@@ -43,6 +43,7 @@
 #include <dbus/dbus-glib.h>
 #include <dbus/dbus-glib-lowlevel.h>
 
+#include "gdm-marshal.h"
 #include "gdm-greeter-server.h"
 
 #define GDM_GREETER_SERVER_DBUS_PATH      "/org/gnome/DisplayManager/GreeterServer"
@@ -156,6 +157,46 @@ send_dbus_string_and_int_signal (GdmGreeterServer *greeter_server,
 }
 
 static void
+send_dbus_string_string_signal (GdmGreeterServer *greeter_server,
+                                const char       *name,
+                                const char       *text1,
+                                const char       *text2)
+{
+        DBusMessage    *message;
+        DBusMessageIter iter;
+        const char     *str;
+
+        g_return_if_fail (greeter_server != NULL);
+
+        message = dbus_message_new_signal (GDM_GREETER_SERVER_DBUS_PATH,
+                                           GDM_GREETER_SERVER_DBUS_INTERFACE,
+                                           name);
+
+        dbus_message_iter_init_append (message, &iter);
+
+        if (text1 != NULL) {
+                str = text1;
+        } else {
+                str = "";
+        }
+        dbus_message_iter_append_basic (&iter, DBUS_TYPE_STRING, &str);
+
+        if (text2 != NULL) {
+                str = text2;
+        } else {
+                str = "";
+        }
+        dbus_message_iter_append_basic (&iter, DBUS_TYPE_STRING, &str);
+
+        g_debug ("GreeterServer: Sending %s (%s)", name, str);
+        if (! send_dbus_message (greeter_server->priv->greeter_connection, message)) {
+                g_debug ("GreeterServer: Could not send %s signal", name);
+        }
+
+        dbus_message_unref (message);
+}
+
+static void
 send_dbus_string_signal (GdmGreeterServer *greeter_server,
                          const char       *name,
                          const char       *text)
@@ -208,34 +249,38 @@ send_dbus_void_signal (GdmGreeterServer *greeter_server,
 
 gboolean
 gdm_greeter_server_info_query (GdmGreeterServer *greeter_server,
+                               const char       *service_name,
                                const char       *text)
 {
-        send_dbus_string_signal (greeter_server, "InfoQuery", text);
+        send_dbus_string_string_signal (greeter_server, "InfoQuery", service_name, text);
 
         return TRUE;
 }
 
 gboolean
 gdm_greeter_server_secret_info_query (GdmGreeterServer *greeter_server,
+                                      const char       *service_name,
                                       const char       *text)
 {
-        send_dbus_string_signal (greeter_server, "SecretInfoQuery", text);
+        send_dbus_string_string_signal (greeter_server, "SecretInfoQuery", service_name, text);
         return TRUE;
 }
 
 gboolean
 gdm_greeter_server_info (GdmGreeterServer *greeter_server,
+                         const char       *service_name,
                          const char       *text)
 {
-        send_dbus_string_signal (greeter_server, "Info", text);
+        send_dbus_string_string_signal (greeter_server, "Info", service_name, text);
         return TRUE;
 }
 
 gboolean
 gdm_greeter_server_problem (GdmGreeterServer *greeter_server,
+                            const char       *service_name,
                             const char       *text)
 {
-        send_dbus_string_signal (greeter_server, "Problem", text);
+        send_dbus_string_string_signal (greeter_server, "Problem", service_name, text);
         return TRUE;
 }
 
@@ -291,9 +336,10 @@ gdm_greeter_server_request_timed_login (GdmGreeterServer *greeter_server,
 }
 
 void
-gdm_greeter_server_user_authorized (GdmGreeterServer *greeter_server)
+gdm_greeter_server_user_authorized (GdmGreeterServer *greeter_server,
+                                    const char       *service_name)
 {
-        send_dbus_void_signal (greeter_server, "UserAuthorized");
+        send_dbus_string_signal (greeter_server, "UserAuthorized", service_name);
 }
 
 /* Note: Use abstract sockets like dbus does by default on Linux. Abstract
@@ -358,6 +404,16 @@ handle_begin_verification (GdmGreeterServer *greeter_server,
                            DBusMessage      *message)
 {
         DBusMessage *reply;
+        DBusError    error;
+        const char  *service_name;
+
+        dbus_error_init (&error);
+        if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID)) {
+                g_warning ("ERROR: %s", error.message);
+        }
+        dbus_error_free (&error);
 
         g_debug ("GreeterServer: BeginVerification");
 
@@ -365,7 +421,7 @@ handle_begin_verification (GdmGreeterServer *greeter_server,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        g_signal_emit (greeter_server, signals [BEGIN_VERIFICATION], 0);
+        g_signal_emit (greeter_server, signals [BEGIN_VERIFICATION], 0, service_name);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -379,7 +435,6 @@ handle_begin_auto_login (GdmGreeterServer *greeter_server,
         DBusError    error;
         const char  *text;
 
-
         dbus_error_init (&error);
         if (! dbus_message_get_args (message, &error,
                                      DBUS_TYPE_STRING, &text,
@@ -406,13 +461,16 @@ handle_begin_verification_for_user (GdmGreeterServer *greeter_server,
         DBusMessage *reply;
         DBusError    error;
         const char  *text;
+        const char  *service_name;
 
         dbus_error_init (&error);
         if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
                                      DBUS_TYPE_STRING, &text,
                                      DBUS_TYPE_INVALID)) {
                 g_warning ("ERROR: %s", error.message);
         }
+        dbus_error_free (&error);
 
         g_debug ("GreeterServer: BeginVerificationForUser for '%s'", text);
 
@@ -420,7 +478,7 @@ handle_begin_verification_for_user (GdmGreeterServer *greeter_server,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        g_signal_emit (greeter_server, signals [BEGIN_VERIFICATION_FOR_USER], 0, text);
+        g_signal_emit (greeter_server, signals [BEGIN_VERIFICATION_FOR_USER], 0, service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -433,13 +491,16 @@ handle_answer_query (GdmGreeterServer *greeter_server,
         DBusMessage *reply;
         DBusError    error;
         const char  *text;
+        const char  *service_name;
 
         dbus_error_init (&error);
         if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
                                      DBUS_TYPE_STRING, &text,
                                      DBUS_TYPE_INVALID)) {
                 g_warning ("ERROR: %s", error.message);
         }
+        dbus_error_free (&error);
 
         g_debug ("GreeterServer: AnswerQuery");
 
@@ -447,7 +508,7 @@ handle_answer_query (GdmGreeterServer *greeter_server,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        g_signal_emit (greeter_server, signals [QUERY_ANSWER], 0, text);
+        g_signal_emit (greeter_server, signals [QUERY_ANSWER], 0, service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -644,9 +705,11 @@ handle_start_session_when_ready (GdmGreeterServer *greeter_server,
         DBusMessage *reply;
         DBusError    error;
         gboolean     should_start_session;
+        char        *service_name;
 
         dbus_error_init (&error);
         if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
                                      DBUS_TYPE_BOOLEAN, &should_start_session,
                                      DBUS_TYPE_INVALID)) {
                 g_warning ("ERROR: %s", error.message);
@@ -660,9 +723,9 @@ handle_start_session_when_ready (GdmGreeterServer *greeter_server,
         dbus_message_unref (reply);
 
         if (should_start_session) {
-                g_signal_emit (greeter_server, signals [START_SESSION_WHEN_READY], 0);
+                g_signal_emit (greeter_server, signals [START_SESSION_WHEN_READY], 0, service_name);
         } else {
-                g_signal_emit (greeter_server, signals [START_SESSION_LATER] ,0);
+                g_signal_emit (greeter_server, signals [START_SESSION_LATER] ,0, service_name);
         }
 
         return DBUS_HANDLER_RESULT_HANDLED;
@@ -735,13 +798,16 @@ do_introspect (DBusConnection *connection,
                                "      <arg name=\"service_name\" direction=\"in\" type=\"s\"/>\n"
                                "    </method>\n"
                                "    <method name=\"BeginVerification\">\n"
+                               "      <arg name=\"service_name\" direction=\"in\" type=\"s\"/>\n"
                                "    </method>\n"
                                "    <method name=\"BeginTimedLogin\">\n"
                                "    </method>\n"
                                "    <method name=\"BeginVerificationForUser\">\n"
+                               "      <arg name=\"service_name\" direction=\"in\" type=\"s\"/>\n"
                                "      <arg name=\"username\" direction=\"in\" type=\"s\"/>\n"
                                "    </method>\n"
                                "    <method name=\"AnswerQuery\">\n"
+                               "      <arg name=\"service_name\" direction=\"in\" type=\"s\"/>\n"
                                "      <arg name=\"text\" direction=\"in\" type=\"s\"/>\n"
                                "    </method>\n"
                                "    <method name=\"SelectSession\">\n"
@@ -764,18 +830,23 @@ do_introspect (DBusConnection *connection,
                                "      <arg name=\"id\" direction=\"out\" type=\"o\"/>\n"
                                "    </method>\n"
                                "    <method name=\"StartSessionWhenReady\">\n"
+                               "      <arg name=\"service_name\" direction=\"in\" type=\"s\"/>\n"
                                "      <arg name=\"should_start_session\" type=\"b\"/>\n"
                                "    </method>\n"
                                "    <signal name=\"Info\">\n"
+                               "      <arg name=\"service_name\" direction=\"in\" type=\"s\"/>\n"
                                "      <arg name=\"text\" type=\"s\"/>\n"
                                "    </signal>\n"
                                "    <signal name=\"Problem\">\n"
+                               "      <arg name=\"service_name\" direction=\"in\" type=\"s\"/>\n"
                                "      <arg name=\"text\" type=\"s\"/>\n"
                                "    </signal>\n"
                                "    <signal name=\"InfoQuery\">\n"
+                               "      <arg name=\"service_name\" direction=\"in\" type=\"s\"/>\n"
                                "      <arg name=\"text\" type=\"s\"/>\n"
                                "    </signal>\n"
                                "    <signal name=\"SecretInfoQuery\">\n"
+                               "      <arg name=\"service_name\" direction=\"in\" type=\"s\"/>\n"
                                "      <arg name=\"text\" type=\"s\"/>\n"
                                "    </signal>\n"
                                "    <signal name=\"SelectedUserChanged\">\n"
@@ -800,6 +871,7 @@ do_introspect (DBusConnection *connection,
                                "    <signal name=\"Reset\">\n"
                                "    </signal>\n"
                                "    <signal name=\"UserAuthorized\">\n"
+                               "      <arg name=\"service_name\" direction=\"in\" type=\"s\"/>\n"
                                "    </signal>\n"
                                "  </interface>\n");
 
@@ -1175,9 +1247,9 @@ gdm_greeter_server_class_init (GdmGreeterServerClass *klass)
                               G_STRUCT_OFFSET (GdmGreeterServerClass, begin_verification),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__VOID,
+                              g_cclosure_marshal_VOID__STRING,
                               G_TYPE_NONE,
-                              0);
+                              1, G_TYPE_STRING);
         signals [BEGIN_AUTO_LOGIN] =
                 g_signal_new ("begin-auto-login",
                               G_OBJECT_CLASS_TYPE (object_class),
@@ -1196,10 +1268,10 @@ gdm_greeter_server_class_init (GdmGreeterServerClass *klass)
                               G_STRUCT_OFFSET (GdmGreeterServerClass, begin_verification_for_user),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
         signals [QUERY_ANSWER] =
                 g_signal_new ("query-answer",
                               G_OBJECT_CLASS_TYPE (object_class),
@@ -1207,10 +1279,10 @@ gdm_greeter_server_class_init (GdmGreeterServerClass *klass)
                               G_STRUCT_OFFSET (GdmGreeterServerClass, query_answer),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
         signals [SESSION_SELECTED] =
                 g_signal_new ("session-selected",
                               G_OBJECT_CLASS_TYPE (object_class),
@@ -1304,9 +1376,9 @@ gdm_greeter_server_class_init (GdmGreeterServerClass *klass)
                               G_STRUCT_OFFSET (GdmGreeterServerClass, start_session_when_ready),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__VOID,
+                              g_cclosure_marshal_VOID__STRING,
                               G_TYPE_NONE,
-                              0);
+                              1, G_TYPE_STRING);
 
         signals [START_SESSION_LATER] =
                 g_signal_new ("start-session-later",
@@ -1315,9 +1387,9 @@ gdm_greeter_server_class_init (GdmGreeterServerClass *klass)
                               G_STRUCT_OFFSET (GdmGreeterServerClass, start_session_later),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__VOID,
+                              g_cclosure_marshal_VOID__STRING,
                               G_TYPE_NONE,
-                              0);
+                              1, G_TYPE_STRING);
 }
 
 static void
diff --git a/daemon/gdm-greeter-server.h b/daemon/gdm-greeter-server.h
index 7333db1..6d0dd87 100644
--- a/daemon/gdm-greeter-server.h
+++ b/daemon/gdm-greeter-server.h
@@ -48,10 +48,13 @@ typedef struct
         void (* start_conversation)         (GdmGreeterServer  *greeter_server,
                                              const char        *service_name);
         void (* begin_auto_login)           (GdmGreeterServer  *greeter_server);
-        void (* begin_verification)         (GdmGreeterServer  *greeter_server);
+        void (* begin_verification)         (GdmGreeterServer  *greeter_server,
+                                             const char        *service_name);
         void (* begin_verification_for_user)(GdmGreeterServer  *greeter_server,
+                                             const char        *service_name,
                                              const char        *username);
         void (* query_answer)               (GdmGreeterServer  *greeter_server,
+                                             const char        *service_name,
                                              const char        *text);
         void (* session_selected)           (GdmGreeterServer  *greeter_server,
                                              const char        *name);
@@ -66,7 +69,8 @@ typedef struct
         void (* cancelled)                  (GdmGreeterServer  *greeter_server);
         void (* connected)                  (GdmGreeterServer  *greeter_server);
         void (* disconnected)               (GdmGreeterServer  *greeter_server);
-        void (* start_session_when_ready)   (GdmGreeterServer  *greeter_server);
+        void (* start_session_when_ready)   (GdmGreeterServer  *greeter_server,
+                                             const char        *service_name);
         void (* start_session_later)        (GdmGreeterServer  *greeter_server);
 } GdmGreeterServerClass;
 
@@ -77,14 +81,17 @@ gboolean            gdm_greeter_server_start                 (GdmGreeterServer *
 gboolean            gdm_greeter_server_stop                  (GdmGreeterServer *greeter_server);
 char *              gdm_greeter_server_get_address           (GdmGreeterServer *greeter_server);
 
-
 gboolean            gdm_greeter_server_info_query            (GdmGreeterServer *greeter_server,
+                                                              const char       *service_name,
                                                               const char       *text);
 gboolean            gdm_greeter_server_secret_info_query     (GdmGreeterServer *greeter_server,
+                                                              const char       *service_name,
                                                               const char       *text);
 gboolean            gdm_greeter_server_info                  (GdmGreeterServer *greeter_server,
+                                                              const char       *service_name,
                                                               const char       *text);
 gboolean            gdm_greeter_server_problem               (GdmGreeterServer *greeter_server,
+                                                              const char       *service_name,
                                                               const char       *text);
 gboolean            gdm_greeter_server_reset                 (GdmGreeterServer *greeter_server);
 gboolean            gdm_greeter_server_ready                 (GdmGreeterServer *greeter_server,
@@ -101,8 +108,8 @@ void                gdm_greeter_server_default_session_name_changed (GdmGreeterS
 void                gdm_greeter_server_request_timed_login   (GdmGreeterServer *greeter_server,
                                                               const char       *username,
                                                               int               delay);
-void                gdm_greeter_server_user_authorized       (GdmGreeterServer *greeter_server);
-
+void                gdm_greeter_server_user_authorized       (GdmGreeterServer *greeter_server,
+                                                              const char       *service_name);
 
 G_END_DECLS
 
diff --git a/daemon/gdm-product-slave.c b/daemon/gdm-product-slave.c
index 15a2820..dd2e1bc 100644
--- a/daemon/gdm-product-slave.c
+++ b/daemon/gdm-product-slave.c
@@ -79,6 +79,8 @@ struct GdmProductSlavePrivate
 
         DBusGProxy       *product_display_proxy;
         DBusGConnection  *connection;
+
+        char             *start_session_service_name;
 };
 
 enum {
@@ -93,6 +95,68 @@ static void     gdm_product_slave_finalize      (GObject             *object);
 G_DEFINE_TYPE (GdmProductSlave, gdm_product_slave, GDM_TYPE_SLAVE)
 
 static gboolean
+send_dbus_string_string_method (DBusConnection *connection,
+                                const char     *method,
+                                const char     *payload1,
+                                const char     *payload2)
+{
+        DBusError       error;
+        DBusMessage    *message;
+        DBusMessage    *reply;
+        DBusMessageIter iter;
+        const char     *str;
+
+        g_debug ("GdmProductSlave: Calling %s", method);
+        message = dbus_message_new_method_call (NULL,
+                                                RELAY_SERVER_DBUS_PATH,
+                                                RELAY_SERVER_DBUS_INTERFACE,
+                                                method);
+        if (message == NULL) {
+                g_warning ("Couldn't allocate the D-Bus message");
+                return FALSE;
+        }
+
+        dbus_message_iter_init_append (message, &iter);
+
+        if (payload1 != NULL) {
+                str = payload1;
+        } else {
+                str = "";
+        }
+        dbus_message_iter_append_basic (&iter,
+                                        DBUS_TYPE_STRING,
+                                        &str);
+        if (payload2 != NULL) {
+                str = payload2;
+        } else {
+                str = "";
+        }
+        dbus_message_iter_append_basic (&iter,
+                                        DBUS_TYPE_STRING,
+                                        &str);
+        dbus_error_init (&error);
+        reply = dbus_connection_send_with_reply_and_block (connection,
+                                                           message,
+                                                           -1,
+                                                           &error);
+
+        dbus_message_unref (message);
+
+        if (dbus_error_is_set (&error)) {
+                g_warning ("%s %s raised: %s\n",
+                           method,
+                           error.name,
+                           error.message);
+                return FALSE;
+        }
+        if (reply != NULL) {
+                dbus_message_unref (reply);
+        }
+        dbus_connection_flush (connection);
+
+        return TRUE;
+}
+static gboolean
 send_dbus_string_method (DBusConnection *connection,
                          const char     *method,
                          const char     *payload)
@@ -356,7 +420,8 @@ setup_session (GdmProductSlave *slave)
         g_free (display_device);
         g_free (auth_file);
 
-        gdm_session_start_session (GDM_SESSION (slave->priv->session));
+        gdm_session_start_session (GDM_SESSION (slave->priv->session),
+                                   slave->priv->start_session_service_name);
 
         return TRUE;
 }
@@ -508,96 +573,112 @@ on_session_reset_failed (GdmSession      *session,
 
 static void
 on_session_authenticated (GdmSession      *session,
+                          const char      *service_name,
                           GdmProductSlave *slave)
 {
-        send_dbus_void_method (slave->priv->session_relay_connection,
-                               "Authenticated");
+        send_dbus_string_method (slave->priv->session_relay_connection,
+                                 "Authenticated", service_name);
 }
 
 static void
 on_session_authentication_failed (GdmSession      *session,
+                                  const char      *service_name,
                                   const char      *message,
                                   GdmProductSlave *slave)
 {
-        send_dbus_string_method (slave->priv->session_relay_connection,
-                                 "AuthenticationFailed",
-                                 message);
+        send_dbus_string_string_method (slave->priv->session_relay_connection,
+                                        "AuthenticationFailed",
+                                        service_name,
+                                        message);
 }
 
 static void
 on_session_authorized (GdmSession      *session,
+                       const char      *service_name,
                        GdmProductSlave *slave)
 {
-        send_dbus_void_method (slave->priv->session_relay_connection,
-                               "Authorized");
+        send_dbus_string_method (slave->priv->session_relay_connection,
+                                 "Authorized", service_name);
 }
 
 static void
 on_session_authorization_failed (GdmSession      *session,
+                                 const char      *service_name,
                                  const char      *message,
                                  GdmProductSlave *slave)
 {
-        send_dbus_string_method (slave->priv->session_relay_connection,
-                                 "AuthorizationFailed",
-                                 message);
+        send_dbus_string_string_method (slave->priv->session_relay_connection,
+                                        "AuthorizationFailed",
+                                        service_name,
+                                        message);
 }
 
 static void
 on_session_accredited (GdmSession      *session,
+                       const char      *service_name,
                        GdmProductSlave *slave)
 {
-        send_dbus_void_method (slave->priv->session_relay_connection,
-                               "Accredited");
+        send_dbus_string_method (slave->priv->session_relay_connection,
+                                 "Accredited", service_name);
 }
 
 static void
 on_session_accreditation_failed (GdmSession      *session,
+                                 const char      *service_name,
                                  const char      *message,
                                  GdmProductSlave *slave)
 {
-        send_dbus_string_method (slave->priv->session_relay_connection,
-                                 "AccreditationFailed",
-                                 message);
+        send_dbus_string_string_method (slave->priv->session_relay_connection,
+                                        "AccreditationFailed",
+                                        service_name,
+                                        message);
 }
 
 static void
 on_session_info (GdmSession      *session,
+                 const char      *service_name,
                  const char      *text,
                  GdmProductSlave *slave)
 {
-        send_dbus_string_method (slave->priv->session_relay_connection,
-                                 "Info",
-                                 text);
+        send_dbus_string_string_method (slave->priv->session_relay_connection,
+                                        "Info",
+                                        service_name,
+                                        text);
 }
 
 static void
 on_session_problem (GdmSession      *session,
+                    const char      *service_name,
                     const char      *text,
                     GdmProductSlave *slave)
 {
-        send_dbus_string_method (slave->priv->session_relay_connection,
-                                 "Problem",
-                                 text);
+        send_dbus_string_string_method (slave->priv->session_relay_connection,
+                                        "Problem",
+                                        service_name,
+                                        text);
 }
 
 static void
 on_session_info_query (GdmSession      *session,
+                       const char      *service_name,
                        const char      *text,
                        GdmProductSlave *slave)
 {
-        send_dbus_string_method (slave->priv->session_relay_connection,
-                                 "InfoQuery",
-                                 text);
+        send_dbus_string_string_method (slave->priv->session_relay_connection,
+                                        "InfoQuery",
+                                        service_name, text);
 }
 
 static void
 on_session_secret_info_query (GdmSession      *session,
+                              const char      *service_name,
                               const char      *text,
                               GdmProductSlave *slave)
 {
-        send_dbus_string_method (slave->priv->session_relay_connection,
-                                 "SecretInfoQuery",
-                                 text);
+        send_dbus_string_string_method (slave->priv->session_relay_connection,
+                                        "SecretInfoQuery",
+                                        service_name,
+                                        text);
 }
 
 static void
@@ -658,36 +739,92 @@ static void
 on_relay_authenticate (GdmProductSlave *slave,
                        DBusMessage     *message)
 {
-        g_debug ("GdmProductSlave: Relay Authenticate");
+        DBusError   error;
+        char *service_name;
+        dbus_bool_t res;
 
-        gdm_session_authenticate (GDM_SESSION (slave->priv->session));
+        dbus_error_init (&error);
+        res = dbus_message_get_args (message,
+                                     &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID);
+        if (res) {
+                g_debug ("GdmProductSlave: Relay Authenticate");
+                gdm_session_authenticate (GDM_SESSION (slave->priv->session), service_name);
+        } else {
+                g_warning ("Unable to get arguments: %s", error.message);
+                dbus_error_free (&error);
+        }
+        dbus_error_free (&error);
 }
 
 static void
 on_relay_authorize (GdmProductSlave *slave,
                     DBusMessage     *message)
 {
-        g_debug ("GdmProductSlave: Relay Authorize");
+        DBusError   error;
+        char *service_name;
+        dbus_bool_t res;
 
-        gdm_session_authorize (GDM_SESSION (slave->priv->session));
+        dbus_error_init (&error);
+        res = dbus_message_get_args (message,
+                                     &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID);
+        if (res) {
+                g_debug ("GdmProductSlave: Relay Authorize");
+                gdm_session_authorize (GDM_SESSION (slave->priv->session), service_name);
+        } else {
+                g_warning ("Unable to get arguments: %s", error.message);
+                dbus_error_free (&error);
+        }
+        dbus_error_free (&error);
 }
 
 static void
 on_relay_establish_credentials (GdmProductSlave *slave,
                                 DBusMessage     *message)
 {
-        g_debug ("GdmProductSlave: Relay EstablishCredentials");
+        DBusError   error;
+        char *service_name;
+        dbus_bool_t res;
 
-        gdm_session_accredit (GDM_SESSION (slave->priv->session), GDM_SESSION_CRED_ESTABLISH);
+        dbus_error_init (&error);
+        res = dbus_message_get_args (message,
+                                     &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID);
+        if (res) {
+                g_debug ("GdmProductSlave: Relay EstablishCredentials");
+                gdm_session_accredit (GDM_SESSION (slave->priv->session), service_name, GDM_SESSION_CRED_ESTABLISH);
+        } else {
+                g_warning ("Unable to get arguments: %s", error.message);
+                dbus_error_free (&error);
+        }
+        dbus_error_free (&error);
 }
 
 static void
 on_relay_refresh_credentials (GdmProductSlave *slave,
                               DBusMessage     *message)
 {
-        g_debug ("GdmProductSlave: Relay RefreshCredentials");
+        DBusError   error;
+        char *service_name;
+        dbus_bool_t res;
 
-        gdm_session_accredit (GDM_SESSION (slave->priv->session), GDM_SESSION_CRED_REFRESH);
+        dbus_error_init (&error);
+        res = dbus_message_get_args (message,
+                                     &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID);
+        if (res) {
+                g_debug ("GdmProductSlave: Relay RefreshCredentials");
+                gdm_session_accredit (GDM_SESSION (slave->priv->session), service_name, GDM_SESSION_CRED_REFRESH);
+        } else {
+                g_warning ("Unable to get arguments: %s", error.message);
+                dbus_error_free (&error);
+        }
+        dbus_error_free (&error);
 }
 
 static void
@@ -696,16 +833,18 @@ on_relay_answer_query (GdmProductSlave *slave,
 {
         DBusError   error;
         const char *text;
+        const char *service_name;
         dbus_bool_t res;
 
         dbus_error_init (&error);
         res = dbus_message_get_args (message,
                                      &error,
+                                     DBUS_TYPE_STRING, &service_name,
                                      DBUS_TYPE_STRING, &text,
                                      DBUS_TYPE_INVALID);
         if (res) {
                 g_debug ("GdmProductSlave: Relay AnswerQuery");
-                gdm_session_answer_query (GDM_SESSION (slave->priv->session), text);
+                gdm_session_answer_query (GDM_SESSION (slave->priv->session), service_name, text);
         } else {
                 g_warning ("Unable to get arguments: %s", error.message);
                 dbus_error_free (&error);
@@ -813,7 +952,25 @@ static void
 on_relay_start_session (GdmProductSlave *slave,
                         DBusMessage     *message)
 {
-        gdm_product_slave_create_server (slave);
+        DBusError   error;
+        const char *service_name;
+        dbus_bool_t res;
+
+        dbus_error_init (&error);
+
+        res = dbus_message_get_args (message,
+                                     &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID);
+        if (res) {
+                g_debug ("GdmProductSlave: Relay StartSession");
+                g_free (slave->priv->start_session_service_name);
+                slave->priv->start_session_service_name = g_strdup (service_name);
+                gdm_product_slave_create_server (slave);
+        } else {
+                g_warning ("Unable to get arguments: %s", error.message);
+                dbus_error_free (&error);
+        }
 }
 
 static void
diff --git a/daemon/gdm-session-direct.c b/daemon/gdm-session-direct.c
index b86475c..1c151fd 100644
--- a/daemon/gdm-session-direct.c
+++ b/daemon/gdm-session-direct.c
@@ -83,10 +83,10 @@ struct _GdmSessionDirectPrivate
         char                *selected_user;
         char                *user_x11_authority_file;
 
-        GdmSessionConversation *conversation;
         GHashTable          *conversations;
 
-        GdmSessionWorkerJob *job;
+        GList               *pending_connections;
+
         GPid                 session_pid;
         guint32              is_running : 1;
 
@@ -193,14 +193,30 @@ send_dbus_void_signal (GdmSessionConversation *conversation,
         dbus_message_unref (message);
 }
 
+static GdmSessionConversation *
+find_conversation_by_name (GdmSessionDirect *session,
+                           const char       *service_name)
+{
+        GdmSessionConversation *conversation;
+
+        conversation = g_hash_table_lookup (session->priv->conversations, service_name);
+
+        if (conversation == NULL) {
+                g_warning ("Tried to look up non-existant conversation");
+        }
+
+        return conversation;
+}
+
 static void
 on_authentication_failed (GdmSession *session,
+                          const char *service_name,
                           const char *message)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
         GdmSessionConversation *conversation;
 
-        conversation = impl->priv->conversation;
+        conversation = find_conversation_by_name (impl, service_name);
         if (conversation != NULL) {
                 gdm_session_record_failed (conversation->worker_pid,
                                            impl->priv->selected_user,
@@ -211,12 +227,13 @@ on_authentication_failed (GdmSession *session,
 }
 
 static void
-on_session_started (GdmSession *session)
+on_session_started (GdmSession *session,
+                    const char *service_name)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
         GdmSessionConversation *conversation;
 
-        conversation = impl->priv->conversation;
+        conversation = find_conversation_by_name (impl, service_name);
         if (conversation != NULL) {
                 gdm_session_record_login (conversation->worker_pid,
                                           impl->priv->selected_user,
@@ -228,12 +245,13 @@ on_session_started (GdmSession *session)
 
 static void
 on_session_start_failed (GdmSession *session,
+                         const char *service_name,
                          const char *message)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
         GdmSessionConversation *conversation;
 
-        conversation = impl->priv->conversation;
+        conversation = find_conversation_by_name (impl, service_name);
         if (conversation != NULL) {
                 gdm_session_record_login (conversation->worker_pid,
                                           impl->priv->selected_user,
@@ -258,7 +276,7 @@ on_session_exited (GdmSession *session,
 
 static DBusHandlerResult
 gdm_session_direct_handle_setup_complete (GdmSessionDirect *session,
-                                          DBusConnection   *connection,
+                                          GdmSessionConversation *conversation,
                                           DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -266,17 +284,17 @@ gdm_session_direct_handle_setup_complete (GdmSessionDirect *session,
         g_debug ("GdmSessionDirect: Emitting 'setup-complete' signal");
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_setup_complete (GDM_SESSION (session));
+        _gdm_session_setup_complete (GDM_SESSION (session), conversation->service_name);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_setup_failed (GdmSessionDirect *session,
-                                        DBusConnection   *connection,
+                                        GdmSessionConversation *conversation,
                                         DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -291,12 +309,12 @@ gdm_session_direct_handle_setup_failed (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'setup-failed' signal");
 
-        _gdm_session_setup_failed (GDM_SESSION (session), text);
+        _gdm_session_setup_failed (GDM_SESSION (session), conversation->service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -304,7 +322,7 @@ gdm_session_direct_handle_setup_failed (GdmSessionDirect *session,
 
 static DBusHandlerResult
 gdm_session_direct_handle_reset_complete (GdmSessionDirect *session,
-                                          DBusConnection   *connection,
+                                          GdmSessionConversation *conversation,
                                           DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -312,7 +330,7 @@ gdm_session_direct_handle_reset_complete (GdmSessionDirect *session,
         g_debug ("GdmSessionDirect: Emitting 'reset-complete' signal");
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         _gdm_session_reset_complete (GDM_SESSION (session));
@@ -322,7 +340,7 @@ gdm_session_direct_handle_reset_complete (GdmSessionDirect *session,
 
 static DBusHandlerResult
 gdm_session_direct_handle_reset_failed (GdmSessionDirect *session,
-                                        DBusConnection   *connection,
+                                        GdmSessionConversation *conversation,
                                         DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -337,7 +355,7 @@ gdm_session_direct_handle_reset_failed (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'reset-failed' signal");
@@ -349,7 +367,7 @@ gdm_session_direct_handle_reset_failed (GdmSessionDirect *session,
 
 static DBusHandlerResult
 gdm_session_direct_handle_authenticated (GdmSessionDirect *session,
-                                         DBusConnection   *connection,
+                                         GdmSessionConversation *conversation,
                                          DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -357,17 +375,17 @@ gdm_session_direct_handle_authenticated (GdmSessionDirect *session,
         g_debug ("GdmSessionDirect: Emitting 'authenticated' signal");
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_authenticated (GDM_SESSION (session));
+        _gdm_session_authenticated (GDM_SESSION (session), conversation->service_name);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_authentication_failed (GdmSessionDirect *session,
-                                                 DBusConnection   *connection,
+                                                 GdmSessionConversation *conversation,
                                                  DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -382,19 +400,19 @@ gdm_session_direct_handle_authentication_failed (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'authentication-failed' signal");
 
-        _gdm_session_authentication_failed (GDM_SESSION (session), text);
+        _gdm_session_authentication_failed (GDM_SESSION (session), conversation->service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_authorized (GdmSessionDirect *session,
-                                      DBusConnection   *connection,
+                                      GdmSessionConversation *conversation,
                                       DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -402,17 +420,17 @@ gdm_session_direct_handle_authorized (GdmSessionDirect *session,
         g_debug ("GdmSessionDirect: Emitting 'authorized' signal");
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_authorized (GDM_SESSION (session));
+        _gdm_session_authorized (GDM_SESSION (session), conversation->service_name);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_authorization_failed (GdmSessionDirect *session,
-                                                DBusConnection   *connection,
+                                                GdmSessionConversation *conversation,
                                                 DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -427,19 +445,19 @@ gdm_session_direct_handle_authorization_failed (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'authorization-failed' signal");
 
-        _gdm_session_authorization_failed (GDM_SESSION (session), text);
+        _gdm_session_authorization_failed (GDM_SESSION (session), conversation->service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_accredited (GdmSessionDirect *session,
-                                      DBusConnection   *connection,
+                                      GdmSessionConversation *conversation,
                                       DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -447,17 +465,17 @@ gdm_session_direct_handle_accredited (GdmSessionDirect *session,
         g_debug ("GdmSessionDirect: Emitting 'accredited' signal");
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_accredited (GDM_SESSION (session));
+        _gdm_session_accredited (GDM_SESSION (session), conversation->service_name);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_accreditation_failed (GdmSessionDirect *session,
-                                                DBusConnection   *connection,
+                                                GdmSessionConversation *conversation,
                                                 DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -472,12 +490,12 @@ gdm_session_direct_handle_accreditation_failed (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'accreditation-failed' signal");
 
-        _gdm_session_accreditation_failed (GDM_SESSION (session), text);
+        _gdm_session_accreditation_failed (GDM_SESSION (session), conversation->service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -725,7 +743,7 @@ gdm_session_direct_select_user (GdmSession *session,
 
 static DBusHandlerResult
 gdm_session_direct_handle_username_changed (GdmSessionDirect *session,
-                                            DBusConnection   *connection,
+                                            GdmSessionConversation *conversation,
                                             DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -740,7 +758,7 @@ gdm_session_direct_handle_username_changed (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: changing username from '%s' to '%s'",
@@ -807,14 +825,11 @@ set_pending_query (GdmSessionConversation *conversation,
 
 static DBusHandlerResult
 gdm_session_direct_handle_info_query (GdmSessionDirect *session,
-                                      DBusConnection   *connection,
+                                      GdmSessionConversation *conversation,
                                       DBusMessage      *message)
 {
         DBusError    error;
         const char  *text;
-        GdmSessionConversation *conversation;
-
-        conversation = session->priv->conversation;
 
         dbus_error_init (&error);
         if (! dbus_message_get_args (message, &error,
@@ -826,21 +841,18 @@ gdm_session_direct_handle_info_query (GdmSessionDirect *session,
         set_pending_query (conversation, message);
 
         g_debug ("GdmSessionDirect: Emitting 'info-query' signal");
-        _gdm_session_info_query (GDM_SESSION (session), text);
+        _gdm_session_info_query (GDM_SESSION (session), conversation->service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_secret_info_query (GdmSessionDirect *session,
-                                             DBusConnection   *connection,
+                                             GdmSessionConversation *conversation,
                                              DBusMessage      *message)
 {
         DBusError    error;
         const char  *text;
-        GdmSessionConversation *conversation;
-
-        conversation = session->priv->conversation;
 
         dbus_error_init (&error);
         if (! dbus_message_get_args (message, &error,
@@ -852,14 +864,14 @@ gdm_session_direct_handle_secret_info_query (GdmSessionDirect *session,
         set_pending_query (conversation, message);
 
         g_debug ("GdmSessionDirect: Emitting 'secret-info-query' signal");
-        _gdm_session_secret_info_query (GDM_SESSION (session), text);
+        _gdm_session_secret_info_query (GDM_SESSION (session), conversation->service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_info (GdmSessionDirect *session,
-                                DBusConnection   *connection,
+                                GdmSessionConversation *conversation,
                                 DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -874,31 +886,28 @@ gdm_session_direct_handle_info (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'info' signal");
-        _gdm_session_info (GDM_SESSION (session), text);
+        _gdm_session_info (GDM_SESSION (session), conversation->service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_cancel_pending_query (GdmSessionDirect *session,
-                                                DBusConnection   *connection,
+                                                GdmSessionConversation *conversation,
                                                 DBusMessage      *message)
 {
         DBusMessage *reply;
-        GdmSessionConversation *conversation;
 
         g_debug ("GdmSessionDirect: worker cancelling pending query");
 
-        conversation = session->priv->conversation;
-
         cancel_pending_query (conversation);
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         return DBUS_HANDLER_RESULT_HANDLED;
@@ -906,7 +915,7 @@ gdm_session_direct_handle_cancel_pending_query (GdmSessionDirect *session,
 
 static DBusHandlerResult
 gdm_session_direct_handle_problem (GdmSessionDirect *session,
-                                   DBusConnection   *connection,
+                                   GdmSessionConversation *conversation,
                                    DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -921,18 +930,18 @@ gdm_session_direct_handle_problem (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'problem' signal");
-        _gdm_session_problem (GDM_SESSION (session), text);
+        _gdm_session_problem (GDM_SESSION (session), conversation->service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_session_started (GdmSessionDirect *session,
-                                           DBusConnection   *connection,
+                                           GdmSessionConversation *conversation,
                                            DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -951,7 +960,7 @@ gdm_session_direct_handle_session_started (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'session-started' signal with pid '%d'",
@@ -960,14 +969,14 @@ gdm_session_direct_handle_session_started (GdmSessionDirect *session,
         session->priv->session_pid = pid;
         session->priv->is_running = TRUE;
 
-        _gdm_session_session_started (GDM_SESSION (session), pid);
+        _gdm_session_session_started (GDM_SESSION (session), conversation->service_name, pid);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_start_failed (GdmSessionDirect *session,
-                                        DBusConnection   *connection,
+                                        GdmSessionConversation *conversation,
                                         DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -982,18 +991,18 @@ gdm_session_direct_handle_start_failed (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'session-start-failed' signal");
-        _gdm_session_session_start_failed (GDM_SESSION (session), text);
+        _gdm_session_session_start_failed (GDM_SESSION (session), conversation->service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
 static DBusHandlerResult
 gdm_session_direct_handle_session_exited (GdmSessionDirect *session,
-                                          DBusConnection   *connection,
+                                          GdmSessionConversation *conversation,
                                           DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -1008,7 +1017,7 @@ gdm_session_direct_handle_session_exited (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'session-exited' signal with exit code '%d'",
@@ -1022,7 +1031,7 @@ gdm_session_direct_handle_session_exited (GdmSessionDirect *session,
 
 static DBusHandlerResult
 gdm_session_direct_handle_session_died (GdmSessionDirect *session,
-                                        DBusConnection   *connection,
+                                        GdmSessionConversation *conversation,
                                         DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -1037,7 +1046,7 @@ gdm_session_direct_handle_session_died (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         g_debug ("GdmSessionDirect: Emitting 'session-died' signal with signal number '%d'",
@@ -1051,7 +1060,7 @@ gdm_session_direct_handle_session_died (GdmSessionDirect *session,
 
 static DBusHandlerResult
 gdm_session_direct_handle_saved_language_name_read (GdmSessionDirect *session,
-                                                    DBusConnection   *connection,
+                                                    GdmSessionConversation *conversation,
                                                     DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -1066,7 +1075,7 @@ gdm_session_direct_handle_saved_language_name_read (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         if (strcmp (language_name,
@@ -1084,7 +1093,7 @@ gdm_session_direct_handle_saved_language_name_read (GdmSessionDirect *session,
 
 static DBusHandlerResult
 gdm_session_direct_handle_saved_layout_name_read (GdmSessionDirect *session,
-                                                  DBusConnection   *connection,
+                                                  GdmSessionConversation *conversation,
                                                   DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -1099,7 +1108,7 @@ gdm_session_direct_handle_saved_layout_name_read (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         if (strcmp (layout_name,
@@ -1117,7 +1126,7 @@ gdm_session_direct_handle_saved_layout_name_read (GdmSessionDirect *session,
 
 static DBusHandlerResult
 gdm_session_direct_handle_saved_session_name_read (GdmSessionDirect *session,
-                                                   DBusConnection   *connection,
+                                                   GdmSessionConversation *conversation,
                                                    DBusMessage      *message)
 {
         DBusMessage *reply;
@@ -1132,7 +1141,7 @@ gdm_session_direct_handle_saved_session_name_read (GdmSessionDirect *session,
         }
 
         reply = dbus_message_new_method_return (message);
-        dbus_connection_send (connection, reply, NULL);
+        dbus_connection_send (conversation->worker_connection, reply, NULL);
         dbus_message_unref (reply);
 
         if (! get_session_command_for_name (session_name, NULL)) {
@@ -1160,54 +1169,57 @@ session_worker_message (DBusConnection *connection,
                         DBusMessage    *message,
                         void           *user_data)
 {
-        GdmSessionDirect *session = GDM_SESSION_DIRECT (user_data);
+        GdmSessionConversation *conversation = user_data;
+        GdmSessionDirect *session;
+
+        session = conversation->session;
 
         if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "InfoQuery")) {
-                return gdm_session_direct_handle_info_query (session, connection, message);
+                return gdm_session_direct_handle_info_query (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "SecretInfoQuery")) {
-                return gdm_session_direct_handle_secret_info_query (session, connection, message);
+                return gdm_session_direct_handle_secret_info_query (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "Info")) {
-                return gdm_session_direct_handle_info (session, connection, message);
+                return gdm_session_direct_handle_info (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "Problem")) {
-                return gdm_session_direct_handle_problem (session, connection, message);
+                return gdm_session_direct_handle_problem (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "CancelPendingQuery")) {
-                return gdm_session_direct_handle_cancel_pending_query (session, connection, message);
+                return gdm_session_direct_handle_cancel_pending_query (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "SetupComplete")) {
-                return gdm_session_direct_handle_setup_complete (session, connection, message);
+                return gdm_session_direct_handle_setup_complete (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "SetupFailed")) {
-                return gdm_session_direct_handle_setup_failed (session, connection, message);
+                return gdm_session_direct_handle_setup_failed (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "ResetComplete")) {
-                return gdm_session_direct_handle_reset_complete (session, connection, message);
+                return gdm_session_direct_handle_reset_complete (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "ResetFailed")) {
-                return gdm_session_direct_handle_reset_failed (session, connection, message);
+                return gdm_session_direct_handle_reset_failed (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "Authenticated")) {
-                return gdm_session_direct_handle_authenticated (session, connection, message);
+                return gdm_session_direct_handle_authenticated (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "AuthenticationFailed")) {
-                return gdm_session_direct_handle_authentication_failed (session, connection, message);
+                return gdm_session_direct_handle_authentication_failed (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "Authorized")) {
-                return gdm_session_direct_handle_authorized (session, connection, message);
+                return gdm_session_direct_handle_authorized (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "AuthorizationFailed")) {
-                return gdm_session_direct_handle_authorization_failed (session, connection, message);
+                return gdm_session_direct_handle_authorization_failed (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "Accredited")) {
-                return gdm_session_direct_handle_accredited (session, connection, message);
+                return gdm_session_direct_handle_accredited (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "AccreditationFailed")) {
-                return gdm_session_direct_handle_accreditation_failed (session, connection, message);
+                return gdm_session_direct_handle_accreditation_failed (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "UsernameChanged")) {
-                return gdm_session_direct_handle_username_changed (session, connection, message);
+                return gdm_session_direct_handle_username_changed (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "SessionStarted")) {
-                return gdm_session_direct_handle_session_started (session, connection, message);
+                return gdm_session_direct_handle_session_started (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "StartFailed")) {
-                return gdm_session_direct_handle_start_failed (session, connection, message);
+                return gdm_session_direct_handle_start_failed (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "SessionExited")) {
-                return gdm_session_direct_handle_session_exited (session, connection, message);
+                return gdm_session_direct_handle_session_exited (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "SessionDied")) {
-                return gdm_session_direct_handle_session_died (session, connection, message);
+                return gdm_session_direct_handle_session_died (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "SavedLanguageNameRead")) {
-                return gdm_session_direct_handle_saved_language_name_read (session, connection, message);
+                return gdm_session_direct_handle_saved_language_name_read (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "SavedLayoutNameRead")) {
-                return gdm_session_direct_handle_saved_layout_name_read (session, connection, message);
+                return gdm_session_direct_handle_saved_layout_name_read (session, conversation, message);
         } else if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "SavedSessionNameRead")) {
-                return gdm_session_direct_handle_saved_session_name_read (session, connection, message);
+                return gdm_session_direct_handle_saved_session_name_read (session, conversation, message);
         }
 
         return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
@@ -1441,6 +1453,27 @@ session_unregister_handler (DBusConnection  *connection,
         g_debug ("session_unregister_handler");
 }
 
+static GdmSessionConversation *
+find_conversation_by_pid (GdmSessionDirect *session,
+                          GPid              pid)
+{
+        GHashTableIter iter;
+        gpointer key, value;
+
+        g_hash_table_iter_init (&iter, session->priv->conversations);
+        while (g_hash_table_iter_next (&iter, &key, &value)) {
+                GdmSessionConversation *conversation;
+
+                conversation = (GdmSessionConversation *) value;
+
+                if (conversation->worker_pid == pid) {
+                        return conversation;
+                }
+        }
+
+        return NULL;
+}
+
 static dbus_bool_t
 allow_user_function (DBusConnection *connection,
                      unsigned long   uid,
@@ -1455,40 +1488,83 @@ allow_user_function (DBusConnection *connection,
         return FALSE;
 }
 
-static GdmSessionConversation *
-find_conversation_by_name (GdmSessionDirect *session,
-                           const char       *service_name)
+static gboolean
+register_worker (GdmSessionDirect *session,
+                 DBusConnection   *connection)
 {
         GdmSessionConversation *conversation;
+        DBusObjectPathVTable vtable = { &session_unregister_handler,
+                                        &session_message_handler,
+                                        NULL, NULL, NULL, NULL };
+        GList *connection_node;
+        gulong pid;
 
-        conversation = g_hash_table_lookup (session->priv->conversations, service_name);
+        g_debug ("GdmSessionDirect: Authenticating new connection");
+
+        connection_node = g_list_find (session->priv->pending_connections, connection);
+
+        if (connection_node == NULL) {
+                g_debug ("GdmSessionDirect: Ignoring connection that we aren't tracking");
+                return FALSE;
+        }
+
+        session->priv->pending_connections =
+                g_list_delete_link (session->priv->pending_connections,
+                                    connection_node);
+
+        if (!dbus_connection_get_unix_process_id (connection, &pid)) {
+                g_warning ("GdmSessionDirect: Unable to read pid on new worker connection");
+                dbus_connection_unref (connection);
+                return FALSE;
+        }
+
+        conversation = find_conversation_by_pid (session, (GPid) pid);
 
         if (conversation == NULL) {
-                g_warning ("Tried to look up non-existant conversation");
+                g_warning ("GdmSessionDirect: New worker connection is from unknown source");
+                dbus_connection_unref (connection);
+                return FALSE;
         }
 
-        return conversation;
+        conversation->worker_connection = connection;
+
+        g_debug ("GdmSessionDirect: worker connection is %p", connection);
+
+        dbus_connection_register_object_path (connection,
+                                              GDM_SESSION_DBUS_PATH,
+                                              &vtable,
+                                              conversation);
+
+        g_debug ("GdmSessionDirect: Emitting conversation-started signal");
+        _gdm_session_conversation_started (GDM_SESSION (session),
+                                           conversation->service_name);
+
+        g_debug ("GdmSessionDirect: Conversation started");
+
+        return TRUE;
 }
 
-static GdmSessionConversation *
-find_conversation_by_pid (GdmSessionDirect *session,
-                          GPid              pid)
+static DBusHandlerResult
+on_message (DBusConnection *connection, DBusMessage *message, void *user_data)
 {
-        GHashTableIter iter;
-        gpointer key, value;
+        GdmSessionDirect *session = GDM_SESSION_DIRECT (user_data);
 
-        g_hash_table_iter_init (&iter, session->priv->conversations);
-        while (g_hash_table_iter_next (&iter, &key, &value)) {
-                GdmSessionConversation *conversation;
+        g_debug ("GdmSessionDirect: got message");
 
-                conversation = (GdmSessionConversation *) value;
+        if (dbus_message_is_method_call (message, GDM_SESSION_DBUS_INTERFACE, "Hello")) {
+                DBusMessage *reply;
 
-                if (conversation->worker_pid == pid) {
-                        return conversation;
+                if (register_worker (session, connection)) {
+                        reply = dbus_message_new_method_return (message);
+                } else {
+                        reply = dbus_message_new_error (message, DBUS_ERROR_FAILED, "");
                 }
+
+                dbus_connection_send (connection, reply, NULL);
+                return DBUS_HANDLER_RESULT_HANDLED;
         }
 
-        return NULL;
+        return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
 }
 
 static void
@@ -1497,50 +1573,23 @@ handle_connection (DBusServer      *server,
                    void            *user_data)
 {
         GdmSessionDirect *session = GDM_SESSION_DIRECT (user_data);
-        GdmSessionConversation *conversation;
-        gulong pid;
-
         g_debug ("GdmSessionDirect: Handing new connection");
 
-        if (!dbus_connection_get_unix_process_id (new_connection, &pid)) {
-                g_warning ("Unable to read pid on new worker connection");
-                return;
-        }
-
-        conversation = find_conversation_by_pid (session, (GPid) pid);
-
-        if (conversation == NULL) {
-                g_warning ("New worker connection is from unknown source");
-                return;
-        }
-
-        if (conversation->worker_connection == NULL) {
-                DBusObjectPathVTable vtable = { &session_unregister_handler,
-                                                &session_message_handler,
-                                                NULL, NULL, NULL, NULL
-                };
-
-                conversation->worker_connection = new_connection;
-                dbus_connection_ref (new_connection);
-                dbus_connection_setup_with_g_main (new_connection, NULL);
-
-                g_debug ("GdmSessionDirect: worker connection is %p", new_connection);
-                dbus_connection_set_exit_on_disconnect (new_connection, FALSE);
-
-                dbus_connection_set_unix_user_function (new_connection,
-                                                        allow_user_function,
-                                                        session,
-                                                        NULL);
-
-                dbus_connection_register_object_path (new_connection,
-                                                      GDM_SESSION_DBUS_PATH,
-                                                      &vtable,
-                                                      session);
+        /* add to the list of pending connections.  We won't be able to
+         * associate it with a specific worker conversation until we have
+         * authenticated the connection (from the Hello handler).
+         */
+        session->priv->pending_connections =
+                g_list_prepend (session->priv->pending_connections,
+                                dbus_connection_ref (new_connection));
+        dbus_connection_setup_with_g_main (new_connection, NULL);
+        dbus_connection_set_exit_on_disconnect (new_connection, FALSE);
 
-                g_debug ("GdmSessionDirect: Emitting conversation-started signal");
-                _gdm_session_conversation_started (GDM_SESSION (session),
-                                                   conversation->service_name);
-        }
+        dbus_connection_set_unix_user_function (new_connection,
+                                                allow_user_function,
+                                                session,
+                                                NULL);
+        dbus_connection_add_filter (new_connection, on_message, session, NULL);
 }
 
 static gboolean
@@ -1725,6 +1774,8 @@ stop_conversation (GdmSessionConversation *conversation)
                                               conversation);
 
         if (conversation->worker_connection != NULL) {
+                dbus_connection_remove_filter (conversation->worker_connection, on_message, session);
+
                 dbus_connection_close (conversation->worker_connection);
                 conversation->worker_connection = NULL;
         }
@@ -1750,10 +1801,6 @@ gdm_session_direct_start_conversation (GdmSession *session,
 
         g_hash_table_insert (impl->priv->conversations,
                              g_strdup (service_name), conversation);
-
-        if (impl->priv->conversation != NULL) {
-                impl->priv->conversation = conversation;
-        }
 }
 
 static void
@@ -1904,45 +1951,50 @@ gdm_session_direct_setup_for_user (GdmSession *session,
 }
 
 static void
-gdm_session_direct_authenticate (GdmSession *session)
+gdm_session_direct_authenticate (GdmSession *session,
+                                 const char *service_name)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
         GdmSessionConversation *conversation;
 
         g_return_if_fail (session != NULL);
-        g_return_if_fail (impl->priv->conversation != NULL);
-        g_return_if_fail (dbus_connection_get_is_connected (impl->priv->conversation->worker_connection));
 
-        conversation = impl->priv->conversation;
-        send_dbus_void_signal (conversation, "Authenticate");
+        conversation = find_conversation_by_name (impl, service_name);
+        if (conversation != NULL) {
+                send_dbus_void_signal (conversation, "Authenticate");
+        }
 }
 
 static void
-gdm_session_direct_authorize (GdmSession *session)
+gdm_session_direct_authorize (GdmSession *session,
+                              const char *service_name)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
         GdmSessionConversation *conversation;
 
         g_return_if_fail (session != NULL);
-        g_return_if_fail (impl->priv->conversation != NULL);
-        g_return_if_fail (dbus_connection_get_is_connected (impl->priv->conversation->worker_connection));
 
-        conversation = impl->priv->conversation;
-        send_dbus_void_signal (conversation, "Authorize");
+        conversation = find_conversation_by_name (impl, service_name);
+        if (conversation != NULL) {
+                send_dbus_void_signal (conversation, "Authorize");
+        }
 }
 
 static void
 gdm_session_direct_accredit (GdmSession *session,
+                             const char *service_name,
                              int         cred_flag)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
         GdmSessionConversation *conversation;
 
         g_return_if_fail (session != NULL);
-        g_return_if_fail (impl->priv->conversation != NULL);
-        g_return_if_fail (dbus_connection_get_is_connected (impl->priv->conversation->worker_connection));
 
-        conversation = impl->priv->conversation;
+        conversation = find_conversation_by_name (impl, service_name);
+        if (conversation == NULL) {
+                return;
+        }
+
         switch (cred_flag) {
         case GDM_SESSION_CRED_ESTABLISH:
                 send_dbus_void_signal (conversation, "EstablishCredentials");
@@ -1956,13 +2008,12 @@ gdm_session_direct_accredit (GdmSession *session,
 }
 
 static void
-send_environment_variable (const char       *key,
-                           const char       *value,
-                           GdmSessionDirect *session)
+send_environment_variable (const char             *key,
+                           const char             *value,
+                           GdmSessionConversation *conversation)
 {
         DBusMessage    *message;
         DBusMessageIter iter;
-        GdmSessionConversation *conversation;
 
         message = dbus_message_new_signal (GDM_SESSION_DBUS_PATH,
                                            GDM_SESSION_DBUS_INTERFACE,
@@ -1972,7 +2023,6 @@ send_environment_variable (const char       *key,
         dbus_message_iter_append_basic (&iter, DBUS_TYPE_STRING, &key);
         dbus_message_iter_append_basic (&iter, DBUS_TYPE_STRING, &value);
 
-        conversation = session->priv->conversation;
         if (! send_dbus_message (conversation, message)) {
                 g_debug ("GdmSessionDirect: Could not send %s signal", "SetEnvironmentVariable");
         }
@@ -1981,12 +2031,13 @@ send_environment_variable (const char       *key,
 }
 
 static void
-send_environment (GdmSessionDirect *session)
+send_environment (GdmSessionDirect       *session,
+                  GdmSessionConversation *conversation)
 {
 
         g_hash_table_foreach (session->priv->environment,
                               (GHFunc) send_environment_variable,
-                              session);
+                              conversation);
 }
 
 static const char *
@@ -2103,7 +2154,8 @@ setup_session_environment (GdmSessionDirect *session)
 }
 
 static void
-gdm_session_direct_start_session (GdmSession *session)
+gdm_session_direct_start_session (GdmSession *session,
+                                  const char *service_name)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
         GdmSessionConversation *conversation;
@@ -2117,10 +2169,11 @@ gdm_session_direct_start_session (GdmSession *session)
         program = g_strdup_printf (GDMCONFDIR "/Xsession \"%s\"", command);
         g_free (command);
 
+        conversation = find_conversation_by_name (impl, service_name);
+
         setup_session_environment (impl);
-        send_environment (impl);
+        send_environment (impl, conversation);
 
-        conversation = impl->priv->conversation;
         send_dbus_string_signal (conversation, "StartProgram", program);
         g_free (program);
 }
@@ -2166,6 +2219,11 @@ gdm_session_direct_close (GdmSession *session)
 
         stop_all_conversations (impl);
 
+        g_list_foreach (impl->priv->pending_connections,
+                        (GFunc) dbus_connection_unref, NULL);
+        g_list_free (impl->priv->pending_connections);
+        impl->priv->pending_connections = NULL;
+
         g_free (impl->priv->selected_user);
         impl->priv->selected_user = NULL;
 
@@ -2198,6 +2256,7 @@ gdm_session_direct_close (GdmSession *session)
 
 static void
 gdm_session_direct_answer_query  (GdmSession *session,
+                                  const char *service_name,
                                   const char *text)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
@@ -2205,7 +2264,7 @@ gdm_session_direct_answer_query  (GdmSession *session,
 
         g_return_if_fail (session != NULL);
 
-        conversation = impl->priv->conversation;
+        conversation = find_conversation_by_name (impl, service_name);
 
         answer_pending_query (conversation, text);
 }
@@ -2231,7 +2290,8 @@ gdm_session_direct_select_session (GdmSession *session,
                                    const char *text)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
-        GdmSessionConversation *conversation;
+        GHashTableIter iter;
+        gpointer key, value;
 
         g_free (impl->priv->selected_session);
 
@@ -2241,9 +2301,15 @@ gdm_session_direct_select_session (GdmSession *session,
                 impl->priv->selected_session = g_strdup (text);
         }
 
-        conversation = impl->priv->conversation;
-        send_dbus_string_signal (conversation, "SetSessionName",
-                                 get_session_name (impl));
+        g_hash_table_iter_init (&iter, impl->priv->conversations);
+        while (g_hash_table_iter_next (&iter, &key, &value)) {
+                GdmSessionConversation *conversation;
+
+                conversation = (GdmSessionConversation *) value;
+
+                send_dbus_string_signal (conversation, "SetSessionName",
+                                         get_session_name (impl));
+        }
 }
 
 static void
@@ -2251,7 +2317,8 @@ gdm_session_direct_select_language (GdmSession *session,
                                     const char *text)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
-        GdmSessionConversation *conversation;
+        GHashTableIter iter;
+        gpointer key, value;
 
         g_free (impl->priv->selected_language);
 
@@ -2261,9 +2328,15 @@ gdm_session_direct_select_language (GdmSession *session,
                 impl->priv->selected_language = g_strdup (text);
         }
 
-        conversation = impl->priv->conversation;
-        send_dbus_string_signal (conversation, "SetLanguageName",
-                                 get_language_name (impl));
+        g_hash_table_iter_init (&iter, impl->priv->conversations);
+        while (g_hash_table_iter_next (&iter, &key, &value)) {
+                GdmSessionConversation *conversation;
+
+                conversation = (GdmSessionConversation *) value;
+
+                send_dbus_string_signal (conversation, "SetLanguageName",
+                                         get_language_name (impl));
+        }
 }
 
 static void
@@ -2271,7 +2344,8 @@ gdm_session_direct_select_layout (GdmSession *session,
                                   const char *text)
 {
         GdmSessionDirect *impl = GDM_SESSION_DIRECT (session);
-        GdmSessionConversation *conversation;
+        GHashTableIter iter;
+        gpointer key, value;
 
         g_free (impl->priv->selected_layout);
 
@@ -2281,9 +2355,15 @@ gdm_session_direct_select_layout (GdmSession *session,
                 impl->priv->selected_layout = g_strdup (text);
         }
 
-        conversation = impl->priv->conversation;
-        send_dbus_string_signal (conversation, "SetLayoutName",
-                                 get_layout_name (impl));
+        g_hash_table_iter_init (&iter, impl->priv->conversations);
+        while (g_hash_table_iter_next (&iter, &key, &value)) {
+                GdmSessionConversation *conversation;
+
+                conversation = (GdmSessionConversation *) value;
+
+                send_dbus_string_signal (conversation, "SetLayoutName",
+                                         get_layout_name (impl));
+        }
 }
 
 static void
diff --git a/daemon/gdm-session-private.h b/daemon/gdm-session-private.h
index 074aa6f..de6e54a 100644
--- a/daemon/gdm-session-private.h
+++ b/daemon/gdm-session-private.h
@@ -29,24 +29,34 @@ G_BEGIN_DECLS
 /* state changes */
 void             _gdm_session_conversation_started         (GdmSession   *session,
                                                             const char   *service_name);
-void             _gdm_session_setup_complete               (GdmSession   *session);
+void             _gdm_session_setup_complete               (GdmSession   *session,
+                                                            const char   *service_name);
 void             _gdm_session_setup_failed                 (GdmSession   *session,
+                                                            const char   *service_name,
                                                             const char   *message);
 void             _gdm_session_reset_complete               (GdmSession   *session);
 void             _gdm_session_reset_failed                 (GdmSession   *session,
                                                             const char   *message);
-void             _gdm_session_authenticated                (GdmSession   *session);
+void             _gdm_session_authenticated                (GdmSession   *session,
+                                                            const char   *service_name);
 void             _gdm_session_authentication_failed        (GdmSession   *session,
+                                                            const char   *service_name,
                                                             const char   *text);
-void             _gdm_session_authorized                   (GdmSession   *session);
+void             _gdm_session_authorized                   (GdmSession   *session,
+                                                            const char   *service_name);
 void             _gdm_session_authorization_failed         (GdmSession   *session,
+                                                            const char   *service_name,
                                                             const char   *text);
-void             _gdm_session_accredited                   (GdmSession   *session);
+void             _gdm_session_accredited                   (GdmSession   *session,
+                                                            const char   *service_name);
 void             _gdm_session_accreditation_failed         (GdmSession   *session,
+                                                            const char   *service_name,
                                                             const char   *text);
 void             _gdm_session_session_started              (GdmSession   *session,
+                                                            const char   *service_name,
                                                             int           pid);
 void             _gdm_session_session_start_failed         (GdmSession   *session,
+                                                            const char   *service_name,
                                                             const char   *message);
 void             _gdm_session_session_exited               (GdmSession   *session,
                                                             int           exit_code);
@@ -67,12 +77,16 @@ void             _gdm_session_selected_user_changed        (GdmSession   *sessio
 
 /* call and response stuff */
 void             _gdm_session_info_query                   (GdmSession   *session,
+                                                            const char   *service_name,
                                                             const char   *text);
 void             _gdm_session_secret_info_query            (GdmSession   *session,
+                                                            const char   *service_name,
                                                             const char   *text);
 void             _gdm_session_info                         (GdmSession   *session,
+                                                            const char   *service_name,
                                                             const char   *text);
 void             _gdm_session_problem                      (GdmSession   *session,
+                                                            const char   *service_name,
                                                             const char   *text);
 
 G_END_DECLS
diff --git a/daemon/gdm-session-relay.c b/daemon/gdm-session-relay.c
index 35b4738..6e15f75 100644
--- a/daemon/gdm-session-relay.c
+++ b/daemon/gdm-session-relay.c
@@ -212,31 +212,34 @@ gdm_session_relay_setup_for_user (GdmSession *session,
 }
 
 static void
-gdm_session_relay_authenticate (GdmSession *session)
+gdm_session_relay_authenticate (GdmSession *session,
+                                const char *service_name)
 {
         GdmSessionRelay *impl = GDM_SESSION_RELAY (session);
-        send_dbus_void_signal (impl, "Authenticate");
+        send_dbus_string_signal (impl, "Authenticate", service_name);
 }
 
 static void
-gdm_session_relay_authorize (GdmSession *session)
+gdm_session_relay_authorize (GdmSession *session,
+                             const char *service_name)
 {
         GdmSessionRelay *impl = GDM_SESSION_RELAY (session);
-        send_dbus_void_signal (impl, "Authorize");
+        send_dbus_string_signal (impl, "Authorize", service_name);
 }
 
 static void
 gdm_session_relay_accredit (GdmSession *session,
+                            const char *service_name,
                             int         cred_flag)
 {
         GdmSessionRelay *impl = GDM_SESSION_RELAY (session);
 
         switch (cred_flag) {
         case GDM_SESSION_CRED_ESTABLISH:
-                send_dbus_void_signal (impl, "EstablishCredentials");
+                send_dbus_string_signal (impl, "EstablishCredentials", service_name);
                 break;
         case GDM_SESSION_CRED_REFRESH:
-                send_dbus_void_signal (impl, "RefreshCredentials");
+                send_dbus_string_signal (impl, "RefreshCredentials", service_name);
                 break;
         default:
                 g_assert_not_reached ();
@@ -245,10 +248,11 @@ gdm_session_relay_accredit (GdmSession *session,
 
 static void
 gdm_session_relay_answer_query (GdmSession *session,
+                                const char *service_name,
                                 const char *text)
 {
         GdmSessionRelay *impl = GDM_SESSION_RELAY (session);
-        send_dbus_string_signal (impl, "AnswerQuery", text);
+        send_dbus_string_string_signal (impl, "AnswerQuery", service_name, text);
 }
 
 static void
@@ -292,11 +296,12 @@ gdm_session_relay_cancel (GdmSession *session)
 }
 
 static void
-gdm_session_relay_start_session (GdmSession *session)
+gdm_session_relay_start_session (GdmSession *session,
+                                 const char *service_name)
 {
         GdmSessionRelay *impl = GDM_SESSION_RELAY (session);
 
-        send_dbus_void_signal (impl, "StartSession");
+        send_dbus_string_signal (impl, "StartSession", service_name);
 }
 
 /* Note: Use abstract sockets like dbus does by default on Linux. Abstract
@@ -334,10 +339,12 @@ handle_info_query (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
-        const char  *text;
+        char  *service_name;
+        char  *text;
 
         dbus_error_init (&error);
         if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
                                      DBUS_TYPE_STRING, &text,
                                      DBUS_TYPE_INVALID)) {
                 g_warning ("ERROR: %s", error.message);
@@ -349,7 +356,7 @@ handle_info_query (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_info_query (GDM_SESSION (session_relay), text);
+        _gdm_session_info_query (GDM_SESSION (session_relay), service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -361,12 +368,14 @@ handle_secret_info_query (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
-        const char  *text;
+        char        *service_name;
+        char  *text;
 
         text = NULL;
 
         dbus_error_init (&error);
         if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
                                      DBUS_TYPE_STRING, &text,
                                      DBUS_TYPE_INVALID)) {
                 g_warning ("ERROR: %s", error.message);
@@ -378,7 +387,7 @@ handle_secret_info_query (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_secret_info_query (GDM_SESSION (session_relay), text);
+        _gdm_session_secret_info_query (GDM_SESSION (session_relay), service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -390,12 +399,14 @@ handle_info (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
-        const char  *text;
+        char        *service_name;
+        char        *text;
 
         text = NULL;
 
         dbus_error_init (&error);
         if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
                                      DBUS_TYPE_STRING, &text,
                                      DBUS_TYPE_INVALID)) {
                 g_warning ("ERROR: %s", error.message);
@@ -407,7 +418,7 @@ handle_info (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_info (GDM_SESSION (session_relay), text);
+        _gdm_session_info (GDM_SESSION (session_relay), service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -419,12 +430,14 @@ handle_problem (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
-        const char  *text;
+        char        *service_name;
+        char        *text;
 
         text = NULL;
 
         dbus_error_init (&error);
         if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
                                      DBUS_TYPE_STRING, &text,
                                      DBUS_TYPE_INVALID)) {
                 g_warning ("ERROR: %s", error.message);
@@ -436,7 +449,7 @@ handle_problem (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_problem (GDM_SESSION (session_relay), text);
+        _gdm_session_problem (GDM_SESSION (session_relay), service_name, text);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -448,8 +461,15 @@ handle_setup_complete (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
+        char        *service_name;
 
         dbus_error_init (&error);
+        if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID)) {
+                g_warning ("ERROR: %s", error.message);
+        }
+        dbus_error_free (&error);
 
         g_debug ("GdmSessionRelay: SetupComplete");
 
@@ -457,7 +477,7 @@ handle_setup_complete (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_setup_complete (GDM_SESSION (session_relay));
+        _gdm_session_setup_complete (GDM_SESSION (session_relay), service_name);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -469,8 +489,15 @@ handle_setup_failed (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
+        char        *service_name;
 
         dbus_error_init (&error);
+        if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID)) {
+                g_warning ("ERROR: %s", error.message);
+        }
+        dbus_error_free (&error);
 
         g_debug ("GdmSessionRelay: SetupFailed");
 
@@ -478,7 +505,7 @@ handle_setup_failed (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_setup_failed (GDM_SESSION (session_relay), NULL);
+        _gdm_session_setup_failed (GDM_SESSION (session_relay), service_name, NULL);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -491,8 +518,15 @@ handle_authenticated (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
+        char        *service_name;
 
         dbus_error_init (&error);
+        if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID)) {
+                g_warning ("ERROR: %s", error.message);
+        }
+        dbus_error_free (&error);
 
         g_debug ("GdmSessionRelay: Authenticated");
 
@@ -500,7 +534,7 @@ handle_authenticated (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_authenticated (GDM_SESSION (session_relay));
+        _gdm_session_authenticated (GDM_SESSION (session_relay), service_name);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -512,8 +546,15 @@ handle_authentication_failed (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
+        char        *service_name;
 
         dbus_error_init (&error);
+        if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID)) {
+                g_warning ("ERROR: %s", error.message);
+        }
+        dbus_error_free (&error);
 
         g_debug ("GdmSessionRelay: AuthenticationFailed");
 
@@ -521,7 +562,7 @@ handle_authentication_failed (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_authentication_failed (GDM_SESSION (session_relay), NULL);
+        _gdm_session_authentication_failed (GDM_SESSION (session_relay), service_name, NULL);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -533,8 +574,15 @@ handle_authorized (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
+        char        *service_name;
 
         dbus_error_init (&error);
+        if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID)) {
+                g_warning ("ERROR: %s", error.message);
+        }
+        dbus_error_free (&error);
 
         g_debug ("GdmSessionRelay: Authorized");
 
@@ -542,7 +590,7 @@ handle_authorized (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_authorized (GDM_SESSION (session_relay));
+        _gdm_session_authorized (GDM_SESSION (session_relay), service_name);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -554,8 +602,15 @@ handle_authorization_failed (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
+        char        *service_name;
 
         dbus_error_init (&error);
+        if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID)) {
+                g_warning ("ERROR: %s", error.message);
+        }
+        dbus_error_free (&error);
 
         g_debug ("GdmSessionRelay: AuthorizationFailed");
 
@@ -563,7 +618,7 @@ handle_authorization_failed (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_authorization_failed (GDM_SESSION (session_relay), NULL);
+        _gdm_session_authorization_failed (GDM_SESSION (session_relay), service_name, NULL);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -575,8 +630,15 @@ handle_accredited (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
+        char        *service_name;
 
         dbus_error_init (&error);
+        if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID)) {
+                g_warning ("ERROR: %s", error.message);
+        }
+        dbus_error_free (&error);
 
         g_debug ("GdmSessionRelay: Accredited");
 
@@ -584,7 +646,7 @@ handle_accredited (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_accredited (GDM_SESSION (session_relay));
+        _gdm_session_accredited (GDM_SESSION (session_relay), service_name);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -596,8 +658,15 @@ handle_accreditation_failed (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
+        char        *service_name;
 
         dbus_error_init (&error);
+        if (! dbus_message_get_args (message, &error,
+                                     DBUS_TYPE_STRING, &service_name,
+                                     DBUS_TYPE_INVALID)) {
+                g_warning ("ERROR: %s", error.message);
+        }
+        dbus_error_free (&error);
 
         g_debug ("GdmSessionRelay: AccreditationFailed");
 
@@ -605,7 +674,7 @@ handle_accreditation_failed (GdmSessionRelay *session_relay,
         dbus_connection_send (connection, reply, NULL);
         dbus_message_unref (reply);
 
-        _gdm_session_accreditation_failed (GDM_SESSION (session_relay), NULL);
+        _gdm_session_accreditation_failed (GDM_SESSION (session_relay), service_name, NULL);
 
         return DBUS_HANDLER_RESULT_HANDLED;
 }
@@ -617,6 +686,7 @@ handle_session_started (GdmSessionRelay *session_relay,
 {
         DBusMessage *reply;
         DBusError    error;
+        char        *service_name;
         int          pid;
 
         dbus_error_init (&error);
@@ -624,6 +694,7 @@ handle_session_started (GdmSessionRelay *session_relay,
         pid = 0;
         if (! dbus_message_get_args (message,
                                      &error,
+                                     DBUS_TYPE_STRING, &service_name,
                                      DBUS_TYPE_INT32, &pid,
                                      DBUS_TYPE_INVALID)) {
                 g_warning ("ERROR: %s", error.message);
@@ -636,6 +707,7 @@ handle_session_started (GdmSessionRelay *session_relay,
         dbus_message_unref (reply);
 
         _gdm_session_session_started (GDM_SESSION (session_relay),
+                                      service_name,
                                       pid);
 
         return DBUS_HANDLER_RESULT_HANDLED;
diff --git a/daemon/gdm-session-worker.c b/daemon/gdm-session-worker.c
index 47a5c08..bcd4f93 100644
--- a/daemon/gdm-session-worker.c
+++ b/daemon/gdm-session-worker.c
@@ -2851,6 +2851,28 @@ worker_dbus_filter_function (DBusConnection *connection,
         return DBUS_HANDLER_RESULT_HANDLED;
 }
 
+static void
+send_hello (GdmSessionWorker *worker)
+{
+        DBusMessage *message, *reply;
+        DBusError error;
+
+        message = dbus_message_new_method_call (NULL,
+                                                GDM_SESSION_DBUS_PATH,
+                                                GDM_SESSION_DBUS_INTERFACE,
+                                                "Hello");
+
+        dbus_error_init (&error);
+        reply = dbus_connection_send_with_reply_and_block (worker->priv->connection,
+                                                           message, -1, &error);
+        dbus_message_unref (message);
+        dbus_error_free (&error);
+
+        if (reply != NULL) {
+                dbus_message_unref (reply);
+        }
+}
+
 static GObject *
 gdm_session_worker_constructor (GType                  type,
                                 guint                  n_construct_properties,
@@ -2877,6 +2899,11 @@ gdm_session_worker_constructor (GType                  type,
                 exit (1);
         }
 
+        /* Send an initial Hello message so that the session can associate
+         * the conversation we manage with our pid.
+         */
+        send_hello (worker);
+
         dbus_connection_setup_with_g_main (worker->priv->connection, NULL);
         dbus_connection_set_exit_on_disconnect (worker->priv->connection, TRUE);
 
diff --git a/daemon/gdm-session.c b/daemon/gdm-session.c
index 0073294..5f6ff5d 100644
--- a/daemon/gdm-session.c
+++ b/daemon/gdm-session.c
@@ -24,6 +24,7 @@
 #include <glib/gi18n.h>
 #include <glib-object.h>
 
+#include "gdm-marshal.h"
 #include "gdm-session.h"
 #include "gdm-session-private.h"
 
@@ -114,37 +115,41 @@ gdm_session_setup_for_user (GdmSession *session,
 }
 
 void
-gdm_session_authenticate (GdmSession *session)
+gdm_session_authenticate (GdmSession *session,
+                          const char *service_name)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
 
-        GDM_SESSION_GET_IFACE (session)->authenticate (session);
+        GDM_SESSION_GET_IFACE (session)->authenticate (session, service_name);
 }
 
 void
-gdm_session_authorize (GdmSession *session)
+gdm_session_authorize (GdmSession *session,
+                       const char *service_name)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
 
-        GDM_SESSION_GET_IFACE (session)->authorize (session);
+        GDM_SESSION_GET_IFACE (session)->authorize (session, service_name);
 }
 
 void
 gdm_session_accredit (GdmSession *session,
+                      const char *service_name,
                       int         flag)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
 
-        GDM_SESSION_GET_IFACE (session)->accredit (session, flag);
+        GDM_SESSION_GET_IFACE (session)->accredit (session, service_name, flag);
 }
 
 void
 gdm_session_answer_query (GdmSession *session,
+                          const char *service_name,
                           const char *text)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
 
-        GDM_SESSION_GET_IFACE (session)->answer_query (session, text);
+        GDM_SESSION_GET_IFACE (session)->answer_query (session, service_name, text);
 }
 
 void
@@ -192,11 +197,12 @@ gdm_session_cancel (GdmSession *session)
 }
 
 void
-gdm_session_start_session (GdmSession *session)
+gdm_session_start_session (GdmSession *session,
+                           const char *service_name)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
 
-        GDM_SESSION_GET_IFACE (session)->start_session (session);
+        GDM_SESSION_GET_IFACE (session)->start_session (session, service_name);
 }
 
 static void
@@ -213,7 +219,7 @@ gdm_session_class_init (gpointer g_iface)
                               NULL,
                               g_cclosure_marshal_VOID__STRING,
                               G_TYPE_NONE,
-                              0);
+                              1, G_TYPE_STRING);
         signals [SETUP_COMPLETE] =
                 g_signal_new ("setup-complete",
                               iface_type,
@@ -221,9 +227,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, setup_complete),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__VOID,
+                              g_cclosure_marshal_VOID__STRING,
                               G_TYPE_NONE,
-                              0);
+                              1,
+                              G_TYPE_STRING);
         signals [SETUP_FAILED] =
                 g_signal_new ("setup-failed",
                               iface_type,
@@ -231,10 +238,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, setup_failed),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
         signals [RESET_COMPLETE] =
                 g_signal_new ("reset-complete",
                               iface_type,
@@ -263,9 +270,9 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, authenticated),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__VOID,
+                              g_cclosure_marshal_VOID__STRING,
                               G_TYPE_NONE,
-                              0);
+                              1, G_TYPE_STRING);
         signals [AUTHENTICATION_FAILED] =
                 g_signal_new ("authentication-failed",
                               iface_type,
@@ -273,10 +280,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, authentication_failed),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
         signals [AUTHORIZED] =
                 g_signal_new ("authorized",
                               iface_type,
@@ -284,9 +291,9 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, authorized),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__VOID,
+                              g_cclosure_marshal_VOID__STRING,
                               G_TYPE_NONE,
-                              0);
+                              1, G_TYPE_STRING);
         signals [AUTHORIZATION_FAILED] =
                 g_signal_new ("authorization-failed",
                               iface_type,
@@ -294,10 +301,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, authorization_failed),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
         signals [ACCREDITED] =
                 g_signal_new ("accredited",
                               iface_type,
@@ -305,9 +312,9 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, accredited),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__VOID,
+                              g_cclosure_marshal_VOID__STRING,
                               G_TYPE_NONE,
-                              0);
+                              1, G_TYPE_STRING);
         signals [ACCREDITATION_FAILED] =
                 g_signal_new ("accreditation-failed",
                               iface_type,
@@ -315,10 +322,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, accreditation_failed),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
 
          signals [INFO_QUERY] =
                 g_signal_new ("info-query",
@@ -327,10 +334,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, info_query),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
         signals [SECRET_INFO_QUERY] =
                 g_signal_new ("secret-info-query",
                               iface_type,
@@ -338,10 +345,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, secret_info_query),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
         signals [INFO] =
                 g_signal_new ("info",
                               iface_type,
@@ -349,10 +356,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, info),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
         signals [PROBLEM] =
                 g_signal_new ("problem",
                               iface_type,
@@ -360,10 +367,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, problem),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
         signals [SESSION_STARTED] =
                 g_signal_new ("session-started",
                               iface_type,
@@ -371,10 +378,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, session_started),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__INT,
+                              gdm_marshal_VOID__STRING_INT,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_INT);
+                              2,
+                              G_TYPE_STRING, G_TYPE_INT);
         signals [SESSION_START_FAILED] =
                 g_signal_new ("session-start-failed",
                               iface_type,
@@ -382,10 +389,10 @@ gdm_session_class_init (gpointer g_iface)
                               G_STRUCT_OFFSET (GdmSessionIface, session_start_failed),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
         signals [SESSION_EXITED] =
                 g_signal_new ("session-exited",
                               iface_type,
@@ -465,19 +472,21 @@ gdm_session_class_init (gpointer g_iface)
 }
 
 void
-_gdm_session_setup_complete (GdmSession   *session)
+_gdm_session_setup_complete (GdmSession   *session,
+                             const char   *service_name)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
 
-        g_signal_emit (session, signals [SETUP_COMPLETE], 0);
+        g_signal_emit (session, signals [SETUP_COMPLETE], 0, service_name);
 }
 
 void
 _gdm_session_setup_failed (GdmSession   *session,
+                           const char   *service_name,
                            const char   *text)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
-        g_signal_emit (session, signals [SETUP_FAILED], 0, text);
+        g_signal_emit (session, signals [SETUP_FAILED], 0, service_name, text);
 }
 
 void
@@ -497,99 +506,111 @@ _gdm_session_reset_failed (GdmSession   *session,
 }
 
 void
-_gdm_session_authenticated (GdmSession   *session)
+_gdm_session_authenticated (GdmSession   *session,
+                            const char   *service_name)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
 
-        g_signal_emit (session, signals [AUTHENTICATED], 0);
+        g_signal_emit (session, signals [AUTHENTICATED], 0, service_name);
 }
 
 void
 _gdm_session_authentication_failed (GdmSession   *session,
+                                    const char   *service_name,
                                     const char   *text)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
-        g_signal_emit (session, signals [AUTHENTICATION_FAILED], 0, text);
+        g_signal_emit (session, signals [AUTHENTICATION_FAILED], 0, service_name, text);
 }
 
 void
-_gdm_session_authorized (GdmSession   *session)
+_gdm_session_authorized (GdmSession   *session,
+                         const char   *service_name)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
 
-        g_signal_emit (session, signals [AUTHORIZED], 0);
+        g_signal_emit (session, signals [AUTHORIZED], 0, service_name);
 }
 
 void
 _gdm_session_authorization_failed (GdmSession   *session,
+                                   const char   *service_name,
                                    const char   *text)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
-        g_signal_emit (session, signals [AUTHORIZATION_FAILED], 0, text);
+        g_signal_emit (session, signals [AUTHORIZATION_FAILED], 0, service_name, text);
 }
 
 void
-_gdm_session_accredited (GdmSession   *session)
+_gdm_session_accredited (GdmSession   *session,
+                         const char   *service_name)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
 
-        g_signal_emit (session, signals [ACCREDITED], 0);
+        g_signal_emit (session, signals [ACCREDITED], 0, service_name);
 }
 
 void
 _gdm_session_accreditation_failed (GdmSession   *session,
+                                   const char   *service_name,
                                    const char   *text)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
-        g_signal_emit (session, signals [ACCREDITATION_FAILED], 0, text);
+        g_signal_emit (session, signals [ACCREDITATION_FAILED], 0, service_name, text);
 }
 
 void
 _gdm_session_info_query (GdmSession   *session,
+                         const char   *service_name,
                          const char   *text)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
-        g_signal_emit (session, signals [INFO_QUERY], 0, text);
+        g_signal_emit (session, signals [INFO_QUERY], 0, service_name, text);
 }
 
 void
 _gdm_session_secret_info_query (GdmSession   *session,
+                                const char   *service_name,
                                 const char   *text)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
-        g_signal_emit (session, signals [SECRET_INFO_QUERY], 0, text);
+        g_signal_emit (session, signals [SECRET_INFO_QUERY], 0, service_name, text);
 }
 
 void
 _gdm_session_info (GdmSession   *session,
+                   const char   *service_name,
                    const char   *text)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
-        g_signal_emit (session, signals [INFO], 0, text);
+        g_signal_emit (session, signals [INFO], 0, service_name, text);
 }
 
 void
 _gdm_session_problem (GdmSession   *session,
+                      const char   *service_name,
                       const char   *text)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
-        g_signal_emit (session, signals [PROBLEM], 0, text);
+        g_signal_emit (session, signals [PROBLEM], 0, service_name, text);
 }
 
 void
 _gdm_session_session_started (GdmSession   *session,
+                              const char   *service_name,
                               int           pid)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
-        g_signal_emit (session, signals [SESSION_STARTED], 0, pid);
+        g_signal_emit (session, signals [SESSION_STARTED], 0, service_name, pid);
 }
 
 void
 _gdm_session_session_start_failed (GdmSession   *session,
+                                   const char   *service_name,
                                    const char   *text)
 {
         g_return_if_fail (GDM_IS_SESSION (session));
-        g_signal_emit (session, signals [SESSION_START_FAILED], 0, text);
+        g_signal_emit (session, signals [SESSION_START_FAILED], 0, service_name, text);
 }
 
 void
diff --git a/daemon/gdm-session.h b/daemon/gdm-session.h
index 77e0cf6..db5fc4a 100644
--- a/daemon/gdm-session.h
+++ b/daemon/gdm-session.h
@@ -53,11 +53,15 @@ struct _GdmSessionIface
                                               const char   *service_name,
                                               const char   *username);
         void (* reset)                       (GdmSession   *session);
-        void (* authenticate)                (GdmSession   *session);
-        void (* authorize)                   (GdmSession   *session);
+        void (* authenticate)                (GdmSession   *session,
+                                              const char   *service_name);
+        void (* authorize)                   (GdmSession   *session,
+                                              const char   *service_name);
         void (* accredit)                    (GdmSession   *session,
+                                              const char   *service_name,
                                               int           cred_flag);
         void (* answer_query)                (GdmSession   *session,
+                                              const char   *service_name,
                                               const char   *text);
         void (* select_language)             (GdmSession   *session,
                                               const char   *text);
@@ -67,38 +71,53 @@ struct _GdmSessionIface
                                               const char   *text);
         void (* select_user)                 (GdmSession   *session,
                                               const char   *text);
-        void (* start_session)               (GdmSession   *session);
+        void (* start_session)               (GdmSession   *session,
+                                              const char   *service_name);
         void (* close)                       (GdmSession   *session);
         void (* cancel)                      (GdmSession   *session);
 
         /* Signals */
-        void (* setup_complete)              (GdmSession   *session);
+        void (* setup_complete)              (GdmSession   *session,
+                                              const char   *service_name);
         void (* setup_failed)                (GdmSession   *session,
+                                              const char   *service_name,
                                               const char   *message);
         void (* reset_complete)              (GdmSession   *session);
         void (* reset_failed)                (GdmSession   *session,
                                               const char   *message);
-        void (* authenticated)               (GdmSession   *session);
+        void (* authenticated)               (GdmSession   *session,
+                                              const char   *service_name);
         void (* authentication_failed)       (GdmSession   *session,
+                                              const char   *service_name,
                                               const char   *message);
-        void (* authorized)                  (GdmSession   *session);
+        void (* authorized)                  (GdmSession   *session,
+                                              const char   *service_name);
         void (* authorization_failed)        (GdmSession   *session,
+                                              const char   *service_name,
                                               const char   *message);
-        void (* accredited)                  (GdmSession   *session);
+        void (* accredited)                  (GdmSession   *session,
+                                              const char   *service_name);
         void (* accreditation_failed)        (GdmSession   *session,
+                                              const char   *service_name,
                                               const char   *message);
 
         void (* info_query)                  (GdmSession   *session,
+                                              const char   *service_name,
                                               const char   *query_text);
         void (* secret_info_query)           (GdmSession   *session,
+                                              const char   *service_name,
                                               const char   *query_text);
         void (* info)                        (GdmSession   *session,
+                                              const char   *service_name,
                                               const char   *info);
         void (* problem)                     (GdmSession   *session,
+                                              const char   *service_name,
                                               const char   *problem);
         void (* session_started)             (GdmSession   *session,
+                                              const char   *service_name,
                                               int           pid);
         void (* session_start_failed)        (GdmSession   *session,
+                                              const char   *service_name,
                                               const char   *message);
         void (* session_exited)              (GdmSession   *session,
                                               int           exit_code);
@@ -128,14 +147,19 @@ void     gdm_session_setup_for_user              (GdmSession *session,
                                                   const char *service_name,
                                                   const char *username);
 void     gdm_session_reset                       (GdmSession *session);
-void     gdm_session_authenticate                (GdmSession *session);
-void     gdm_session_authorize                   (GdmSession *session);
+void     gdm_session_authenticate                (GdmSession *session,
+                                                  const char *service_name);
+void     gdm_session_authorize                   (GdmSession *session,
+                                                  const char *service_name);
 void     gdm_session_accredit                    (GdmSession *session,
+                                                  const char *service_name,
                                                   int         cred_flag);
-void     gdm_session_start_session               (GdmSession *session);
+void     gdm_session_start_session               (GdmSession *session,
+                                                  const char *service_name);
 void     gdm_session_close                       (GdmSession *session);
 
 void     gdm_session_answer_query                (GdmSession *session,
+                                                  const char *service_name,
                                                   const char *text);
 void     gdm_session_select_session              (GdmSession *session,
                                                   const char *session_name);
diff --git a/daemon/gdm-simple-slave.c b/daemon/gdm-simple-slave.c
index 4db7440..9421a64 100644
--- a/daemon/gdm-simple-slave.c
+++ b/daemon/gdm-simple-slave.c
@@ -71,6 +71,8 @@ struct GdmSimpleSlavePrivate
         guint              greeter_reset_id;
         guint              start_session_id;
 
+        char              *start_session_service_name;
+
         int                ping_interval;
 
         GPid               server_pid;
@@ -101,6 +103,7 @@ static void start_greeter      (GdmSimpleSlave *slave);
 
 static void
 on_session_started (GdmSession       *session,
+                    const char       *service_name,
                     int               pid,
                     GdmSimpleSlave   *slave)
 {
@@ -204,19 +207,22 @@ queue_greeter_reset (GdmSimpleSlave *slave)
 
 static void
 on_session_setup_complete (GdmSession     *session,
+                           const char     *service_name,
                            GdmSimpleSlave *slave)
 {
-        gdm_session_authenticate (session);
+        gdm_session_authenticate (session, service_name);
 }
 
 static void
 on_session_setup_failed (GdmSession     *session,
+                         const char     *service_name,
                          const char     *message,
                          GdmSimpleSlave *slave)
 {
         if (slave->priv->greeter_server != NULL) {
                 gdm_greeter_server_problem (slave->priv->greeter_server,
-                                           message != NULL ? message:  _("Unable to initialize login system"));
+                                            service_name,
+                                            message != NULL ? message:  _("Unable to initialize login system"));
         }
 
         destroy_session (slave);
@@ -240,18 +246,21 @@ on_session_reset_failed (GdmSession     *session,
 
 static void
 on_session_authenticated (GdmSession     *session,
+                          const char     *service_name,
                           GdmSimpleSlave *slave)
 {
-        gdm_session_authorize (session);
+        gdm_session_authorize (session, service_name);
 }
 
 static void
 on_session_authentication_failed (GdmSession     *session,
+                                  const char     *service_name,
                                   const char     *message,
                                   GdmSimpleSlave *slave)
 {
         if (slave->priv->greeter_server != NULL) {
                 gdm_greeter_server_problem (slave->priv->greeter_server,
+                                            service_name,
                                             message != NULL ? message : _("Unable to authenticate user"));
         }
         destroy_session (slave);
@@ -259,7 +268,8 @@ on_session_authentication_failed (GdmSession     *session,
 }
 
 static void
-gdm_simple_slave_accredit_when_ready (GdmSimpleSlave *slave)
+gdm_simple_slave_accredit_when_ready (GdmSimpleSlave *slave,
+                                      const char     *service_name)
 {
         if (slave->priv->start_session_when_ready) {
                 char *ssid;
@@ -280,7 +290,7 @@ gdm_simple_slave_accredit_when_ready (GdmSimpleSlave *slave)
                 g_free (ssid);
                 g_free (username);
 
-                gdm_session_accredit (GDM_SESSION (slave->priv->session), cred_flag);
+                gdm_session_accredit (GDM_SESSION (slave->priv->session), service_name, cred_flag);
         } else {
                 slave->priv->waiting_to_start_session = TRUE;
         }
@@ -288,25 +298,28 @@ gdm_simple_slave_accredit_when_ready (GdmSimpleSlave *slave)
 
 static void
 on_session_authorized (GdmSession     *session,
+                       const char     *service_name,
                        GdmSimpleSlave *slave)
 {
         if (slave->priv->greeter_server != NULL) {
-                gdm_greeter_server_user_authorized (slave->priv->greeter_server);
-                gdm_simple_slave_accredit_when_ready (slave);
+                gdm_greeter_server_user_authorized (slave->priv->greeter_server, service_name);
+                gdm_simple_slave_accredit_when_ready (slave, service_name);
         } else {
                 slave->priv->start_session_when_ready = TRUE;
-                gdm_simple_slave_accredit_when_ready (slave);
+                gdm_simple_slave_accredit_when_ready (slave, service_name);
         }
 }
 
 static void
 on_session_authorization_failed (GdmSession     *session,
+                                 const char     *service_name,
                                  const char     *message,
                                  GdmSimpleSlave *slave)
 {
         if (slave->priv->greeter_server != NULL) {
                 gdm_greeter_server_problem (slave->priv->greeter_server,
-                                           message != NULL ? message :  _("Unable to authorize user"));
+                                            service_name,
+                                            message != NULL ? message :  _("Unable to authorize user"));
         }
 
         destroy_session (slave);
@@ -386,31 +399,38 @@ start_session_timeout (GdmSimpleSlave *slave)
 
         g_free (auth_file);
 
-        gdm_session_start_session (GDM_SESSION (slave->priv->session));
+        gdm_session_start_session (GDM_SESSION (slave->priv->session),
+                                   slave->priv->start_session_service_name);
  out:
         slave->priv->start_session_id = 0;
+        g_free (slave->priv->start_session_service_name);
+        slave->priv->start_session_service_name = NULL;
         return FALSE;
 }
 
 static void
-queue_start_session (GdmSimpleSlave *slave)
+queue_start_session (GdmSimpleSlave *slave,
+                     const char     *service_name)
 {
         if (slave->priv->start_session_id > 0) {
                 return;
         }
 
         slave->priv->start_session_id = g_idle_add ((GSourceFunc)start_session_timeout, slave);
+        slave->priv->start_session_service_name = g_strdup (service_name);
 }
 
 static void
 on_session_accredited (GdmSession     *session,
+                       const char     *service_name,
                        GdmSimpleSlave *slave)
 {
-        queue_start_session (slave);
+        queue_start_session (slave, service_name);
 }
 
 static void
 on_session_accreditation_failed (GdmSession     *session,
+                                 const char     *service_name,
                                  const char     *message,
                                  GdmSimpleSlave *slave)
 {
@@ -431,6 +451,7 @@ on_session_accreditation_failed (GdmSession     *session,
                                 problem = _("Unable to establish credentials");
                         }
                         gdm_greeter_server_problem (slave->priv->greeter_server,
+                                                    service_name,
                                                     problem);
                 }
         }
@@ -446,41 +467,45 @@ on_session_accreditation_failed (GdmSession     *session,
 
 static void
 on_session_info (GdmSession     *session,
+                 const char     *service_name,
                  const char     *text,
                  GdmSimpleSlave *slave)
 {
         g_debug ("GdmSimpleSlave: Info: %s", text);
         if (slave->priv->greeter_server != NULL) {
-                gdm_greeter_server_info (slave->priv->greeter_server, text);
+                gdm_greeter_server_info (slave->priv->greeter_server, service_name, text);
         }
 }
 
 static void
 on_session_problem (GdmSession     *session,
+                    const char     *service_name,
                     const char     *text,
                     GdmSimpleSlave *slave)
 {
         g_debug ("GdmSimpleSlave: Problem: %s", text);
-        gdm_greeter_server_problem (slave->priv->greeter_server, text);
+        gdm_greeter_server_problem (slave->priv->greeter_server, service_name, text);
 }
 
 static void
 on_session_info_query (GdmSession     *session,
+                       const char     *service_name,
                        const char     *text,
                        GdmSimpleSlave *slave)
 {
 
         g_debug ("GdmSimpleSlave: Info query: %s", text);
-        gdm_greeter_server_info_query (slave->priv->greeter_server, text);
+        gdm_greeter_server_info_query (slave->priv->greeter_server, service_name, text);
 }
 
 static void
 on_session_secret_info_query (GdmSession     *session,
+                              const char     *service_name,
                               const char     *text,
                               GdmSimpleSlave *slave)
 {
         g_debug ("GdmSimpleSlave: Secret info query: %s", text);
-        gdm_greeter_server_secret_info_query (slave->priv->greeter_server, text);
+        gdm_greeter_server_secret_info_query (slave->priv->greeter_server, service_name, text);
 }
 
 static void
@@ -750,11 +775,12 @@ on_greeter_start_conversation (GdmGreeterServer *greeter_server,
 
 static void
 on_greeter_begin_verification (GdmGreeterServer *greeter_server,
+                               const char       *service_name,
                                GdmSimpleSlave   *slave)
 {
         g_debug ("GdmSimpleSlave: begin verification");
         gdm_session_setup (GDM_SESSION (slave->priv->session),
-                           "gdm");
+                           service_name);
 }
 
 static void
@@ -770,21 +796,23 @@ on_greeter_begin_auto_login (GdmGreeterServer *greeter_server,
 
 static void
 on_greeter_begin_verification_for_user (GdmGreeterServer *greeter_server,
+                                        const char       *service_name,
                                         const char       *username,
                                         GdmSimpleSlave   *slave)
 {
         g_debug ("GdmSimpleSlave: begin verification");
         gdm_session_setup_for_user (GDM_SESSION (slave->priv->session),
-                                    "gdm",
+                                    service_name,
                                     username);
 }
 
 static void
 on_greeter_answer (GdmGreeterServer *greeter_server,
+                   const char       *service_name,
                    const char       *text,
                    GdmSimpleSlave   *slave)
 {
-        gdm_session_answer_query (GDM_SESSION (slave->priv->session), text);
+        gdm_session_answer_query (GDM_SESSION (slave->priv->session), service_name, text);
 }
 
 static void
@@ -847,18 +875,20 @@ on_greeter_connected (GdmGreeterServer *greeter_server,
 
 static void
 on_start_session_when_ready (GdmGreeterServer *session,
+                             const char       *service_name,
                              GdmSimpleSlave   *slave)
 {
         g_debug ("GdmSimpleSlave: Will start session when ready");
         slave->priv->start_session_when_ready = TRUE;
 
         if (slave->priv->waiting_to_start_session) {
-                gdm_simple_slave_accredit_when_ready (slave);
+                gdm_simple_slave_accredit_when_ready (slave, service_name);
         }
 }
 
 static void
 on_start_session_later (GdmGreeterServer *session,
+                        const char       *service_name,
                         GdmSimpleSlave   *slave)
 {
         g_debug ("GdmSimpleSlave: Will start session when ready and told");
diff --git a/daemon/test-session.c b/daemon/test-session.c
index d9fa26e..3cf8483 100644
--- a/daemon/test-session.c
+++ b/daemon/test-session.c
@@ -44,10 +44,11 @@ on_conversation_started (GdmSession *session,
 
 static void
 on_session_setup_complete (GdmSession *session,
+                           const char *service_name,
                            gpointer    data)
 {
         g_debug ("Session setup complete");
-        gdm_session_authenticate (session);
+        gdm_session_authenticate (session, service_name);
 }
 
 static void
@@ -79,10 +80,11 @@ on_session_reset_failed (GdmSession *session,
 
 static void
 on_session_authenticated (GdmSession *session,
+                          const char *service_name,
                           gpointer    data)
 {
         g_debug ("Session authenticated");
-        gdm_session_authorize (session);
+        gdm_session_authorize (session, service_name);
 }
 
 static void
@@ -97,14 +99,16 @@ on_session_authentication_failed (GdmSession *session,
 
 static void
 on_session_authorized (GdmSession *session,
+                       const char *service_name,
                        gpointer    data)
 {
         g_debug ("Session authorized");
-        gdm_session_accredit (session, GDM_SESSION_CRED_ESTABLISH);
+        gdm_session_accredit (session, service_name, GDM_SESSION_CRED_ESTABLISH);
 }
 
 static void
 on_session_authorization_failed (GdmSession *session,
+                                 const char *service_name,
                                  const char *message,
                                  gpointer    data)
 {
@@ -115,6 +119,7 @@ on_session_authorization_failed (GdmSession *session,
 
 static void
 on_session_accredited (GdmSession *session,
+                       const char *service_name,
                        gpointer    data)
 {
         char *username;
@@ -125,12 +130,13 @@ on_session_accredited (GdmSession *session,
                  username ? username : "", username ? " " : "");
         g_free (username);
 
-        gdm_session_start_session (session);
+        gdm_session_start_session (session, service_name);
 
 }
 
 static void
 on_session_accreditation_failed (GdmSession *session,
+                                 const char *service_name,
                                  const char *message,
                                  gpointer    data)
 {
@@ -165,6 +171,7 @@ on_session_died (GdmSession *session,
 
 static void
 on_info_query (GdmSession *session,
+               const char *service_name,
                const char *query_text)
 {
         char answer[1024];
@@ -178,12 +185,13 @@ on_info_query (GdmSession *session,
                 gdm_session_close (session);
                 g_main_loop_quit (loop);
         } else {
-                gdm_session_answer_query (session, answer);
+                gdm_session_answer_query (session, service_name, answer);
         }
 }
 
 static void
 on_info (GdmSession *session,
+         const char *service_name,
          const char *info)
 {
         g_print ("\n** NOTE: %s\n", info);
@@ -191,6 +199,7 @@ on_info (GdmSession *session,
 
 static void
 on_problem (GdmSession *session,
+            const char *service_name,
             const char *problem)
 {
         g_print ("\n** WARNING: %s\n", problem);
@@ -198,6 +207,7 @@ on_problem (GdmSession *session,
 
 static void
 on_secret_info_query (GdmSession *session,
+                      const char *service_name,
                       const char *query_text)
 {
         char           answer[1024];
@@ -222,7 +232,7 @@ on_secret_info_query (GdmSession *session,
 
         g_print ("\n");
 
-        gdm_session_answer_query (session, answer);
+        gdm_session_answer_query (session, service_name, answer);
 }
 
 static void
diff --git a/gui/simple-greeter/gdm-greeter-client.c b/gui/simple-greeter/gdm-greeter-client.c
index 1e2c55d..0bd27a9 100644
--- a/gui/simple-greeter/gdm-greeter-client.c
+++ b/gui/simple-greeter/gdm-greeter-client.c
@@ -134,6 +134,37 @@ emit_string_and_int_signal_for_message (GdmGreeterClient *client,
 }
 
 static void
+emit_string_and_string_signal_for_message (GdmGreeterClient *client,
+                                           const char       *name,
+                                           DBusMessage      *message,
+                                           int               signal)
+{
+        DBusError   error;
+        char *text1;
+        char *text2;
+        dbus_bool_t res;
+
+        dbus_error_init (&error);
+        res = dbus_message_get_args (message,
+                                     &error,
+                                     DBUS_TYPE_STRING, &text1,
+                                     DBUS_TYPE_STRING, &text2,
+                                     DBUS_TYPE_INVALID);
+        if (res) {
+
+                g_debug ("GdmGreeterClient: Received %s (%s, %s)", name, text1, text2);
+
+                g_signal_emit (client,
+                               gdm_greeter_client_signals[signal],
+                               0, text1, text2);
+        } else {
+                g_warning ("Unable to get arguments: %s", error.message);
+                dbus_error_free (&error);
+        }
+        dbus_error_free (&error);
+}
+
+static void
 emit_string_signal_for_message (GdmGreeterClient *client,
                                 const char       *name,
                                 DBusMessage      *message,
@@ -200,37 +231,35 @@ static void
 on_user_authorized (GdmGreeterClient *client,
                     DBusMessage      *message)
 {
-        g_signal_emit (client,
-                       gdm_greeter_client_signals[USER_AUTHORIZED],
-                       0);
+        emit_string_signal_for_message (client, "UserAuthorized", message, USER_AUTHORIZED);
 }
 
 static void
 on_info_query (GdmGreeterClient *client,
                DBusMessage      *message)
 {
-        emit_string_signal_for_message (client, "InfoQuery", message, INFO_QUERY);
+        emit_string_and_string_signal_for_message (client, "InfoQuery", message, INFO_QUERY);
 }
 
 static void
 on_secret_info_query (GdmGreeterClient *client,
                       DBusMessage      *message)
 {
-        emit_string_signal_for_message (client, "SecretInfoQuery", message, SECRET_INFO_QUERY);
+        emit_string_and_string_signal_for_message (client, "SecretInfoQuery", message, SECRET_INFO_QUERY);
 }
 
 static void
 on_info (GdmGreeterClient *client,
          DBusMessage      *message)
 {
-        emit_string_signal_for_message (client, "Info", message, INFO);
+        emit_string_and_string_signal_for_message (client, "Info", message, INFO);
 }
 
 static void
 on_problem (GdmGreeterClient *client,
             DBusMessage      *message)
 {
-        emit_string_signal_for_message (client, "Problem", message, PROBLEM);
+        emit_string_and_string_signal_for_message (client, "Problem", message, PROBLEM);
 }
 
 static void
@@ -307,14 +336,22 @@ send_dbus_string_method (DBusConnection *connection,
 }
 
 static gboolean
-send_dbus_bool_method (DBusConnection *connection,
-                       const char     *method,
-                       gboolean        payload)
+send_dbus_string_and_bool_method (DBusConnection *connection,
+                                  const char     *method,
+                                  const char     *string_payload,
+                                  gboolean        bool_payload)
 {
         DBusError       error;
         DBusMessage    *message;
         DBusMessage    *reply;
         DBusMessageIter iter;
+        const char     *str;
+
+        if (string_payload != NULL) {
+                str = string_payload;
+        } else {
+                str = "";
+        }
 
         g_debug ("GdmGreeterClient: Calling %s", method);
         message = dbus_message_new_method_call (NULL,
@@ -328,8 +365,77 @@ send_dbus_bool_method (DBusConnection *connection,
 
         dbus_message_iter_init_append (message, &iter);
         dbus_message_iter_append_basic (&iter,
+                                        DBUS_TYPE_STRING,
+                                        &str);
+
+        dbus_message_iter_append_basic (&iter,
                                         DBUS_TYPE_BOOLEAN,
-                                        &payload);
+                                        &bool_payload);
+
+        dbus_error_init (&error);
+        reply = dbus_connection_send_with_reply_and_block (connection,
+                                                           message,
+                                                           -1,
+                                                           &error);
+
+        dbus_message_unref (message);
+
+        if (dbus_error_is_set (&error)) {
+                g_warning ("%s %s raised: %s\n",
+                           method,
+                           error.name,
+                           error.message);
+                return FALSE;
+        }
+        if (reply != NULL) {
+                dbus_message_unref (reply);
+        }
+        dbus_connection_flush (connection);
+
+        return TRUE;
+}
+
+static gboolean
+send_dbus_string_and_string_method (DBusConnection *connection,
+                                    const char     *method,
+                                    const char     *payload1,
+                                    const char     *payload2)
+{
+        DBusError       error;
+        DBusMessage    *message;
+        DBusMessage    *reply;
+        DBusMessageIter iter;
+        const char     *str;
+
+        g_debug ("GdmGreeterClient: Calling %s", method);
+        message = dbus_message_new_method_call (NULL,
+                                                GREETER_SERVER_DBUS_PATH,
+                                                GREETER_SERVER_DBUS_INTERFACE,
+                                                method);
+        if (message == NULL) {
+                g_warning ("Couldn't allocate the D-Bus message");
+                return FALSE;
+        }
+
+        dbus_message_iter_init_append (message, &iter);
+
+        if (payload1 != NULL) {
+                str = payload1;
+        } else {
+                str = "";
+        }
+        dbus_message_iter_append_basic (&iter,
+                                        DBUS_TYPE_STRING,
+                                        &str);
+
+        if (payload2 != NULL) {
+                str = payload2;
+        } else {
+                str = "";
+        }
+        dbus_message_iter_append_basic (&iter,
+                                        DBUS_TYPE_STRING,
+                                        &str);
 
         dbus_error_init (&error);
         reply = dbus_connection_send_with_reply_and_block (connection,
@@ -412,37 +518,44 @@ gdm_greeter_client_call_begin_auto_login (GdmGreeterClient *client,
 }
 
 void
-gdm_greeter_client_call_begin_verification (GdmGreeterClient *client)
+gdm_greeter_client_call_begin_verification (GdmGreeterClient *client,
+                                            const char       *service_name)
 {
-        send_dbus_void_method (client->priv->connection,
-                               "BeginVerification");
+        send_dbus_string_method (client->priv->connection,
+                                 "BeginVerification", service_name);
 }
 
 void
 gdm_greeter_client_call_begin_verification_for_user (GdmGreeterClient *client,
+                                                     const char       *service_name,
                                                      const char       *username)
 {
-        send_dbus_string_method (client->priv->connection,
-                                 "BeginVerificationForUser",
-                                 username);
+        send_dbus_string_and_string_method (client->priv->connection,
+                                            "BeginVerificationForUser",
+                                            service_name,
+                                            username);
 }
 
 void
 gdm_greeter_client_call_answer_query (GdmGreeterClient *client,
+                                      const char       *service_name,
                                       const char       *text)
 {
-        send_dbus_string_method (client->priv->connection,
-                                 "AnswerQuery",
-                                 text);
+        send_dbus_string_and_string_method (client->priv->connection,
+                                            "AnswerQuery",
+                                            service_name,
+                                            text);
 }
 
 void
 gdm_greeter_client_call_start_session_when_ready  (GdmGreeterClient *client,
+                                                   const char       *service_name,
                                                    gboolean          should_start_session)
 {
-        send_dbus_bool_method (client->priv->connection,
-                               "StartSessionWhenReady",
-                               should_start_session);
+        send_dbus_string_and_bool_method (client->priv->connection,
+                                          "StartSessionWhenReady",
+                                          service_name,
+                                          should_start_session);
 }
 
 void
@@ -835,10 +948,10 @@ gdm_greeter_client_class_init (GdmGreeterClientClass *klass)
                               G_STRUCT_OFFSET (GdmGreeterClientClass, info_query),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
 
         gdm_greeter_client_signals[SECRET_INFO_QUERY] =
                 g_signal_new ("secret-info-query",
@@ -847,10 +960,10 @@ gdm_greeter_client_class_init (GdmGreeterClientClass *klass)
                               G_STRUCT_OFFSET (GdmGreeterClientClass, secret_info_query),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
 
         gdm_greeter_client_signals[INFO] =
                 g_signal_new ("info",
@@ -859,10 +972,10 @@ gdm_greeter_client_class_init (GdmGreeterClientClass *klass)
                               G_STRUCT_OFFSET (GdmGreeterClientClass, info),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
 
         gdm_greeter_client_signals[PROBLEM] =
                 g_signal_new ("problem",
@@ -871,10 +984,10 @@ gdm_greeter_client_class_init (GdmGreeterClientClass *klass)
                               G_STRUCT_OFFSET (GdmGreeterClientClass, problem),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__STRING,
+                              gdm_marshal_VOID__STRING_STRING,
                               G_TYPE_NONE,
-                              1,
-                              G_TYPE_STRING);
+                              2,
+                              G_TYPE_STRING, G_TYPE_STRING);
 
         gdm_greeter_client_signals[READY] =
                 g_signal_new ("ready",
@@ -956,8 +1069,9 @@ gdm_greeter_client_class_init (GdmGreeterClientClass *klass)
                               G_STRUCT_OFFSET (GdmGreeterClientClass, user_authorized),
                               NULL,
                               NULL,
-                              g_cclosure_marshal_VOID__VOID,
-                              G_TYPE_NONE, 0);
+                              g_cclosure_marshal_VOID__STRING,
+                              G_TYPE_NONE,
+                              1, G_TYPE_STRING);
 }
 
 static void
diff --git a/gui/simple-greeter/gdm-greeter-client.h b/gui/simple-greeter/gdm-greeter-client.h
index 88b0281..2f857dc 100644
--- a/gui/simple-greeter/gdm-greeter-client.h
+++ b/gui/simple-greeter/gdm-greeter-client.h
@@ -45,17 +45,22 @@ typedef struct
         GObjectClass   parent_class;
 
         void (* info_query)              (GdmGreeterClient  *client,
+                                          const char        *service_name,
                                           const char        *query_text);
 
         void (* secret_info_query)       (GdmGreeterClient  *client,
+                                          const char        *service_name,
                                           const char        *query_text);
 
         void (* info)                    (GdmGreeterClient  *client,
+                                          const char        *service_name,
                                           const char        *info);
 
         void (* problem)                 (GdmGreeterClient  *client,
+                                          const char        *service_name,
                                           const char        *problem);
-        void (* ready)                   (GdmGreeterClient  *client);
+        void (* ready)                   (GdmGreeterClient  *client,
+                                          const char        *service_name);
         void (* reset)                   (GdmGreeterClient  *client);
         void (* selected_user_changed)   (GdmGreeterClient  *client,
                                           const char        *username);
@@ -69,7 +74,8 @@ typedef struct
         void (* timed_login_requested)   (GdmGreeterClient  *client,
                                           const char        *username,
                                           int                delay);
-        void (* user_authorized)         (GdmGreeterClient  *client);
+        void (* user_authorized)         (GdmGreeterClient  *client,
+                                          const char        *service_name);
 } GdmGreeterClientClass;
 
 #define GDM_GREETER_CLIENT_ERROR (gdm_greeter_client_error_quark ())
@@ -95,8 +101,10 @@ void               gdm_greeter_client_call_start_conversation        (GdmGreeter
                                                                       const char       *service_name);
 void               gdm_greeter_client_call_begin_auto_login          (GdmGreeterClient *client,
                                                                       const char       *username);
-void               gdm_greeter_client_call_begin_verification        (GdmGreeterClient *client);
+void               gdm_greeter_client_call_begin_verification        (GdmGreeterClient *client,
+                                                                      const char       *service_name);
 void               gdm_greeter_client_call_begin_verification_for_user (GdmGreeterClient *client,
+                                                                        const char       *service_name,
                                                                         const char       *username);
 void               gdm_greeter_client_call_cancel                    (GdmGreeterClient *client);
 void               gdm_greeter_client_call_disconnect                (GdmGreeterClient *client);
@@ -111,9 +119,11 @@ void               gdm_greeter_client_call_select_layout             (GdmGreeter
 void               gdm_greeter_client_call_select_session            (GdmGreeterClient *client,
                                                                       const char       *text);
 void               gdm_greeter_client_call_answer_query              (GdmGreeterClient *client,
+                                                                      const char       *service_name,
                                                                       const char       *text);
 
 void               gdm_greeter_client_call_start_session_when_ready  (GdmGreeterClient *client,
+                                                                      const char       *service_name,
                                                                       gboolean          should_start_session);
 
 
diff --git a/gui/simple-greeter/gdm-greeter-session.c b/gui/simple-greeter/gdm-greeter-session.c
index cd0cbdf..e856dd4 100644
--- a/gui/simple-greeter/gdm-greeter-session.c
+++ b/gui/simple-greeter/gdm-greeter-session.c
@@ -65,6 +65,7 @@ static gpointer session_object = NULL;
 
 static void
 on_info (GdmGreeterClient  *client,
+         const char        *service_name,
          const char        *text,
          GdmGreeterSession *session)
 {
@@ -75,6 +76,7 @@ on_info (GdmGreeterClient  *client,
 
 static void
 on_problem (GdmGreeterClient  *client,
+            const char        *service_name,
             const char        *text,
             GdmGreeterSession *session)
 {
@@ -173,6 +175,7 @@ on_user_authorized (GdmGreeterClient  *client,
 
 static void
 on_info_query (GdmGreeterClient  *client,
+               const char        *service_name,
                const char        *text,
                GdmGreeterSession *session)
 {
@@ -183,6 +186,7 @@ on_info_query (GdmGreeterClient  *client,
 
 static void
 on_secret_info_query (GdmGreeterClient  *client,
+                      const char        *service_name,
                       const char        *text,
                       GdmGreeterSession *session)
 {
@@ -204,7 +208,8 @@ static void
 on_begin_verification (GdmGreeterLoginWindow *login_window,
                        GdmGreeterSession     *session)
 {
-        gdm_greeter_client_call_begin_verification (session->priv->client);
+        gdm_greeter_client_call_begin_verification (session->priv->client,
+                                                    "gdm");
 }
 
 static void
@@ -213,6 +218,7 @@ on_begin_verification_for_user (GdmGreeterLoginWindow *login_window,
                                 GdmGreeterSession     *session)
 {
         gdm_greeter_client_call_begin_verification_for_user (session->priv->client,
+                                                             "gdm",
                                                              username);
 }
 
@@ -222,6 +228,7 @@ on_query_answer (GdmGreeterLoginWindow *login_window,
                  GdmGreeterSession     *session)
 {
         gdm_greeter_client_call_answer_query (session->priv->client,
+                                              "gdm",
                                               text);
 }
 
@@ -285,7 +292,7 @@ static void
 on_start_session (GdmGreeterLoginWindow *login_window,
                   GdmGreeterSession     *session)
 {
-        gdm_greeter_client_call_start_session_when_ready (session->priv->client, TRUE);
+        gdm_greeter_client_call_start_session_when_ready (session->priv->client, "gdm", TRUE);
 }
 
 static int



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