/** If it actually changed the directory it returns true */ void do_subshell_chdir (const vfs_path_t * vpath, gboolean update_prompt) { char *pcwd; pcwd = vfs_path_to_str_flags (current_panel->cwd_vpath, 0, VPF_RECODE); if (!(subshell_state == INACTIVE && strcmp (subshell_cwd, pcwd) != 0)) { /* We have to repaint the subshell prompt if we read it from * the main program. Please note that in the code after this * if, the cd command that is sent will make the subshell * repaint the prompt, so we don't have to paint it. */ if (update_prompt) do_update_prompt (); g_free (pcwd); return; } /* The initial space keeps this out of the command history (in bash because we set "HISTCONTROL=ignorespace") */ write_all (mc_global.tty.subshell_pty, " cd ", 4); if (vpath != NULL) { char *translate; translate = vfs_translate_path_n (vfs_path_as_str (vpath)); if (translate != NULL) { GString *temp; temp = subshell_name_quote (translate); write_all (mc_global.tty.subshell_pty, temp->str, temp->len); g_string_free (temp, TRUE); g_free (translate); } else { write_all (mc_global.tty.subshell_pty, ".", 1); } } else { write_all (mc_global.tty.subshell_pty, "/", 1); } write_all (mc_global.tty.subshell_pty, "\n", 1); subshell_state = RUNNING_COMMAND; feed_subshell (QUIETLY, FALSE); if (subshell_alive) { int bPathNotEq = strcmp (subshell_cwd, pcwd); if (bPathNotEq && subshell_type == TCSH) { char rp_subshell_cwd[PATH_MAX]; char rp_current_panel_cwd[PATH_MAX]; char *p_subshell_cwd = mc_realpath (subshell_cwd, rp_subshell_cwd); char *p_current_panel_cwd = mc_realpath (pcwd, rp_current_panel_cwd); if (p_subshell_cwd == NULL) p_subshell_cwd = subshell_cwd; if (p_current_panel_cwd == NULL) p_current_panel_cwd = pcwd; bPathNotEq = strcmp (p_subshell_cwd, p_current_panel_cwd); } if (bPathNotEq && !DIR_IS_DOT (pcwd)) { char *cwd; cwd = vfs_path_to_str_flags (current_panel->cwd_vpath, 0, VPF_STRIP_PASSWORD); vfs_print_message (_("Warning: Cannot change to %s.\n"), cwd); g_free (cwd); } } update_subshell_prompt = FALSE; g_free (pcwd); /* Make sure that MC never stores the CWD in a silly format */ /* like /usr////lib/../bin, or the strcmp() above will fail */ }
void do_executev (const char *shell, int flags, char *const argv[]) { #ifdef ENABLE_SUBSHELL vfs_path_t *new_dir_vpath = NULL; #endif /* ENABLE_SUBSHELL */ vfs_path_t *old_vfs_dir_vpath = NULL; if (!vfs_current_is_local ()) old_vfs_dir_vpath = vfs_path_clone (vfs_get_raw_current_dir ()); if (mc_global.mc_run_mode == MC_RUN_FULL) save_cwds_stat (); pre_exec (); if (mc_global.tty.console_flag != '\0') handle_console (CONSOLE_RESTORE); if (!mc_global.tty.use_subshell && *argv != NULL && (flags & EXECUTE_INTERNAL) == 0) { printf ("%s%s\n", mc_prompt, *argv); fflush (stdout); } #ifdef ENABLE_SUBSHELL if (mc_global.tty.use_subshell && (flags & EXECUTE_INTERNAL) == 0) { do_update_prompt (); /* We don't care if it died, higher level takes care of this */ invoke_subshell (*argv, VISIBLY, old_vfs_dir_vpath != NULL ? NULL : &new_dir_vpath); } else #endif /* ENABLE_SUBSHELL */ my_systemv_flags (flags, shell, argv); if ((flags & EXECUTE_INTERNAL) == 0) { if ((pause_after_run == pause_always || (pause_after_run == pause_on_dumb_terminals && !mc_global.tty.xterm_flag && mc_global.tty.console_flag == '\0')) && quit == 0 #ifdef ENABLE_SUBSHELL && subshell_state != RUNNING_COMMAND #endif /* ENABLE_SUBSHELL */ ) { printf (_("Press any key to continue...")); fflush (stdout); tty_raw_mode (); get_key_code (0); printf ("\r\n"); fflush (stdout); } if (mc_global.tty.console_flag != '\0' && output_lines != 0 && mc_global.keybar_visible) { putchar ('\n'); fflush (stdout); } } if (mc_global.tty.console_flag != '\0') handle_console (CONSOLE_SAVE); edition_post_exec (); #ifdef ENABLE_SUBSHELL if (new_dir_vpath != NULL) { do_possible_cd (new_dir_vpath); vfs_path_free (new_dir_vpath); } #endif /* ENABLE_SUBSHELL */ if (old_vfs_dir_vpath != NULL) { mc_chdir (old_vfs_dir_vpath); vfs_path_free (old_vfs_dir_vpath); } if (mc_global.mc_run_mode == MC_RUN_FULL) { update_panels (UP_OPTIMIZE, UP_KEEPSEL); update_xterm_title_path (); } do_refresh (); use_dash (TRUE); }
/** If it actually changed the directory it returns true */ void do_subshell_chdir (const char *directory, gboolean update_prompt, gboolean reset_prompt) { char *pcwd; char *temp; char *translate; pcwd = vfs_translate_path_n (current_panel->cwd); if (!(subshell_state == INACTIVE && strcmp (subshell_cwd, pcwd) != 0)) { /* We have to repaint the subshell prompt if we read it from * the main program. Please note that in the code after this * if, the cd command that is sent will make the subshell * repaint the prompt, so we don't have to paint it. */ if (update_prompt) do_update_prompt (); g_free (pcwd); return; } /* The initial space keeps this out of the command history (in bash because we set "HISTCONTROL=ignorespace") */ write_all (mc_global.tty.subshell_pty, " cd ", 4); if (*directory) { translate = vfs_translate_path_n (directory); if (translate) { temp = subshell_name_quote (translate); if (temp) { write_all (mc_global.tty.subshell_pty, temp, strlen (temp)); g_free (temp); } else { /* Should not happen unless the directory name is so long that we don't have memory to quote it. */ write_all (mc_global.tty.subshell_pty, ".", 1); } g_free (translate); } else { write_all (mc_global.tty.subshell_pty, ".", 1); } } else { write_all (mc_global.tty.subshell_pty, "/", 1); } write_all (mc_global.tty.subshell_pty, "\n", 1); subshell_state = RUNNING_COMMAND; feed_subshell (QUIETLY, FALSE); if (subshell_alive) { int bPathNotEq = strcmp (subshell_cwd, pcwd); if (bPathNotEq && subshell_type == TCSH) { char rp_subshell_cwd[PATH_MAX]; char rp_current_panel_cwd[PATH_MAX]; char *p_subshell_cwd = mc_realpath (subshell_cwd, rp_subshell_cwd); char *p_current_panel_cwd = mc_realpath (pcwd, rp_current_panel_cwd); if (p_subshell_cwd == NULL) p_subshell_cwd = subshell_cwd; if (p_current_panel_cwd == NULL) p_current_panel_cwd = pcwd; bPathNotEq = strcmp (p_subshell_cwd, p_current_panel_cwd); } if (bPathNotEq && strcmp (pcwd, ".")) { char *cwd = strip_password (g_strdup (pcwd), 1); fprintf (stderr, _("Warning: Cannot change to %s.\n"), cwd); g_free (cwd); } } if (reset_prompt) prompt_pos = 0; update_subshell_prompt = FALSE; g_free (pcwd); /* Make sure that MC never stores the CWD in a silly format */ /* like /usr////lib/../bin, or the strcmp() above will fail */ }
static void do_execute (const char *shell, const char *command, int flags) { #ifdef HAVE_SUBSHELL_SUPPORT char *new_dir = NULL; #endif /* HAVE_SUBSHELL_SUPPORT */ #ifdef USE_VFS char *old_vfs_dir = 0; if (!vfs_current_is_local ()) old_vfs_dir = g_strdup (vfs_get_current_dir ()); #endif /* USE_VFS */ save_cwds_stat (); pre_exec (); if (console_flag) handle_console (CONSOLE_RESTORE); if (!use_subshell && command && !(flags & EXECUTE_INTERNAL)) { printf ("%s%s\n", prompt, command); } #ifdef HAVE_SUBSHELL_SUPPORT if (use_subshell && !(flags & EXECUTE_INTERNAL)) { do_update_prompt (); /* We don't care if it died, higher level takes care of this */ #ifdef USE_VFS invoke_subshell (command, VISIBLY, old_vfs_dir ? 0 : &new_dir); #else invoke_subshell (command, VISIBLY, &new_dir); #endif /* !USE_VFS */ } else #endif /* HAVE_SUBSHELL_SUPPORT */ my_system (flags, shell, command); if (!(flags & EXECUTE_INTERNAL)) { if ((pause_after_run == pause_always || (pause_after_run == pause_on_dumb_terminals && !xterm_flag && !console_flag)) && !quit #ifdef HAVE_SUBSHELL_SUPPORT && subshell_state != RUNNING_COMMAND #endif /* HAVE_SUBSHELL_SUPPORT */ ) { printf (_("Press any key to continue...")); fflush (stdout); mc_raw_mode (); get_key_code (0); printf ("\r\n"); fflush (stdout); } if (console_flag) { if (output_lines && keybar_visible) { putchar ('\n'); fflush (stdout); } } } if (console_flag) handle_console (CONSOLE_SAVE); edition_post_exec (); #ifdef HAVE_SUBSHELL_SUPPORT if (new_dir) do_possible_cd (new_dir); #endif /* HAVE_SUBSHELL_SUPPORT */ #ifdef USE_VFS if (old_vfs_dir) { mc_chdir (old_vfs_dir); g_free (old_vfs_dir); } #endif /* USE_VFS */ update_panels (UP_OPTIMIZE, UP_KEEPSEL); update_xterm_title_path (); do_refresh (); use_dash (TRUE); }