DLL注入经典方法

注入Dll:

1. OpenProcess获得要注入进程的句柄(可以先通过通过CreateProcess创建进程,获取PID,然后由OpenProcessPID获取)

2VirtualAllocEx在远程进程中开辟出一段内存,长度为strlen(dllname)+1;

3WriteProcessMemory将Dll的名字写入第二步开辟出的内存中。

4CreateRemoteThread将LoadLibraryA作为线程函数,参数为Dll的名称,创建新线程

5CloseHandle关闭线程句柄

卸载Dll:

1CreateRemoteThread将GetModuleHandle注入到远程进程中,参数为被注入的Dll名

2GetExitCodeThread将线程退出的退出码作为Dll模块的句柄值。

3CloseHandle关闭线程句柄

3CreateRemoteThread将FreeLibraryA注入到远程进程中,参数为第二步获得的句柄值。

4WaitForSingleObject等待对象句柄返回

5CloseHandle关闭线程及进程句柄。


  
  
  
  
  1. //Code By Pnig0s1992 
  2. //Date:2012,3,13 
  3. #include <stdio.h> 
  4. #include <Windows.h> 
  5. #include <TlHelp32.h> 
  1. //根据进程名查找进程PID
  2. DWORD GetProcessHandle(LPCTSTR lpProcessName)
  3. //创建进程快照
  4.     DWORD dwRet = 0; 
  5.     HANDLE hSnapShot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS,0); 
  6.     if(hSnapShot == INVALID_HANDLE_VALUE) 
  7.     { 
  8.         printf("\n获得进程快照失败%d",GetLastError()); 
  9.         return dwRet; 
  10.     } 
  11.  
  12. //遍历进程快照
  13.     PROCESSENTRY32 pe32;//声明进程入口对象 
  14.     pe32.dwSize = sizeof(PROCESSENTRY32);//填充进程入口对象大小 
  15.     BOOL bMore = Process32First(hSnapShot,&pe32);//遍历进程列表 
  16.     while (bMore)
  17.     { 
  18. //查找指定进程名的PID 
  19.         if(!lstrcmp(pe32.szExeFile,lpProcessName))
  20.         { 
  21.             dwRet = pe32.th32ProcessID; 
  22.             break
  23.         } 
  24. bMore = Process32Next(hSnapShot,&pe32);
  25.     }
  1. //关闭快照句柄 
  2. CloseHandle(hSnapShot); 
  3.     return dwRet;
  1.  
  2. INT main(INT argc,CHAR * argv[]) 
  3. //通过进程名称获取进程ID
  4.     DWORD dwPid = getProcessHandle((LPCTSTR)argv[1]); 
  5.     
  6. //通过进程ID获取进程句柄
  7.     HANDLE hProcess = OpenProcess(PROCESS_VM_OPERATION|PROCESS_VM_WRITE,FALSE,dwPid); 
  8.     if(hProcess == NULL) 
  9.     { 
  10.         printf("\n获取进程句柄错误%d",GetLastError()); 
  11.         return -1; 
  12.     } 
  13. //计算DLL路径名需要的内存空间
  14. LPCSTR lpDllName = "EvilDll.dll"
  15.   DWORD dwSize = strlen(lpDllName)+1;  
  16. //使用VirtualAllocEx函数在远程进程的内存地址空间分配DLL文件名缓冲区,成功返回分配内存的首地址.
  17.     LPVOID lpRemoteBuf = VirtualAllocEx(hProcess,NULL,dwSize,MEM_COMMIT,PAGE_READWRITE); 
  18. //使用WriteProcessMemory函数将DLL的路径名复制到远程进程的内存空间,成功返回TRUE.
  19. DWORD dwHasWrite = 0;
  20.     if(WriteProcessMemory(hProcess,lpRemoteBuf,lpDllName,dwSize,&dwHasWrite)) 
  21.     { 
  22.         if(dwHasWrite != dwSize) 
  23.         { 
  24.             VirtualFreeEx(hProcess,lpRemoteBuf,dwSize,MEM_COMMIT); 
  25.             CloseHandle(hProcess); 
  26.             return -1; 
  27.         } 
  28.  
  29.     }
  30. else 
  31.     { 
  32.         printf("\n写入远程进程内存空间出错%d。",GetLastError()); 
  33.         CloseHandle(hProcess); 
  34.         return -1; 
  35.     } 
  36.  
  37. //创建一个在其它进程地址空间中运行的线程(也称:创建远程线程),成功返回新线程句柄.
  38.     DWORD dwThreadId = 0; 
  39.     LPVOID lpLoadDll = LoadLibraryA; 
  40.     HANDLE hRemoteThread = CreateRemoteThread(hProcess,NULL,0,(LPTHREAD_START_ROUTINE)lpLoadDll,lpRemoteBuf,0,&dwThreadId); 
  41.     if(hRemoteThread == NULL) 
  42.     { 
  43.         printf("\n建立远程线程失败%d",GetLastError()); 
  44.         CloseHandle(hProcess); 
  45.         return -1; 
  46.     } 
  47.  
  48.     WaitForSingleObject(hRemoteThread,INFINITE); 
  49.     CloseHandle(hRemoteThread); 
  50.  
  51.     //准备卸载之前注入的Dll 
  52.     DWORD dwHandle,dwID; 
  53.     LPVOID pFunc = GetModuleHandleA;//获得在远程线程中被注入的Dll的句柄 
  54.     HANDLE hThread = CreateRemoteThread(hProcess,NULL,0,(LPTHREAD_START_ROUTINE)pFunc,lpRemoteBuf,0,&dwID); 
  55.     WaitForSingleObject(hThread,INFINITE); 
  56.     GetExitCodeThread(hThread,&dwHandle);//线程的结束码即为Dll模块儿的句柄 
  57.     CloseHandle(hThread); 
  58.     pFunc = FreeLibrary; 
  59.     hThread = CreateRemoteThread(hThread,NULL,0,(LPTHREAD_START_ROUTINE)pFunc,(LPVOID)dwHandle,0,&dwID); //将FreeLibraryA注入到远程线程中去卸载Dll 
  60.     WaitForSingleObject(hThread,INFINITE); 
  61.     CloseHandle(hThread); 
  62.     CloseHandle(hProcess); 
  63.     return 0; 

你可能感兴趣的:(DLL注入经典方法)