Geoff Chappell - Software Analyst
The public symbol file NTKRPAMP.PDB for the original release of Windows 10 tells that the kernel is built with the CPER.H header at
d:\th.public.fre\sdk\inc
and draws from it the type definitions that are tablulated below.
Nowadays, CPER.H is among the headers in the Software Development Kit (SDK) for Windows 10. It is there in the “um” subdirectory with many other headers that are intended only for user-mode programming. It dates from Windows 7, again in the SDK. CPER.H seems never to have been supplied with a Windows Driver Kit (WDK) except in bundles with the SDK. All its significant content is anyway duplicated in NTDDK.H and in NTOSP.H, but no sign is known of how this happens.
NTDDK.H is, of course, a standard header for kernel-mode programming, and NTOSP.H is similar but for Microsoft’s private use (notwithstanding its disclosure in two early editions of the WDK for Windows 10). The kernel’s own source code does not #include either NTDDK.H or NTOSP.H. Of the definitions that these headers share with CPER.H, those that the kernel’s public symbols files also report for the kernel are there from including CPER.H.
Since CPER.H is published, it is readily seen that the user-defined types that the kernel’s public symbol files attribute to CPER.H are not all that are defined in CPER.H. Indeed, they are barely a quarter. In the table below, the line numbers on the left are from CPER.H as supplied with the SDK for the original Windows 10. Line numbers for types that don’t show in the public symbols are in parentheses. The line numbers on the right are from the NTDDK.H and NTOSP.H in the contemporaneous WDK.
Line Number | Type | NTDDK.H | NTOSP.H |
---|---|---|---|
134 | union _WHEA_REVISION | 14688 | 49605 |
142 | enum _WHEA_ERROR_SEVERITY | 14696 | 49613 |
149 | union _WHEA_TIMESTAMP | 14703 | 49620 |
164 | union _WHEA_PERSISTENCE_INFO | 14718 | 49635 |
195 | union _WHEA_ERROR_STATUS | 14749 | 49666 |
213 | union _WHEA_ERROR_RECORD_HEADER_VALIDBITS | 14767 | 49684 |
227 | union _WHEA_ERROR_RECORD_HEADER_FLAGS | 14781 | 49698 |
241 | struct _WHEA_ERROR_RECORD_HEADER | 14795 | 49712 |
296 | union _WHEA_ERROR_RECORD_SECTION_DESCRIPTOR_FLAGS | 14850 | 49767 |
317 | union _WHEA_ERROR_RECORD_SECTION_DESCRIPTOR_VALIDBITS | 14871 | 49788 |
327 | struct _WHEA_ERROR_RECORD_SECTION_DESCRIPTOR | 14881 | 49798 |
367 | struct _WHEA_ERROR_RECORD | 14921 | 49838 |
(406) | union _WHEA_PROCESSOR_FAMILY_INFO | 14960 | 49877 |
(421) | union _WHEA_PROCESSOR_GENERIC_ERROR_SECTION_VALIDBITS | 14975 | 49892 |
(442) | struct _WHEA_PROCESSOR_GENERIC_ERROR_SECTION | 14996 | 49913 |
(516) | union _WHEA_XPF_CACHE_CHECK | 15070 | 49987 |
(558) | union _WHEA_XPF_TLB_CHECK | 15112 | 50029 |
(609) | union _WHEA_XPF_BUS_CHECK | 15163 | 50080 |
(651) | union _WHEA_XPF_MS_CHECK | 15205 | 50122 |
(676) | union _WHEA_XPF_PROCINFO_VALIDBITS | 15230 | 50147 |
(688) | struct _WHEA_XPF_PROCINFO | 15242 | 50159 |
(708) | struct _WHEA_X86_REGISTER_STATE | 15262 | 50179 |
(736) | struct _WHEA128A | 15290 | 50207 |
(748) | struct _WHEA_X64_REGISTER_STATE | 15302 | 50219 |
(801) | struct _WHEA_XPF_CONTEXT_INFO | 15355 | 50272 |
(817) | union _WHEA_XPF_PROCESSOR_ERROR_SECTION_VALIDBITS | 15371 | 50288 |
(829) | struct _WHEA_XPF_PROCESSOR_ERROR_SECTION | 15383 | 50300 |
943 | union _WHEA_MEMORY_ERROR_SECTION_VALIDBITS | 15497 | 50414 |
980 | struct _WHEA_MEMORY_ERROR_SECTION | 15534 | 50451 |
(1037) | union _WHEA_PCIEXPRESS_ERROR_SECTION_VALIDBITS | 15591 | 50508 |
(1053) | struct _WHEA_PCIEXPRESS_DEVICE_ID | 15607 | 50524 |
(1067) | union _WHEA_PCIEXPRESS_VERSION | 15621 | 50538 |
(1076) | union _WHEA_PCIEXPRESS_COMMAND_STATUS | 15630 | 50547 |
(1084) | union _WHEA_PCIEXPRESS_BRIDGE_CONTROL_STATUS | 15638 | 50555 |
(1093) | enum _WHEA_PCIEXPRESS_DEVICE_TYPE | 15647 | 50564 |
(1105) | struct _WHEA_PCIEXPRESS_ERROR_SECTION | 15659 | 50576 |
(1156) | union _WHEA_PCIXBUS_ERROR_SECTION_VALIDBITS | 15710 | 50627 |
(1172) | union _WHEA_PCIXBUS_ID | 15726 | 50643 |
(1180) | union _WHEA_PCIXBUS_COMMAND | 15734 | 50651 |
(1189) | struct _WHEA_PCIXBUS_ERROR_SECTION | 15743 | 50660 |
(1228) | union _WHEA_PCIXDEVICE_ERROR_SECTION_VALIDBITS | 15782 | 50669 |
(1241) | struct _WHEA_PCIXDEVICE_ID | 15795 | 50712 |
(1253) | struct WHEA_PCIXDEVICE_REGISTER_PAIR | 15807 | 50724 |
(1258) | struct _WHEA_PCIXDEVICE_ERROR_SECTION | 15812 | 50729 |
(1288) | struct _WHEA_FIRMWARE_ERROR_RECORD_REFERENCE | 15842 | 50759 |
(1314) | union _MCG_STATUS | 15868 | 50785 |
(1325) | union _MCI_STATUS | 15879 | 50796 |
(1343) | enum _WHEA_CPU_VENDOR | 15897 | 50814 |
(1352) | struct _WHEA_XPF_MCA_SECTION | 15906 | 50823 |
(1370) | union _WHEA_NMI_ERROR_SECTION_FLAGS | 15924 | 50841 |
(1378) | struct _WHEA_NMI_ERROR_SECTION | 15932 | 50849 |
For the record, lines 41 to 1384 inclusive of the 1391-line CPER.H are duplicated as lines 14595 to 15938 of NTDDK.H and 49512 to 50855 of NTOSP.H. In both these standard headers, the definitions they share with CPER.H immediately follow those from WHEADEF.H. The difference apparently doesn’t matter but when building the kernel—or, to be precise, when compiling the separate source file ntsym.c for merging type information into the kernel’s public symbols—the CPER.H definitions come first.