移动导出表:
思路:
添加节之后新建一个句柄用来重新安排结构情况,然后将的句柄的内容写入读入的数据流中。
前期知识:
fopen()和 fclose()
两个函数都是文件操作函数,对数据流进行操作
fopen将文件读入一个文件流,文件流就是文件原本的形式。
fclose()将文件流关闭。
fwrite():fwrite(NewBuffer,pOptionalHeader->SizeOfImage,1,fp);
可以直接将内存写入数据流中
RVA 和 FOA的转化:
FOA->RVA:修改新的导出表的AddressOfFunctions、AddressOfNameOrdinals、AddressOfNames地址,需要转化成RVA
RVA->FOA:定位导出地址表、导出名称表、导出序号表需要将内容转化成FOA
添加节:
1.判断节表空间是否够2个节表的长度(最后一个节表需要全部为0)
2.对节表进行赋值
3.FileHeader的节区数量+1
4.OptionalHeader的ImageBase的大小+0x1000
移动导出表:
1.申请一个新的内存NewBuffer,将原来内存复制。
2.定位三个表的位置(需要RVA -> FOA)
3.复制三个表的内容到新的句柄
4.复制函数名称(每复制一个函数名就要计算偏移RVA添加到函数名称表的地址中)
5.复制IMAGE_EXPORT_DIRECTORY结构体
6.修改新的导出表的AddressOfFunctions、AddressOfNameOrdinals、AddressOfNames地址
7.修改VirtualAddress值,指向新的导出表地址
8.读取文件,将修改后的新的句柄写入文件流中
代码
#include <stdio.h>
#include <stdlib.h>
#include <windows.h>
DWORD RVATOFOA(DWORD RVA,LPVOID pFileBuffer)
{
DWORD FOA = NULL;
PIMAGE_DOS_HEADER pDosHeader = NULL;
PIMAGE_NT_HEADERS pNtHeaders = NULL;
PIMAGE_FILE_HEADER pFileHeader = NULL;
PIMAGE_OPTIONAL_HEADER pOptionalHeader = NULL;
PIMAGE_SECTION_HEADER pSectionHeader = NULL;
pDosHeader = (PIMAGE_DOS_HEADER)pFileBuffer;
pNtHeaders = (PIMAGE_NT_HEADERS)((DWORD)pDosHeader + pDosHeader->e_lfanew);
pFileHeader = (PIMAGE_FILE_HEADER)((DWORD)pNtHeaders + 4);
pOptionalHeader = (PIMAGE_OPTIONAL_HEADER)((DWORD)pFileHeader + IMAGE_SIZEOF_FILE_HEADER);
pSectionHeader = (PIMAGE_SECTION_HEADER)((DWORD)pOptionalHeader + pFileHeader->SizeOfOptionalHeader);
if(RVA <= pOptionalHeader->SizeOfHeaders)
return RVA;
for(;RVA >(pSectionHeader->Misc.VirtualSize + pSectionHeader->VirtualAddress);pSectionHeader++);//定位到所在的节
FOA = RVA - pSectionHeader->VirtualAddress + pSectionHeader->PointerToRawData;
return FOA;
}
DWORD FOATORVA(DWORD FOA,LPVOID pFileBuffer)
{
DWORD RVA = NULL;
PIMAGE_DOS_HEADER pDosHeader = NULL;
PIMAGE_NT_HEADERS pNtHeaders = NULL;
PIMAGE_FILE_HEADER pFileHeader = NULL;
PIMAGE_OPTIONAL_HEADER pOptionalHeader = NULL;
PIMAGE_SECTION_HEADER pSectionHeader = NULL;
pDosHeader = (PIMAGE_DOS_HEADER)pFileBuffer;
pNtHeaders = (PIMAGE_NT_HEADERS)((DWORD)pDosHeader + pDosHeader->e_lfanew);
pFileHeader = (PIMAGE_FILE_HEADER)((DWORD)pNtHeaders + 4);
pOptionalHeader = (PIMAGE_OPTIONAL_HEADER)((DWORD)pFileHeader + IMAGE_SIZEOF_FILE_HEADER);
pSectionHeader = (PIMAGE_SECTION_HEADER)((DWORD)pOptionalHeader + pFileHeader->SizeOfOptionalHeader);
if(FOA <= pOptionalHeader->SizeOfHeaders)
return RVA;
for