Geoff Chappell - Software Analyst
The NT_IMAGE_INFO structure (formally _NT_IMAGE_INFO) is the type of a variable named NtImageInfo which the Windows kernel exports in the 1703 release of Windows 10 and higher. This variable is statically initialised, such that its contents are meaningful even before the kernel executes. The variable thus provides the boot loader, e.g., WINLOAD.EFI, with information about the kernel that it has just loaded. If only in principle, the NT_IMAGE_INFO might describe capabilities that the loader could adapt to in its preparation for the kernel’s first execution, but the only use the loader yet makes of the information is to decide whether the kernel fits the loader’s expectations well enough that execution can proceed.
At least to the 2004 release of Windows 10, the information in the NT_IMAGE_INFO comprises version numbers and the sizes of important structures that the loader prepares for the kernel’s initialisation. Because these structures are undocumented—not even given C-language definitions in headers from contemporaneous editions of the Windows Driver Kit (WDK)—and the memory that holds them is freed when the kernel completes its initialisation, the suggestion is strong that the boot loader is the only intended importer of the NtImageInfo variable and thus the only intended interpreter of the NT_IMAGE_INFO.
That said, the variable is not discarded and the NT_IMAGE_INFO structure is not without value to kernel-mode software that seeks a programmatic determination of the Windows version. Interfaces exist for obtaining the build number, but this is not readily correlated with the roughly half-yearly updates that Microsoft promotes as significant advances rather than mere updates. From the NT_IMAGE_INFO, they can learn the NTDDI version number from the kernel in contrast to repeatedly asking the RtlIsNtddiVersionAvailable function whether the kernel is at least some particular NTDDI version number.
The NT_IMAGE_INFO is 0x18 bytes in both 32-bit and 64-bit Windows, in all versions that are yet known to have it. The structure is not documented. It is not defined in any header, nor even is it known from public symbols. The structure’s name and the offsets and definitions of its members are instead known from type information in the statically linked library CLFSMGMT.LIB for the 1703 to 1903 releases of Windows 10.
Offset | Definition | Versions |
---|---|---|
0x00 |
ULONG Version; |
1703 and higher |
0x04 |
ULONG OsMajorVersion; |
1703 and higher |
0x08 |
ULONG OsMinorVersion; |
1703 and higher |
0x0C |
ULONG MajorRelease; |
1703 and higher |
0x10 |
ULONG LoaderBlockSize; |
1703 and higher |
0x14 |
ULONG LoaderExtensionSize; |
1703 and higher |
The Version is presumably of the structure. The only value yet observed for any kernel is 0. The OsMajorVersion and OsMinorVersion look to be straightforwardly the major and minor version numbers of Windows, which are notoriously unhelpful for being 10 and 0 in all new releases of Windows for getting on to a decade. What would once upon a time have counted as at least a service pack, if not a minor version, is instead reported as the MajorRelease. This is an NTDDI version number as defined in the SDKDDKVER.H header. This version number starts at 0x0A000003 for the 1703 release. It has been incremented for all but one of the roughly bi-annual updates (the 1909 release being for all practical effect a minor rebuild of the 1903 release). This brings it to 0x0A000008 for the 2004 release, which is the last that is yet studied for this note.
The LoaderBlockSize and LoaderExtensionSize are respectively the sizes in bytes of the LOADER_PARAMETER_BLOCK and LOADER_PARAMETER_EXTENSION.