Fix crash in "run" on macOS when gdb is not signed
On macOS, when gdb is not code-signed, it will throw an exception from darwin_attach_pid. However, gdb also then crashes: thread.c:93: internal-error: struct thread_info *inferior_thread(): Assertion `tp' failed. I think the problem here is that darwin_attach_pid does not clean up inferior_ptid and inf->pid on failure. This leads to a situation where gdb tries to find a thread, but cannot. In other cases, gdb would mourn the inferior at this point; but here this is not possible because the target has not been pushed. Instead this patch works by simply updating the inferior and inferior_ptid on failure. Tested by building an unsigned gdb on macOS and trying to run an inferior. gdb/ChangeLog 2018-07-03 Tom Tromey <tom@tromey.com> PR cli/23340: * darwin-nat.c (darwin_attach_pid): Reset inferior and inferior_ptid on error.
This commit is contained in:
parent
b8a6ced796
commit
a50c11c666
2 changed files with 75 additions and 54 deletions
|
@ -1,3 +1,9 @@
|
|||
2018-07-03 Tom Tromey <tom@tromey.com>
|
||||
|
||||
PR cli/23340:
|
||||
* darwin-nat.c (darwin_attach_pid): Reset inferior and
|
||||
inferior_ptid on error.
|
||||
|
||||
2018-07-02 Maciej W. Rozycki <macro@mips.com>
|
||||
Simon Marchi <simon.marchi@polymtl.ca>
|
||||
|
||||
|
|
123
gdb/darwin-nat.c
123
gdb/darwin-nat.c
|
@ -1583,77 +1583,92 @@ darwin_attach_pid (struct inferior *inf)
|
|||
darwin_inferior *priv = new darwin_inferior;
|
||||
inf->priv.reset (priv);
|
||||
|
||||
kret = task_for_pid (gdb_task, inf->pid, &priv->task);
|
||||
if (kret != KERN_SUCCESS)
|
||||
TRY
|
||||
{
|
||||
int status;
|
||||
|
||||
if (!inf->attach_flag)
|
||||
kret = task_for_pid (gdb_task, inf->pid, &priv->task);
|
||||
if (kret != KERN_SUCCESS)
|
||||
{
|
||||
kill (inf->pid, 9);
|
||||
waitpid (inf->pid, &status, 0);
|
||||
int status;
|
||||
|
||||
if (!inf->attach_flag)
|
||||
{
|
||||
kill (inf->pid, 9);
|
||||
waitpid (inf->pid, &status, 0);
|
||||
}
|
||||
|
||||
error
|
||||
(_("Unable to find Mach task port for process-id %d: %s (0x%lx).\n"
|
||||
" (please check gdb is codesigned - see taskgated(8))"),
|
||||
inf->pid, mach_error_string (kret), (unsigned long) kret);
|
||||
}
|
||||
|
||||
error (_("Unable to find Mach task port for process-id %d: %s (0x%lx).\n"
|
||||
" (please check gdb is codesigned - see taskgated(8))"),
|
||||
inf->pid, mach_error_string (kret), (unsigned long) kret);
|
||||
}
|
||||
inferior_debug (2, _("inferior task: 0x%x, pid: %d\n"),
|
||||
priv->task, inf->pid);
|
||||
|
||||
inferior_debug (2, _("inferior task: 0x%x, pid: %d\n"),
|
||||
priv->task, inf->pid);
|
||||
if (darwin_ex_port == MACH_PORT_NULL)
|
||||
{
|
||||
/* Create a port to get exceptions. */
|
||||
kret = mach_port_allocate (gdb_task, MACH_PORT_RIGHT_RECEIVE,
|
||||
&darwin_ex_port);
|
||||
if (kret != KERN_SUCCESS)
|
||||
error (_("Unable to create exception port, mach_port_allocate "
|
||||
"returned: %d"),
|
||||
kret);
|
||||
|
||||
if (darwin_ex_port == MACH_PORT_NULL)
|
||||
{
|
||||
/* Create a port to get exceptions. */
|
||||
kret = mach_port_insert_right (gdb_task, darwin_ex_port,
|
||||
darwin_ex_port,
|
||||
MACH_MSG_TYPE_MAKE_SEND);
|
||||
if (kret != KERN_SUCCESS)
|
||||
error (_("Unable to create exception port, mach_port_insert_right "
|
||||
"returned: %d"),
|
||||
kret);
|
||||
|
||||
/* Create a port set and put ex_port in it. */
|
||||
kret = mach_port_allocate (gdb_task, MACH_PORT_RIGHT_PORT_SET,
|
||||
&darwin_port_set);
|
||||
if (kret != KERN_SUCCESS)
|
||||
error (_("Unable to create port set, mach_port_allocate "
|
||||
"returned: %d"),
|
||||
kret);
|
||||
|
||||
kret = mach_port_move_member (gdb_task, darwin_ex_port,
|
||||
darwin_port_set);
|
||||
if (kret != KERN_SUCCESS)
|
||||
error (_("Unable to move exception port into new port set, "
|
||||
"mach_port_move_member\n"
|
||||
"returned: %d"),
|
||||
kret);
|
||||
}
|
||||
|
||||
/* Create a port to be notified when the child task terminates. */
|
||||
kret = mach_port_allocate (gdb_task, MACH_PORT_RIGHT_RECEIVE,
|
||||
&darwin_ex_port);
|
||||
&priv->notify_port);
|
||||
if (kret != KERN_SUCCESS)
|
||||
error (_("Unable to create exception port, mach_port_allocate "
|
||||
error (_("Unable to create notification port, mach_port_allocate "
|
||||
"returned: %d"),
|
||||
kret);
|
||||
|
||||
kret = mach_port_insert_right (gdb_task, darwin_ex_port, darwin_ex_port,
|
||||
MACH_MSG_TYPE_MAKE_SEND);
|
||||
kret = mach_port_move_member (gdb_task,
|
||||
priv->notify_port, darwin_port_set);
|
||||
if (kret != KERN_SUCCESS)
|
||||
error (_("Unable to create exception port, mach_port_insert_right "
|
||||
"returned: %d"),
|
||||
kret);
|
||||
|
||||
/* Create a port set and put ex_port in it. */
|
||||
kret = mach_port_allocate (gdb_task, MACH_PORT_RIGHT_PORT_SET,
|
||||
&darwin_port_set);
|
||||
if (kret != KERN_SUCCESS)
|
||||
error (_("Unable to create port set, mach_port_allocate "
|
||||
"returned: %d"),
|
||||
kret);
|
||||
|
||||
kret = mach_port_move_member (gdb_task, darwin_ex_port, darwin_port_set);
|
||||
if (kret != KERN_SUCCESS)
|
||||
error (_("Unable to move exception port into new port set, "
|
||||
error (_("Unable to move notification port into new port set, "
|
||||
"mach_port_move_member\n"
|
||||
"returned: %d"),
|
||||
kret);
|
||||
|
||||
darwin_setup_request_notification (inf);
|
||||
|
||||
darwin_setup_exceptions (inf);
|
||||
}
|
||||
CATCH (ex, RETURN_MASK_ALL)
|
||||
{
|
||||
inf->pid = 0;
|
||||
inf->priv.reset ();
|
||||
inferior_ptid = null_ptid;
|
||||
|
||||
/* Create a port to be notified when the child task terminates. */
|
||||
kret = mach_port_allocate (gdb_task, MACH_PORT_RIGHT_RECEIVE,
|
||||
&priv->notify_port);
|
||||
if (kret != KERN_SUCCESS)
|
||||
error (_("Unable to create notification port, mach_port_allocate "
|
||||
"returned: %d"),
|
||||
kret);
|
||||
|
||||
kret = mach_port_move_member (gdb_task,
|
||||
priv->notify_port, darwin_port_set);
|
||||
if (kret != KERN_SUCCESS)
|
||||
error (_("Unable to move notification port into new port set, "
|
||||
"mach_port_move_member\n"
|
||||
"returned: %d"),
|
||||
kret);
|
||||
|
||||
darwin_setup_request_notification (inf);
|
||||
|
||||
darwin_setup_exceptions (inf);
|
||||
throw_exception (ex);
|
||||
}
|
||||
END_CATCH
|
||||
|
||||
target_ops *darwin_ops = get_native_target ();
|
||||
if (!target_is_pushed (darwin_ops))
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue