修改PE文件注入dll

修改思路
PE文件中导入dll信息以结构体列表形式存储在IDT中。只要将myhack.dll添加到列表尾部即可。

IDT结构
在这里插入图片描述
IDT的描述在IMAGE_OPTION_HEADER里面的IMPORT Table,通过size可以确定是否有足够的空间让我们添加
IDT是由IMAGE_IMPORT_DESCRIPTION(简称IID)结构体组成的数组,数组末尾以NULL结构体结束。每个IID结构体为0x14字节所以这里IID区域为RVA
真正的IDT在Section .rdata的IMPORT Directory Table
在这里插入图片描述
这里可以数一下我这里有16个结构体(18*0x14=0x168)前面查到的size为0x168
没有足够的空间。
移动IDT
需要找一个足够大的空间,这段空间在磁盘文件中但是不会被加载到内存。
看一下rdata头的信息
在这里插入图片描述
size of raw data表示该节区在磁盘中的大小,0x50a00
virtual size表示该节区在内存中的大小,0x5081c
回头看一下IDT的size是0x168,需要的是0x168+0x14=0x17c
data段没被加载的空间大小为

>>> hex(0x50a00-0x5081c)
'0x1e4'

所以.rdata区域的空间完全足够用了。
找到IDT的所有数据准备搬家
在这里插入图片描述
把它放到hex(0x152600+0x5081c)='0x1a2e1c’这个地址处
在这里插入图片描述

修改IIMPORT Table的值
需要把刚才设置的IDT的地址和size放入到IMPORT Table里面,注意这里填入的是RVA(也就是载入内存时的地址)。
RVA_IDT=RVA_idata+size_idata_R=0x154000+0x5081c=0x1A481C
这里是小端存储所以应该倒着存放,别忘了size要改为0x17c
在这里插入图片描述
删除绑定导入表

BOUND IMPORT TABLE(绑定导入表)是一种提高DLL加载速度的技术,不是必须项这里为了方便删除掉它。这里不存在就不需要多余的操作了。
创建IDT表项
在这里插入图片描述
如图,每一项都有
import Name Table RVA RVA to INT
紧跟着2位0
Name RVA RVA to Dll Name
import Address Table RVA RVA to IAT

IDT表结构
在这里插入图片描述
这三项也放在不被加载的区域即可,这里放置在IDT表下面。

修改如下
在这里插入图片描述
修改IAT节区属性
实际运行的时候IAT将会被替换所以写入的IAT可以是随意的数据,但是想要执行这个操作还需要修改IAT节区为可写。
在这里插入图片描述
可以看到,默认rdata节区是不可写的。
在原属性上添加IMAGE_SCN_MEM_WRITE(80000000)
跟原本的40000040进行或运算c0000040.
在这里插入图片描述

找到了一个自动化的脚本

https://www.cnblogs.com/HsinTsao/p/7435137.html

myhack.dll

#include"stdio.h"
#include"windows.h"
#include"shlobj.h"
#include"Wininet.h"
#include"tchar.h"
#pragma comment(lib,"Wininet.lib")
#define DEF_BUF_SIZE (4096)
#define DEF_URL L"http://www.google.com/index.html"
#define DEF_INDEX_FILE L"index.html"


