处理segfault信号SIGSEGV需要使用siginfo_t确定segfault的原因
我正在为 pthread 库制作一个包装器,它允许每个线程拥有自己的一组非共享内存。现在,如果任何线程尝试读取另一个线程的数据,程序就会出现段错误。这很好,我可以用ighandler 捕获它并调用pthread_exit() 并继续执行该程序。
但并不是所有的段错误都是由坏的 RWE 造成的。我需要找到一种方法来使用 siginfo 类型来确定段错误是否是错误的编程或此错误。有什么想法吗?
由于我使用 mmap 来管理内存页面,我认为在 siginfo 中使用 si_addr 会帮助我。
I'm making a wrapper for the pthread library that allows each thread to have its own set of non-shared memory. Right now the way c is set up if any thread tries to rwe another threads data, the program segfaults. This is fine, I can catch it with a sighandler and call pthread_exit()
and continue on with the program.
But not every segfault is going to be the result of a bad rwe. I need to find a way to use the siginfo type to determine if the segfault was bad programming or this error. Any ideas?
Since I am using mmap to manage the memory pages I think using si_addr
in siginfo
will help me out.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
听起来您真正想要的是线程本地存储,它已经比这更便携地解决了。 GCC提供
__thread
,MSVC提供__declspec(thread)
。 boost::thread 提供可移植的线程本地存储根据平台/工具链等使用各种机制。如果你真的想走这条路,它可以工作,但这条路充满了危险。从 SIGSEGV 中恢复在技术上是未定义的行为,尽管它可以在相当多的平台上工作,但它既不健壮也不可移植。您也需要非常小心在信号处理程序中所做的事情 - 异步安全函数,即那些可以合法地从信号处理程序安全调用的函数非常小。
我过去已经成功地使用过这个技巧几次,通常用于在用户空间中将“页面”标记为“脏”。我这样做的方法是设置一个哈希表,其中包含我感兴趣的所有内存“页面”的基地址。当您在处理程序中捕获 SIGSEGV 时,您可以使用简单的方法将地址映射回页面算术运算。如果哈希表可以在没有锁的情况下读取,那么您就可以查找这是您关心的页面还是来自其他地方的段错误,并决定如何操作。
It sounds like what you're really after is thread local storage which is already solved much more portably than this. GCC provides
__thread
, MSVC provides__declspec(thread)
. boost::thread provides portable thread local storage using a variety of mechanisms depending on platform/toolchain etc.If you really do want to go down this road it can be made to work however the path is fraught with dangers. Recovering from SIGSEGV is undefined behaviour technically, although it can be made to work on quite a few platforms it is neither robust nor portable. You need to be very careful what you do in the signal handler though too -- the list of async-safe functions, i.e. those which may legally be safely called from a signal handler is very small.
I've used this trick successfully a few times in the past, normally for marking "pages" as "dirty" in userspace. The way I did this was by setting up a hashtable which contained the base address of all the "pages" of memory that I was interested in. When you catch a SIGSEGV in a handler you can then map an address back to a page with simple arithmetic operations. Provided the hashtable can be read without locks you can then lookup if this is a page that you care about or a segfault from somewhere else and decide how to act.