先来段简单的,亲测成功!!!

// test2.cpp : 定义控制台应用程序的入口点。
//#include "stdafx.h"
#include <Windows.h>
#include<iostream>
#include<stdlib.h>using namespace std;int _tmain(int argc, _TCHAR* argv[])
{TCHAR szDll[] = TEXT("d:\\zlib1.dll");  STARTUPINFO si = {0};  PROCESS_INFORMATION pi = {0};  si.cb = sizeof(si);  si.dwFlags = STARTF_USESHOWWINDOW;  si.wShowWindow = SW_SHOW;  TCHAR szCommandLine[MAX_PATH] = TEXT("D:\\软件目录\\dll查看器\\ViewApi.exe");  CreateProcess(NULL, szCommandLine, NULL, NULL, FALSE, CREATE_SUSPENDED, NULL, NULL, &si, &pi);  LPVOID Param = VirtualAllocEx(pi.hProcess, NULL, MAX_PATH, MEM_COMMIT, PAGE_EXECUTE_READWRITE);  WriteProcessMemory(pi.hProcess, Param, (LPVOID)szDll, _tcslen(szDll)*2+sizeof(TCHAR), NULL);  HANDLE hThread = CreateRemoteThread(pi.hProcess, NULL, NULL, (LPTHREAD_START_ROUTINE)LoadLibraryW,Param, CREATE_SUSPENDED, NULL);  ResumeThread(pi.hThread);  if (hThread)  {  ResumeThread(hThread);  WaitForSingleObject(hThread, INFINITE);  }  return 0;
}

==============================================================================================

一、DLL注入技术的用途

DLL注入技术的用途是很广泛的,这主要体现在:

1、假如你要操纵的对象涉及的数据不在进程内;

2、你想对目标进程中的函数进行拦截(甚至API函数,嘿嘿,由此编写个拦截timeGettime的过程,变速齿轮不就出来了么?改天我试试),比如对它所属窗口进行子类化。

3、你想编写一些函数用于增强或增加目标进程功能,比如可以给目标进程的某个窗口插入个消息循环增加其响应能力。(Mfc Windows程序设计称之为消息泵)。

4、隐藏自己的程序,很多恶意程序都是这样做的,即使你将恶意程序的进程结束掉也毫无意义了,因为它自己已经插入到很多进程中去了,唯一有效的办法只有注销windows.。如果你是个爱搞破坏的人就更应该掌握该技术了,不但可以利用该技术实现隐藏自己的进程,还可以破坏某个目标进程。因为将破坏代码插入到目标进程进行破坏的话简直易如反掌。不信试试?:(

二、实现DLL注入的另一种方法

1、将DLL注入进程技术在实现Api函数的监视程序中不可缺少的一项工作。其中最常见的就是用SetWindowsHookEx函数实现了。不过,该方法的缺点是被监视的目标进程必须有窗口,这样,SetWindowsHookEx才能将DLL注入目标进程中。而且,目标程序已经运行了,那么,在窗口创建之前的Api函数就不能被Hook了。
2、另外一种方法用Debug方案,就可以实现在程序创建时监视所有的Api了,缺点是必须是目标进程的Debug源,在监视程序终了时,目标进程会无条件终了。最大的缺点就是无法调试注入的DLL。
3、还有其他多种方案也可以实现DLL的注入,在《Windows核心编程》一书中就介绍了8-9种,其中有一种采用CreateProcess的方法,实现起来比较复杂,但没有上面几种方法的局限性。且可以用其他工具(VC等)调试注入的DLL。下面进行介绍。
原理如下:
1). 用CreateProcess(CREATE_SUSPENDED)启动目标进程。
2). 找到目标进程的入口,用ImageHlp中的函数可以实现。
3). 将目标进程入口的代码保存起来。
4). 在目标进程的入口写入LoadLibrary(MyDll)实现Dll的注入。
5). 用ResumeThread运行目标进程。
6). 目标进程就运行了LoadLibrary(MyDll),实现DLL的注入。
7). 目标进程运行完LoadLibrary(MyDll)后,将原来的代码写回目标进程的入口。
8). 目标进程Jmp至原来的入口,继续运行程序。
从原理上可以看出,DLL的注入在目标进程的开始就运行了,而且不是用Debug的方案,这样,就没有上面方案的局限性了。该方案的关键在6,7,8三步,实现方法需要监视进程和DLL合作。下面,结合代码进行分析。
在监视进程中,创建FileMapping,用来保存目标进程的入口代码,同时保证DLL中可以访问。在第7步实现将原目标代码写回目标进程的入口。

