因此,当glibc崩溃时,它有一个 * glibc检测到* 崩溃消息。然后打印出一堆回溯,比如
*** glibc detected *** ./odin: free(): invalid pointer: 0xbfba4444 ***
======= Backtrace: =========
/lib/tls/i686/cmov/libc.so.6(+0x6b161)[0xb75f9161]
/lib/tls/i686/cmov/libc.so.6(+0x6c9b8)[0xb75fa9b8]
/lib/tls/i686/cmov/libc.so.6(cfree+0x6d)[0xb75fda9d]
/usr/lib/libstdc++.so.6(_ZdlPv+0x1f)[0xb77da2ef]
一切都很好,但其他情况下,当事情崩溃时,我一直在做backtrace(),然后使用系统调用addr2line并打印函数中的实际点。但是当它是一个glibc崩溃时,它会绕过我调用的任何信号处理程序。
有没有办法解决这些glibc崩溃问题?
答案 0 :(得分:3)
这是记忆功能的一个选项,您可以使用mallopt
切换它。根据它的声音,你想将M_CHECK_ACTION
设置为零以允许继续执行,除非你希望程序立即退出,在这种情况下看看2
是否允许你做你想做的事。 / p>
这个小程序会产生正常的glibc错误:test1.c
这个忽略了错误并继续:test2.c
这个中止错误:test3.c
答案 1 :(得分:3)
IIRC,glibc实际上会调用abort()
,因此处理SIGABRT
并从中打印回溯应该会为您提供所需的信息。
但是,我建议尝试valgrind:你收到的消息表明你有内存损坏问题。
一边评论(对不起,如果这是多余的;-)):核心转储有时更有用,只是回溯。它们可以通过例如在bash中设置ulimit -c unlimited
。当程序崩溃时,它将生成一个名为core.
的文件(或仅core
- 这取决于您正在运行的系统;如果您的系统运行,则将核心文件放入/var/cache/abrt
如果我没错的话)。然后,您可以通过运行gdb -c core a.out
来使用gdb检查核心文件; gdb会话看起来就像进程刚崩溃一样。