From 2310be2a06fc94d0be8249f90a2ab5fc269d532c Mon Sep 17 00:00:00 2001 From: Alexander Schwinn Date: Mon, 26 Nov 2018 21:57:37 +0100 Subject: [PATCH] run on logout feature (Bug #10172) --- settings/xfae-model.c | 42 ++++++ settings/xfae-model.h | 60 +++++---- settings/xfae-window.c | 104 +++++++++++--- xfce4-session/xfsm-global.c | 306 ++++++++++++++++++++++++++++++++++++++++++ xfce4-session/xfsm-global.h | 4 + xfce4-session/xfsm-shutdown.c | 6 + xfce4-session/xfsm-startup.c | 296 +--------------------------------------- 7 files changed, 481 insertions(+), 337 deletions(-) diff --git a/settings/xfae-model.c b/settings/xfae-model.c index f87d030..1b285e5 100644 --- a/settings/xfae-model.c +++ b/settings/xfae-model.c @@ -98,6 +98,7 @@ struct _XfaeItem gchar *relpath; gboolean hidden; gchar *tooltip; + gchar *run_hook; gboolean show_in_xfce; gboolean show_in_override; @@ -204,6 +205,7 @@ xfae_model_get_column_type (GtkTreeModel *tree_model, { case XFAE_MODEL_COLUMN_NAME: case XFAE_MODEL_COLUMN_TOOLTIP: + case XFAE_MODEL_RUN_HOOK: return G_TYPE_STRING; case XFAE_MODEL_COLUMN_ICON: @@ -262,6 +264,32 @@ xfae_model_get_path (GtkTreeModel *tree_model, +gboolean +xfae_model_set_run_hook (GtkTreeModel *tree_model, + GtkTreeIter *iter, + const gchar *new_text, + GError **error) +{ + XfaeItem *item = ((GList *) iter->user_data)->data; + XfceRc *rc; + + /* try to open the resource config */ + rc = xfce_rc_config_open (XFCE_RESOURCE_CONFIG, item->relpath, FALSE); + if (G_UNLIKELY (rc == NULL)) + { + g_set_error (error, G_FILE_ERROR, g_file_error_from_errno (EIO), + _("Failed to open %s for writing"), item->relpath); + return FALSE; + } + + xfce_rc_set_group (rc, "Desktop Entry"); + g_free (item->run_hook); + item->run_hook = g_strdup (new_text); + xfce_rc_write_entry (rc, "RunHook", item->run_hook); + xfce_rc_close (rc); + return TRUE; +} + static void xfae_model_get_value (GtkTreeModel *tree_model, GtkTreeIter *iter, @@ -319,6 +347,12 @@ xfae_model_get_value (GtkTreeModel *tree_model, g_value_set_static_string (value, item->tooltip); break; + case XFAE_MODEL_RUN_HOOK: + g_value_init (value, G_TYPE_STRING); + name = g_markup_printf_escaped ("%s", item->run_hook); + g_value_take_string (value, name); + break; + default: g_assert_not_reached (); } @@ -481,6 +515,12 @@ xfae_item_new (const gchar *relpath) if (G_LIKELY (value != NULL)) item->tooltip = g_markup_printf_escaped ("%s %s", _("Command:"), value); + value = xfce_rc_read_entry (rc, "RunHook", NULL); + if (G_LIKELY (value != NULL)) + item->run_hook = g_strdup (value); + else + item->run_hook = g_strdup ("on login"); // for bw-compatibility + item->hidden = xfce_rc_read_bool_entry (rc, "Hidden", FALSE); } else @@ -567,6 +607,7 @@ xfae_item_free (XfaeItem *item) g_free (item->comment); g_free (item->name); g_free (item->tooltip); + g_free (item->run_hook); g_free (item); } @@ -713,6 +754,7 @@ xfae_model_add (XfaeModel *model, xfce_rc_write_entry (rc, "Comment", description); xfce_rc_write_entry (rc, "Exec", command); xfce_rc_write_entry (rc, "OnlyShowIn", "XFCE;"); + xfce_rc_write_entry (rc, "RunHook", "on login"); xfce_rc_write_bool_entry (rc, "StartupNotify", FALSE); xfce_rc_write_bool_entry (rc, "Terminal", FALSE); xfce_rc_write_bool_entry (rc, "Hidden", FALSE); diff --git a/settings/xfae-model.h b/settings/xfae-model.h index 731a691..51d91a6 100644 --- a/settings/xfae-model.h +++ b/settings/xfae-model.h @@ -49,6 +49,7 @@ typedef enum XFAE_MODEL_COLUMN_ENABLED, XFAE_MODEL_COLUMN_REMOVABLE, XFAE_MODEL_COLUMN_TOOLTIP, + XFAE_MODEL_RUN_HOOK, XFAE_MODEL_N_COLUMNS, } XfaeModelColumn; @@ -56,33 +57,38 @@ GType xfae_model_get_type (void) G_GNUC_CONST; GtkTreeModel *xfae_model_new (void); -gboolean xfae_model_add (XfaeModel *model, - const gchar *name, - const gchar *description, - const gchar *command, - GError **error); - -gboolean xfae_model_get (XfaeModel *model, - GtkTreeIter *iter, - gchar **name, - gchar **description, - gchar **command, - GError **error); - -gboolean xfae_model_remove (XfaeModel *model, - GtkTreeIter *iter, - GError **error); - -gboolean xfae_model_edit (XfaeModel *model, - GtkTreeIter *iter, - const gchar *name, - const gchar *description, - const gchar *command, - GError **error); - -gboolean xfae_model_toggle (XfaeModel *model, - GtkTreeIter *iter, - GError **error); +gboolean xfae_model_add (XfaeModel *model, + const gchar *name, + const gchar *description, + const gchar *command, + GError **error); + +gboolean xfae_model_get (XfaeModel *model, + GtkTreeIter *iter, + gchar **name, + gchar **description, + gchar **command, + GError **error); + +gboolean xfae_model_remove (XfaeModel *model, + GtkTreeIter *iter, + GError **error); + +gboolean xfae_model_edit (XfaeModel *model, + GtkTreeIter *iter, + const gchar *name, + const gchar *description, + const gchar *command, + GError **error); + +gboolean xfae_model_toggle (XfaeModel *model, + GtkTreeIter *iter, + GError **error); + +gboolean xfae_model_set_run_hook (GtkTreeModel *tree_model, + GtkTreeIter *iter, + const gchar *new_text, + GError **error); G_END_DECLS; diff --git a/settings/xfae-window.c b/settings/xfae-window.c index ed0b3a1..37321bc 100644 --- a/settings/xfae-window.c +++ b/settings/xfae-window.c @@ -30,16 +30,17 @@ #include -static void xfae_window_add (XfaeWindow *window); -static void xfae_window_remove (XfaeWindow *window); -static void xfae_window_edit (XfaeWindow *window); -static gboolean xfae_window_button_press_event (GtkWidget *treeview, - GdkEventButton *event, - XfaeWindow *window); -static void xfae_window_item_toggled (XfaeWindow *window, - gchar *path_string); -static void xfae_window_selection_changed (GtkTreeSelection *selection, - GtkWidget *remove_button); +static void xfae_window_add (XfaeWindow *window); +static void xfae_window_remove (XfaeWindow *window); +static void xfae_window_edit (XfaeWindow *window); +static gboolean xfae_window_button_press_event (GtkWidget *treeview, + GdkEventButton *event, + XfaeWindow *window); +static void xfae_window_item_toggled (XfaeWindow *window, + gchar *path_string); +static void xfae_window_selection_changed (GtkTreeSelection *selection, + GtkWidget *remove_button); +static GtkTreeModel* xfae_window_create_run_hooks_combo_model (void); @@ -57,6 +58,18 @@ struct _XfaeWindow GtkWidget *treeview; }; +static const gchar *run_hooks[] = +{ + N_("on login"), + N_("on logout"), + N_("on shutdown"), + N_("on restart"), + N_("on suspend"), + N_("on hibernate"), + N_("on hybrid sleep"), + N_("on switch user"), + NULL, +}; G_DEFINE_TYPE (XfaeWindow, xfae_window, GTK_TYPE_BOX); @@ -68,6 +81,30 @@ xfae_window_class_init (XfaeWindowClass *klass) { } +static void +run_hook_changed(GtkCellRenderer *render, + const gchar *path_str, + const gchar *new_text, + gpointer user_data) +{ + GtkTreeView *treeview = user_data; + GtkTreeModel *model = gtk_tree_view_get_model (treeview); + GtkTreePath *path = gtk_tree_path_new_from_string (path_str); + GtkTreeIter iter; + + TRACE("entering"); + + if(gtk_tree_model_get_iter (model, &iter, path)) + { + GError *error = NULL; + if (!xfae_model_set_run_hook (model, &iter, new_text, &error)) + { + xfce_dialog_show_error (NULL, error, _("Failed to set run hook")); + g_error_free (error); + } + } + gtk_tree_path_free(path); +} static void @@ -103,11 +140,11 @@ xfae_window_init (XfaeWindow *window) label = g_object_new (GTK_TYPE_LABEL, "justify", GTK_JUSTIFY_LEFT, "label", _("Below is the list of applications that will be started " - "automatically when you login to your Xfce desktop, " - "in addition to the applications that were saved when " - "you logged out last time. Cursive applications belong " - "to another desktop environment, but you can still enable " - "them if you want."), + "automatically on specific events like login, logout, shutdown, etc. " + "On login additionally all applications that were saved when " + "you logged out last time will be started.\n" + "Cursive applications belong to another desktop environment, " + "but you can still enable them if you want."), "xalign", 0.0f, NULL); gtk_label_set_line_wrap (GTK_LABEL (label), TRUE); @@ -154,7 +191,29 @@ xfae_window_init (XfaeWindow *window) "active", XFAE_MODEL_COLUMN_ENABLED, NULL); gtk_tree_view_append_column (GTK_TREE_VIEW (window->treeview), column); + + column = g_object_new (GTK_TYPE_TREE_VIEW_COLUMN, + "reorderable", FALSE, + "resizable", FALSE, + NULL); + renderer = gtk_cell_renderer_combo_new (); + model = xfae_window_create_run_hooks_combo_model (); + g_object_set (renderer, + "has-entry", FALSE, + "model", model, + "text-column", 0, + "editable", TRUE, + "mode", GTK_CELL_RENDERER_MODE_EDITABLE, + NULL); + g_signal_connect (renderer, "edited", G_CALLBACK (run_hook_changed), window->treeview); + + gtk_tree_view_column_pack_start (column, renderer, FALSE); + gtk_tree_view_column_set_attributes (column, renderer, + "text", XFAE_MODEL_RUN_HOOK, + NULL); + gtk_tree_view_append_column (GTK_TREE_VIEW (window->treeview), column); + g_object_unref (model); column = g_object_new (GTK_TYPE_TREE_VIEW_COLUMN, "reorderable", FALSE, "resizable", FALSE, @@ -203,7 +262,20 @@ xfae_window_init (XfaeWindow *window) xfae_window_selection_changed (window->selection, button); } - +static GtkTreeModel * +xfae_window_create_run_hooks_combo_model (void) +{ + GtkListStore *ls = gtk_list_store_new (1, G_TYPE_STRING); + GtkTreeIter iter; + gint i; + + for(i = 0; run_hooks[i]; ++i) + { + gtk_list_store_append (ls, &iter); + gtk_list_store_set (ls, &iter, 0, _(run_hooks[i]), -1); + } + return GTK_TREE_MODEL(ls); +} static gboolean xfae_window_button_press_event (GtkWidget *treeview, diff --git a/xfce4-session/xfsm-global.c b/xfce4-session/xfsm-global.c index c8106da..3296877 100644 --- a/xfce4-session/xfsm-global.c +++ b/xfce4-session/xfsm-global.c @@ -42,6 +42,12 @@ #include #endif +#ifdef HAVE_ERRNO_H +#include +#endif + +#include + #include #include @@ -213,3 +219,303 @@ xfsm_g_value_free (GValue *value) } } + + +void +xfsm_autostart_migrate (void) +{ + const gchar *entry; + gchar source_path[4096]; + gchar target_path[4096]; + gchar *source; + gchar *target; + FILE *fp; + GDir *dp; + + /* migrate the content */ + source = xfce_get_homefile ("Desktop", "Autostart/", NULL); + dp = g_dir_open (source, 0, NULL); + if (G_UNLIKELY (dp != NULL)) + { + /* check if the LOCATION-CHANGED.txt file exists and the target can be opened */ + g_snprintf (source_path, 4096, "%s/LOCATION-CHANGED.txt", source); + target = xfce_resource_save_location (XFCE_RESOURCE_CONFIG, "autostart/", TRUE); + if (G_LIKELY (target != NULL && !g_file_test (source_path, G_FILE_TEST_IS_REGULAR))) + { + g_message ("Trying to migrate autostart items from %s to %s...", source, target); + + for (;;) + { + entry = g_dir_read_name (dp); + if (entry == NULL) + break; + + /* determine full source and dest paths */ + g_snprintf (source_path, 4096, "%s%s", source, entry); + g_snprintf (target_path, 4096, "%s%s", target, entry); + + /* try to move the file */ + if (rename (source_path, target_path) < 0) + { + g_warning ("Failed to rename %s to %s: %s", + source_path, target_path, + g_strerror (errno)); + continue; + } + + /* check if the file is executable */ + if (!g_file_test (target_path, G_FILE_TEST_IS_EXECUTABLE)) + continue; + + /* generate a .desktop file for the executable file */ + g_snprintf (source_path, 4096, "%s.desktop", target_path); + if (!g_file_test (source_path, G_FILE_TEST_IS_REGULAR)) + { + fp = fopen (source_path, "w"); + if (G_LIKELY (fp != NULL)) + { + fprintf (fp, + "# This file was automatically generated for the autostart\n" + "# item %s\n" + "[Desktop Entry]\n" + "Type=Application\n" + "Exec=%s\n" + "Hidden=False\n" + "Terminal=False\n" + "StartupNotify=False\n" + "Version=0.9.4\n" + "Name=%s\n", + entry, target_path, entry); + fclose (fp); + } + else + { + g_warning ("Failed to create a .desktop file for %s: %s", + target_path, g_strerror (errno)); + } + } + } + + /* create the LOCATION-CHANGED.txt file to let the user know */ + g_snprintf (source_path, 4096, "%s/LOCATION-CHANGED.txt", source); + fp = fopen (source_path, "w"); + if (G_LIKELY (fp != NULL)) + { + g_fprintf (fp, _("The location and the format of the autostart directory has changed.\n" + "The new location is\n" + "\n" + " %s\n" + "\n" + "where you can place .desktop files to, that describe the applications\n" + "to start when you login to your Xfce desktop. The files in your old\n" + "autostart directory have been successfully migrated to the new\n" + "location.\n" + "You should delete this directory now.\n"), target); + fclose (fp); + } + + g_free (target); + } + + g_dir_close (dp); + } +} + + + +static gboolean +xfsm_check_valid_exec (const gchar *exec) +{ + gboolean result = TRUE; + gchar *tmp; + gchar *p; + + if (*exec == '/') + { + result = (access (exec, X_OK) == 0); + } + else + { + tmp = g_strdup (exec); + p = strchr (tmp, ' '); + if (G_UNLIKELY (p != NULL)) + *p = '\0'; + + p = g_find_program_in_path (tmp); + g_free (tmp); + + if (G_UNLIKELY (p == NULL)) + { + result = FALSE; + } + else + { + result = (access (p, X_OK) == 0); + g_free (p); + } + } + + return result; +} + + + +gint +xfsm_launch_desktop_files_for_run_hook (gboolean start_at_spi, + const char *run_hook_name) +{ + const gchar *try_exec; + const gchar *type; + const gchar *run_hook; + const gchar *exec; + gboolean startup_notify; + gboolean terminal; + gboolean skip; + GError *error = NULL; + XfceRc *rc; + gchar **files; + gchar **only_show_in; + gchar **not_show_in; + gint started = 0; + gint n, m; + gchar *filename; + const gchar *pattern; + + /* migrate the old autostart location (if still present) */ + xfsm_autostart_migrate (); + + /* pattern for only at-spi desktop files or everything */ + if (start_at_spi) + pattern = "autostart/at-spi-*.desktop"; + else + pattern = "autostart/*.desktop"; + + files = xfce_resource_match (XFCE_RESOURCE_CONFIG, pattern, TRUE); + for (n = 0; files[n] != NULL; ++n) + { + rc = xfce_rc_config_open (XFCE_RESOURCE_CONFIG, files[n], TRUE); + if (G_UNLIKELY (rc == NULL)) + continue; + + xfce_rc_set_group (rc, "Desktop Entry"); + + /* check the Hidden key */ + skip = xfce_rc_read_bool_entry (rc, "Hidden", FALSE); + + run_hook = xfce_rc_read_entry (rc, "RunHook", NULL); + if (G_LIKELY (run_hook != NULL)) + { + if(g_strcmp0(run_hook, run_hook_name) != 0) + skip = TRUE; + } + + if (G_LIKELY (!skip)) + { + xfsm_verbose("hidden set\n"); + + if (xfce_rc_read_bool_entry (rc, "X-XFCE-Autostart-Override", FALSE)) + { + /* override the OnlyShowIn check */ + skip = FALSE; + xfsm_verbose ("X-XFCE-Autostart-Override set, launching\n"); + } + else + { + /* check the OnlyShowIn setting */ + only_show_in = xfce_rc_read_list_entry (rc, "OnlyShowIn", ";"); + if (G_UNLIKELY (only_show_in != NULL)) + { + /* check if "XFCE" is specified */ + for (m = 0, skip = TRUE; only_show_in[m] != NULL; ++m) + { + if (g_ascii_strcasecmp (only_show_in[m], "XFCE") == 0) + { + skip = FALSE; + xfsm_verbose ("only show in XFCE set, launching\n"); + break; + } + } + + g_strfreev (only_show_in); + } + } + + /* check the NotShowIn setting */ + not_show_in = xfce_rc_read_list_entry (rc, "NotShowIn", ";"); + if (G_UNLIKELY (not_show_in != NULL)) + { + /* check if "Xfce" is not specified */ + for (m = 0; not_show_in[m] != NULL; ++m) + if (g_ascii_strcasecmp (not_show_in[m], "XFCE") == 0) + { + skip = TRUE; + xfsm_verbose ("NotShowIn Xfce set, skipping\n"); + break; + } + + g_strfreev (not_show_in); + } + + /* skip at-spi launchers if not in at-spi mode or don't skip + * them no matter what the OnlyShowIn key says if only + * launching at-spi */ + filename = g_path_get_basename (files[n]); + if (g_str_has_prefix (filename, "at-spi-")) + { + skip = !start_at_spi; + xfsm_verbose ("start_at_spi (a11y support), %s\n", skip ? "skipping" : "showing"); + } + g_free (filename); + } + + /* check the "Type" key */ + type = xfce_rc_read_entry (rc, "Type", NULL); + if (G_UNLIKELY (!skip && type != NULL && g_ascii_strcasecmp (type, "Application") != 0)) + { + skip = TRUE; + xfsm_verbose ("Type == Application, skipping\n"); + } + + /* check the "TryExec" key */ + try_exec = xfce_rc_read_entry (rc, "TryExec", NULL); + if (G_UNLIKELY (!skip && try_exec != NULL)) + { + skip = !xfsm_check_valid_exec (try_exec); + if (skip) + xfsm_verbose ("TryExec set and xfsm_check_valid_exec failed, skipping\n"); + } + + /* execute the item */ + exec = xfce_rc_read_entry (rc, "Exec", NULL); + if (G_LIKELY (!skip && exec != NULL)) + { + /* query launch parameters */ + startup_notify = xfce_rc_read_bool_entry (rc, "StartupNotify", FALSE); + terminal = xfce_rc_read_bool_entry (rc, "Terminal", FALSE); + + /* try to launch the command */ + xfsm_verbose ("Autostart: running command \"%s\"\n", exec); + if (!xfce_spawn_command_line_on_screen (gdk_screen_get_default (), + exec, + terminal, + startup_notify, + &error)) + { + g_warning ("Unable to launch \"%s\" (specified by %s): %s", exec, files[n], error->message); + xfsm_verbose ("Unable to launch \"%s\" (specified by %s): %s\n", exec, files[n], error->message); + g_error_free (error); + error = NULL; + } + else + { + ++started; + } + } + + /* cleanup */ + xfce_rc_close (rc); + } + g_strfreev (files); + + return started; +} diff --git a/xfce4-session/xfsm-global.h b/xfce4-session/xfsm-global.h index 610d5bf..94c6453 100644 --- a/xfce4-session/xfsm-global.h +++ b/xfce4-session/xfsm-global.h @@ -74,4 +74,8 @@ GdkPixbuf *xfsm_load_session_preview (const gchar *name); GValue *xfsm_g_value_new (GType gtype); void xfsm_g_value_free (GValue *value); +void xfsm_autostart_migrate (void); +gint xfsm_launch_desktop_files_for_run_hook (gboolean start_at_spi, + const char *run_hook_name); + #endif /* !__XFSM_GLOBAL_H__ */ diff --git a/xfce4-session/xfsm-shutdown.c b/xfce4-session/xfsm-shutdown.c index bfcf0bf..b8bd635 100644 --- a/xfce4-session/xfsm-shutdown.c +++ b/xfce4-session/xfsm-shutdown.c @@ -198,21 +198,27 @@ xfsm_shutdown_try_type (XfsmShutdown *shutdown, switch (type) { case XFSM_SHUTDOWN_SHUTDOWN: + xfsm_launch_desktop_files_for_run_hook (FALSE,"on shutdown"); return xfsm_shutdown_try_shutdown (shutdown, error); case XFSM_SHUTDOWN_RESTART: + xfsm_launch_desktop_files_for_run_hook (FALSE,"on restart"); return xfsm_shutdown_try_restart (shutdown, error); case XFSM_SHUTDOWN_SUSPEND: + xfsm_launch_desktop_files_for_run_hook (FALSE,"on suspend"); return xfsm_shutdown_try_suspend (shutdown, error); case XFSM_SHUTDOWN_HIBERNATE: + xfsm_launch_desktop_files_for_run_hook (FALSE,"on hibernate"); return xfsm_shutdown_try_hibernate (shutdown, error); case XFSM_SHUTDOWN_HYBRID_SLEEP: + xfsm_launch_desktop_files_for_run_hook (FALSE,"on hybrid sleep"); return xfsm_shutdown_try_hybrid_sleep (shutdown, error); case XFSM_SHUTDOWN_SWITCH_USER: + xfsm_launch_desktop_files_for_run_hook (FALSE,"on switch user"); return xfsm_shutdown_try_switch_user (shutdown, error); default: diff --git a/xfce4-session/xfsm-startup.c b/xfce4-session/xfsm-startup.c index e487bcd..45c91b6 100644 --- a/xfce4-session/xfsm-startup.c +++ b/xfce4-session/xfsm-startup.c @@ -467,304 +467,12 @@ figure_app_name (const gchar *program_path) -static gboolean -xfsm_check_valid_exec (const gchar *exec) -{ - gboolean result = TRUE; - gchar *tmp; - gchar *p; - - if (*exec == '/') - { - result = (access (exec, X_OK) == 0); - } - else - { - tmp = g_strdup (exec); - p = strchr (tmp, ' '); - if (G_UNLIKELY (p != NULL)) - *p = '\0'; - - p = g_find_program_in_path (tmp); - g_free (tmp); - - if (G_UNLIKELY (p == NULL)) - { - result = FALSE; - } - else - { - result = (access (p, X_OK) == 0); - g_free (p); - } - } - - return result; -} - - - -static void -xfsm_startup_autostart_migrate (void) -{ - const gchar *entry; - gchar source_path[4096]; - gchar target_path[4096]; - gchar *source; - gchar *target; - FILE *fp; - GDir *dp; - - /* migrate the content */ - source = xfce_get_homefile ("Desktop", "Autostart/", NULL); - dp = g_dir_open (source, 0, NULL); - if (G_UNLIKELY (dp != NULL)) - { - /* check if the LOCATION-CHANGED.txt file exists and the target can be opened */ - g_snprintf (source_path, 4096, "%s/LOCATION-CHANGED.txt", source); - target = xfce_resource_save_location (XFCE_RESOURCE_CONFIG, "autostart/", TRUE); - if (G_LIKELY (target != NULL && !g_file_test (source_path, G_FILE_TEST_IS_REGULAR))) - { - g_message ("Trying to migrate autostart items from %s to %s...", source, target); - - for (;;) - { - entry = g_dir_read_name (dp); - if (entry == NULL) - break; - - /* determine full source and dest paths */ - g_snprintf (source_path, 4096, "%s%s", source, entry); - g_snprintf (target_path, 4096, "%s%s", target, entry); - - /* try to move the file */ - if (rename (source_path, target_path) < 0) - { - g_warning ("Failed to rename %s to %s: %s", - source_path, target_path, - g_strerror (errno)); - continue; - } - - /* check if the file is executable */ - if (!g_file_test (target_path, G_FILE_TEST_IS_EXECUTABLE)) - continue; - - /* generate a .desktop file for the executable file */ - g_snprintf (source_path, 4096, "%s.desktop", target_path); - if (!g_file_test (source_path, G_FILE_TEST_IS_REGULAR)) - { - fp = fopen (source_path, "w"); - if (G_LIKELY (fp != NULL)) - { - fprintf (fp, - "# This file was automatically generated for the autostart\n" - "# item %s\n" - "[Desktop Entry]\n" - "Type=Application\n" - "Exec=%s\n" - "Hidden=False\n" - "Terminal=False\n" - "StartupNotify=False\n" - "Version=0.9.4\n" - "Name=%s\n", - entry, target_path, entry); - fclose (fp); - } - else - { - g_warning ("Failed to create a .desktop file for %s: %s", - target_path, g_strerror (errno)); - } - } - } - - /* create the LOCATION-CHANGED.txt file to let the user know */ - g_snprintf (source_path, 4096, "%s/LOCATION-CHANGED.txt", source); - fp = fopen (source_path, "w"); - if (G_LIKELY (fp != NULL)) - { - g_fprintf (fp, _("The location and the format of the autostart directory has changed.\n" - "The new location is\n" - "\n" - " %s\n" - "\n" - "where you can place .desktop files to, that describe the applications\n" - "to start when you login to your Xfce desktop. The files in your old\n" - "autostart directory have been successfully migrated to the new\n" - "location.\n" - "You should delete this directory now.\n"), target); - fclose (fp); - } - - g_free (target); - } - - g_dir_close (dp); - } -} - - - -static gint -xfsm_startup_autostart_xdg (XfsmManager *manager, - gboolean start_at_spi) -{ - const gchar *try_exec; - const gchar *type; - const gchar *exec; - gboolean startup_notify; - gboolean terminal; - gboolean skip; - GError *error = NULL; - XfceRc *rc; - gchar **files; - gchar **only_show_in; - gchar **not_show_in; - gint started = 0; - gint n, m; - gchar *filename; - const gchar *pattern; - - /* migrate the old autostart location (if still present) */ - xfsm_startup_autostart_migrate (); - - /* pattern for only at-spi desktop files or everything */ - if (start_at_spi) - pattern = "autostart/at-spi-*.desktop"; - else - pattern = "autostart/*.desktop"; - - files = xfce_resource_match (XFCE_RESOURCE_CONFIG, pattern, TRUE); - for (n = 0; files[n] != NULL; ++n) - { - rc = xfce_rc_config_open (XFCE_RESOURCE_CONFIG, files[n], TRUE); - if (G_UNLIKELY (rc == NULL)) - continue; - - xfce_rc_set_group (rc, "Desktop Entry"); - - /* check the Hidden key */ - skip = xfce_rc_read_bool_entry (rc, "Hidden", FALSE); - if (G_LIKELY (!skip)) - { - xfsm_verbose("hidden set\n"); - - if (xfce_rc_read_bool_entry (rc, "X-XFCE-Autostart-Override", FALSE)) - { - /* override the OnlyShowIn check */ - skip = FALSE; - xfsm_verbose ("X-XFCE-Autostart-Override set, launching\n"); - } - else - { - /* check the OnlyShowIn setting */ - only_show_in = xfce_rc_read_list_entry (rc, "OnlyShowIn", ";"); - if (G_UNLIKELY (only_show_in != NULL)) - { - /* check if "XFCE" is specified */ - for (m = 0, skip = TRUE; only_show_in[m] != NULL; ++m) - { - if (g_ascii_strcasecmp (only_show_in[m], "XFCE") == 0) - { - skip = FALSE; - xfsm_verbose ("only show in XFCE set, launching\n"); - break; - } - } - - g_strfreev (only_show_in); - } - } - - /* check the NotShowIn setting */ - not_show_in = xfce_rc_read_list_entry (rc, "NotShowIn", ";"); - if (G_UNLIKELY (not_show_in != NULL)) - { - /* check if "Xfce" is not specified */ - for (m = 0; not_show_in[m] != NULL; ++m) - if (g_ascii_strcasecmp (not_show_in[m], "XFCE") == 0) - { - skip = TRUE; - xfsm_verbose ("NotShowIn Xfce set, skipping\n"); - break; - } - - g_strfreev (not_show_in); - } - - /* skip at-spi launchers if not in at-spi mode or don't skip - * them no matter what the OnlyShowIn key says if only - * launching at-spi */ - filename = g_path_get_basename (files[n]); - if (g_str_has_prefix (filename, "at-spi-")) - { - skip = !start_at_spi; - xfsm_verbose ("start_at_spi (a11y support), %s\n", skip ? "skipping" : "showing"); - } - g_free (filename); - } - - /* check the "Type" key */ - type = xfce_rc_read_entry (rc, "Type", NULL); - if (G_UNLIKELY (!skip && type != NULL && g_ascii_strcasecmp (type, "Application") != 0)) - { - skip = TRUE; - xfsm_verbose ("Type == Application, skipping\n"); - } - - /* check the "TryExec" key */ - try_exec = xfce_rc_read_entry (rc, "TryExec", NULL); - if (G_UNLIKELY (!skip && try_exec != NULL)) - { - skip = !xfsm_check_valid_exec (try_exec); - if (skip) - xfsm_verbose ("TryExec set and xfsm_check_valid_exec failed, skipping\n"); - } - - /* execute the item */ - exec = xfce_rc_read_entry (rc, "Exec", NULL); - if (G_LIKELY (!skip && exec != NULL)) - { - /* query launch parameters */ - startup_notify = xfce_rc_read_bool_entry (rc, "StartupNotify", FALSE); - terminal = xfce_rc_read_bool_entry (rc, "Terminal", FALSE); - - /* try to launch the command */ - xfsm_verbose ("Autostart: running command \"%s\"\n", exec); - if (!xfce_spawn_command_line_on_screen (gdk_screen_get_default (), - exec, - terminal, - startup_notify, - &error)) - { - g_warning ("Unable to launch \"%s\" (specified by %s): %s", exec, files[n], error->message); - xfsm_verbose ("Unable to launch \"%s\" (specified by %s): %s\n", exec, files[n], error->message); - g_error_free (error); - error = NULL; - } - else - { - ++started; - } - } - - /* cleanup */ - xfce_rc_close (rc); - } - g_strfreev (files); - - return started; -} - - - static void xfsm_startup_autostart (XfsmManager *manager) { gint n; - n = xfsm_startup_autostart_xdg (manager, FALSE); + n = xfsm_launch_desktop_files_for_run_hook (FALSE,"on login"); if (n > 0) { @@ -870,7 +578,7 @@ xfsm_startup_at (XfsmManager *manager) gint n, i; /* start at-spi-dbus-bus and/or at-spi-registryd */ - n = xfsm_startup_autostart_xdg (manager, TRUE); + n = xfsm_launch_desktop_files_for_run_hook (TRUE,"on login"); if (n > 0) { -- 2.11.0