[cpp] view plain copy
  1. // 监视程序和DLL共用的结构体
  2. #pragma pack (push ,1)  // 保证下面的结构体采用BYTE对齐(必须)
  3. typedef struct
  4. {
  5. BYTE int_PUSHAD;    // pushad 0x60
  6. BYTE int_PUSH;      // push &szDLL 0x68
  7. DWORD push_Value;   // &szDLL = "ApiSpy.dll"的path
  8. BYTE int_MOVEAX;    // move eax &LoadLibrary 0xB8
  9. DWORD eax_Value;    // &LoadLibrary
  10. WORD call_eax;      // call eax 0xD0FF(FF D0) (LoadLibrary("ApiSpy.dll");
  11. BYTE jmp_MOVEAX;    // move eax &ReplaceOldCode 0xB8
  12. DWORD jmp_Value;    // JMP的参数
  13. WORD jmp_eax;       // jmp eax 0xE0FF(FF E0) jmp ReplaceOldCode;
  14. char szDLL[MAX_PATH]; // "ApiSpy.dll"的FullPath
  15. }INJECT_LOADLIBRARY_CODE, *LPINJECT_CODE;
  16. #pragma pack (pop , 1)

上面结构体的代码为汇编代码,对应的汇编为:

[cpp] view plain copy
  1. pushad
  2. push szDll
  3. mov eax, &LoadLibraryA
  4. call eax                                // 实现调用LoadLibrary(szDll)的代码
  5. mov eax, oldentry
  6. jmp eax                                 // 实现在LoadLibrary运行完后, 跳至目标进程的入口继续运行
  7. // FileMaping的结构体
  8. typedef struct
  9. {
  10. LPBYTE lpEntryPoint;                // 目标进程的入口地址
  11. BYTE oldcode[sizeof(INJECT_CODE)];  // 目标进程的代码保存
  12. }SPY_MEM_SHARE, * LPSPY_MEM_SHARE;

准备工作:
第一步:用CreateProcess(CREATE_SUSPENDED)启动目标进程。

[cpp] view plain copy
  1. CreateProcessA(0, szRunFile, 0, 0, FALSE, CREATE_SUSPENDED
  2. 0, NULL, &stInfo,
  3. &m_proInfo) ;

用CreateProcess启动一个暂停的目标进程;
找到目标进程的入口点,函数如下
第二步:找到目标进程的入口,用ImageHlp中的函数可以实现。

[cpp] view plain copy
  1. pEntryPoint = GetExeEntryPoint(szRunFile);
  2. LPBYTE GetExeEntryPoint(char *filename)
  3. {
  4. PIMAGE_NT_HEADERS pNTHeader;
  5. DWORD pEntryPoint;
  6. PLOADED_IMAGE pImage;
  7. pImage = ImageLoad(filename, NULL);
  8. if(pImage == NULL)
  9. return NULL;
  10. pNTHeader = pImage->FileHeader;
  11. pEntryPoint = pNTHeader->OptionalHeader.AddressOfEntryPoint + pNTHeader->OptionalHeader.ImageBase;
  12. ImageUnload(pImage);
  13. return (LPBYTE)pEntryPoint;
  14. }

// 创建FileMapping

[cpp] view plain copy
  1. hMap = CreateFileMapping((HANDLE)0xFFFFFFFF, NULL,
  2. PAGE_READWRITE, 0, sizeof(SPY_MEM_SHARE), “MyDllMapView”);

// 保存目标进程的代码
第三步:将目标进程入口的代码保存起来。

[cpp] view plain copy
  1. LPSPY_MEM_SHARE lpMap = pMapViewOfFile(hMap, FILE_MAP_ALL_ACCESS,0, 0, 0);
  2. ReadProcessMemory(m_proInfo.hProcess, pEntryPoint,&lpMap->oldcode, sizeof(INJECT_CODE),&cBytesMoved);
  3. lpMap->lpEntryPoint = pEntryPoint;

