1 /* Execution routines for GNU Midnight Commander
2 Copyright (C) 1994-2003 The Free Software Foundation
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or
7 (at your option) any later version.
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
19 #include <signal.h> /* kill() */
25 #include "cons.saver.h"
34 edition_post_exec (void)
38 /* FIXME: Missing on slang endwin? */
42 keypad (stdscr
, TRUE
);
46 if (alternate_plus_minus
)
47 application_keypad_mode ();
52 edition_pre_exec (void)
54 if (clear_before_exec
)
57 if (!(console_flag
|| xterm_flag
))
65 keypad (stdscr
, FALSE
);
68 numeric_keypad_mode ();
70 /* on xterms: maybe endwin did not leave the terminal on the shell
71 * screen page: do it now.
73 * Do not move this before endwin: in some systems rmcup includes
74 * a call to clear screen, so it will end up clearing the shell screen.
80 /* Set up the terminal before executing a program */
90 do_execute (const char *shell
, const char *command
, int flags
)
92 #ifdef HAVE_SUBSHELL_SUPPORT
94 #endif /* HAVE_SUBSHELL_SUPPORT */
97 char *old_vfs_dir
= 0;
99 if (!vfs_current_is_local ())
100 old_vfs_dir
= g_strdup (vfs_get_current_dir ());
106 handle_console (CONSOLE_RESTORE
);
108 if (!use_subshell
&& command
&& !(flags
& EXECUTE_INTERNAL
)) {
109 printf ("%s%s\n", prompt
, command
);
111 #ifdef HAVE_SUBSHELL_SUPPORT
112 if (use_subshell
&& !(flags
& EXECUTE_INTERNAL
)) {
115 /* We don't care if it died, higher level takes care of this */
117 invoke_subshell (command
, VISIBLY
, old_vfs_dir
? 0 : &new_dir
);
119 invoke_subshell (command
, VISIBLY
, &new_dir
);
120 #endif /* !USE_VFS */
122 #endif /* HAVE_SUBSHELL_SUPPORT */
123 my_system (flags
, shell
, command
);
125 if (!(flags
& EXECUTE_INTERNAL
)) {
126 if ((pause_after_run
== pause_always
127 || (pause_after_run
== pause_on_dumb_terminals
&& !xterm_flag
128 && !console_flag
)) && !quit
129 #ifdef HAVE_SUBSHELL_SUPPORT
130 && subshell_state
!= RUNNING_COMMAND
131 #endif /* HAVE_SUBSHELL_SUPPORT */
133 printf (_("Press any key to continue..."));
141 if (output_lines
&& keybar_visible
) {
149 handle_console (CONSOLE_SAVE
);
150 edition_post_exec ();
152 #ifdef HAVE_SUBSHELL_SUPPORT
154 do_possible_cd (new_dir
);
156 #endif /* HAVE_SUBSHELL_SUPPORT */
160 mc_chdir (old_vfs_dir
);
161 g_free (old_vfs_dir
);
165 update_panels (UP_OPTIMIZE
, UP_KEEPSEL
);
166 update_xterm_title_path ();
173 /* Executes a command */
175 shell_execute (const char *command
, int flags
)
177 #ifdef HAVE_SUBSHELL_SUPPORT
179 if (subshell_state
== INACTIVE
)
180 do_execute (shell
, command
, flags
| EXECUTE_AS_SHELL
);
182 message (1, MSG_ERROR
,
183 _(" The shell is already running a command "));
185 #endif /* HAVE_SUBSHELL_SUPPORT */
186 do_execute (shell
, command
, flags
| EXECUTE_AS_SHELL
);
193 do_execute (shell
, 0, 0);
200 #ifdef HAVE_SUBSHELL_SUPPORT
201 char *new_dir
= NULL
;
203 #endif /* HAVE_SUBSHELL_SUPPORT */
207 if (clear_before_exec
)
209 if (alternate_plus_minus
)
210 numeric_keypad_mode ();
212 /* With slang we don't want any of this, since there
213 * is no mc_raw_mode supported
217 #endif /* !HAVE_SLANG */
218 keypad (stdscr
, FALSE
);
223 handle_console (CONSOLE_RESTORE
);
225 #ifdef HAVE_SUBSHELL_SUPPORT
227 new_dir_p
= vfs_current_is_local ()? &new_dir
: NULL
;
228 if (invoke_subshell (NULL
, VISIBLY
, new_dir_p
))
229 quiet_quit_cmd (); /* User did `exit' or `logout': quit MC quietly */
231 #endif /* HAVE_SUBSHELL_SUPPORT */
233 if (output_starts_shell
) {
235 _("Type `exit' to return to the Midnight Commander"));
236 fprintf (stderr
, "\n\r\n\r");
238 my_system (EXECUTE_AS_SHELL
, shell
, NULL
);
243 handle_console (CONSOLE_SAVE
);
248 keypad (stdscr
, TRUE
);
250 /* Prevent screen flash when user did 'exit' or 'logout' within
257 if (alternate_plus_minus
)
258 application_keypad_mode ();
260 #ifdef HAVE_SUBSHELL_SUPPORT
264 do_possible_cd (new_dir
);
265 if (console_flag
&& output_lines
)
266 show_console_contents (output_start_y
,
267 LINES
- keybar_visible
- output_lines
-
268 1, LINES
- keybar_visible
- 1);
270 #endif /* HAVE_SUBSHELL_SUPPORT */
272 update_panels (UP_OPTIMIZE
, UP_KEEPSEL
);
273 update_xterm_title_path ();
279 do_suspend_cmd (void)
283 if (console_flag
&& !use_subshell
)
284 handle_console (CONSOLE_RESTORE
);
288 struct sigaction sigtstp_action
;
290 /* Make sure that the SIGTSTP below will suspend us directly,
291 without calling ncurses' SIGTSTP handler; we *don't* want
292 ncurses to redraw the screen immediately after the SIGCONT */
293 sigaction (SIGTSTP
, &startup_handler
, &sigtstp_action
);
295 kill (getpid (), SIGTSTP
);
297 /* Restore previous SIGTSTP action */
298 sigaction (SIGTSTP
, &sigtstp_action
, NULL
);
302 if (console_flag
&& !use_subshell
)
303 handle_console (CONSOLE_SAVE
);
305 edition_post_exec ();
314 update_panels (UP_OPTIMIZE
, UP_KEEPSEL
);
320 * Execute command on a filename that can be on VFS.
321 * Errors are reported to the user.
324 execute_with_vfs_arg (const char *command
, const char *filename
)
331 /* Simplest case, this file is local */
332 if (!filename
|| vfs_file_is_local (filename
)) {
333 do_execute (command
, filename
, EXECUTE_INTERNAL
);
337 /* FIXME: Creation of new files on VFS is not supported */
341 localcopy
= mc_getlocalcopy (filename
);
342 if (localcopy
== NULL
) {
343 message (1, MSG_ERROR
, _(" Cannot fetch a local copy of %s "),
349 * filename can be an entry on panel, it can be changed by executing
350 * the command, so make a copy. Smarter VFS code would make the code
353 fn
= g_strdup (filename
);
354 mc_stat (localcopy
, &st
);
356 do_execute (command
, localcopy
, EXECUTE_INTERNAL
);
357 mc_stat (localcopy
, &st
);
358 mc_ungetlocalcopy (fn
, localcopy
, mtime
!= st
.st_mtime
);