2 * Copyright (C) 2010 Robert Ancell.
3 * Author: Robert Ancell <robert.ancell@canonical.com>
5 * This library is free software; you can redistribute it and/or modify it under
6 * the terms of the GNU Lesser General Public License as published by the Free
7 * Software Foundation; either version 3 of the License, or (at your option) any
8 * later version. See http://www.gnu.org/copyleft/lgpl.html the full text of the
13 #include <gio/gdesktopappinfo.h>
15 #include "lightdm/session.h"
29 } LightDMSessionPrivate;
31 G_DEFINE_TYPE (LightDMSession, lightdm_session, G_TYPE_OBJECT);
33 #define GET_PRIVATE(obj) G_TYPE_INSTANCE_GET_PRIVATE ((obj), LIGHTDM_TYPE_SESSION, LightDMSessionPrivate)
35 static gboolean have_sessions = FALSE;
36 static GList *local_sessions = NULL;
37 static GList *remote_sessions = NULL;
40 compare_session (gconstpointer a, gconstpointer b)
42 LightDMSessionPrivate *priv_a = GET_PRIVATE (a);
43 LightDMSessionPrivate *priv_b = GET_PRIVATE (b);
44 return strcmp (priv_a->name, priv_b->name);
47 static LightDMSession *
48 load_session (GKeyFile *key_file, const gchar *key)
51 LightDMSession *session;
52 LightDMSessionPrivate *priv;
55 if (g_key_file_get_boolean (key_file, G_KEY_FILE_DESKTOP_GROUP, G_KEY_FILE_DESKTOP_KEY_NO_DISPLAY, NULL) ||
56 g_key_file_get_boolean (key_file, G_KEY_FILE_DESKTOP_GROUP, G_KEY_FILE_DESKTOP_KEY_HIDDEN, NULL))
59 #ifdef G_KEY_FILE_DESKTOP_KEY_GETTEXT_DOMAIN
60 domain = g_key_file_get_string (key_file, G_KEY_FILE_DESKTOP_GROUP, G_KEY_FILE_DESKTOP_KEY_GETTEXT_DOMAIN, NULL);
62 domain = g_key_file_get_string (key_file, G_KEY_FILE_DESKTOP_GROUP, "X-GNOME-Gettext-Domain", NULL);
64 name = g_key_file_get_locale_string (key_file, G_KEY_FILE_DESKTOP_GROUP, G_KEY_FILE_DESKTOP_KEY_NAME, domain, NULL);
67 g_warning ("Ignoring session without name");
72 try_exec = g_key_file_get_locale_string (key_file, G_KEY_FILE_DESKTOP_GROUP, G_KEY_FILE_DESKTOP_KEY_TRY_EXEC, domain, NULL);
77 full_path = g_find_program_in_path (try_exec);
89 session = g_object_new (LIGHTDM_TYPE_SESSION, NULL);
90 priv = GET_PRIVATE (session);
93 priv->key = g_strdup (key);
98 g_free (priv->comment);
99 priv->comment = g_key_file_get_locale_string (key_file, G_KEY_FILE_DESKTOP_GROUP, G_KEY_FILE_DESKTOP_KEY_COMMENT, domain, NULL);
101 priv->comment = g_strdup ("");
109 load_sessions (const gchar *sessions_dir)
112 GList *sessions = NULL;
113 GError *error = NULL;
115 directory = g_dir_open (sessions_dir, 0, &error);
117 g_warning ("Failed to open sessions directory: %s", error->message);
118 g_clear_error (&error);
124 const gchar *filename;
129 filename = g_dir_read_name (directory);
130 if (filename == NULL)
133 if (!g_str_has_suffix (filename, ".desktop"))
136 path = g_build_filename (sessions_dir, filename, NULL);
138 key_file = g_key_file_new ();
139 result = g_key_file_load_from_file (key_file, path, G_KEY_FILE_NONE, &error);
141 g_warning ("Failed to load session file %s: %s:", path, error->message);
142 g_clear_error (&error);
147 LightDMSession *session;
149 key = g_strndup (filename, strlen (filename) - strlen (".desktop"));
150 session = load_session (key_file, key);
153 g_debug ("Loaded session %s (%s, %s)", path, GET_PRIVATE (session)->name, GET_PRIVATE (session)->comment);
154 sessions = g_list_insert_sorted (sessions, session, compare_session);
157 g_debug ("Ignoring session %s", path);
162 g_key_file_free (key_file);
165 g_dir_close (directory);
171 update_sessions (void)
173 GKeyFile *config_key_file = NULL;
174 gchar *config_path = NULL;
175 gchar *xsessions_dir;
176 gchar *remote_sessions_dir;
178 GError *error = NULL;
183 xsessions_dir = g_strdup (XSESSIONS_DIR);
184 remote_sessions_dir = g_strdup (REMOTE_SESSIONS_DIR);
186 /* Use session directory from configuration */
187 /* FIXME: This should be sent in the greeter connection */
188 config_path = g_build_filename (CONFIG_DIR, "lightdm.conf", NULL);
189 config_key_file = g_key_file_new ();
190 result = g_key_file_load_from_file (config_key_file, config_path, G_KEY_FILE_NONE, &error);
192 g_warning ("Failed to open configuration file: %s", error->message);
193 g_clear_error (&error);
198 value = g_key_file_get_string (config_key_file, "LightDM", "xsessions-directory", NULL);
201 g_free (xsessions_dir);
202 xsessions_dir = value;
205 value = g_key_file_get_string (config_key_file, "LightDM", "remote-sessions-directory", NULL);
208 g_free (remote_sessions_dir);
209 remote_sessions_dir = value;
212 g_key_file_free (config_key_file);
213 g_free (config_path);
215 local_sessions = load_sessions (xsessions_dir);
216 remote_sessions = load_sessions (remote_sessions_dir);
218 g_free (xsessions_dir);
219 g_free (remote_sessions_dir);
221 have_sessions = TRUE;
225 * lightdm_get_sessions:
227 * Get the available sessions.
229 * Return value: (element-type LightDMSession) (transfer none): A list of #LightDMSession
232 lightdm_get_sessions (void)
235 return local_sessions;
239 * lightdm_get_remote_sessions:
241 * Get the available remote sessions.
243 * Return value: (element-type LightDMSession) (transfer none): A list of #LightDMSession
246 lightdm_get_remote_sessions (void)
249 return remote_sessions;
253 * lightdm_session_get_key:
254 * @session: A #LightDMSession
256 * Get the key for a session
258 * Return value: The session key
261 lightdm_session_get_key (LightDMSession *session)
263 g_return_val_if_fail (LIGHTDM_IS_SESSION (session), NULL);
264 return GET_PRIVATE (session)->key;
268 * lightdm_session_get_name:
269 * @session: A #LightDMSession
271 * Get the name for a session
273 * Return value: The session name
276 lightdm_session_get_name (LightDMSession *session)
278 g_return_val_if_fail (LIGHTDM_IS_SESSION (session), NULL);
279 return GET_PRIVATE (session)->name;
283 * lightdm_session_get_comment:
284 * @session: A #LightDMSession
286 * Get the comment for a session
288 * Return value: The session comment
291 lightdm_session_get_comment (LightDMSession *session)
293 g_return_val_if_fail (LIGHTDM_IS_SESSION (session), NULL);
294 return GET_PRIVATE (session)->comment;
298 lightdm_session_init (LightDMSession *session)
303 lightdm_session_set_property (GObject *object,
308 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
312 lightdm_session_get_property (GObject *object,
317 LightDMSession *self;
319 self = LIGHTDM_SESSION (object);
323 g_value_set_string (value, lightdm_session_get_key (self));
326 g_value_set_string (value, lightdm_session_get_name (self));
329 g_value_set_string (value, lightdm_session_get_comment (self));
332 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
338 lightdm_session_finalize (GObject *object)
340 LightDMSession *self = LIGHTDM_SESSION (object);
341 LightDMSessionPrivate *priv = GET_PRIVATE (self);
345 g_free (priv->comment);
349 lightdm_session_class_init (LightDMSessionClass *klass)
351 GObjectClass *object_class = G_OBJECT_CLASS (klass);
353 g_type_class_add_private (klass, sizeof (LightDMSessionPrivate));
355 object_class->set_property = lightdm_session_set_property;
356 object_class->get_property = lightdm_session_get_property;
357 object_class->finalize = lightdm_session_finalize;
359 g_object_class_install_property (object_class,
361 g_param_spec_string ("key",
366 g_object_class_install_property (object_class,
368 g_param_spec_string ("name",
373 g_object_class_install_property (object_class,
375 g_param_spec_string ("comment",