【发布时间】:2010-04-09 02:14:44
【问题描述】:
我正在尝试在 gdb 中调试一些基于 STL 的 C++ 代码。 代码有类似
int myfunc()
{
std::map<int,int> m;
...
}
现在在 gdb 中,在 myfunc 中使用“print m”给出了一些非常难看的东西。 我所看到的推荐是编译类似
void printmap( std::map<int,int> m )
{
for( std::map<int,int>::iterator it = ... )
{
printf("%d : %d", it->first, it->second );
}
}
然后在gdb中做
(gdb) call printmap( m )
这似乎是处理问题的好方法...但是我可以将 printmap 放入一个单独的目标文件(甚至是动态库)中,然后在运行时将其加载到 gdb 中,而不是将其编译到我的二进制文件中 - 作为重新编译每次我想查看另一个 STL 变量时,二进制文件并不好玩.. 而为打印例程编译和加载单个 .o 文件可能是可以接受的。
更新:
在 Nikolais 的建议下,我正在查看 dlopen/dlsym。
所以我还没有完成这项工作,但感觉离我越来越近了。
在 printit.cpp 中
#include <stdio.h>
extern "C" void printit()
{
printf("OMG Fuzzies");
}
使用
编译成 .sog++ -Wall -g -fPIC -c printit.cpp
g++ -shared -Wl,-undefined,dynamic_lookup -o printit.so printit.o
启动我的测试应用程序并使用 dlopen ( 2 = RTLD_NOW ) 加载 .so,然后尝试使用 dlsym 获取调试功能的符号。
(gdb) break main
(gdb) run
(gdb) print (void*) dlopen("printit.so", 2 )
$1 = (void *) 0x100270
(gdb) print (void*) dlsym( 0x100270, "_printit" )
$2 = (void *) 0x0
如此接近,但由于某种原因我无法得到那个符号......(如果我把 dlopen/dlsym 在我的可执行文件中调用)我猜我要么编译了错误的库,要么错误地使用了 dlsym。
如果我能得到符号,我假设我可以使用类似的方法调用函数
(gdb) print (( void(*)() )(0x....))()
我正在 OS X 10.4 上编译它,这可能会导致我的一些 .so 问题...任何指针将不胜感激。
了解如何让所有这些工作。已在下面发布为解决方案。
【问题讨论】: