【发布时间】:2014-10-10 11:49:51
【问题描述】:
为什么这段代码调用了错误的虚函数?它调用偏移量 8 处的那个,而它应该调用偏移量 4 处的那个。如果我在 8 处重命名函数,它会正确调用 4 处的那个。代码生成错误?我错过了什么愚蠢的东西?
来源:
class surface_c
{
public:
virtual ~surface_c() = 0; // 0
virtual bool blit(int) = 0; // 4
virtual bool blit() = 0; // 8
};
int main()
{
surface_c* surface;
surface->blit(0);
return 0;
}
反汇编:
int main()
{
00A11250 push ebp
00A11251 mov ebp,esp
00A11253 sub esp,44h
00A11256 push ebx
00A11257 push esi
00A11258 push edi
surface_c* surface;
surface->blit(0);
00A11259 push 0
00A1125B mov eax,dword ptr [surface]
00A1125E mov edx,dword ptr [eax]
00A11260 mov ecx,dword ptr [surface]
00A11263 mov eax,dword ptr [edx+8]
00A11266 call eax
return 0;
00A11268 xor eax,eax
}
00A1126A pop edi
00A1126B pop esi
00A1126C pop ebx
00A1126D mov esp,ebp
00A1126F pop ebp
00A11270 ret
【问题讨论】:
-
你怎么知道
bool blit(int)的位置?我不认为 C++ 标准对 vtable 布局有任何说明。 -
顺便说一句,vtable 的开头可以包含其他东西,而不是虚拟方法。
-
这意味着
blit(int)位于偏移量 8,而不是您认为的 4。 -
@Tobias 对了,VC2013如何对vtable中的函数进行排序?我知道它是定义的实现。通常我不在乎,但这是一个逆向工程项目(游戏 Red Alert 2 的),我需要匹配原始的 vtable 布局。
-
那么也许你应该编辑你的问题(或开始一个新问题)来询问VC的vtable布局。
标签: c++ visual-studio-2013 virtual