// 第四步:在目标进程的入口写入LoadLibrary(MyDll)实现Dll的注入。
// 准备注入DLL的代码

[cpp] view plain copy
  1. INJECT_CODE newCode;
  2. // 写入MyDll―――用全路径
  3. lstrcpy(newCode.szDLL, szMyDll);
  4. // 准备硬代码(汇编代码)
  5. newCode.int_PUSHAD = 0x60;
  6. newCode.int_PUSH = 0x68;
  7. newCode.int_MOVEAX = 0xB8;
  8. newCode.call_eax = 0xD0FF;
  9. newCode.jmp_MOVEAX = 0xB8;
  10. newCode.jmp_eax = 0xE0FF;
  11. newCode.eax_Value = (DWORD)&LoadLibrary;
  12. newCode.push_Value=(pEntryPoint + offsetof(INJECT_CODE,szDLL));
  13. // 将硬代码写入目标进程的入口
  14. // 修改内存属性
  15. DWORD dwNewFlg, dwOldFlg;
  16. dwNewFlg = PAGE_READWRITE;
  17. VirtualProtectEx(m_proInfo.hProcess, (LPVOID)pEntryPoint, sizeof(DWORD), dwNewFlg, &dwOldFlg);
  18. WriteProcessMemory(m_proInfo.hProcess, pEntryPoint,&newCode, sizeof(newCode), NULL);//&dwWrited);
  19. VirtualProtectEx(proInfo.hProcess, (LPVOID)pEntryPoint, sizeof(DWORD), dwOldFlg, &dwNewFlg);
  20. // 释放FileMaping 注意,不是Closehandle(hMap)
  21. UnmapViewOfFile(lpMap);

// 继续目标进程的运行
第五步:用ResumeThread运行目标进程。

[cpp] view plain copy
  1. ResumeThread(m_proInfo.hThread);

在监视进程中就结束了自己的任务,剩下的第6,7,8步就需要在Dll的DllMain中进行配合。
DLL中用来保存数据的结构体

[cpp] view plain copy
  1. typedef struct
  2. {
  3. DWORD lpEntryPoint;
  4. DWORD OldAddr;
  5. DWORD OldCode[4];
  6. }JMP_CODE,* LPJMP_CODE;
  7. static JMP_CODE _lpCode;

// 在DllMain的DLL_PROCESS_ATTACH中调用InitApiSpy函数
// 在该函数中实现第6,7,8步
第六步:目标进程就运行了LoadLibrary(MyDll),实现DLL的注入。

