(一)检验PE文件的有效性:检验PE中的关键数据结构是否有效。
(二)我们要验证的重要数据结构就是 PE header。从编程角度看,PE header 实际就是一个 IMAGE_NT_HEADERS 结构。定义如下:
IMAGE_NT_HEADERS STRUCT
Signature dd ?
FileHeader IMAGE_FILE_HEADER <>
OptionalHeader IMAGE_OPTIONAL_HEADER32 <>
IMAGE_NT_HEADERS ENDS
Signature一dword类型,值为50h, 45h, 00h, 00h(PE )。本域为PE标记,我们可以此识别给定文件是否为有效PE文件。
FileHeader 该结构域包含了关于PE文件物理分布的信息,比如节数目、文件执行机器等。
OptionalHeader该结构域包含了关于PE文件逻辑分布的信息,虽然域名有"可选"字样,但实际上本结构总是存在的。
(三)如果IMAGE_NT_HEADERS的signature域值等于"PE ",那么就是有效的PE文件。实际上,为了比较方便,Microsoft已定义了常量IMAGE_NT_SIGNATURE供我们使用。
IMAGE_DOS_SIGNATURE equ 5A4Dh
IMAGE_OS2_SIGNATURE equ 454Eh
IMAGE_OS2_SIGNATURE_LE equ 454Ch
IMAGE_VXD_SIGNATURE equ 454Ch
IMAGE_NT_SIGNATURE equ 4550h
接下来的问题是: 如何定位 PE header? 答案很简单: DOS MZ header 已经包含了指向 PE header 的文件偏移量。DOS MZ header 又定义成结构IMAGE_DOS_HEADER。查询windows.inc,我们知道 IMAGE_DOS_HEADER结构的e_lfanew成员就是指向 PE header 的文件偏移量。
现在将所有步骤总结如下:
- 首先检验文件头部第一个字的值是否等于 IMAGE_DOS_SIGNATURE,是则 DOS MZ header 有效。
- 一旦证明文件的 DOS header 有效后,就可用e_lfanew来定位 PE header 了。
- 比较 PE header 的第一个字的值是否等于IMAGE_NT_SIGNATURE。如果前后两个值都匹配,那我们就认为该文件是一个有效的PE文件。