有没有办法返回在C中导致SIGSEGV的地址?

时间:2018-11-28 22:41:31

标签: c sigsegv

我是C语言的虚拟人,正在一个C项目上工作,该项目要求我编写一个信号处理程序以捕获SIGSEGV信号并执行一些操作。

基本上,主程序将尝试访问既不可读也不可写的内存块。当主程序访问该内存块时,它将引发SIGSEGV信号,并且在我的信号处理程序函数中,我将捕获该信号并使用mprotect()将该内存块转换为可读写的块。

但是我不知道有什么方法可以获取当信号被我的信号处理程序捕获时导致SIGSEGV的地址。如果我没有引起SIGSEGV的实际地址,我无能为力。而且不允许我从main抓取地址到我的信号处理程序中。

有人可以帮助我吗?谢谢!

1 个答案:

答案 0 :(得分:3)

至少在Linux上答案是肯定的。

您使用sigaction注册信号处理程序,并设置SA_SIGINFO标志并设置sa_sigaction处理程序。

这使您可以访问siginfo_t(信号处理程序的第二个参数),该信号(除其他外)包含一个void *si_addr;字段,该字段(对于SIGSEGV)包含故障地址

#define _POSIX_C_SOURCE 199309L
#include <signal.h>

void my_handler(int sig, siginfo_t *info, void *ucontext) {
    ... info->si_addr ...
}

...
struct sigaction act = {0};
act.sa_sigaction = my_handler;
act.sa_flags = SA_SIGINFO;
sigaction(SIGSEGV, &act, NULL);

有关详细信息,请参见man 2 sigaction