还是Thunk的问题,实现我已经实现,不过还有些细节没弄明白。
首先,资源共享一下。
在atlbase.h中有个CStdCallThunk类。可以用做通用的thunk实现,而且支持大部分的CPU。
好了,说问题。
CStdCallThunk是将第一个参数替换成对象指针pThis。
在这里,
pthunk->m_mov = 0x0424444c7;
pthunk->m_this = (DWORD) pThis;
代表着
mov dword ptr [esp+0x4], pThis
我试过,无论函数参数有多少,总是正确的。也就是说第一个参数总是在esp+0x4上。
msdn上说stdcall调用方式是参数从右往左压栈,也就是说第一个参数是最后一个压栈的。那么它的位置应该是不定的,与参数们的类型和多少有关。
为什么它总在esp+0x4呢。
还有第二参数会在哪个位置呢?第三个呢?(esp增吗)
嗯,下面是那个类的使用代码:
#include <iostream>
#include <stdlib.h>
#include <windows.h>
#include <atlbase.h>
#include "Main.h"
using namespace ATL;
using namespace std;
class MyClass
{
public:
void out()
{
printf ("%d\n", m_ncount);
}
static void staticout(MyClass * pThis)
{
pThis->out();
}
int m_ncount;
};
typedef void(*MyCallBack)();
main()
{
MyClass myObject;
myObject.m_ncount = 12;
MyCallBack Caller = NULL;
CStdCallThunk thunk;
thunk.Init((DWORD_PTR) myObject.staticout, &myObject);
Caller =(MyCallBack) thunk.GetCodeAddress();
Caller();
}