============================================================
 Rename pipefds to daemon_pipe_fds

  This fits the naming style of the surrounding code
better.  Also, we're going to need another pipe, so
better to use a specific name here.

diff --git a/gnome-settings-daemon/main.c b/gnome-settings-daemon/main.c
--- a/gnome-settings-daemon/main.c
+++ b/gnome-settings-daemon/main.c
@@ -47,7 +47,7 @@
 static char      *gconf_prefix = NULL;
 static gboolean   no_daemon    = FALSE;
 static gboolean   debug        = FALSE;
-static int        pipefds[2];
+static int        daemon_pipe_fds[2];
 
 static GOptionEntry entries[] = {
         {"debug", 0, 0, G_OPTION_ARG_NONE, &debug, N_("Enable debugging code"), NULL },
@@ -247,7 +247,7 @@ daemon_start (void)
         gnome_settings_profile_msg ("forking daemon");
 
         signal (SIGPIPE, SIG_IGN);
-        if (-1 == pipe (pipefds)) {
+        if (-1 == pipe (daemon_pipe_fds)) {
                 g_error ("Could not create pipe: %s", g_strerror (errno));
                 exit (EXIT_FAILURE);
         }
@@ -262,17 +262,17 @@ daemon_start (void)
         case 0:
                 /* child */
 
-                close (pipefds[0]);
+                close (daemon_pipe_fds[0]);
 
                 return;
 
          default:
                 /* parent */
 
-                close (pipefds[1]);
+                close (daemon_pipe_fds[1]);
 
                 /* Wait for child to signal that we are good to go. */
-                read (pipefds[0], buf, 1);
+                read (daemon_pipe_fds[0], buf, 1);
 
                 exit (EXIT_SUCCESS);
         }
@@ -305,8 +305,8 @@ daemon_terminate_parent (void)
 
         gnome_settings_profile_msg ("terminating parent");
 
-        write (pipefds[1], "1", 1);
-        close (pipefds[1]);
+        write (daemon_pipe_fds[1], "1", 1);
+        close (daemon_pipe_fds[1]);
 }
 
 static void

============================================================
 Listen for SIGTERM and shut down properly

  
diff --git a/gnome-settings-daemon/main.c b/gnome-settings-daemon/main.c
--- a/gnome-settings-daemon/main.c
+++ b/gnome-settings-daemon/main.c
@@ -48,6 +48,7 @@ static char      *gconf_prefix = NULL;
 static gboolean   no_daemon    = FALSE;
 static gboolean   debug        = FALSE;
 static int        daemon_pipe_fds[2];
+static int        term_signal_pipe_fds[2];
 
 static GOptionEntry entries[] = {
         {"debug", 0, 0, G_OPTION_ARG_NONE, &debug, N_("Enable debugging code"), NULL },
@@ -177,6 +178,54 @@ on_session_over (DBusGProxy *proxy, GnomeSettingsManager *manager)
 }
 
 static void
+on_term_signal (int signal)
+{
+        /* Wake up main loop to tell it to shutdown */
+        close (term_signal_pipe_fds[1]);
+        term_signal_pipe_fds[1] = -1;
+}
+
+static gboolean
+on_term_signal_pipe_closed (GIOChannel *source,
+                            GIOCondition condition,
+                            gpointer data)
+{
+        GnomeSettingsManager *manager;
+
+        manager = GNOME_SETTINGS_MANAGER (data);
+
+        term_signal_pipe_fds[0] = -1;
+
+        /* Got SIGTERM, time to clean up and get out
+         */
+        gtk_main_quit ();
+
+        return FALSE;
+}
+
+static void
+watch_for_term_signal (GnomeSettingsManager *manager)
+{
+        GIOChannel *channel;
+
+        if (-1 == pipe (term_signal_pipe_fds) ||
+            -1 == fcntl (term_signal_pipe_fds[0], F_SETFD, FD_CLOEXEC) ||
+            -1 == fcntl (term_signal_pipe_fds[1], F_SETFD, FD_CLOEXEC)) {
+                g_error ("Could not create pipe: %s", g_strerror (errno));
+                exit (EXIT_FAILURE);
+        }
+
+        channel = g_io_channel_unix_new (term_signal_pipe_fds[0]);
+        g_io_channel_set_encoding (channel, NULL, NULL);
+        g_io_channel_set_buffered (channel, FALSE);
+        g_io_add_watch (channel, G_IO_HUP, on_term_signal_pipe_closed, manager);
+        g_io_channel_unref (channel);
+
+        signal (SIGTERM, on_term_signal);
+
+}
+
+static void
 set_session_over_handler (DBusGConnection *bus, GnomeSettingsManager *manager)
 {
         DBusGProxy *session_proxy;
@@ -206,6 +255,7 @@ set_session_over_handler (DBusGConnection *bus, GnomeSettingsManager *manager)
                                      manager,
                                      NULL);
 
+        watch_for_term_signal (manager);
         gnome_settings_profile_end (NULL);
 }
 

============================================================
 Shutdown properly when bus goes away

  Previously we were just letting libdbus
call exit(1) for us which bypasses the
clean up paths.

diff --git a/gnome-settings-daemon/main.c b/gnome-settings-daemon/main.c
--- a/gnome-settings-daemon/main.c
+++ b/gnome-settings-daemon/main.c
@@ -114,6 +114,21 @@ acquire_name_on_proxy (DBusGProxy *bus_proxy)
         return ret;
 }
 
+static DBusHandlerResult
+bus_message_handler (DBusConnection *connection,
+                     DBusMessage    *message,
+                     void           *user_data)
+{
+        if (dbus_message_is_signal (message,
+                                    DBUS_INTERFACE_LOCAL,
+                                    "Disconnected")) {
+                gtk_main_quit ();
+                return DBUS_HANDLER_RESULT_HANDLED;
+        }
+
+        return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
+}
+
 static DBusGConnection *
 get_session_bus (void)
 {
@@ -131,7 +146,12 @@ get_session_bus (void)
         }
 
         connection = dbus_g_connection_get_connection (bus);
-        dbus_connection_set_exit_on_disconnect (connection, TRUE);
+        dbus_connection_add_filter (connection,
+                                    (DBusHandleMessageFunction)
+                                    bus_message_handler,
+                                    NULL, NULL);
+
+        dbus_connection_set_exit_on_disconnect (connection, FALSE);
 
  out:
         return bus;
