如何在不将信号传递给应用程序的情况下步进?

时间:2018-09-11 10:12:53

标签: gdb signals breakpoints

假设在GDB下运行的进程由于接收到一个信号而停止,例如SIGSEGV由于访问无效的位置。然后,我通过写寄存器或任何其他方式修复该位置,并想单步执行,然后重试错误的指令。

有一个命令stepi,如果忽略或最初未接收到信号,该命令将起作用。但是,由于有一个待处理的信号,所以我至少不能直接使用它。如果我使用signal 0命令,它将忽略该信号,但是它将作为continue使用。因此,如果我使用signal 0,则必须找出下一条指令的起始位置,在其上添加tb,以此类推。这不方便。

另一种方式是,像handle SIGSEGV ignore之后是stepi,然后是另一个handle命令来恢复其原始状态。也是不方便的:为此,甚至无法define使用“黑匣子”功能,因为信号处理的原始状态可能不是默认状态,并且在si之后很难恢复它。

那么,有什么简单的方法可以在不继续执行的情况下删除挂起的信号?

1 个答案:

答案 0 :(得分:2)

在gdb version 7.9和更高版本中,有一个queue-signal命令可以让您发送信号(或者,如果您将0作为参数,则根本不发送信号),下次恢复目标。以下是一些documentation

  

队列信号将在线程恢复执行时立即传递到当前线程。 信号可以是信号的名称或编号。必须设置信号处理方式以将信号传递给程序,否则GDB将报告错误。您可以使用handle命令控制来自GDB的信号处理。

     

或者,如果 signal 为零,则将丢弃当前线程中当前排队的任何信号,并且当执行恢复时将不会传递任何信号。

     

此命令与signal命令的区别在于,信号只是排队,不恢复执行。并且queue-signal不能用于传递其处理状态已设置为nopass的信号。