进程代码注入
2012-12-10 20:35
387 查看
参考教程:windows api编程
实现步骤如下:
(1)得到指向远程进程的句柄,可以使用OpenProcess函数实现。
(2)使用VirtualAllocEx函数在远程进程中为动态链接库名称分配内存。
(3)使用WriteProcessMemory函数把动态链接库的名称包括路径信息写入到分配的内存中。
(4)通过CreateRemoteThread和LoadLibrary函数映射动态链接库到远程进程。
(5)调用WaitForSingleObject函数等待远程线程终止,这时远程线程调用LoadLibrary返回。换句话说,线程只有在动态链接库的DllMain中的DLL_PROCESS_ATTACH处理结束时才返回。
(6)调用GetExitCodeThread获得远程线程的返回码,这个值实际上是LoadLibrary返回的值,也就是映射的动态链接库返回的加载基地址。
(7)使用VirtualFreeEx函数释放第2步分配的内存。
(8)利用第(6)步返回的模块句柄通过CreateRemoteThread和FreeLibrary函数卸载动态链接库。如果注入的动态链接库又在调用期间创建了新的线程,用户必须确保这些线程,在卸载前终止。
(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;
}
实现步骤如下:
(1)得到指向远程进程的句柄,可以使用OpenProcess函数实现。
(2)使用VirtualAllocEx函数在远程进程中为动态链接库名称分配内存。
(3)使用WriteProcessMemory函数把动态链接库的名称包括路径信息写入到分配的内存中。
(4)通过CreateRemoteThread和LoadLibrary函数映射动态链接库到远程进程。
(5)调用WaitForSingleObject函数等待远程线程终止,这时远程线程调用LoadLibrary返回。换句话说,线程只有在动态链接库的DllMain中的DLL_PROCESS_ATTACH处理结束时才返回。
(6)调用GetExitCodeThread获得远程线程的返回码,这个值实际上是LoadLibrary返回的值,也就是映射的动态链接库返回的加载基地址。
(7)使用VirtualFreeEx函数释放第2步分配的内存。
(8)利用第(6)步返回的模块句柄通过CreateRemoteThread和FreeLibrary函数卸载动态链接库。如果注入的动态链接库又在调用期间创建了新的线程,用户必须确保这些线程,在卸载前终止。
(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;
}
相关文章推荐
- [windows平台] 给进程注入代码 -- 导入DLL到指定进程的地址空间
- 向其他进程注入代码的三种方法
- 向其他进程注入代码的三种方法
- 向其他进程注入代码的三种方法
- Linux 平台一种进程代码注入方法
- [原创&译]向其他进程注入代码的三种方法
- 向其他进程注入代码的三种方法
- 向其他进程注入代码的三种方法
- Linux 平台一种进程代码注入方法
- Pe研究之:从内存中加载Pe文件(代码重定位,进程隐藏,代码注入)
- 向其他进程注入代码的三种方法
- 向其他进程注入代码的三种方法
- 向其他进程注入代码的三种方法
- 直接将自身代码注入傀儡进程
- Delphi进程注入的部分代码 (非DLL注入)
- 注入下载文件的代码到IE进程然后执行下载的文件
- 劫持正在运行进程的EIP注入代码的方法
- 重定向已经运行进程的标准输出到文件的办法(通过ptrace注入代码到其他进程并运行)
- 远程进程注入 - 把自己的代码注入explorer.exe
- 游戏进程注入代码