[cpp] view plain copy
  1. int WINAPI DllMain(HINSTANCE hInst, DWORD dwReason, LPVOID lpReserved)
  2. {
  3. switch(dwReason)
  4. {
  5. case DLL_PROCESS_ATTACH:
  6. return InitApiSpy();
  7. ……

// InitApiSpy函数的实现

[cpp] view plain copy
  1. BOOL WINAPI InitApiSpy()
  2. {
  3. HANDLE hMap;
  4. LPSPY_MEM_SHARE lpMem;
  5. DWORD dwSize;
  6. BOOL rc;
  7. BYTE* lpByte;
  8. // 取得FileMapping的句柄
  9. hMap = OpenFileMapping(FILE_MAP_ALL_ACCESS, 0, “MyDllMapView”);
  10. if(hMap)
  11. {
  12. lpMem = (LPSPY_MEM_SHARE)MapViewOfFile(hMap,FILE_MAP_ALL_ACCESS,0, 0, 0);
  13. if(lpMem)
  14. {

第七步:目标进程运行完LoadLibrary(MyDll)后,将原来的代码写回目标进程的入口。

[cpp] view plain copy
  1. BOOL WINAPI InitApiSpy()
  2. {
  3. HANDLE hMap;
  4. LPSPY_MEM_SHARE lpMem;
  5. DWORD dwSize;
  6. BOOL rc;
  7. BYTE* lpByte;
  8. // 取得FileMapping的句柄
  9. hMap = OpenFileMapping(FILE_MAP_ALL_ACCESS, 0, “MyDllMapView”);
  10. if(hMap)
  11. {
  12. lpMem = (LPSPY_MEM_SHARE)MapViewOfFile(hMap,FILE_MAP_ALL_ACCESS,0, 0, 0);
  13. if(lpMem)
  14. {
  15. // 恢复目标进程的入口代码
  16. // 得到mov eax, value代码的地址
  17. _lpCode.OldAddr = (DWORD)((BYTE*)lpMem->lpEntryPoint + offsetof(INJECT_CODE, jmp_MOVEAX));
  18. _lpCode.lpEntryPoint = (DWORD)lpMem->lpEntryPoint;
  19. // 保存LoadLibrary()后面的代码
  20. memcpy(&_lpCode.OldCode, (BYTE*)lpMem->oldcode + offsetof(INJECT_CODE, jmp_MOVEAX), 2*sizeof(DWORD));
  21. // 恢复目标进程的入口代码
  22. rc = WriteProcessMemory(GetCurrentProcess(), lpMem->lpEntryPoint, lpMem->oldcode, sizeof(INJECT_CODE), &dwSize);
  23. lpByte = (BYTE*)lpMem->lpEntryPoint + offsetof(INJECT_CODE, jmp_MOVEAX);
  24. UnmapViewOfFile(lpMem);
  25. }
  26. CloseHandle(hMap);
  27. }
  28. // 实现自己Dll的其他功能,如导入表的替换
  29. // ……
  30. // 将LoadLibrary后面的代码写为转入处理程序中
  31. // 指令为:mov eax, objAddress
  32. // jmp eax
  33. {
  34. BYTE* lpMovEax;
  35. DWORD* lpMovEaxValu;
  36. WORD* lpJmp;
  37. DWORD fNew, fOld;
  38. fNew = PAGE_READWRITE;
  39. lpMovEax = lpByte;
  40. VirtualProtect(lpMovEax, 2*sizeof(DWORD), fNew, &fOld);
  41. *lpMovEax = 0xB8;
  42. lpMovEaxValu = (DWORD*)(lpMovEax + 1);
  43. *lpMovEaxValu = (DWORD)&DoJmpEntryPoint;
  44. lpJmp = (WORD*)(lpMovEax + 5);
  45. *lpJmp = 0xE0FF; // (FF E0)
  46. VirtualProtect(lpMovEax, 2*sizeof(DWORD), fOld, &fNew);
  47. }
  48. return TRUE;
  49. }
[cpp] view plain copy
  1. // 转入处理程序
  2. DWORD* lpMovEax;
  3. DWORD fNew, fOld;
  4. void __declspec(naked) DoJmpEntryPoint ()
  5. {
  6. // 恢复LoadLibrary后面的代码
  7. _gfNew = PAGE_READWRITE;
  8. _glpMovEax = (DWORD*)_lpCode.OldAddr;
  9. VirtualProtect(_glpMovEax, 2*sizeof(DWORD), _gfNew, &_gfOld);
  10. *_glpMovEax = _lpCode.OldCode[0];
  11. *(_glpMovEax + 1) = _lpCode.OldCode[1];
  12. VirtualProtect(_glpMovEax, 2*sizeof(DWORD), _gfOld, &_gfNew);
  13. //第八步:目标进程Jmp至原来的入口,继续运行程序。
  14. // 跳至目标代码的入口
  15. _asm popad
  16. _asm jmp _lpCode.lpEntryPoint
  17. }

第八步:目标进程Jmp至原来的入口,继续运行程序。

[cpp] view plain copy
  1. // 跳至目标代码的入口
  2. _asm popad
  3. _asm jmp _lpCode.lpEntryPoint
  4. }

这样就实现了原来的目标,将DLL的注入放在目标进程的入口运行,实现了目标进程运行之前运行我们的注入Dll的功能。

CreateProcess启动游戏注入DLL相关推荐

  1. c语言游戏注入dll能干什么,教大家写一个远程线程的DLL注入,其实还是蛮简单的……………………...

    该楼层疑似违规已被系统折叠 隐藏此楼查看此楼 然后新建一个win32 application 的工程 新建c++ source file 写入: #include #include int WINAP ...

  2. windows 启动exe程序前注入dll(c++)

    //需要的头文件: #include <iostream> #include <stdarg.h> #include <Windows.h> #include &l ...

  3. 后渗透篇:劫持技术(lpk.dll劫持游戏注入【Win7 实例】)

    当你的才华 还撑不起你的野心时 那你就应该静下心来学习 lpk.dll劫持游戏注入 由于 输入表中只包含DLL名而没有它的路径名,因此加载程序必须在磁盘上搜索 DLL文件.首先会尝试从当前程序所在的目 ...

  4. 无法启动游戏 计算机丢失,win7系统无法启动游戏提示缺少vcomp100.dll文件怎么办...

    许多游戏玩家喜欢在雨林木风win7系统电脑安装各种游戏软件,但是在运行过程中总会遇到一些问题.最近有位用户在win7系统下运行三国无双系列游戏,提示"无法启动此程序,因为计算机中丢失vcom ...

  5. 编程实现木马的ActiveX启动和注入IE的启动方式

    木马的启动方式有很多种,现在比较流行的就是注册为系统服务启动(只适合Windows 2000以上的系统),或者以驱动的方式启动.不过,最近以ActiveX方式启动又比较流行了,因为它适合Windows ...

  6. 驱动无模块注入dll

    文章目录 实现效果 三环无模块注入的方案 反射型dll注入方式的改进 零环无模块注入方案 petoshellcode 无模块注入流程 实现代码 Xenos注入方案研究 IT_MMap注入 IT_Thr ...

  7. visual studio 怎么生成coredump文件_玩游戏丢失dll文件别着急 认识这些就妥了

    点击上方电脑爱好者关注我们 装好游戏之后,一打开就跳出各种报错信息的情况小伙伴一定见过,其中缺少各种dll文件最常见.小伙伴们一定奇怪,用得好好的电脑,怎么会缺文件呢?为啥其他游戏/应用就没事呢?其实 ...

  8. dll中使用dialogbox_玩游戏丢失dll文件别着急 认识这些就妥了

    点击上方电脑爱好者关注我们 装好游戏之后,一打开就跳出各种报错信息的情况小伙伴一定见过,其中缺少各种dll文件最常见.小伙伴们一定奇怪,用得好好的电脑,怎么会缺文件呢?为啥其他游戏/应用就没事呢?其实 ...

  9. 易语言大漠实现辅助一键启动游戏

    我们要实现一键登录游戏, 首先要通过易语言启动您系统里的游戏,这里主要使用易语言的 运行()和 执行()命令,但直接使用是无法启动游戏的,所有我们可以采用创建进程,运行,执行,API封装等等. 易语言 ...

最新文章

  1. Python集合之set()使用方法详解
  2. 关于FluentNhibernate数据库连接配置,请教
  3. kafka mysql安装与配置_Mac环境canal+mysql+kafka的安装及使用
  4. SpringBoot+Mybatis加载Mapper.xml文件的两种方式
  5. [Leetcode][第112题][JAVA][路径总和][递归][队列]
  6. 带你认识Flink容错机制的两大方面:作业执行和守护进程
  7. c++ 游戏_C/C++编程笔记:C语言实现连连看游戏,项目源码分享
  8. 石头剪刀布代码android,微信小程序源码解说:石头剪刀布(附源码下载)
  9. 最简单的PHP MVC留言本实例(二)
  10. 在Java中通过线程池实现异步执行
  11. vce 题库导入_Visual CertExam(VCE)试题制作教程.pdf
  12. 智能安防及视频监控系统
  13. JUCE框架教程(3)—— Component ClassGraphics入门
  14. 一图搞懂梯度、散度、旋度、Jacobian、Hessian、Laplacian之间的关系
  15. 起底身份倒卖产业:那些被公开叫卖的人生
  16. 打造超级IP,你真悟错了道!
  17. 异常:java.lang.ArithmeticException
  18. 【互补松弛定理】12.7.16省队集训
  19. 视频特效剪辑小技巧,给每个视频添加反相特效
  20. Stata:面板数据,一般加上个体固定效应和时间固定效应

热门文章

  1. Maven软件的下载安装
  2. 缓存-分布式锁-Redisson-读写锁补充
  3. 类文件结构-访问标识和继承信息
  4. logback 的拆分 Appender
  5. 事务与分布式事务原理与实现
  6. 使用RabbitMQ实现松耦合设计
  7. htc u11 android o,HTC U11+和HTC U11有什么区别?对比完秒懂 (全文)
  8. 210122阶段三进程间信号
  9. DOM基本操作(二:对节点的操作)
  10. 文本右上角右下角添加文本