20#include "gdbsupport/common-defs.h"
23#include "gdbsupport/filestuff.h"
25#include "gdbsupport/common-inferior.h"
26#include "gdbsupport/common-gdbthread.h"
27#include "gdbsupport/pathstuff.h"
28#include "gdbsupport/signals-state-save-restore.h"
29#include "gdbsupport/gdb_tilde_expand.h"
42 execv_argv (
const char *exec_file,
const std::string &allargs,
43 const char *shell_file);
53 return const_cast<char **
> (&
m_argv[0]);
64 const std::string &allargs);
69 const std::string &allargs,
70 const char *shell_file);
94 const std::string &allargs)
101 std::string &args_copy =
m_storage = allargs;
103 m_argv.push_back (exec_file);
105 for (
size_t cur_pos = 0; cur_pos < args_copy.size ();)
108 std::size_t pos = args_copy.find_first_not_of (
" \t\n", cur_pos);
110 if (pos != std::string::npos)
114 std::size_t next_sep = args_copy.find_first_of (
" \t\n", cur_pos);
116 if (next_sep == std::string::npos)
120 next_sep = args_copy.size ();
125 args_copy[next_sep++] =
'\0';
128 m_argv.push_back (&args_copy[cur_pos]);
144 size_t shell_file_len = strlen (shell_file);
150 if (shell_file_len < 3)
153 if (shell_file[shell_file_len - 3] ==
'c'
154 && shell_file[shell_file_len - 2] ==
's'
155 && shell_file[shell_file_len - 1] ==
'h')
164 const std::string &allargs,
165 const char *shell_file)
167 if (shell_file == NULL)
177 const std::string &allargs,
178 const char *shell_file)
205 const char *p = exec_file;
223 need_to_quote =
true;
227 need_to_quote =
false;
239 for (p = exec_file; *p !=
'\0'; ++p)
243 else if (*p ==
'!' && escape_bang)
259 m_argv.push_back (shell_file);
269 char **env,
void (*traceme_fun) (),
270 gdb::function_view<
void (
int)> init_trace_fun,
271 void (*pre_trace_fun) (),
272 const char *shell_file_arg,
273 void (*exec_fun)(
const char *file,
char *
const *argv,
279 const char *shell_file;
280 const char *exec_file;
287 if (exec_file_arg == NULL)
290 exec_file = exec_file_arg;
295 if (startup_with_shell)
297 shell_file = shell_file_arg;
300 if (shell_file == NULL)
301 shell_file = get_shell ();
303 gdb_assert (shell_file != NULL);
309 execv_argv child_argv (exec_file, allargs, shell_file);
329 if (!inferior_cwd.empty ())
333 inferior_cwd = gdb_tilde_expand (inferior_cwd.c_str ());
339 if (pre_trace_fun != NULL)
353#if !(defined(__UCLIBC__) && defined(HAS_NOMMU))
354 if (pre_trace_fun || debug_fork)
361 perror_with_name ((
"vfork"));
373 if (!inferior_cwd.empty ())
375 if (chdir (inferior_cwd.c_str ()) < 0)
403 restore_original_signals_state ();
412 char **argv = child_argv.
argv ();
414 if (exec_fun != NULL)
415 (*exec_fun) (argv[0], &argv[0], env);
417 execvp (argv[0], &argv[0]);
421 warning (
"Cannot exec %s", argv[0]);
423 for (i = 1; argv[i] != NULL; i++)
424 warning (
" %s", argv[i]);
426 warning (
"Error: %s", safe_strerror (save_errno));
440 init_trace_fun (
pid);
455 int pending_execs = ntraps;
456 int terminal_initted = 0;
459 if (startup_with_shell)
466 resume_ptid = ptid_t (
pid);
468 resume_ptid = minus_one_ptid;
484 if (last_waitstatus != NULL)
485 *last_waitstatus = ws;
486 if (last_ptid != NULL)
487 *last_ptid = event_ptid;
508 error (_(
"During startup program terminated with signal %s, %s."),
509 gdb_signal_to_name (ws.
sig ()),
510 gdb_signal_to_string (ws.
sig ()));
517 error (_(
"During startup program exited with code %d."),
520 error (_(
"During startup program exited normally."));
543 if (!terminal_initted)
557 terminal_initted = 1;
560 if (--pending_execs == 0)
579 warning (
"Could not trace the inferior process.");
execv_argv(const char *exec_file, const std::string &allargs, const char *shell_file)
DISABLE_COPY_AND_ASSIGN(execv_argv)
std::vector< const char * > m_argv
void init_for_no_shell(const char *exec_file, const std::string &allargs)
void init_for_shell(const char *exec_file, const std::string &allargs, const char *shell_file)
static void shell_command(const char *arg, int from_tty)
const char * get_exec_file(int err)
void prefork_hook(const char *args)
const char * get_exec_wrapper()
static std::string exec_wrapper
void postfork_child_hook()
void postfork_hook(pid_t pid)
void trace_start_error_with_name(const char *string)
void trace_start_error(const char *fmt,...)
ptid_t startup_inferior(process_stratum_target *proc_target, pid_t pid, int ntraps, struct target_waitstatus *last_waitstatus, ptid_t *last_ptid)
pid_t fork_inferior(const char *exec_file_arg, const std::string &allargs, char **env, void(*traceme_fun)(), gdb::function_view< void(int)> init_trace_fun, void(*pre_trace_fun)(), const char *shell_file_arg, void(*exec_fun)(const char *file, char *const *argv, char *const *env))
static bool escape_bang_in_quoted_argument(const char *shell_file)
void switch_to_thread(struct thread_info *thr)
mach_port_t mach_port_t name mach_port_t mach_port_t name kern_return_t int int rusage_t pid_t pid
const std::string & get_inferior_cwd()
target_waitkind kind() const
ptid_t target_wait(ptid_t ptid, struct target_waitstatus *status, target_wait_flags options)
void target_continue(ptid_t ptid, enum gdb_signal signal)
int target_supports_multi_process(void)
void target_continue_no_signal(ptid_t ptid)
void target_mourn_inferior(ptid_t ptid)
void vwarning(const char *string, va_list args)
@ TARGET_WAITKIND_SPURIOUS
@ TARGET_WAITKIND_SIGNALLED
@ TARGET_WAITKIND_STOPPED
@ TARGET_WAITKIND_SYSCALL_RETURN
@ TARGET_WAITKIND_SYSCALL_ENTRY
@ TARGET_WAITKIND_VFORKED