如何使用 C++ 和 Window.h 解析 EXE 文件并从 IMAGE_DOS_HEADER 结构中获取数据?
How to parse EXE file and get data from IMAGE_DOS_HEADER structure using c++ and Window.h?
我正在尝试解析 windows 中的 PE 文件并从此结构中获取数据
我写了这段代码,它从 exe 文件中读取字节。
#include <Windows.h>
int main()
{
// open the file for binary reading
std::ifstream file;
file.open("D:/SomeProgram.exe", ios_base::binary);
if (!file.is_open())
return 1;
// get the length of the file
file.seekg(0, ios::end);
size_t fileSize = file.tellg();
file.seekg(0, ios::beg);
// create a vector to hold all the bytes in the file
std::vector<byte> data(fileSize, 0);
// read the file
file.read(reinterpret_cast<char*>(&data[0]), fileSize);
我不知道如何获取数据,其中包含 e_magic
、e_cbip
、e_cp
.... 以及最重要的 e_ifanew
。
我知道,这个结构 IMAGE_DOS_HEADER 存储在 Windows.h 中,但我不知道如何使用它从任何 exe 文件中获取字段。
声明结构实例并将数据复制到其中:
IMAGE_DOS_HEADER idh;
if ( fileSize >= sizeof(idh) )
{
std::memcpy(&idh, &data[0], sizeof(idh));
}
查找以下过程以从不同的 headers 获取数据:
LPCSTR fileName; //exe file to parse
HANDLE hFile;
HANDLE hFileMapping;
LPVOID lpFileBase;
PIMAGE_DOS_HEADER dosHeader;
PIMAGE_NT_HEADERS peHeader;
hFile = CreateFileA(fileName,GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,0);
if(hFile==INVALID_HANDLE_VALUE)
{
printf("\n CreateFile failed in read mode \n");
return 1;
}
hFileMapping = CreateFileMapping(hFile,NULL,PAGE_READONLY,0,0,NULL);
if(hFileMapping==0)
{
printf("\n CreateFileMapping failed \n");
CloseHandle(hFile);
return 1;
}
lpFileBase = MapViewOfFile(hFileMapping,FILE_MAP_READ,0,0,0);
if(lpFileBase==0)
{
printf("\n MapViewOfFile failed \n");
CloseHandle(hFileMapping);
CloseHandle(hFile);
return 1;
}
dosHeader = (PIMAGE_DOS_HEADER) lpFileBase; //pointer to dos headers
if(dosHeader->e_magic==IMAGE_DOS_SIGNATURE)
{
//if it is executable file print different fileds of structure
//dosHeader->e_lfanew : RVA for PE Header
printf("\n DOS Signature (MZ) Matched");
//pointer to PE/NT header
peHeader = (PIMAGE_NT_HEADERS) ((u_char*)dosHeader+dosHeader->e_lfanew);
if(peHeader->Signature==IMAGE_NT_SIGNATURE)
{
printf("\n PE Signature (PE) Matched \n");
//important fileds
//peHeader->FileHeader : Refrence to FileHeader
//peHeader->OptionalHeader : Refrence to Optional Header
// lots of imprtant fileds are present in File header and Optional header to retrive code/data/different sections address of exe
}
UnmapViewOfFile(lpFileBase);
CloseHandle(hFileMapping);
CloseHandle(hFile);
return 0;
}
else
{
printf("\n DOS Signature (MZ) Not Matched \n");
UnmapViewOfFile(lpFileBase);
CloseHandle(hFileMapping);
CloseHandle(hFile);
return 1;
}
将文件读入缓冲区并将其部分转换为结构。
// READ FILE ASSUMING IT EXISTS AND IS A VALID PE FILE
char* buffer = nullptr;
std::ifstream infile("C:\file.exe", std::ios::binary);
std::filebuf* pbuf = infile.rdbuf();
size_t size = pbuf->pubseekoff(0, infile.end, infile.in);
buffer = new char[size];
pbuf->pubseekpos(0, infile.in);
pbuf->sgetn(buffer, size);
infile.close();
// CAST
IMAGE_DOS_HEADER* MS_DOS = (IMAGE_DOS_HEADER*)buffer;
IMAGE_NT_HEADERS* PE = (IMAGE_NT_HEADERS*)((DWORD)buffer + MS_DOS->e_lfanew);
// DO YOUR STUFF
// ...
delete[] buffer;
我正在尝试解析 windows 中的 PE 文件并从此结构中获取数据
我写了这段代码,它从 exe 文件中读取字节。
#include <Windows.h>
int main()
{
// open the file for binary reading
std::ifstream file;
file.open("D:/SomeProgram.exe", ios_base::binary);
if (!file.is_open())
return 1;
// get the length of the file
file.seekg(0, ios::end);
size_t fileSize = file.tellg();
file.seekg(0, ios::beg);
// create a vector to hold all the bytes in the file
std::vector<byte> data(fileSize, 0);
// read the file
file.read(reinterpret_cast<char*>(&data[0]), fileSize);
我不知道如何获取数据,其中包含 e_magic
、e_cbip
、e_cp
.... 以及最重要的 e_ifanew
。
我知道,这个结构 IMAGE_DOS_HEADER 存储在 Windows.h 中,但我不知道如何使用它从任何 exe 文件中获取字段。
声明结构实例并将数据复制到其中:
IMAGE_DOS_HEADER idh;
if ( fileSize >= sizeof(idh) )
{
std::memcpy(&idh, &data[0], sizeof(idh));
}
查找以下过程以从不同的 headers 获取数据:
LPCSTR fileName; //exe file to parse
HANDLE hFile;
HANDLE hFileMapping;
LPVOID lpFileBase;
PIMAGE_DOS_HEADER dosHeader;
PIMAGE_NT_HEADERS peHeader;
hFile = CreateFileA(fileName,GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,0);
if(hFile==INVALID_HANDLE_VALUE)
{
printf("\n CreateFile failed in read mode \n");
return 1;
}
hFileMapping = CreateFileMapping(hFile,NULL,PAGE_READONLY,0,0,NULL);
if(hFileMapping==0)
{
printf("\n CreateFileMapping failed \n");
CloseHandle(hFile);
return 1;
}
lpFileBase = MapViewOfFile(hFileMapping,FILE_MAP_READ,0,0,0);
if(lpFileBase==0)
{
printf("\n MapViewOfFile failed \n");
CloseHandle(hFileMapping);
CloseHandle(hFile);
return 1;
}
dosHeader = (PIMAGE_DOS_HEADER) lpFileBase; //pointer to dos headers
if(dosHeader->e_magic==IMAGE_DOS_SIGNATURE)
{
//if it is executable file print different fileds of structure
//dosHeader->e_lfanew : RVA for PE Header
printf("\n DOS Signature (MZ) Matched");
//pointer to PE/NT header
peHeader = (PIMAGE_NT_HEADERS) ((u_char*)dosHeader+dosHeader->e_lfanew);
if(peHeader->Signature==IMAGE_NT_SIGNATURE)
{
printf("\n PE Signature (PE) Matched \n");
//important fileds
//peHeader->FileHeader : Refrence to FileHeader
//peHeader->OptionalHeader : Refrence to Optional Header
// lots of imprtant fileds are present in File header and Optional header to retrive code/data/different sections address of exe
}
UnmapViewOfFile(lpFileBase);
CloseHandle(hFileMapping);
CloseHandle(hFile);
return 0;
}
else
{
printf("\n DOS Signature (MZ) Not Matched \n");
UnmapViewOfFile(lpFileBase);
CloseHandle(hFileMapping);
CloseHandle(hFile);
return 1;
}
将文件读入缓冲区并将其部分转换为结构。
// READ FILE ASSUMING IT EXISTS AND IS A VALID PE FILE
char* buffer = nullptr;
std::ifstream infile("C:\file.exe", std::ios::binary);
std::filebuf* pbuf = infile.rdbuf();
size_t size = pbuf->pubseekoff(0, infile.end, infile.in);
buffer = new char[size];
pbuf->pubseekpos(0, infile.in);
pbuf->sgetn(buffer, size);
infile.close();
// CAST
IMAGE_DOS_HEADER* MS_DOS = (IMAGE_DOS_HEADER*)buffer;
IMAGE_NT_HEADERS* PE = (IMAGE_NT_HEADERS*)((DWORD)buffer + MS_DOS->e_lfanew);
// DO YOUR STUFF
// ...
delete[] buffer;