summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/Makefile.am2
-rw-r--r--src/ck-manager.c56
-rw-r--r--src/ck-marshal.list1
-rw-r--r--src/ck-seat.c161
-rw-r--r--src/ck-seat.h5
5 files changed, 200 insertions, 25 deletions
diff --git a/src/Makefile.am b/src/Makefile.am
index cbe8a09..6ab05c8 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -205,5 +205,7 @@ MAINTAINERCLEANFILES = \
install-data-local:
-mkdir -p $(DESTDIR)$(sysconfdir)/ConsoleKit/run-session.d
-mkdir -p $(DESTDIR)$(prefix)/lib/ConsoleKit/run-session.d
+ -mkdir -p $(DESTDIR)$(sysconfdir)/ConsoleKit/run-seat.d
+ -mkdir -p $(DESTDIR)$(prefix)/lib/ConsoleKit/run-seat.d
-mkdir -p $(DESTDIR)$(localstatedir)/run/ConsoleKit
-mkdir -p $(DESTDIR)$(localstatedir)/log/ConsoleKit
diff --git a/src/ck-manager.c b/src/ck-manager.c
index 440163b..4b7200b 100644
--- a/src/ck-manager.c
+++ b/src/ck-manager.c
@@ -1228,29 +1228,50 @@ ck_manager_can_stop (CkManager *manager,
}
static void
-on_seat_active_session_changed (CkSeat *seat,
- const char *ssid,
- CkManager *manager)
+on_seat_active_session_changed_full (CkSeat *seat,
+ CkSession *old_session,
+ CkSession *session,
+ CkManager *manager)
{
+ char *ssid = NULL;
+
+ if (session != NULL) {
+ ck_session_get_id (session, &ssid, NULL);
+ }
+
ck_manager_dump (manager);
+ ck_seat_run_programs (seat, old_session, session, "seat_active_session_changed");
+
log_seat_active_session_changed_event (manager, seat, ssid);
}
static void
-on_seat_session_added (CkSeat *seat,
- const char *ssid,
- CkManager *manager)
+on_seat_session_added_full (CkSeat *seat,
+ CkSession *session,
+ CkManager *manager)
{
+ char *ssid = NULL;
+
+ ck_session_get_id (session, &ssid, NULL);
+
ck_manager_dump (manager);
+ ck_session_run_programs (session, "session_added");
+
log_seat_session_added_event (manager, seat, ssid);
}
static void
-on_seat_session_removed (CkSeat *seat,
- const char *ssid,
- CkManager *manager)
+on_seat_session_removed_full (CkSeat *seat,
+ CkSession *session,
+ CkManager *manager)
{
+ char *ssid = NULL;
+
+ ck_session_get_id (session, &ssid, NULL);
+
ck_manager_dump (manager);
+ ck_session_run_programs (session, "session_removed");
+
log_seat_session_removed_event (manager, seat, ssid);
}
@@ -1276,9 +1297,9 @@ static void
connect_seat_signals (CkManager *manager,
CkSeat *seat)
{
- g_signal_connect (seat, "active-session-changed", G_CALLBACK (on_seat_active_session_changed), manager);
- g_signal_connect (seat, "session-added", G_CALLBACK (on_seat_session_added), manager);
- g_signal_connect (seat, "session-removed", G_CALLBACK (on_seat_session_removed), manager);
+ g_signal_connect (seat, "active-session-changed-full", G_CALLBACK (on_seat_active_session_changed_full), manager);
+ g_signal_connect (seat, "session-added-full", G_CALLBACK (on_seat_session_added_full), manager);
+ g_signal_connect (seat, "session-removed-full", G_CALLBACK (on_seat_session_removed_full), manager);
g_signal_connect (seat, "device-added", G_CALLBACK (on_seat_device_added), manager);
g_signal_connect (seat, "device-removed", G_CALLBACK (on_seat_device_removed), manager);
}
@@ -1287,9 +1308,9 @@ static void
disconnect_seat_signals (CkManager *manager,
CkSeat *seat)
{
- g_signal_handlers_disconnect_by_func (seat, on_seat_active_session_changed, manager);
- g_signal_handlers_disconnect_by_func (seat, on_seat_session_added, manager);
- g_signal_handlers_disconnect_by_func (seat, on_seat_session_removed, manager);
+ g_signal_handlers_disconnect_by_func (seat, on_seat_active_session_changed_full, manager);
+ g_signal_handlers_disconnect_by_func (seat, on_seat_session_added_full, manager);
+ g_signal_handlers_disconnect_by_func (seat, on_seat_session_removed_full, manager);
g_signal_handlers_disconnect_by_func (seat, on_seat_device_added, manager);
g_signal_handlers_disconnect_by_func (seat, on_seat_device_removed, manager);
}
@@ -1325,7 +1346,9 @@ add_new_seat (CkManager *manager,
g_debug ("Added seat: %s kind:%d", sid, kind);
ck_manager_dump (manager);
+ ck_seat_run_programs (seat, NULL, NULL, "seat_added");
+ g_debug ("Emitting seat-added: %s", sid);
g_signal_emit (manager, signals [SEAT_ADDED], 0, sid);
log_seat_added_event (manager, seat);
@@ -1366,6 +1389,7 @@ remove_seat (CkManager *manager,
}
ck_manager_dump (manager);
+ ck_seat_run_programs (seat, NULL, NULL, "seat_removed");
g_debug ("Emitting seat-removed: %s", sid);
g_signal_emit (manager, signals [SEAT_REMOVED], 0, sid);
@@ -2429,7 +2453,9 @@ add_seat_for_file (CkManager *manager,
g_debug ("Added seat: %s", sid);
ck_manager_dump (manager);
+ ck_seat_run_programs (seat, NULL, NULL, "seat_added");
+ g_debug ("Emitting seat-added: %s", sid);
g_signal_emit (manager, signals [SEAT_ADDED], 0, sid);
log_seat_added_event (manager, seat);
diff --git a/src/ck-marshal.list b/src/ck-marshal.list
index f9eed10..7f60efc 100644
--- a/src/ck-marshal.list
+++ b/src/ck-marshal.list
@@ -1,2 +1,3 @@
VOID:UINT,STRING
BOOLEAN:POINTER
+VOID:OBJECT,OBJECT
diff --git a/src/ck-seat.c b/src/ck-seat.c
index 27ccf14..4f5e63f 100644
--- a/src/ck-seat.c
+++ b/src/ck-seat.c
@@ -67,8 +67,11 @@ struct CkSeatPrivate
enum {
ACTIVE_SESSION_CHANGED,
- SESSION_ADDED,
+ ACTIVE_SESSION_CHANGED_FULL,
+ SESSION_ADDED, /* Carries the session as path for D-Bus */
+ SESSION_ADDED_FULL, /* Carries the session as CkSession for other uses */
SESSION_REMOVED,
+ SESSION_REMOVED_FULL,
DEVICE_ADDED,
DEVICE_REMOVED,
LAST_SIGNAL
@@ -480,15 +483,17 @@ static void
change_active_session (CkSeat *seat,
CkSession *session)
{
- char *ssid;
+ char *ssid;
+ CkSession *old_session;
if (seat->priv->active_session == session) {
return;
}
- if (seat->priv->active_session != NULL) {
- ck_session_set_active (seat->priv->active_session, FALSE, NULL);
- g_object_unref (seat->priv->active_session);
+ old_session = seat->priv->active_session;
+
+ if (old_session != NULL) {
+ ck_session_set_active (old_session, FALSE, NULL);
}
seat->priv->active_session = session;
@@ -502,8 +507,21 @@ change_active_session (CkSeat *seat,
g_debug ("Active session changed: %s", ssid ? ssid : "(null)");
+ /* The order of signal emission matters here. The manager
+ * dumps the database when receiving the
+ * 'active-session-changed-full' signal and does callout
+ * handling. dbus-glib will then send out a D-Bus on the
+ * 'active-session-changed' signal. Since the D-Bus signal
+ * must be sent when the database dump is finished it is
+ * important that the '-full' signalled is emitted first. */
+
+ g_signal_emit (seat, signals [ACTIVE_SESSION_CHANGED_FULL], 0, old_session, session);
g_signal_emit (seat, signals [ACTIVE_SESSION_CHANGED], 0, ssid);
+ if (old_session != NULL) {
+ g_object_unref (old_session);
+ }
+
g_free (ssid);
}
@@ -586,9 +604,13 @@ ck_seat_remove_session (CkSeat *seat,
* unref until the signal is emitted */
g_hash_table_steal (seat->priv->sessions, ssid);
- ck_session_run_programs (session, "session_removed");
-
g_debug ("Emitting session-removed: %s", ssid);
+
+ /* The order of signal emission matters here, too, for similar
+ * reasons as for 'session-added'/'session-added-full'. See
+ * above. */
+
+ g_signal_emit (seat, signals [SESSION_REMOVED_FULL], 0, session);
g_signal_emit (seat, signals [SESSION_REMOVED], 0, ssid);
/* try to change the active session */
@@ -624,10 +646,12 @@ ck_seat_add_session (CkSeat *seat,
g_signal_connect_object (session, "activate", G_CALLBACK (session_activate), seat, 0);
/* FIXME: attach to property notify signals? */
- ck_session_run_programs (session, "session_added");
-
g_debug ("Emitting added signal: %s", ssid);
+ /* The order of signal emission matters here, too. See
+ * above. */
+
+ g_signal_emit (seat, signals [SESSION_ADDED_FULL], 0, session);
g_signal_emit (seat, signals [SESSION_ADDED], 0, ssid);
maybe_update_active_session (seat);
@@ -920,6 +944,15 @@ ck_seat_class_init (CkSeatClass *klass)
g_cclosure_marshal_VOID__STRING,
G_TYPE_NONE,
1, G_TYPE_STRING);
+ signals [ACTIVE_SESSION_CHANGED_FULL] = g_signal_new ("active-session-changed-full",
+ G_TYPE_FROM_CLASS (object_class),
+ G_SIGNAL_RUN_LAST,
+ 0,
+ NULL,
+ NULL,
+ ck_marshal_VOID__OBJECT_OBJECT,
+ G_TYPE_NONE,
+ 2, CK_TYPE_SESSION, CK_TYPE_SESSION);
signals [SESSION_ADDED] = g_signal_new ("session-added",
G_TYPE_FROM_CLASS (object_class),
G_SIGNAL_RUN_LAST,
@@ -929,6 +962,15 @@ ck_seat_class_init (CkSeatClass *klass)
g_cclosure_marshal_VOID__BOXED,
G_TYPE_NONE,
1, DBUS_TYPE_G_OBJECT_PATH);
+ signals [SESSION_ADDED_FULL] = g_signal_new ("session-added-full",
+ G_TYPE_FROM_CLASS (object_class),
+ G_SIGNAL_RUN_LAST,
+ 0,
+ NULL,
+ NULL,
+ g_cclosure_marshal_VOID__OBJECT,
+ G_TYPE_NONE,
+ 1, CK_TYPE_SESSION);
signals [SESSION_REMOVED] = g_signal_new ("session-removed",
G_TYPE_FROM_CLASS (object_class),
G_SIGNAL_RUN_LAST,
@@ -938,7 +980,15 @@ ck_seat_class_init (CkSeatClass *klass)
g_cclosure_marshal_VOID__BOXED,
G_TYPE_NONE,
1, DBUS_TYPE_G_OBJECT_PATH);
-
+ signals [SESSION_REMOVED_FULL] = g_signal_new ("session-removed-full",
+ G_TYPE_FROM_CLASS (object_class),
+ G_SIGNAL_RUN_LAST,
+ 0,
+ NULL,
+ NULL,
+ g_cclosure_marshal_VOID__OBJECT,
+ G_TYPE_NONE,
+ 1, CK_TYPE_SESSION);
signals [DEVICE_ADDED] = g_signal_new ("device-added",
G_TYPE_FROM_CLASS (object_class),
G_SIGNAL_RUN_LAST,
@@ -1134,6 +1184,97 @@ ck_seat_new_from_file (const char *sid,
}
static void
+env_add_session_info (CkSession *session,
+ const char *prefix,
+ char **extra_env,
+ int *n)
+{
+ char *s;
+ gboolean b;
+ guint u;
+
+ if (session == NULL) {
+ return;
+ }
+
+ if (ck_session_get_id (session, &s, NULL) && s != NULL && *s != '\0') {
+ extra_env[(*n)++] = g_strdup_printf ("%sID=%s", prefix, s);
+ g_free (s);
+ }
+
+ if (ck_session_get_session_type (session, &s, NULL) && s != NULL && *s != '\0') {
+ extra_env[(*n)++] = g_strdup_printf ("%sTYPE=%s", prefix, s);
+ g_free (s);
+ }
+
+ if (ck_session_get_unix_user (session, &u, NULL)) {
+ extra_env[(*n)++] = g_strdup_printf ("%sUSER_UID=%u", prefix, u);
+ g_free (s);
+ }
+
+ if (ck_session_get_display_device (session, &s, NULL) && s != NULL && *s != '\0') {
+ extra_env[(*n)++] = g_strdup_printf ("%sDISPLAY_DEVICE=%s", prefix, s);
+ g_free (s);
+ }
+
+ if (ck_session_get_x11_display_device (session, &s, NULL) && s != NULL && *s != '\0') {
+ extra_env[(*n)++] = g_strdup_printf ("%sX11_DISPLAY_DEVICE=%s", prefix, s);
+ g_free (s);
+ }
+
+ if (ck_session_get_x11_display (session, &s, NULL) && s != NULL && *s != '\0') {
+ extra_env[(*n)++] = g_strdup_printf ("%sX11_DISPLAY=%s", prefix, s);
+ g_free (s);
+ }
+
+ if (ck_session_get_remote_host_name (session, &s, NULL) && s != NULL && *s != '\0') {
+ extra_env[(*n)++] = g_strdup_printf ("%sREMOTE_HOST_NAME=%s", prefix, s);
+ g_free (s);
+ }
+
+ if (ck_session_is_local (session, &b, NULL))
+ extra_env[(*n)++] = g_strdup_printf ("%sIS_LOCAL=%s", prefix, b ? "true" : "false");
+}
+
+void
+ck_seat_run_programs (CkSeat *seat,
+ CkSession *old_session,
+ CkSession *new_session,
+ const char *action)
+{
+ int n;
+ char *extra_env[18]; /* be sure to adjust this as needed when
+ * you add more variables to the callout's
+ * environment */
+
+ n = 0;
+
+ extra_env[n++] = g_strdup_printf ("CK_SEAT_ID=%s", seat->priv->id);
+
+ /* Callout scripts/binaries should check if CK_SEAT_SESSION_ID
+ * resp. CK_SEAT_OLD_SESSON_ID is set to figure out if there
+ * will be an active session after the switch, or if there was
+ * one before. At least one of those environment variables
+ * will be set, possibly both. Only after checking these
+ * variables the script should check for the other session
+ * property variables. */
+
+ env_add_session_info (old_session, "CK_SEAT_OLD_SESSION_", extra_env, &n);
+ env_add_session_info (new_session, "CK_SEAT_SESSION_", extra_env, &n);
+
+ extra_env[n++] = NULL;
+
+ g_assert(n <= G_N_ELEMENTS(extra_env));
+
+ ck_run_programs (SYSCONFDIR "/ConsoleKit/run-seat.d", action, extra_env);
+ ck_run_programs (PREFIX "/lib/ConsoleKit/run-seat.d", action, extra_env);
+
+ for (n = 0; extra_env[n] != NULL; n++) {
+ g_free (extra_env[n]);
+ }
+}
+
+static void
dump_seat_session_iter (char *id,
CkSession *session,
GString *str)
diff --git a/src/ck-seat.h b/src/ck-seat.h
index 47d10a7..fb9a955 100644
--- a/src/ck-seat.h
+++ b/src/ck-seat.h
@@ -93,6 +93,11 @@ CkSeat * ck_seat_new_with_devices (const char *sid,
gboolean ck_seat_register (CkSeat *seat);
+void ck_seat_run_programs (CkSeat *seat,
+ CkSession *old_session,
+ CkSession *new_session,
+ const char *action);
+
void ck_seat_dump (CkSeat *seat,
GKeyFile *key_file);