PE文件 是微軟 Win32 環境下可執行文件的標准格式。
所謂的可執行文件並不僅僅是常見的 EXE 文件,DLL,SYS,VXD 等文件也都屬於 PE 格式。
|-------> DOS_MZ_Header ------> 結構體:IMAGE_DOS_HEADER
|-------> DOS_Header ------|
| |-------> DOS_Stub ------->"This program cannot be run in DOS mode."
|
PE 文件格式 |-------> PE_Header -------> 結構體:IMAGE_NT_HEADERS
|
|
|-------> Section_Table --------> 結構體:IMAGE_SECTION_HEADER
IMAGE_DOS_HEADER 結構體:
typedef struct _IMAGE_DOS_HEADER // 該結構體大小為 64byte。
{ WORD e_magic; // DOS 可執行文件標記。值為 0x5A4D,由於低位在前高位在后,所以存儲為 0x4D5A。即 ASCII 字符為"MZ"。 WORD e_cblp; WORD e_cp; WORD e_crlc; WORD e_cparhdr; WORD e_minalloc; WORD e_maxalloc; WORD e_ss; // DOS 代碼的初始化堆棧。 WORD e_sp; // DOS 代碼的初始化堆棧指針SP。 WORD e_csum; WORD e_ip; // DOS 代碼的初始化指令入口[指針IP] WORD e_cs; // DOS 代碼的初始化堆棧入口。 WORD e_lfarlc; WORD e_ovno; WORD e_res[4]; WORD e_oemid; WORD e_oeminfo; WORD e_res2[10]; LONG e_lfanew; // PE 文件頭偏移位置。 } IMAGE_DOS_HEADER, *PIMAGE_DOS_HEADER;
IMAGE_NT_HEADERS 結構體:
typedef struct _IMAGE_NT_HEADERS
{ DWORD Signature; // 標識 PE 文件頭部。值為 0x00004550,ASCII 碼即 "PE00"。 IMAGE_FILE_HEADER FileHeader; IMAGE_OPTIONAL_HEADER32 OptionalHeader; } IMAGE_NT_HEADERS32, *PIMAGE_NT_HEADERS32;
IMAGE_FILE_HEADER 結構體:
typedef struct _IMAGE_FILE_HEADER
{ WORD Machine; // 計算機的體系結構類型。 WORD NumberOfSections; // 節數。這指示節表的大小, 它緊跟在標題后面。 DWORD TimeDateStamp; // 圖像的時間戳的低32位。這表示鏈接器創建映像的日期和時間。 DWORD PointerToSymbolTable; // 符號表的偏移量 DWORD NumberOfSymbols; // 符號表中的符號數。 WORD SizeOfOptionalHeader; // 緊跟在該結構體后面的 IMAGE_OPTIONAL_HEADER32 結構體的大小。 WORD Characteristics; // 圖像的特征。 } IMAGE_FILE_HEADER, *PIMAGE_FILE_HEADER;
IMAGE_OPTIONAL_HEADER32 結構體:
typedef struct _IMAGE_OPTIONAL_HEADER
{ WORD Magic; // 圖像文件的狀態。 BYTE MajorLinkerVersion; // 鏈接器的主要版本號。 BYTE MinorLinkerVersion; // 鏈接器的次要版本號。 DWORD SizeOfCode; // 代碼節的大小。 DWORD SizeOfInitializedData; // 初始化數據節的大小。 DWORD SizeOfUninitializedData; // 未初始化數據節的大小。 DWORD AddressOfEntryPoint; // 指向入口點函數的指針。 DWORD BaseOfCode; // 指向代碼節的開頭的指針 DWORD BaseOfData; // 指向數據節開頭的指針 DWORD ImageBase; // 在內存中加載圖像的第一個字節的首選地址。 DWORD SectionAlignment; // 在內存中加載的節的對齊方式。 DWORD FileAlignment; // 圖像文件中各節的原始數據的對齊方式 WORD MajorOperatingSystemVersion; // 所需操作系統的主要版本號。 WORD MinorOperatingSystemVersion; // 所需操作系統的次要版本號。 WORD MajorImageVersion; // 圖像的主要版本號。 WORD MinorImageVersion; // 圖像的次要版本號。 WORD MajorSubsystemVersion; // 子系統的主要版本號。 WORD MinorSubsystemVersion; // 子系統的次要要版本號。 DWORD Win32VersionValue; // 必須為 0。 DWORD SizeOfImage; // 圖像的大小。 DWORD SizeOfHeaders; // 頭結構體的總大小, DWORD CheckSum; // 圖像文件校驗和。 WORD Subsystem; // 運行此映像所需的子系統。 WORD DllCharacteristics; // 圖像的 DLL 特征。 DWORD SizeOfStackReserve; // 要為堆棧保留的字節數。 DWORD SizeOfStackCommit; // 要為堆棧提交的字節數。 DWORD SizeOfHeapReserve; // 要為本地堆保留的字節數。 DWORD SizeOfHeapCommit; // 要為本地堆提交的字節數。 DWORD LoaderFlags; DWORD NumberOfRvaAndSizes; IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES]; } IMAGE_OPTIONAL_HEADER32, *PIMAGE_OPTIONAL_HEADER32;
IMAGE_DATA_DIRECTORY 結構體:
typedef struct _IMAGE_DATA_DIRECTORY
{ DWORD VirtualAddress; // 表的相對虛擬地址。 DWORD Size; // 表的大小。 } IMAGE_DATA_DIRECTORY, *PIMAGE_DATA_DIRECTORY;
IMAGE_SECTION_HEADER 結構體:
typedef struct _IMAGE_SECTION_HEADER
{ BYTE Name[IMAGE_SIZEOF_SHORT_NAME]; // 用了定義區塊名。 union { DWORD PhysicalAddress; // 文件地址。 DWORD VirtualSize; // 加載到內存中的節的總大小 } Misc; DWORD VirtualAddress; // 加載到內存中的節的第一個字節的地址 (相對於映像基)。 DWORD SizeOfRawData; // 磁盤上初始化數據的大小。 DWORD PointerToRawData; // 指向 COFF 文件中第一頁的文件指針。 DWORD PointerToRelocations; // 指向該節的重新定位項開頭的文件指針。如果沒有遷移, 則此值為零。 DWORD PointerToLinenumbers; // 指向該節的行號條目開頭的文件指針。如果沒有 COFF 行號, 則此值為零。 WORD NumberOfRelocations; // 該節的搬遷條目數。此值為可執行圖像的零。 WORD NumberOfLinenumbers; // 節的行號條目數。 DWORD Characteristics; // 圖像的特征。 } IMAGE_SECTION_HEADER, *PIMAGE_SECTION_HEADER;