不久前, 我们玩过valgrind定位程序的各类内存问题, 当时非常希望valgrind能对一个已经存在的进程进行attach在线调试, 后来看了valgrind的原理, 发现这样不可行。 只能让valgrind重新拉取新进程进行调试。
在前面的文章中, 也介绍了kill -6和abort函数, 让程序core dump来获取当时栈的值, 其实, 这样似乎没有必要。 慢慢来看。
我们再回忆下strace命令, 可以用strace -p pid, 附着到一个已经在跑的进程上, 实时观察进程。 那么, gdb能做到吗? 能! 这就是gdb的attch调试, 可以获取当前栈的所有变量值。
回忆一下, 比如编译(加-g)后生成了a.out文件:
1. 可以直接用gdb a.out来调试, 其实gdb拉取了新的进程。 类似于valgrind.
2. 如果有core文件, 那么用gdb a.out core, 此时没有拉取新的进程。 在实际开发中, 这种方式常用。
很多时候, 在服务端, 进程已经跑起来, 此时不再适合用gdb来拉取新的进程, 而期望用gdb附着到这个已经存在的进程, 如下两种方式是等价的:
3. gdb attach pid (注意, 没有拉取新的进程)
4. gdb a.out pid (注意, 没有拉取新的进程)
看程序:
#include <iostream>#include <cmath>using namespace std;struct Point{ int x; int y;};int main() { Point po; po.x = 1; po.y = 2; float distance = sqrt(po.x * po.x + po.y * po.y); getchar(); return 0;}
看看利用方法3,4来调试(进程运行在一个窗口, 调试在另外一个窗口):
xxxxxx $ ps -aux | grep a.outWarning: bad ps syntax, perhaps a bogus '-'? See http://procps.sf.net/faq.html1000 3265 0.0 0.0 2804 876 pts/1 S+ 08:18 0:00 ./a.out1000 20400 0.0 0.0 3072 804 pts/0 S+ 21:02 0:00 grep a.outxxxxxx $ xxxxxx $ xxxxxx $ xxxxxx $ gdb attach 3265GNU gdb 6.6Copyright (C) 2006 Free Software Foundation, Inc.GDB is free software, covered by the GNU General Public License, and you arewelcome to change it and/or distribute copies of it under certain conditions.Type "show copying" to see the conditions.There is absolutely no warranty for GDB. Type "show warranty" for details.This GDB was configured as "i586-suse-linux"...attach: No such file or directory.Attaching to process 3265Reading symbols from /data/home/xxxxxx/a.out...done.Using host libthread_db library "/lib/libthread_db.so.1".Reading symbols from /lib/libonion.so...done.Loaded symbols for /lib/libonion.soReading symbols from /usr/lib/libstdc++.so.6...done.Loaded symbols for /usr/lib/libstdc++.so.6Reading symbols from /lib/libm.so.6...done.Loaded symbols for /lib/libm.so.6Reading symbols from /lib/libgcc_s.so.1...done.Loaded symbols for /lib/libgcc_s.so.1Reading symbols from /lib/libc.so.6...done.Loaded symbols for /lib/libc.so.6Reading symbols from /lib/libdl.so.2...done.Loaded symbols for /lib/libdl.so.2Reading symbols from /lib/libpthread.so.0...done.[Thread debugging using libthread_db enabled][New Thread -1211562320 (LWP 3265)]Loaded symbols for /lib/libpthread.so.0Reading symbols from /lib/ld-linux.so.2...done.Loaded symbols for /lib/ld-linux.so.20xb7d5eb0e in __read_nocancel () from /lib/libc.so.6(gdb) bt#0 0xb7d5eb0e in __read_nocancel () from /lib/libc.so.6#1 0xb7d0e0d8 in _IO_file_read_internal () from /lib/libc.so.6#2 0xb7d0f35b in _IO_new_file_underflow () from /lib/libc.so.6#3 0xb7d0fa9b in _IO_default_uflow_internal () from /lib/libc.so.6#4 0xb7d10ddd in __uflow () from /lib/libc.so.6#5 0xb7d0aebe in getchar () from /lib/libc.so.6#6 0x0804867c in main () at test.cpp:18(gdb) f 6#6 0x0804867c in main () at test.cpp:1818 getchar();(gdb) i localspo = {x = 1, y = 2}distance = 2.23606801(gdb) qThe program is running. Quit anyway (and detach it)? (y or n) yDetaching from program: /data/home/xxxxxx/a.out, process 3265xxxxxx $ xxxxxx $ xxxxxx $ xxxxxx $ xxxxxx $ xxxxxx $ xxxxxx $ gdb a.out 3265GNU gdb 6.6Copyright (C) 2006 Free Software Foundation, Inc.GDB is free software, covered by the GNU General Public License, and you arewelcome to change it and/or distribute copies of it under certain conditions.Type "show copying" to see the conditions.There is absolutely no warranty for GDB. Type "show warranty" for details.This GDB was configured as "i586-suse-linux"...Using host libthread_db library "/lib/libthread_db.so.1".Attaching to program: /data/home/xxxxxx/a.out, process 3265Reading symbols from /lib/libonion.so...done.Loaded symbols for /lib/libonion.soReading symbols from /usr/lib/libstdc++.so.6...done.Loaded symbols for /usr/lib/libstdc++.so.6Reading symbols from /lib/libm.so.6...done.Loaded symbols for /lib/libm.so.6Reading symbols from /lib/libgcc_s.so.1...done.Loaded symbols for /lib/libgcc_s.so.1Reading symbols from /lib/libc.so.6...done.Loaded symbols for /lib/libc.so.6Reading symbols from /lib/libdl.so.2...done.Loaded symbols for /lib/libdl.so.2Reading symbols from /lib/libpthread.so.0...done.[Thread debugging using libthread_db enabled][New Thread -1211562320 (LWP 3265)]Loaded symbols for /lib/libpthread.so.0Reading symbols from /lib/ld-linux.so.2...done.Loaded symbols for /lib/ld-linux.so.20xb7d5eb0e in __read_nocancel () from /lib/libc.so.6(gdb) bt#0 0xb7d5eb0e in __read_nocancel () from /lib/libc.so.6#1 0xb7d0e0d8 in _IO_file_read_internal () from /lib/libc.so.6#2 0xb7d0f35b in _IO_new_file_underflow () from /lib/libc.so.6#3 0xb7d0fa9b in _IO_default_uflow_internal () from /lib/libc.so.6#4 0xb7d10ddd in __uflow () from /lib/libc.so.6#5 0xb7d0aebe in getchar () from /lib/libc.so.6#6 0x0804867c in main () at test.cpp:18(gdb) f 6#6 0x0804867c in main () at test.cpp:1818 getchar();(gdb) i localspo = {x = 1, y = 2}distance = 2.23606801(gdb)
好, 介绍完毕。 简单。
再分享一下我老师大神的人工智能教程吧。零基础!通俗易懂!风趣幽默!还带黄段子!希望你也加入到我们人工智能的队伍中来!https://blog.youkuaiyun.com/jiangjunshow