You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
BEGIN_MESSAGE_MAP(CreverseApp, CWinApp)
ON_COMMAND(ID_HELP, &CWinApp::OnHelp)
END_MESSAGE_MAP()
// CreverseApp construction
CreverseApp::CreverseApp()
{
// support Restart Manager
m_dwRestartManagerSupportFlags = AFX_RESTART_MANAGER_SUPPORT_RESTART;
// TODO: add construction code here,// Place all significant initialization in InitInstance
}
// The one and only CreverseApp object
CreverseApp theApp;
structAFX_MSGMAP
{
const AFX_MSGMAP* (PASCAL* pfnGetBaseMap)(); // 基类消息映射入口地址 const AFX_MSGMAP_ENTRY* lpEntries; // 当前类消息映射入口地址
};
structAFX_MSGMAP_ENTRY
{
UINT nMessage; // windows message
UINT nCode; // control code or WM_NOTIFY code
UINT nID; // control ID (or 0 for windows messages)
UINT nLastID; // used for entries specifying a range of control id's
UINT_PTR nSig; // signature type (action) or pointer to message #
AFX_PMSG pfn; // routine to call (or special value)
};
writeup大纲
GetMessageMap处理函数寻找
通过MessageBox寻找
通过od2 设置
MessageBox
断点,断下来后,我们来看调用栈(这里比较了od1,od2,x32dbg,最终还是od2显示的效果最好!)之后跟进每一个函数查看函数大致功能,因为真正的处理函数距离
MessageBox
不会太远函数
40B1A2
可以看到该函数中
MessageBox
所有的参数都已经确定了,再往前翻函数
40B71C
可以发现
失败
这一状态,在这个函数前已经确认了,再往前翻:函数
4071FD
可以发现,真正的确认状态的函数就是
4071FD
,成功找到MessageMap处理函数通过od1 字符串智能搜索
直接搜到处理函数
通过查找GetMessageMap函数
介绍该方法时,首先要了解两方面的知识:
c++ 虚函数表相关知识
c++普遍使用类,虚拟类派生的类都会维护一个虚函数表
vtable
,并且编译器在编译时会将虚函数表插入到生成的二进制文件中,而且一般存在rodata
区块中。该类的每一个实例(对象)会维护一个vptr
,即指向虚函数表的指针。大概的空间布局是这样的MFC消息处理机制
首先,我们先对MFC的消息映射做一个简单介绍。MFC为了实现消息映射在响应消息的类内部自动做了如下两方面的处理:
a、消息映射声明和实现
在类的定义(头文件)里,添加声明消息映射的宏DECLARE_MESSAGE_MAP,在类的实现(源文件)里,通过BEGIN_MESSAGE_MAP和END_MESSAGE_MAP()实现消息映射。
b、消息响应函数的声明和实现
当通过ClassWizard添加消息响应函数时就会自动添加函数的声明和实现,代码如下:
声明:
映射:
实现:
简单点说就是
MFC
的类在声明时会调用DECLARE_MESSAGE_MAP()
声明消息映射,在生成对象后会映射AFX_MSG_MAP
。MFC
源码大概是这样的MFC
就是靠这样的机制来处理程序的整个消息的,现在需要理清的就是消息和消息处理函数的映射,其中涉及到主要的两个结构体:其中
AFX_MSGMAP
由GetMessageMap
函数获取,其最后一个成员直接指向映射关系数组。GetMessagemap
函数是个虚函数,每个实现的类的虚函数表都有该函数,我们需要找到对应的窗口类或是对话框类的GetMessageMap
函数。而最终的目标就是找到这个映射关系数组,好方便找到对应的消息处理函数ida中实践寻找映射关系
首先找到
MFC
开始函数,大概是这样的再来看看
AfxWinMain
的源代码不同版本的
MFC
可能会有所区别,但是整体的结构基本不会变,再来对比一下第五题的反汇编代码这里的
InitInstance
很重要,其中有CXXDialog
的指针,顺着这个指针,我们能够找到第五题中涉及到的窗口处理类的虚函数表可以先大概看一下
InitInstance
在MFC
中的源码int 2d处理函数寻找
参考
逆向C++虚函数(一)
逆向C++虚函数(二)
MFC 消息映射机制详解
The text was updated successfully, but these errors were encountered: