进程代码注入

参考教程:windows api编程

实现步骤如下:

(1)得到指向远程进程的句柄,可以使用OpenProcess函数实现。

(2)使用VirtualAllocEx函数在远程进程中为动态链接库名称分配内存。

(3)使用WriteProcessMemory函数把动态链接库的名称包括路径信息写入到分配的内存中。

(4)通过CreateRemoteThreadLoadLibrary函数映射动态链接库到远程进程。

(5)调用WaitForSingleObject函数等待远程线程终止,这时远程线程调用LoadLibrary返回。换句话说,线程只有在动态链接库的DllMain中的DLL_PROCESS_ATTACH处理结束时才返回。

(6)调用GetExitCodeThread获得远程线程的返回码,这个值实际上是LoadLibrary返回的值,也就是映射的动态链接库返回的加载基地址。

(7)使用VirtualFreeEx函数释放第2步分配的内存。

(8)利用第(6)步返回的模块句柄通过CreateRemoteThreadFreeLibrary函数卸载动态链接库。如果注入的动态链接库又在调用期间创建了新的线程,用户必须确保这些线程,在卸载前终止。

(9)调用WaitForSingleObject等待线程结束。

(10)关闭所有打开的句柄,包括第(4)和第(8)步中创建的线程句柄、远程进程句柄。

#include "stdafx.h"
#include "windows.h"
#pragma comment(lib,"kernel32.lib")

int _tmain(int argc, _TCHAR* argv[])
{
      HANDLE  hThread;
      wchar_t  szLibPath[_MAX_PATH];//动态链接库名称(包含完整路径)
      void  *pLibRemote;//远程线程的地址,存放库文件名称
      DWORD  hLibModule;//加载模块的基地址
      lstrcpy(szLibPath,L"d:\\test.dll");    //要远程进程调用的dll
      HANDLE   hProcess=OpenProcess(PROCESS_VM_OPERATION |PROCESS_VM_READ |PROCESS_VM_WRITE |PROCESS_CREATE_THREAD |PROCESS_QUERY_INFORMATION |SYNCHRONIZE, FALSE,pID);       //此处的pID是要注入进程的PID,可以自己写个函数由进程名获取PID,利用进程枚举函数。OpenProcess的第一个参数很重要,调用不同的函数要获得不同的权限,此处这五个参数缺一不可。
      if(!hProcess) return 1;
      //1.在远程进程中为szLibPath分配内存
      //2.并把szLibPath写入到该内存中
      pLibRemote=VirtualAllocEx(hProcess,NULL,2*sizeof(szLibPath),MEM_COMMIT,PAGE_READWRITE);
      if(!pLibRemote) return 1;
      BOOL  wflag;
      wflag=WriteProcessMemory(hProcess,pLibRemote,(void*)szLibPath,2*sizeof(szLibPath),NULL);
      if(wflag==false) return 1;
      //把动态链接库加载到远程进程的地址空间
      HMODULE  hModule=NULL;
      hModule=GetModuleHandle(L"kernel32.dll");   //LoadLibrary函数在kernel32.dll中;
      if(!hModule) return 1;

      FARPROC paddr;
      paddr=GetProcAddress(hModule,"LoadLibraryW");   //第二个参数调用很容易出错,此处加W是因为本没有LoadLibrary函数,实际调用的是LoadLibraryW和LoadLibraryA函数。
      // paddr=(FARPROC)0x7C80AEEB;   //上面获得LoadLibraryW函数地址还有一种方式,取得kernel32.dll载入内存中的地址,再加上导出函数的偏移地址,再加上LoadLibraryW函数的偏移地址。后两个偏移地址是一定的,其实这种方法很好用,之前用第一种方法失败就用的此种方法。
       if(!paddr) return 1;  

       hThread=CreateRemoteThread(hProcess,NULL,0,(LPTHREAD_START_ROUTINE)paddr,pLibRemote,0,NULL);
       if(!hThread) return 1;

       WaitForSingleObject(hThread,30000);

//得到加载模块的基地址
      GetExitCodeThread(hThread,&hLibModule);

//清理
      CloseHandle(hThread);
      VirtualFreeEx(hProcess,pLibRemote,2*sizeof(szLibPath),MEM_RELEASE);

      hModule=GetModuleHandle(L"kernel32.dll");
      if(!hModule) return 1;
      paddr=GetProcAddress(hModule,"FreeLibrary");
      if(!paddr) return 1;

//卸载:
      hThread=CreateRemoteThread(hProcess,NULL,0,(LPTHREAD_START_ROUTINE)paddr,(void*)hLibModule,0,NULL);
      if(!hThread) return 1;
      WaitForSingleObject(hThread,30000);
//清理
      CloseHandle(hThread);

      CloseHandle(hProcess);
      getchar(); 
      return 0;
}

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值