34
30

More than 5 years have passed since last update.

PEファイルフォーマットについて

Last updated at Posted at 2018-06-25

はじめに

PEについて少し勉強してみようと思ったので、ほぼ受け売りになりますが自分用メモとしてまとめてみました。
用語や各フィールドの詳細などについてはこちらにまとめます。
内容は勉強が進み次第随時更新・修正する予定です。
誤りや補足等ありましたら、コメント欄にお願い致します。

PE(Portable Executable)とは

現在主流となっている、実行ファイルのフォーマットの一つです。
データ構造はWindows SDKに含まれるwinnt.hで定義されています。

layout

MS-DOS HEADER
MS-DOS REAL-MODE STUB PROGRUM

MS-DOS HEADER


_IMAGE_DOS_HEADER

typedef struct _IMAGE_DOS_HEADER {       // DOS .EXE header
    WORD   e_magic;                     // Magic number
    WORD   e_cblp;                      // Bytes on last page of file
    WORD   e_cp;                        // Pages in file
    WORD   e_crlc;                      // Relocations
    WORD   e_cparhdr;                   // Size of header in paragraphs
    WORD   e_minalloc;                   // Minimum extra paragraphs needed
    WORD   e_maxalloc;                  // Maximum extra paragraphs needed
    WORD   e_ss;                        // Initial (relative) SS value
    WORD   e_sp;                        // Initial SP value
    WORD   e_csum;                      // Checksum
    WORD   e_ip;                         // Initial IP value
    WORD   e_cs;                        // Initial (relative) CS value
    WORD   e_lfarlc;                    // File address of relocation table
    WORD   e_ovno;                      // Overlay number
    WORD   e_res[4];                    // Reserved words
    WORD   e_oemid;                     // OEM identifier (for e_oeminfo)
    WORD   e_oeminfo;                   // OEM information; e_oemid specific
    WORD   e_res2[10];                  // Reserved words
    LONG   e_lfanew;                    // File address of new exe header
  } IMAGE_DOS_HEADER, *PIMAGE_DOS_HEADER;

MS-DOSとの互換性をとるためのものです。
Windows上でこのファイルを実行した際には、e_magice_lfanewの2つのフィールドのみ使われます。

e_magic
マジックナンバー0x5A4D(MZ)が格納される。

e_lfanew
NT HEADERの位置を示す。


MS-DOS REAL-MODE STUB PROGRUM

MS-DOS HEADERNT HEADERの間に位置します。
デフォルトで付加されるDOSスタブでは、MS-DOS上でこのファイルを実行した際に"This program cannot be run in DOS mode."と表示させます。
サイズは可変長です。


NT HEADER

NT HEADERS


_IMAGE_NT_HEADERS

typedef struct _IMAGE_NT_HEADERS {
    DWORD Signature;
    IMAGE_FILE_HEADER FileHeader;
    IMAGE_OPTIONAL_HEADER32 OptionalHeader;
} IMAGE_NT_HEADERS32, *PIMAGE_NT_HEADERS32;
#ifdef _WIN64
typedef IMAGE_NT_HEADERS64                  IMAGE_NT_HEADERS;
typedef PIMAGE_NT_HEADERS64                 PIMAGE_NT_HEADERS;
#else
typedef IMAGE_NT_HEADERS32                  IMAGE_NT_HEADERS;
typedef PIMAGE_NT_HEADERS32                 PIMAGE_NT_HEADERS;
#endif

マジックナンバーとヘッダのまとまりです。
SignatureFileHeaderOptionalHeaderの3つを持っています。

Signature
マジックナンバー0x50450000(PE\0\0)が格納される。
0x50450000でない場合は、別のフォーマットである。

FileHeader
FileHeader(構造体)。

OptionalHeader
OptionalHeader(構造体)。


FILE HEADER


_IMAGE_FILE_HEADER

