>给定一个挂起的线程在Delphi编译的32或64位Windows程序中,走堆栈(doable)
>给定堆栈条目,枚举每个方法中的局部变量及其值。也就是说,至少找到它们的地址和类型(integer32 / 64 / signed / unsigned,string,float,record,class …),它们的组合可以用来找到它们的值。
第一个是罚款,这是这个问题的第二个。在高级别,你如何在Delphi中枚举局部变量给一个堆栈条目?
在低水平,这是我一直在调查:
RTTI:不列出这种方法的信息。这不是我实际上认为是一个现实的选择,但在这里无论如何。
调试信息:加载为调试版本生成的调试信息。
>地图文件:即使是详细的地图文件(一个文本格式的文件!打开一个看看)不包含本地变量信息。它基本上是一个地址和源文件行号的列表。伟大的地址文件和线相关,例如。在沟槽中的蓝点;不是很好的更详细的信息
>远程调试信息(RSM文件) – no known information其内容或格式。
> TD32 / TDS文件:我当前的研究行。它们在许多其他信息中包含全局和局部符号。
我遇到的问题是:
>没有TD32文件格式的文档(我可以找到。)
>我的大部分知识他们来自使用它们的Jedi JCL代码(JclTD32.pas),我不知道如何使用该代码,或者是否有足够的结构来显示局部变量。我确信它会处理全局符号,但我对本地很不确定。有各种各样的常量定义和没有文件格式,读他们的意思,我剩下猜测。但是,这些常量及其名称必须来自某处。
> Source I can find using TDS info不加载或处理本地符号。
如果这是正确的方法,那么这个问题变成“有TDS / TD32文件格式的文档,是否有加载局部变量的代码示例?
代码示例不是必需的,但可能非常有用,即使它非常小。
解决方法
也可能是使用GDB(在Windows上的一个端口
它)。这将是巨大的,如果你发现一个.dbg或.dSYM
文件。它们包含源代码,例如。
gdb> list foo 56 void foo() 57 { 58 bar(); 59 sighandler_t fnc = signal(SIGHUP,SIG_IGN); 60 raise(SIGHUP); 61 signal(SIGHUP,fnc); 62 baz(fnc); 63 }
如果你没有任何调试文件,你可以尝试获取MinGW或Cygwin,并使用nm(1)(man page)。它将从二进制读取符号名称。它们可能包含一些类型,如C:
int abc::def::Ghi::jkl(const std::string,int,const void*)
不要忘记添加–demangle选项然后或你会得到像:
__ZN11MRasterFont21getRasterForCharacterEh
代替:
MRasterFont::getRasterForCharacter(unsigned char)