我们在MIP核心上运行嵌入式Linux内核版本。我们编写的程序运行特定的测试套件。在其中一次压力测试(运行约12小时)期间,我们得到一个seg故障。这反过来又会产生核心转储。
不幸的是核心转储不是很有用。崩溃发生在一些动态链接的系统库中(可能是pthread或glibc)。核心转储中的回溯没有帮助,因为它只显示崩溃点而没有其他调用者(我们的用户空间应用程序是使用-g -O0构建的,但仍然没有回溯信息):
Cannot access memory at address 0x2aab1004
(gdb) bt
#0 0x2ab05d18 in ?? ()
warning: GDB can't find the start of the function at 0x2ab05d18.
GDB is unable to find the start of the function at 0x2ab05d18
and thus can't determine the size of that function's stack frame.
This means that GDB may be unable to access that stack frame, or
the frames below it.
This problem is most likely caused by an invalid program counter or
stack pointer.
However, if you think GDB should simply search farther back
from 0x2ab05d18 for code which looks like the beginning of a
function, you can increase the range of the search using the `set
heuristic-fence-post' command.
另一个不幸的是我们无法运行gdb / gdbserver。 gdb / gdbserver继续打破__nptl_create_event。看到测试创建了线程,定时器并且每隔5秒就会破坏它们几乎不可能长时间坐下来继续它们。
编辑: 我们的工具链不支持另一个注释,backtrace和backtrace_symbols。
因此:
有没有一种方法来捕获seg错误并生成更多的回溯数据,堆栈指针,调用堆栈等?
有没有办法从崩溃在.so文件中的核心转储中获取更多数据?
感谢。
答案 0 :(得分:1)
如果所有其他方法都失败,请使用调试器运行命令!
只需将“gdb”以正常启动命令的形式输入并输入“c”ontinue即可使进程运行。当任务段错误时,它将返回交互式gdb提示而不是核心转储。然后,您应该能够获得更有意义的堆栈跟踪等。
另一种选择是使用“truss”(如果可用)。这将告诉您在异常终止时正在使用哪些系统调用。
答案 1 :(得分:1)
GDB无法在0x2ab05d18找到该函数的开头
坠机时该地址是什么?
执行info shared
,并查看是否有包含该地址的库。
导致问题的最可能原因是:您是否在将strip libpthread.so.0
上传到目标之前运行了它?不要那样做:GDB要求libpthread.so.0去除而不是。如果您的工具链包含带有调试符号的libpthread.so.0
(因此对于目标而言太大),请在其上运行strip -g
,而不是完整的strip
。
更新
产生的内存
info shared
无法访问地址0x2ab05d18
这意味着GDB无法访问共享库列表(这将解释丢失的堆栈跟踪)。最常见的原因:实际生成core
的二进制文件与您为GDB提供的二进制文件不匹配。一个不太常见的原因:您的核心转储被截断(可能是由于ulimit -c
设置得太低)。