#pragma once
#include <Windows.h>
class InectDll
{
public:
InectDll(void);
~InectDll(void);
static BOOL InjectDll(const char *DllFullPath, LPCTSTR ProcessName);
static BOOL InjectDll(const char *DllFullPath, const DWORD dwRemoteProcessId);
private:
static int processNameToId(LPCTSTR lpszProcessName);
static int EnableDebugPriv(const char * name);
};
#include "InectDll.h"
#include <Windows.h>
#include <stdio.h>
#include <Tlhelp32.h>
InectDll::InectDll(void)
{
}
InectDll::~InectDll(void)
{
}
int InectDll::processNameToId(LPCTSTR lpszProcessName)
{
HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
if (hSnapshot == INVALID_HANDLE_VALUE)
{
return -1;
}
PROCESSENTRY32 pe;
pe.dwSize = sizeof(PROCESSENTRY32);
if (!Process32First(hSnapshot, &pe))
{
CloseHandle(hSnapshot);
return -2;
}
while (Process32Next(hSnapshot, &pe))
{
if (!strcmp(lpszProcessName, pe.szExeFile))
{
CloseHandle(hSnapshot);
return pe.th32ProcessID;
}
}
CloseHandle(hSnapshot);
return 0;
}
int InectDll::EnableDebugPriv(const char * name)
{
HANDLE hToken;
TOKEN_PRIVILEGES tp;
LUID luid;
BOOL bRet = 0;
//打开进程令牌环
bRet = OpenProcessToken(GetCurrentProcess(),
TOKEN_ADJUST_PRIVILEGES|TOKEN_QUERY,
&hToken);
if ( !bRet)
{
return -1;
}
//获得进程本地唯一ID
bRet = LookupPrivilegeValue(NULL,name,&luid);
if (!bRet)
{
return -2;
}
tp.PrivilegeCount = 1;
tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
tp.Privileges[0].Luid = luid;
//调整权限
bRet = AdjustTokenPrivileges(hToken,0,&tp,sizeof(TOKEN_PRIVILEGES),NULL,NULL);
if (!bRet)
{
return -3;
}
return 0;
}
BOOL InectDll::InjectDll(const char *DllFullPath, const DWORD dwRemoteProcessId)
{
if (DllFullPath == NULL)
{
return FALSE;
}
HANDLE hRemoteProcess;
int nRet = EnableDebugPriv(SE_DEBUG_NAME);
if ( nRet < 0)
{
return FALSE;
}
//打开远程线程
hRemoteProcess = OpenProcess(
PROCESS_CREATE_THREAD | PROCESS_VM_OPERATION | PROCESS_VM_WRITE
,FALSE, dwRemoteProcessId );
if ( hRemoteProcess == INVALID_HANDLE_VALUE)
return FALSE;
//使用VirtualAllocEx函数在远程进程的内存地址空间分配DLL文件名空间
char *pszLibFileRemote = (char *) VirtualAllocEx( hRemoteProcess, NULL, lstrlen(DllFullPath)+1,
MEM_COMMIT, PAGE_READWRITE);
//使用WriteProcessMemory函数将DLL的路径名写入到远程进程的内存空间
BOOL bRet = WriteProcessMemory(hRemoteProcess, pszLibFileRemote, (void *) DllFullPath, lstrlen(DllFullPath)+1, NULL);
if (!bRet)
{
return FALSE;
}
//计算LoadLibraryA的入口地址
PTHREAD_START_ROUTINE pfnStartAddr = (PTHREAD_START_ROUTINE)GetProcAddress(GetModuleHandle(TEXT("Kernel32")), "LoadLibraryA");
//启动远程线程LoadLibraryA,通过远程线程调用创建新的线程
HANDLE hRemoteThread = INVALID_HANDLE_VALUE;
if( (hRemoteThread = CreateRemoteThread( hRemoteProcess, NULL, 0, pfnStartAddr, pszLibFileRemote, 0, NULL) ) == NULL)
{
DWORD dwError = GetLastError();
printf("CreateRemoteThread error!\n The last error is : %d",dwError);
CloseHandle(hRemoteProcess);
CloseHandle(hRemoteThread);
return FALSE;
}
CloseHandle(hRemoteProcess);
CloseHandle(hRemoteThread);
return TRUE;
}
BOOL InectDll::InjectDll( const char *DllFullPath, LPCTSTR ProcessName )
{
int Processid = processNameToId(ProcessName);
if (Processid < 1)
{
return FALSE;
}
return InjectDll(DllFullPath,Processid);
}
main.cpp
#include <stdio.h>
#include "InectDll.h"
void main()
{
InectDll::InjectDll("D:\\Project\\testdll1\\Debug\\testdll1.dll","NOTEPAD.EXE");
getchar();
}