typedef struct _IMAGE_FILE_HEADER {
    WORD    Machine;
    WORD    NumberOfSections;
    DWORD   TimeDateStamp;
    DWORD   PointerToSymbolTable;
    DWORD   NumberOfSymbols;
    WORD    SizeOfOptionalHeader;
    WORD    Characteristics;
} IMAGE_FILE_HEADER, *PIMAGE_FILE_HEADER;
#define IMAGE_SIZEOF_FILE_HEADER             20

Machine
このファイルがどのマシンを対象として作られたものか表す値。

NumberOfSections
セクションの数を示す値。

TimeDateStamp
ファイルのタイムスタンプ。

PointerToSymbolTable
NumberOfSymbols
PEファイルはシンボルテーブルを含まないので0がセットされる。

SizeOfOptionalHeader
OptionalHeaderのサイズ。

Characteristics
ファイルの特性を示すフラグの論理和。


OPTIONAL HEADER


_IMAGE_OPTIONAL_HEADER

typedef struct _IMAGE_OPTIONAL_HEADER {
    //
    // Standard fields.
    //
    WORD    Magic;
    BYTE    MajorLinkerVersion;
    BYTE    MinorLinkerVersion;
    DWORD   SizeOfCode;
    DWORD   SizeOfInitializedData;
    DWORD   SizeOfUninitializedData;
    DWORD   AddressOfEntryPoint;
    DWORD   BaseOfCode;
    DWORD   BaseOfData;
    //
    // NT additional fields.
    //
    DWORD   ImageBase;
    DWORD   SectionAlignment;
    DWORD   FileAlignment;
    WORD    MajorOperatingSystemVersion;
    WORD    MinorOperatingSystemVersion;
    WORD    MajorImageVersion;
    WORD    MinorImageVersion;
    WORD    MajorSubsystemVersion;
    WORD    MinorSubsystemVersion;
    DWORD   Win32VersionValue;
    DWORD   SizeOfImage;
    DWORD   SizeOfHeaders;
    DWORD   CheckSum;
    WORD    Subsystem;
    WORD    DllCharacteristics;
    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;

COFFでは不要なことからOPTIONALという名前がついたそうです。
しかしPEでは必須となります。
サイズは可変長です。

Magic
マジックナンバー0x10b(PE32)、0x20b(PE+)、0x107(ROM)のいずれかの値をとる。
通常は32bit用であることを示す0x10bである。
0x20bの場合は64bit用のファイルとなり、構造やフィールドのサイズが異なる。

MajorLinkerVersion
MinorLinkerVersion
リンカのバージョン情報。

SizeOfCode
コード領域のサイズ。

SizeOfInitializedData
文字列リテラルなどの値が確定しているデータ領域のサイズ。

SizeOfUninitializedData
グローバル変数などの値が確定していないデータ領域のサイズ。

AddressOfEntryPoint
エントリポイントのRVA。
実際のエントリポイントのアドレスは後述のImageBaseAddressOfEntryPointを加算することで得られる。

BaseOfCode
コード領域のベースアドレス。
RVAで記述されている。

BaseOfData
グローバルアドレスなどの値が確定していないデータ領域のベースアドレス。
RVAで記述されている。

ImageBase
ファイルがロードされるアドレス。
Microsoft製の開発環境ではデフォルトでEXEファイルは0x00400000、DLLファイルは0x10000000と設定されている。
リンカオプション等で変更可能。
ロードに失敗した場合、再配置が行われる。

SectionAlignment
各セクションがロードされる際のアラインメント。
各セクションの開始アドレスはSectionAlignmentの倍数になる。
次のセクションの開始アドレスまでの余りの領域はNULLで埋められる。

FileAlignment
ファイル内で各セクションが配置される際のアラインメント。
各セクションの開始アドレスはFileAlignmentの倍数になる。
次のセクションの開始アドレスまでの余りの領域はNULLで埋められる。

MajorOperatingSystemVersion
MinorOperatingSystemVersion
対象とされるOSのバージョン情報。

MajorImageVersion
MinorImageVersion
このファイルのバージョン情報。

MajorSubsystemVersion
MinorSubsystemVersion
サブシステムのバージョン情報。

Recerved1
使用しない。

SizeOfImage
プログラムをロードする際に必要なサイズ。
セクションが必要とするバイト数をページ境界、SectionAlignment境界に揃えた合計から算出される。
ロードされる前の実行ファイルのサイズとは異なるので注意。

SizeOfHeader
FILE HEADERMS-DOS HEADERNT HEADERSECTION TABLESを含むヘッダのサイズ。
FileAlignmentの倍数でなければならない。

CheckSum
ロード時にファイルを確認するのに使われるチェックサム。
値はリンカによってセット・確認されている。
アルゴリズムはIMAGEHELP.DLLにて確認できる。

Subsystem
ファイルのターゲットとなるサブシステム。
IMAGE_SUBSYSTEM_NATIVE(1)ならデバイスドライバ、
IMAGE_SUBSYSTEM_WINDOWS_GUI(2)ならGUI、
IMAGE_SUBSYSTEM_WINDOWS_CUI(3)ならCUIと判断できる。

DllCharacteristics
DLLの特性を示すフラグの論理和。

SizeOfStackReserve
スタック領域として予約されるサイズ。

SizeOfStackCommit
スタック領域としてコミットされるサイズ。

SizeOfHeapReserve
ヒープ領域として予約されるサイズ。

SizeOfHeapCommit
ヒープ領域としてコミットされるサイズ。

LoaderFlag
廃止。

NumberOfRvaAndSize
IMAGE_DATA_DIRECTRYの数。
通常はIMAGE_NUMBEROF_DIRECTRY_ENTRIES(16)。

DataDirectory
IMAGE_DATA_DIRECTORY構造体の配列。
構造体は各エントリがある位置のRVAとサイズで構成されている。
配列の長さは16で、DataDirectory[0]にはエクスポートテーブル、DataDirectory[1]にはインポートテーブルなど、インデックスによって保持されるエントリの意味が決まっている。


_IMAGE_DATA_DIRECTORY

typedef struct _IMAGE_DATA_DIRECTORY {
    DWORD   VirtualAddress;
    DWORD   Size;
} IMAGE_DATA_DIRECTORY, *PIMAGE_DATA_DIRECTORY;


SECTION TABLE
SECTION DATA

SECTION TABLE
SECTION DATA


_IMAGE_SECTION_HEADER

#define IMAGE_SIZEOF_SHORT_NAME              8
typedef struct _IMAGE_SECTION_HEADER {
    BYTE    Name[IMAGE_SIZEOF_SHORT_NAME];
    union {
            DWORD   PhysicalAddress;
            DWORD   VirtualSize;
    } Misc;
    DWORD   VirtualAddress;
    DWORD   SizeOfRawData;
    DWORD   PointerToRawData;
    DWORD   PointerToRelocations;
    DWORD   PointerToLinenumbers;
    WORD    NumberOfRelocations;
    WORD    NumberOfLinenumbers;
    DWORD   Characteristics;
} IMAGE_SECTION_HEADER, *PIMAGE_SECTION_HEADER;
#define IMAGE_SIZEOF_SECTION_HEADER          40

セクションテーブルはセクションヘッダの配列です。
セクションヘッダにはセクションの特性やデータのオフセットなどの情報が収められています。
また、PEでは同じ名前や特性のセクションは一つにまとめられています。
セクションヘッダのPointerToRawDataSizeOfRawDataに値が入っている場合のみセクションデータが存在します。

Name
セクション名。

VirtualSize
セクションのサイズ。

VirtualAddress
セクションのRVA。

PointerToRawData
セクションが初期値の場合、ファイル内オフセットが格納されている。
み初期化変数などデータがないセクションでは0が格納される。

PointerToRelocations
PEファイルでは使用しない。

PointerToLinenumbers
行番号へのオフセット。
古い形式のデバック情報であるため、通常は0が格納される。
clに/Z7オプションを付けることで生成される。

NumberOfRelocations
再配置情報の数。
PEファイルでは0が格納される。

NumberOfLinenumbers
行番号情報の数。

Characteristics
セクションの特性を表すフラグの論理和。


参考

34
30
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
34
30