初始思路

image.png

实现功能

1.找到源程序

1.加壳:脱壳
2.多进程:
使用进程遍历工具分析
调试,CreateProcessA/W下端分析

2.去掉程序中的广告

1.广告:
对话框
网页
2.去广告(API)
DialogBoxA/W 弹出窗口
CreateWindowExA/W 创建窗口API
WinExec 启动可执行文件、打开一个网址
CreateProcelssA/W 创建进程
ShellExecuteA/W 创建进程

3.写一个连连看的外挂

1.功能:意见秒杀

2.分析+算法+模拟点击:
找到连连看数组,使用算法完成自动连接
模拟点击对应位置,实现一键秒杀

3.利用游戏本身功能函数完成一键秒杀:
分析道具,使用指南针完成自动连接
找到消除CALL,实现一键秒杀

已知条件

vc 6.0 MFC程序

程序特点

1.多进程
2.由东条修改代码
3,。MFC界面程序

分析工具

1.Ollydbg
2.Cheat Engine
3.Visual Studio

需要使用的技术:

1.MFC DLL使用MFC DLL,方便之处在于不需要自己写DLLMain的case了,直接写在Initlnstance函数中即可,且调试时使用Cstring比较方便。
2.SetWindowLong修改窗口回调函数,在自己的窗口回调函数中处理快捷键响应。
3.CallWindowProc,调用指定窗口回调函数
4.多线程

边分析边测试

在搭建完框架之后,就是边分析边测试,流程如下:
1.先去广告2.分析数据
3.搭建框架、测试。
4.分析道具CALL、测试5.分析消除CALL,测试

分析

CreateProcess

image.png

WriteProcessMemory

ResumeThread

提取源程序

方法一:从内存dump下exe

http://www.kanhaige.com/post-67.html
方法二:
image.png

栈回溯rand

跳转到随机数并且下断点,点击“练习”
image.png
调用堆栈窗口找到调用这个函数的地址
image.png
image.png

随机过程分析.pptx

代码

