[gnome-terminal] screen: Use async spawning
- From: Christian Persch <chpe src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-terminal] screen: Use async spawning
- Date: Fri, 25 Nov 2016 21:45:19 +0000 (UTC)
commit d4e25a57a8fa9b1dae4b18a8a36735775f9bfd77
Author: Christian Persch <chpe gnome org>
Date: Fri Nov 25 22:18:53 2016 +0100
screen: Use async spawning
Use the new async spawning functions from vte.
https://bugzilla.gnome.org/show_bug.cgi?id=772354
src/terminal-screen.c | 106 ++++++++++++++++++++++++++++--------------------
1 files changed, 62 insertions(+), 44 deletions(-)
---
diff --git a/src/terminal-screen.c b/src/terminal-screen.c
index 9a0b450..06f5db2 100644
--- a/src/terminal-screen.c
+++ b/src/terminal-screen.c
@@ -63,6 +63,8 @@
#define URL_MATCH_CURSOR (GDK_HAND2)
+#define SPAWN_TIMEOUT (30 * 1000 /* 30s */)
+
typedef struct {
int *fd_list;
int fd_list_len;
@@ -1346,6 +1348,50 @@ terminal_screen_child_setup (FDSetupData *data)
}
}
+static void
+spawn_result_cb (VteTerminal *terminal,
+ GPid pid,
+ GError *error,
+ gpointer user_data)
+{
+ TerminalScreen *screen;
+ TerminalScreenPrivate *priv;
+
+ /* Terminal was destroyed while the spawn operation was in progress; nothing to do. */
+ if (terminal == NULL)
+ return;
+
+ screen = TERMINAL_SCREEN (terminal);
+ priv = screen->priv;
+
+ priv->child_pid = pid;
+
+ if (error) {
+ GtkWidget *info_bar;
+
+ vte_terminal_set_pty (terminal, NULL);
+ info_bar = terminal_info_bar_new (GTK_MESSAGE_ERROR,
+ _("_Profile Preferences"), RESPONSE_EDIT_PROFILE,
+ _("_Relaunch"), RESPONSE_RELAUNCH,
+ NULL);
+ terminal_info_bar_format_text (TERMINAL_INFO_BAR (info_bar),
+ _("There was an error creating the child process for this terminal"));
+ terminal_info_bar_format_text (TERMINAL_INFO_BAR (info_bar),
+ "%s", error->message);
+ g_signal_connect (info_bar, "response",
+ G_CALLBACK (info_bar_response_cb), screen);
+
+ gtk_widget_set_halign (info_bar, GTK_ALIGN_FILL);
+ gtk_widget_set_valign (info_bar, GTK_ALIGN_START);
+ gtk_overlay_add_overlay (GTK_OVERLAY (terminal_screen_container_get_from_screen (screen)),
+ info_bar);
+ gtk_info_bar_set_default_response (GTK_INFO_BAR (info_bar), GTK_RESPONSE_CANCEL);
+ gtk_widget_show (info_bar);
+
+ return;
+ }
+}
+
static gboolean
terminal_screen_do_exec (TerminalScreen *screen,
FDSetupData *data /* adopting */,
@@ -1356,13 +1402,11 @@ terminal_screen_do_exec (TerminalScreen *screen,
GSettings *profile;
char **env, **argv;
char *shell = NULL;
- GError *err = NULL;
const char *working_dir;
VtePtyFlags pty_flags = VTE_PTY_DEFAULT;
GSpawnFlags spawn_flags = G_SPAWN_SEARCH_PATH_FROM_ENVP |
VTE_SPAWN_NO_PARENT_ENVV;
- GPid pid;
- gboolean result = FALSE;
+ GCancellable *cancellable = NULL;
if (priv->child_pid != -1) {
g_set_error_literal (error, G_DBUS_ERROR, G_DBUS_ERROR_FAILED,
@@ -1387,53 +1431,27 @@ terminal_screen_do_exec (TerminalScreen *screen,
env = get_child_environment (screen, working_dir, &shell);
argv = NULL;
- if (!get_child_command (screen, shell, &spawn_flags, &argv, &err) ||
- !vte_terminal_spawn_sync (terminal,
- pty_flags,
- working_dir,
- argv,
- env,
- spawn_flags,
- (GSpawnChildSetupFunc) (data ? terminal_screen_child_setup : NULL),
- data,
- &pid,
- NULL /* cancellable */,
- &err)) {
- GtkWidget *info_bar;
-
- info_bar = terminal_info_bar_new (GTK_MESSAGE_ERROR,
- _("_Profile Preferences"), RESPONSE_EDIT_PROFILE,
- _("_Relaunch"), RESPONSE_RELAUNCH,
- NULL);
- terminal_info_bar_format_text (TERMINAL_INFO_BAR (info_bar),
- _("There was an error creating the child process for this terminal"));
- terminal_info_bar_format_text (TERMINAL_INFO_BAR (info_bar),
- "%s", err->message);
- g_signal_connect (info_bar, "response",
- G_CALLBACK (info_bar_response_cb), screen);
-
- gtk_widget_set_halign (info_bar, GTK_ALIGN_FILL);
- gtk_widget_set_valign (info_bar, GTK_ALIGN_START);
- gtk_overlay_add_overlay (GTK_OVERLAY (terminal_screen_container_get_from_screen (screen)),
- info_bar);
- gtk_info_bar_set_default_response (GTK_INFO_BAR (info_bar), GTK_RESPONSE_CANCEL);
- gtk_widget_show (info_bar);
-
- g_propagate_error (error, err);
- goto out;
- }
-
- priv->child_pid = pid;
+ if (!get_child_command (screen, shell, &spawn_flags, &argv, error))
+ return FALSE;
- result = TRUE;
+ vte_terminal_spawn_async (terminal,
+ pty_flags,
+ working_dir,
+ argv,
+ env,
+ spawn_flags,
+ (GSpawnChildSetupFunc) (data ? terminal_screen_child_setup : NULL),
+ data,
+ (GDestroyNotify) (data ? free_fd_setup_data : NULL),
+ SPAWN_TIMEOUT,
+ cancellable,
+ spawn_result_cb, NULL);
-out:
g_free (shell);
g_strfreev (argv);
g_strfreev (env);
- free_fd_setup_data (data);
- return result;
+ return TRUE; /* can't report any more errors since they only occur async */
}
static gboolean
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]