//DownloadURL
BOOL DownloadURL(LPCTSTR szURL, LPCTSTR szFile)
{
	BOOL bRet = FALSE;
	HINTERNET hInternet = NULL, hURL = NULL;
	BYTE pBuf[DEF_BUF_SIZE] = { 0, };
	DWORD dwBytesRead = 0;
	FILE *pFile = NULL;
	errno_t err = 0;
	hInternet = InternetOpen(L"ReverseCore", INTERNET_OPEN_TYPE_PRECONFIG, NULL, NULL, 0);
	if (NULL == hInternet)
	{
		OutputDebugString(L"InternetOpen() failed!\n");
		return FALSE;
	}
	hURL = InternetOpenUrl(hInternet, szURL, NULL, 0, INTERNET_FLAG_RELOAD,0);
	if (NULL == hInternet)
	{
		OutputDebugString(L"InternetOpen() failed!\n");
		goto _DownloadURL_EXIT;
	}
	if (err == _tfopen_s(&pFile, szFile, L"wt"))
	{
		OutputDebugString(L"fopen() failed");
		goto _DownloadURL_EXIT;
	}
	while (InternetReadFile(hURL, pBuf, DEF_BUF_SIZE, &dwBytesRead))
	{
		if (!dwBytesRead)
			break;
		fwrite(pBuf, dwBytesRead, 1, pFile);
	}
	bRet = TRUE;
_DownloadURL_EXIT:
	if (pFile)
		fclose(pFile);
	if (hURL)
		InternetCloseHandle(hURL);
	if (hInternet)
	{
		InternetCloseHandle(hInternet);
	}

	return bRet;
}

//downloadURL会下载szURL中指定的网页文件并将其保存在szFile目录中

//DropFile
HWND g_hWnd = 0;
BOOL CALLBACK EnumWindowsProc(HWND hWnd, LPARAM lParam)
{
	DWORD dwPID = 0;
	
	GetWindowThreadProcessId(hWnd, &dwPID);
	if (dwPID == (DWORD)lParam)
	{
		g_hWnd = hWnd;
		return FALSE;
	}
	return TRUE;
}

HWND GetWindowHandleFromPID(DWORD dwPID)
{
	EnumWindows(EnumWindowsProc, dwPID);
	return g_hWnd;
}
BOOL DropFile(LPCTSTR wcsFile)
{
	HWND hWnd = NULL;
	DWORD dwBufSize = 0;
	BYTE *pBuf = NULL;
	DROPFILES *pDrop = NULL;
	char szFile[MAX_PATH] = { 0 ,};
	HANDLE hMem = 0;
	WideCharToMultiByte(CP_ACP, 0, wcsFile, -1, szFile, MAX_PATH, NULL, NULL);
	dwBufSize = sizeof(DROPFILES)+strlen(szFile) + 1;
	if (!(hMem = GlobalAlloc(GMEM_ZEROINIT, dwBufSize)))
	{
		OutputDebugString(L"GlobalAlloc() failed!!!");
		return FALSE;
	}
	pBuf = (LPBYTE)GlobalLock(hMem);
	pDrop = (DROPFILES*)pBuf;
	pDrop->pFiles = sizeof(DROPFILES);
	strcpy_s((char *)(pBuf + sizeof(DROPFILES)), strlen(szFile) + 1, szFile);
	GlobalUnlock(hMem);
	if (!(hWnd = GetWindowHandleFromPID(GetCurrentProcessId())))
	{
		OutputDebugString(L"GetWndHandleFromPIF() failed!!\n");
		return FALSE;
	}
	PostMessage(hWnd, WM_DROPFILES, (WPARAM)pBuf, NULL);
	return TRUE;
}

//dummy函数
#ifdef __cplusplus
extern "C"{
#endif
	//出现在IDT中的dump export function......
	__declspec(dllexport)void dummy()
	{
		return;
	}
#ifdef __cplusplus
}
#endif


//dll main函数
DWORD WINAPI ThreadProc(LPVOID lParam)
{
	TCHAR szPath[MAX_PATH] = { 0, };
	TCHAR *p = NULL;
	GetModuleFileName(NULL, szPath, sizeof(szPath));
	if (p = _tcsrchr(szPath, L'\\'))
	{
		_tcscpy_s(p + 1, wcslen(DEF_INDEX_FILE) + 1, DEF_INDEX_FILE);
		if (DownloadURL(DEF_URL, szPath))
		{
			DropFile(szPath);
		}
	}
	return 0;
}

BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
{
	switch (fdwReason)
	{
	case DLL_PROCESS_ATTACH:
		CloseHandle(CreateThread(NULL, 0, ThreadProc, NULL, 0, NULL));
		break;
	}
	return TRUE;
}
  • 2
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值