Record in `struct inferior' whether the target process id we have has been faked by GDB or not. From: Pedro Alves --- gdb/inferior.c | 1 + gdb/inferior.h | 2 ++ gdb/linux-nat.c | 18 ++++++++++++++---- gdb/remote.c | 42 ++++++++++++++++++++++++++++++++---------- 4 files changed, 49 insertions(+), 14 deletions(-) diff --git a/gdb/inferior.c b/gdb/inferior.c index 65948c4..4df8c77 100644 --- a/gdb/inferior.c +++ b/gdb/inferior.c @@ -276,6 +276,7 @@ exit_inferior_1 (struct inferior *inftoex, int silent) observer_notify_inferior_exit (inf); inf->pid = 0; + inf->fake_pid_p = 0; if (inf->vfork_parent != NULL) { inf->vfork_parent->vfork_child = NULL; diff --git a/gdb/inferior.h b/gdb/inferior.h index f05789f..7857cbf 100644 --- a/gdb/inferior.h +++ b/gdb/inferior.h @@ -421,6 +421,8 @@ struct inferior /* Actual target inferior id, usually, a process id. This matches the ptid_t.pid member of threads of this inferior. */ int pid; + /* True if the PID was actually faked by GDB. */ + int fake_pid_p; /* State of GDB control of inferior process execution. See `struct inferior_control_state'. */ diff --git a/gdb/linux-nat.c b/gdb/linux-nat.c index d333c44..17236ec 100644 --- a/gdb/linux-nat.c +++ b/gdb/linux-nat.c @@ -5012,7 +5012,8 @@ linux_nat_info_proc_cmd_1 (char *args, enum info_proc_what what, int from_tty) { /* A long is used for pid instead of an int to avoid a loss of precision compiler warning from the output of strtoul. */ - long pid = PIDGET (inferior_ptid); + long pid = 0; + int explicit_pid = 0; int procfile; char buffer[MAXPATHLEN]; char fname1[MAXPATHLEN], fname2[MAXPATHLEN]; @@ -5026,14 +5027,23 @@ linux_nat_info_proc_cmd_1 (char *args, enum info_proc_what what, int from_tty) int target_errno; if (args && isdigit (args[0])) - pid = strtoul (args, &args, 10); + { + pid = strtoul (args, &args, 10); + explicit_pid = 1; + } args = skip_spaces (args); if (args && args[0]) error (_("Too many parameters: %s"), args); - if (pid == 0) - error (_("No current process: you must name one.")); + if (!explicit_pid) + { + if (!target_has_execution) + error (_("No current process: you must name one.")); + if (current_inferior ()->fake_pid_p) + error (_("Can't determine the current process's PID: you must name one.")); + pid = ptid_get_pid (inferior_ptid); + } printf_filtered (_("process %ld\n"), pid); if (cmdline_f) diff --git a/gdb/remote.c b/gdb/remote.c index 7542882..c5c9481 100644 --- a/gdb/remote.c +++ b/gdb/remote.c @@ -3253,6 +3253,10 @@ remote_start_remote (int from_tty, struct target_ops *target, int extended_p) if (!non_stop) { + ptid_t ptid; + int fake_pid_p = 0; + struct inferior *inf; + if (rs->buf[0] == 'W' || rs->buf[0] == 'X') { if (!extended_p) @@ -3272,19 +3276,37 @@ remote_start_remote (int from_tty, struct target_ops *target, int extended_p) /* Let the stub know that we want it to return the thread. */ set_continue_thread (minus_one_ptid); - /* Without this, some commands which require an active target - (such as kill) won't work. This variable serves (at least) - double duty as both the pid of the target process (if it has - such), and as a flag indicating that a target is active. - These functions should be split out into seperate variables, - especially since GDB will someday have a notion of debugging - several processes. */ - inferior_ptid = magic_null_ptid; + inferior_ptid = minus_one_ptid; /* Now, if we have thread information, update inferior_ptid. */ - inferior_ptid = remote_current_thread (inferior_ptid); + ptid = remote_current_thread (inferior_ptid); + if (!ptid_equal (ptid, minus_one_ptid)) + { + if (ptid_get_pid (ptid) == -1) + { + ptid = ptid_build (ptid_get_pid (magic_null_ptid), + ptid_get_lwp (ptid), + ptid_get_tid (ptid)); + fake_pid_p = 1; + } + + inferior_ptid = ptid; + } + else + { + /* Without this, some commands which require an active + target (such as kill) won't work. This variable serves + (at least) double duty as both the pid of the target + process (if it has such), and as a flag indicating that a + target is active. These functions should be split out + into seperate variables, especially since GDB will + someday have a notion of debugging several processes. */ + inferior_ptid = magic_null_ptid; + fake_pid_p = 1; + } - remote_add_inferior (ptid_get_pid (inferior_ptid), -1); + inf = remote_add_inferior (ptid_get_pid (inferior_ptid), -1); + inf->fake_pid_p = fake_pid_p; /* Always add the main thread. */ add_thread_silent (inferior_ptid);