Wndbase.cpp
上传用户:hyb6888
上传日期:2016-01-24
资源大小:5186k
文件大小:3k
- #include "stdafx.h"
- #include "stdio.h"
- #include "Wndbase.h"
- #include "windows.h"
- #include "math.h"
- //一个类实例只能有一个窗口
- //如果一个实例调用了多次,只有第一次调用时会建立窗口,后面的只显示窗口
- WNDPROC Wndbase::CreateThunk()
- {
- Thunk* thunk = new Thunk;
-
- ///////////////////////////////////////////////
- //系统调用m_thunk时的堆栈:
- //ret HWND MSG WPARAM LPARAM
- //-------------------------------------------
- //栈顶 栈底
- ///////////////////////////////////////////////
- //call Offset
- //调用code[0],call执行时会把下一条指令压栈,即把Proc压栈
- thunk->Call = 0xE8; // call [rel]32
- thunk->Offset = (size_t)&(((Thunk*)0)->Code)-(size_t)&(((Thunk*)0)->Proc); // 偏移量,跳过Proc到Code[0]
- thunk->Proc = Wndbase::stdProc; //静态窗口过程
- //pop ecx,Proc已压栈,弹出Proc到ecx
- thunk->Code[0] = 0x59; //pop ecx
-
- //mov dword ptr [esp+0x4],this
- //Proc已弹出,栈顶是返回地址,紧接着就是HWND了。
- //[esp+0x4]就是HWND
- thunk->Code[1] = 0xC7; // mov
- thunk->Code[2] = 0x44; // dword ptr
- thunk->Code[3] = 0x24; // disp8[esp]
- thunk->Code[4] = 0x04; // +4
- thunk->Window = this;
-
- //偷梁换柱成功!跳转到Proc
- //jmp [ecx]
- thunk->Jmp = 0xFF; // jmp [r/m]32
- thunk->ECX = 0x21; // [ecx]
-
- m_thunk = (WNDPROC)thunk;
- return m_thunk;
- }
- LRESULT WINAPI Wndbase::endProc(HWND hWnd,UINT uMsg,UINT wParam,LONG lParam)
- {
- //MessageBox(0,"WM_DESTROY",0,0);
- return 0;
- }
- LRESULT WINAPI Wndbase::stdProc(HWND hWnd,UINT uMsg,UINT wParam,LONG lParam)
- {
- Wndbase* w = (Wndbase*)hWnd;
-
- return w->WindowProc(uMsg,wParam,lParam);
- }
- //①得到This指针,可以直接使用内部的变量,
- //②或者是直接调用窗口处理函数。
- //③或者使用thunk技术。
- //注:在static函中,所有实例都使用同一个函数的,及静态数据。
- //由于static为公共代码,无法为每个实例保存一个THIS指针。
- //最好还是使用thunk技术
- LRESULT WINAPI Wndbase::InitProc(HWND hWnd,UINT uMsg,UINT wParam,LONG lParam)
- {
- if(uMsg == WM_NCCREATE)
- {
- Wndbase *w = NULL;
- w = (Wndbase*)((LPCREATESTRUCT)lParam)->lpCreateParams;
- if(w)
- {
- //记录hWnd
- w->m_hWnd = hWnd;
-
- //改变窗口过程为m_thunk
- w->Oldproc=*(WNDPROC)SetWindowLong(hWnd,GWL_WNDPROC,(LONG)w->CreateThunk());
- return (*(WNDPROC)(w->GetThunk()))(hWnd,uMsg,wParam,lParam);
- }
- }
- return DefWindowProc(hWnd,uMsg,wParam,lParam);
- }
- LRESULT WINAPI Wndbase::WindowProc(UINT uMsg,UINT wParam,LONG lParam)
- {
- switch (uMsg)
- {
- case WM_CREATE:
- break;
- default:
- return DefWindowProc(m_hWnd,uMsg,wParam,lParam);
- break;
- }
- return 0;
- }
- ///////////////////////////////////////////////////////////
- //