Rich Header & Manifest¶
Rich header¶
Microsoft's linker writes an undocumented, XOR-masked block between the DOS stub and the PE header, the Rich header. It records each tool (compiler, assembler, linker, import library) that contributed objects, with its product ID, build number and object count.
PPEE decodes it and names the Visual Studio version:
$ ppee-cli --richheader explorer.exe
Rich Header:
CheckSum(XOR key) = D34DFA25
DanS sign = 536E6144 DanS
MD5 = 92C3A2A89B45668A5013AD79762FDAB4
Product ID = 0093 Import, VS2008
Minor Compiler Version = 7809 Build 30729
Count = 00000104
Product ID = 0104 C object, VS2015
Minor Compiler Version = 6B14 Build 27412
Count = 00000020
Windows screenshot: Rich header of a shellcode loader: VS2015-family C, C++, ASM and import objects from two compiler builds
In the GUI each entry is a group of three rows. This shellcode loader (86c6bd80….exe) was built from C++, C and assembler objects by two toolset builds, 33145 and 35721. The pair, with the counts and the MD5 row, is a fingerprint to search for in other samples.
Why it matters:
- Attribution and clustering: samples built on the same machine or toolchain share Rich headers. The MD5 row gives you a searchable fingerprint.
- Tamper detection: a Rich header that lists tools inconsistent with the rest of the file (for example VS2008 objects in a binary whose linker version is 14.x) suggests it was forged or transplanted from another binary.
- Files not linked by Microsoft's toolchain (MinGW, Go, Rust with the GNU toolchain, Delphi) have no Rich header:
"present": false.
Application manifest¶
The RT_MANIFEST resource tells Windows how to run the program. PPEE parses the XML into rows:
| Row | Why it matters |
|---|---|
| RequestedPrivileges → Level | asInvoker, highestAvailable or requireAdministrator (triggers UAC) |
| uiAccess | true lets the app drive higher-integrity UI; it requires a signed binary in a secure location |
| AssemblyIdentity | Name, version, architecture |
| SupportedOS | Windows version GUIDs the app declares |
| dpiAware / dpiAwareness | High-DPI behavior |
| Dependencies | Side-by-side assemblies (Common Controls v6, …) |
A NativeAOT ransomware (d1337711….exe) asks for requireAdministrator, shown in the warning color, and the AppManifest node gets a warning dot. It needs those rights for what its method names say it does, such as deleting shadow copies (see NativeAOT). The identity is Visual Studio's default MyApplication.app, left unchanged.
ppee-cli --json --appmanifest f.exe | jq -r '.appManifest.rows[] | select(.member|test("Level")) | .value'
Related: --richheader · --appmanifest · CI: forbid requireAdministrator
References¶
- Application manifests (Microsoft): every element of the embedded manifest, including requestedExecutionLevel.

