【发布时间】:2016-04-28 15:56:28
【问题描述】:
我正在尝试在研究代码中调试 C 中的段错误。我无法修改源代码/makefile。由于我无法修改 makefile(即重新编译程序)并且未使用 -g 选项编译可执行文件,我假设这会将 gdb 调试抛出窗口?或者有没有办法在不使用-g编译可执行文件的情况下使用gdb?
我可以请求更改源代码,但我几乎可以肯定 seg 错误是由于我的一个输入文件造成的,所以它不应该是源代码问题。
有人建议我使用我不太熟悉的“strace”。这是我对程序进行 strace 时输出的结尾:
close(27) = 0
munmap(0x2abe4843d000, 65536) = 0
write(2, "==== backtrace ====\n", 20==== backtrace ====
) = 20
write(2, " 2 0x00000000000597bc mxm_handle"..., 113 2 0x00000000000597bc mxm_handle_error() /var/tmp/OFED_topdir/BUILD/mxm-3.3.3055/src/mxm/util/debug/debug.c:641
) = 113
write(2, " 3 0x000000000005992c mxm_error_"..., 121 3 0x000000000005992c mxm_error_signal_handler() /var/tmp/OFED_topdir/BUILD/mxm-3.3.3055/src/mxm/util/debug/debug.c:616
) = 121
write(2, " 4 0x00000037ccc326a0 killpg() "..., 37 4 0x00000037ccc326a0 killpg() ??:0
) = 37
write(2, " 5 0x00000000004ec6ef interpLema"..., 99 5 0x00000000004ec6ef interpLemansToMopar_linear() /home/dzdang/w16/sources/mopar_bc_interp.c:559
) = 99
write(2, " 6 0x000000000040c4ee main() /h"..., 68 6 0x000000000040c4ee main() /home/dzdang/w16/sources/lemans.c:611
) = 68
write(2, " 7 0x00000037ccc1ed5d __libc_sta"..., 48 7 0x00000037ccc1ed5d __libc_start_main() ??:0
) = 48
write(2, " 8 0x0000000000403c99 _start() "..., 37 8 0x0000000000403c99 _start() ??:0
) = 37
write(2, "===================\n", 20===================
) = 20
brk(0x2958000) = 0x2958000
tgkill(15432, 15432, SIGSEGV) = 0
rt_sigreturn(0x3c48) = 46993935941696
--- SIGSEGV (Segmentation fault) @ 0 (0) ---
+++ killed by SIGSEGV +++
Segmentation fault
任何想法这意味着什么?或者关于如何调试的任何建议?
【问题讨论】:
-
错误的输入数据不应产生段错误。就是这样,真的。一条错误消息,比如“第 XX 行输入数据错误”,没问题。
-
如何将命令直接编译到您的终端,而不使用 makefile 来获取带有调试信息的可执行文件?
-
此代码涉及读取输入文件并将它们存储在动态分配的数组中。我在想也许输入文件是错误的,它导致不正确的读取(或根本没有读取),因此在尝试访问该数组时,它可能超出范围?这个程序没有太多的错误检查代码。
-
@MikeCAT 嗯。这对于很多源代码是否实用?我有超过 500 多个用 C&Fortran 编写的文件链接在一起。
-
不过,总的来说,您可以通过非常仔细地检查输入文件以检查其有效性,甚至编写程序来验证它们,从而更有效地利用您的时间。
标签: c segmentation-fault gdb strace