我正在为一个程序进行逆向工程。我正在使用IDA Pro和Hex-Rays Decompiler。我遇到了大量的代码,我知道有一个对象,并且对象上有一个方法调用,但它以一种我无法弄清楚的方式显示出来。例如:
if ( (*(*interfacePtr + 24))(interfacePtr, &v23) >= 0 )
我在这里知道interfacePtr指向ICLRRuntimeHost对象。 (C ++,.NET CLR运行时)但是......我不知道*(* interfacePtr + 24)是什么。我可以告诉它这是一种方法,但我如何弄清楚什么是+24?
答案 0 :(得分:2)
类的vtable只是函数指针的列表。它包含每个虚函数的一个指针,顺序为:非常非常顶级的基类,下一个基类,它的子类,。 。 。大多数派生类。
示例:
struct A {
virtual ~A() {}
virtual void foo() = 0;
}
struct B : public A {
virtual void foo() { // do something }
virtual void bar() { // do something else }
}
B的vtable将按以下顺序包含:
(A的那些必须先到,所以相同的vtable可以被具有类型A的指针的代码部分用于该对象;该代码不知道底层对象是否真的是B 。)
如果您正在查看32位源,指针是4个字节,那么24 = 4 * 6,您正在查看第7个虚函数(索引从0开始)。如果你是64位,指针是8个字节,所以24 = 8 * 3,你正在寻找第4个。实际上,我没有使用IDA“转换为C ++”功能,所以24可能实际上是表中的第24个条目。
简单的确认方法:编写自己的程序。声明ICLRRuntimeHost类型的变量。调用你怀疑的函数(基于查看头文件并计数到7或4,取决于位数,或24,如果我误解了你的例子)。查看生成的汇编代码,并确认您的索引是否正确。 (在这种事情上我总是一个人,所以这将提供一个检查。)
答案 1 :(得分:0)
查看ICLRRuntimeHostVtbl
ICLRRuntimeHostVtbl
和mscoree.h
的定义
粗略地翻译成hexrays会理解的东西,它们看起来像这样:
struct ICLRRuntimeHost {
ICLRRuntimeHostVtbl *vtbl;
};
struct ICLRRuntimeHostVtbl {
_DWORD (*QueryInterface)(ICLRRuntimeHost*, _DWORD*, void**);
_DWORD (*AddRef)(ICLRRuntimeHost*);
_DWORD (*Release)(ICLRRuntimeHost*);
_DWORD (*Start)(ICLRRuntimeHost*);
_DWORD (*Stop)(ICLRRuntimeHost*);
_DWORD (*SetHostControl)(ICLRRuntimeHost*, void*);
_DWORD (*GetCLRControl)(ICLRRuntimeHost*, void**);
};
您的变量interfacePtr应该具有类型:ICLRRuntimeHost,那么您的代码应该像这样反编译:
interfacePtr->GetCLRControl(&v23);