创建MFC的静态共享库

  1. //stdafx.h
  2. //增加三个消息的宏定义
  3. #define WM_DATA1 WM_USER+1
  4. #define WM_DATA2 WM_USER+2
  5. #define WM_DATA3 WM_USER+3
  1. // MFCLLK.cpp: 定义 DLL 的初始化例程。
  2. //
  3. #include "stdafx.h"
  4. #include "MFCLLK.h"
  5. #include "CMyDlg.h"
  6. #ifdef _DEBUG
  7. #define new DEBUG_NEW
  8. #endif
  9. //
  10. //TODO: 如果此 DLL 相对于 MFC DLL 是动态链接的,
  11. // 则从此 DLL 导出的任何调入
  12. // MFC 的函数必须将 AFX_MANAGE_STATE 宏添加到
  13. // 该函数的最前面。
  14. //
  15. // 例如:
  16. //
  17. // extern "C" BOOL PASCAL EXPORT ExportedFunction()
  18. // {
  19. // AFX_MANAGE_STATE(AfxGetStaticModuleState());
  20. // // 此处为普通函数体
  21. // }
  22. //
  23. // 此宏先于任何 MFC 调用
  24. // 出现在每个函数中十分重要。 这意味着
  25. // 它必须作为以下项中的第一个语句:
  26. // 出现,甚至先于所有对象变量声明,
  27. // 这是因为它们的构造函数可能生成 MFC
  28. // DLL 调用。
  29. //
  30. // 有关其他详细信息,
  31. // 请参阅 MFC 技术说明 33 和 58。
  32. //
  33. // CMFCLLKApp
  34. BEGIN_MESSAGE_MAP(CMFCLLKApp, CWinApp)
  35. END_MESSAGE_MAP()
  36. // CMFCLLKApp 构造
  37. CMFCLLKApp::CMFCLLKApp()
  38. {
  39. // TODO: 在此处添加构造代码,
  40. // 将所有重要的初始化放置在 InitInstance 中
  41. }
  42. // 唯一的 CMFCLLKApp 对象
  43. CMFCLLKApp theApp;
  44. WNDPROC g_OldhProc;
  45. // CMFCLLKApp 初始化
  46. LRESULT CALLBACK WindowProc(
  47. _In_ HWND hWnd,
  48. _In_ UINT Msg,
  49. _In_ WPARAM wParam,
  50. _In_ LPARAM lParam)
  51. {
  52. if (Msg == WM_DATA1)
  53. {
  54. //调试技巧
  55. //_asm {
  56. // mov eax,eax
  57. // mov eax,eax
  58. //}
  59. _asm {
  60. mov ecx, 0x45DEBC
  61. mov ecx,[ecx]
  62. lea ecx,DWORD PTR DS:[ecx+0x494]
  63. push 0xF0
  64. push 0
  65. push 0
  66. mov eax,0x0041E691
  67. call eax
  68. }
  69. return DefWindowProc(hWnd, Msg, wParam, lParam);
  70. }
  71. else if (Msg==WM_DATA2)
  72. {
  73. //1.获取可以连接的两个点
  74. POINT pt1 = { 0 };
  75. POINT pt2 = { 0 };
  76. //调试技巧
  77. //_asm {
  78. // mov eax,eax
  79. // mov eax,eax
  80. //}
  81. _asm {
  82. mov ecx, 0x45DEBC
  83. mov ecx, [ecx]
  84. lea ecx, DWORD PTR DS : [ecx + 0x494]
  85. mov ecx, DWORD PTR DS : [ecx + 0x19F0]
  86. lea eax, pt1.x
  87. push eax
  88. lea eax, pt2.x
  89. push eax
  90. mov eax ,0x0042923F
  91. call eax
  92. }
  93. CString strCode;
  94. strCode.Format(L"点1 x=%d,y=%d,点2 x=%d,y=%d", pt1.x, pt1.y, pt2.x, pt2.y);
  95. OutputDebugString(strCode);
  96. if (pt1.x==0&&pt1.x==pt1.y)
  97. {
  98. return DefWindowProc(hWnd, Msg, wParam, lParam);
  99. }
  100. //2.调用消除call
  101. _asm {
  102. //传递ecx
  103. mov ecx, 0x45DEBC
  104. mov ecx, [ecx]
  105. //第一个参数,固定值
  106. push 0x4
  107. //第二个参数:坐标点数组
  108. lea eax, DWORD PTR DS : [ecx + 0x494]
  109. mov eax, DWORD PTR DS : [eax + 0x19F0]
  110. add eax,0x40
  111. push eax
  112. //第三个参数 坐标点1
  113. lea eax, pt1.x
  114. push eax
  115. //第四个参数 坐标点2
  116. lea eax, pt2.x
  117. push eax
  118. //第五个参数
  119. lea eax, DWORD PTR DS : [ecx + 0x494]
  120. mov eax, DWORD PTR DS : [eax + 0x19F0]
  121. mov eax, DWORD PTR DS : [eax + 0x4]
  122. push eax
  123. //第六个参数
  124. push 0
  125. mov eax,0x0041C68E
  126. call eax
  127. }
  128. return DefWindowProc(hWnd, Msg, wParam, lParam);
  129. }
  130. return CallWindowProc(g_OldhProc, hWnd, Msg, wParam, lParam);
  131. }
  132. unsigned _stdcall ThreadProc()
  133. {
  134. //模态对话框
  135. CMyDlg pDlg;
  136. pDlg.DoModal();
  137. return 0;
  138. }
  139. BOOL CMFCLLKApp::InitInstance()
  140. {
  141. CWinApp::InitInstance();
  142. //1.通过查找窗口,获取窗口句柄
  143. m_Wnd = ::FindWindow(NULL, L"QQ连连看");
  144. if (NULL == m_Wnd)
  145. {
  146. OutputDebugString(L"无法找到 QQ连连看窗口");
  147. return false;
  148. }
  149. //2.设置窗口回调函数
  150. g_OldhProc = (WNDPROC)SetWindowLong(m_Wnd, GWL_WNDPROC, (LONG)WindowProc);//设置窗口句柄(窗口句柄,索引值,)
  151. if (NULL == g_OldhProc)
  152. {
  153. OutputDebugString(L"设置窗口回调函数 失败");
  154. return false;
  155. }
  156. //3/弹出对话框
  157. _beginthreadex(0, 0, _beginthreadex_proc_type(ThreadProc), 0, 0, 0);
  158. return TRUE;
  159. }

创建CMyDlg的窗口类
image.png

  1. //CMyDlg.cpp
  2. //添加的三个按钮
  3. #include "stdafx.h"
  4. #include "MFCLLK.h"
  5. #include "CMyDlg.h"
  6. #include "afxdialogex.h"
  7. void CMyDlg::OnBnClickedButton1()
  8. {
  9. // TODO: 在此添加控件通知处理程序代码
  10. //响应指南针
  11. CMFCLLKApp* pApp = (CMFCLLKApp*)AfxGetApp();//返回的是the APP对象的指针
  12. pApp->m_Wnd;//获取窗口的句柄
  13. ::SendMessage(pApp->m_Wnd, WM_DATA1, 0, 0);
  14. }
  15. void CMyDlg::OnBnClickedButton2()
  16. {
  17. // TODO: 在此添加控件通知处理程序代码
  18. CMFCLLKApp* pApp = (CMFCLLKApp*)AfxGetApp();//返回的是the APP对象的指针
  19. pApp->m_Wnd;//获取窗口的句柄
  20. ::SendMessage(pApp->m_Wnd, WM_DATA2, 0, 0);
  21. }
  22. void CMyDlg::OnBnClickedButton3()
  23. {
  24. // TODO: 在此添加控件通知处理程序代码
  25. //循环消除
  26. CMFCLLKApp* pApp = (CMFCLLKApp*)AfxGetApp();//返回的是the APP对象的指针
  27. for (int i=0;i<100;i++)
  28. {
  29. int Ret = ::SendMessage(pApp->m_Wnd, WM_DATA2, 0, 0);
  30. if (Ret==-1)
  31. {
  32. break;
  33. }
  34. }
  35. }