当我用 gdb 运行程序时,我得到这个错误信息。错误显示在这一行:
long a = thread_fake(); //in file1.c
我遇到了在单独文件中定义的其他函数的问题,因此我将其简化为一个只返回 0 的简单函数。 该函数定义为:
long thread_fake(){ //defined in file2.c
return 0;
}
正如@EmployedRussian 指出的那样,程序似乎用完了堆栈。 valgrind 显示以下错误:
==14711== 144 bytes in 1 blocks are possibly lost in loss record 17 of 32
==14711== at 0x4025315: calloc (vg_replace_malloc.c:467)
==14711== by 0x4010CD7: allocate_dtv (dl-tls.c:300)
==14711== by 0x401146B: _dl_allocate_tls (dl-tls.c:464)
==14711== by 0x40475C6: pthread_create@@GLIBC_2.1 (allocatestack.c:570)
==14711== by 0x8050583: tm_main_startup
==14711== by 0x8048F6B: main (genome.c:201)
==14711== 144 bytes in 1 blocks are possibly lost in loss record 18 of 32
==14711== at 0x4025315: calloc (vg_replace_malloc.c:467)
==14711== by 0x4010CD7: allocate_dtv (dl-tls.c:300)
==14711== by 0x401146B: _dl_allocate_tls (dl-tls.c:464)
==14711== by 0x40475C6: pthread_create@@GLIBC_2.1 (allocatestack.c:570)
==14711== by 0x804DFE3: thread_startup (thread.c:151)
==14711== by 0x8048F73: main (genome.c:203)
所有创建的线程都加入了相应的 pthread_join 调用。我还尝试了 sgcheck 工具,但它在平台“x86-linux”上不起作用。请帮忙。
bt命令的完整输出:
Program received signal SIGSEGV, Segmentation fault.
[Switching to Thread 0x406e8b70 (LWP 19416)]
sequencer_run (argPtr=0x89fce00) at sequencer.c:251
251 a = thread_fake();
(gdb) bt
#0 sequencer_run (argPtr=0x89fce00) at sequencer.c:251
#1 0x0804e306 in threadWait (argPtr=0x89dc1f4) at ../lib/thread.c:105
#2 0x4003be99 in start_thread (arg=0x406e8b70) at pthread_create.c:304
#3 0x40253cbe in clone () at ../sysdeps/unix/sysv/linux/i386/clone.S:130
最佳答案
The error is shown at this line:
long a = thread_fake(); //in file1.c
这可能会导致 SIGSEGV
如果您的程序已用完堆栈。
使用 x/i $pc
检查 GDB 中的实际崩溃指令.
如果指令是 PUSH
, 或 CALL
,那么我的猜测得到了证实。
另一种可能性:您已经通过优化编译了代码,而实际的错误指令与它归因于的源代码行几乎没有关系。
更新:
Yes it gives a call
call 0x804e580 <thread_fake>
. What could be the solution?
解决方案是不要用完堆栈。执行 GDB where
命令,然后,在导致崩溃的每个帧中,执行 info frame
并寻找过大的框架。
不要在堆栈上分配太多数据,或增加堆栈大小 (ulimit -s
)。
valgrind shows the following error:
也就是
- 不是错误
- 与你的问题无关
更新 2:
How do I check the size of each frame?
鉴于此:
Stack level 0, frame at 0xffffc248:
...
Stack level 1, frame at 0xffffc250:
...
Stack level 2, frame at 0xffffc2a0:
第 1 帧的大小是 8
( 0xffffc250 - 0xffffc248
),第 2 帧是 80
等
最终更新:
事实证明,我上面的程序未能测量 frame#0 的大小,结果是……61MB!由于存在巨大的本地数组(正如 Grady Player 正确猜到的那样)。
关于c - 程序接收到信号 SIGSEGV,段错误(程序用完堆栈。),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18751532/