gpt4 book ai didi

c - 谁调用了 atexit()?

转载 作者:太空宇宙 更新时间:2023-11-04 00:48:58 24 4
gpt4 key购买 nike

我有一个 C 程序在 Linux 上意外退出,我很难找出原因(没有核心转储,请参阅 XIO: fatal IO error 11)。我在程序的开头放置了一个 atexit() 并且当崩溃发生时确实调用了回调函数。

我怎么知道调用了atexit回调函数?通过阅读手册页,atexit 在退出(d'ho!)或从 main 返回时被调用。我可以排除后者,因为在 main 的末尾有一堆 printf 而我没有看到它们。我可以排除前者,因为我的程序中没有任何 exit()。

只有一个解决方案:exit 是从库函数中调用的。那是唯一的可能性吗?我怎么知道从哪里?是否可以从 atexit 回调中打印出堆栈跟踪或强制核心转储?

最佳答案

调用例如在你的 atexit 处理程序中中止(),并检查 gdb 中的核心转储。如果运行 atexit 处理程序,gdb backtrace 命令会显示它退出的位置。这是一个演示:

#include <stdlib.h>


void exit_handler(void)
{
abort();
}

void startup()
{
#ifdef DO_EXIT
exit(99);
#endif
}


int main(int argc, char *argv[])
{
atexit(exit_handler);

startup();

return 0;
}

然后这样做:

$ gcc -DDO_EXIT -g atexit.c
$ ulimit -c unlimited
$ ./a.out
Aborted (core dumped)
$ gdb ./a.out core.28162
GNU gdb (GDB) Fedora 7.7.1-19.fc20
..
Core was generated by `./a.out'.
Program terminated with signal SIGABRT, Aborted.
#0 0xb77d7424 in __kernel_vsyscall ()
Missing separate debuginfos, use: debuginfo-install glibc-2.18-16.fc20.i686
(gdb) bt
#0 0xb77d7424 in __kernel_vsyscall ()
#1 0x42e1a8e7 in raise () from /lib/libc.so.6
#2 0x42e1c123 in abort () from /lib/libc.so.6
#3 0x0804851b in exit_handler () at atexit.c:6
#4 0x42e1dd61 in __run_exit_handlers () from /lib/libc.so.6
#5 0x42e1ddbd in exit () from /lib/libc.so.6
#6 0x0804852d in startup () at atexit.c:12
#7 0x08048547 in main (argc=1, argv=0xbfc39fb4) at atexit.c:21

正如预期的那样,它显示 startup() 调用 exit。

您当然也可以交互式调试它,在 gdb 中启动您的程序并在 atexit 处理程序中设置断点。

关于c - 谁调用了 atexit()?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26256996/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com