Commit f21bc72a authored by Ray Strode's avatar Ray Strode

system: add api for detecting if this is the last session for a user

parent 70728f6a
......@@ -39,6 +39,7 @@
#include "gsm-manager.h"
#include "org.gnome.SessionManager.h"
#include "org.freedesktop.DBus.h"
#ifdef HAVE_SYSTEMD
#include <systemd/sd-journal.h>
......@@ -156,6 +157,7 @@ struct GsmManagerPrivate
GsmSystem *system;
GDBusConnection *connection;
GsmBus *bus_proxy;
GsmExportedManager *skeleton;
gboolean dbus_disconnected : 1;
......@@ -935,6 +937,92 @@ _client_stop (const char *id,
return FALSE;
}
static GPid *
get_pids_for_bus_clients (GsmManager *manager,
const char * const *bus_clients)
{
GHashTable *process_id_hash;
GHashTableIter iter;
gpointer key, value;
GPid *process_ids;
int i, j;
process_id_hash = g_hash_table_new (NULL, NULL);
for (i = 0; bus_clients[i] != NULL; i++) {
gboolean ret;
GError *error;
guint pid;
error = NULL;
ret = gsm_bus_call_get_connection_unix_process_id_sync (manager->priv->bus_proxy,
bus_clients[i],
&pid,
NULL,
&error);
if (! ret) {
g_debug ("GsmManager: couldn't get process id of client '%s': %s",
bus_clients[i], error->message);
g_error_free (error);
continue;
}
g_hash_table_add (process_id_hash, GUINT_TO_POINTER (pid));
}
j = 0;
process_ids = g_new0 (GPid, g_hash_table_size (process_id_hash) + 1);
g_hash_table_iter_init (&iter, process_id_hash);
while (g_hash_table_iter_next (&iter, &key, &value)) {
process_ids[j++] = (GPid) GPOINTER_TO_UINT (key);
}
g_hash_table_unref (process_id_hash);
return process_ids;
}
static void
maybe_kill_bus_clients (GsmManager *manager)
{
GsmSystem *system;
gboolean ret;
GError *error;
GPid *process_ids;
char **bus_clients;
int i;
if (manager->priv->dbus_disconnected)
return;
system = gsm_get_system ();
if (!gsm_system_is_last_session_for_user (system))
return;
error = NULL;
ret = gsm_bus_call_list_names_sync (manager->priv->bus_proxy,
&bus_clients,
NULL,
&error);
if (! ret) {
g_warning ("Unable to list bus clients: %s", error->message);
g_error_free (error);
return;
}
process_ids = get_pids_for_bus_clients (manager, (const char * const *) bus_clients);
g_strfreev (bus_clients);
for (i = 0; process_ids[i] != 0; i++) {
kill (process_ids[i], SIGTERM);
}
free (process_ids);
}
static void
do_phase_exit (GsmManager *manager)
{
......@@ -944,6 +1032,8 @@ do_phase_exit (GsmManager *manager)
NULL);
}
maybe_kill_bus_clients (manager);
end_phase (manager);
}
......@@ -3074,6 +3164,20 @@ register_manager (GsmManager *manager)
exit (1);
}
manager->priv->bus_proxy = gsm_bus_proxy_new_sync (connection,
G_DBUS_PROXY_FLAGS_NONE,
"org.freedesktop.DBus",
"/org/freedesktop/DBus",
NULL,
&error);
if (error != NULL) {
g_critical ("error getting proxy to bus daemon: %s", error->message);
g_error_free (error);
exit (1);
}
skeleton = gsm_exported_manager_skeleton_new ();
g_dbus_interface_skeleton_export (G_DBUS_INTERFACE_SKELETON (skeleton),
connection,
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment