15.3. UEFI GetMemoryMap() 启动服务函数
启用 EFI 的系统使用 UEFI GetMemoryMap() 启动服务函数将内存资源传达给操作系统加载器。然后,这些资源必须由操作系统加载器传达给 OSPM。
GetMemoryMap 接口仅在启动服务期间可用。在 OSPM 加载后,它不作为运行时服务提供。操作系统或其加载器通过调用 ExitBootServices() 启动从启动服务到运行时服务的转换。调用 ExitBootServices() 后,所有系统内存映射信息都必须从 ACPI 命名空间中的对象派生。
GetMemoryMap() 接口返回一个 UEFI 内存描述符数组。这些内存描述符定义了一个系统内存映射,其中包括所有已安装的 RAM,以及由固件保留的物理内存范围。每个描述符都包含一个类型字段,该字段规定了操作系统应如何处理该物理地址范围。下表定义了从 UEFI 内存类型(参见 UEFI 规范)到 ACPI 地址范围类型 的映射,该映射:
如果平台启动固件在 UEFI 和传统 BIOS 模式下都描述该内存范围,则应遵循此映射;并且
如果 OS 加载器使用 ACPI E820h 系统地址映射表将该信息传递给 OS,则应使用此映射。
表 15.6 UEFI 内存类型及其到 ACPI 地址范围类型的映射
| 类型 | 助记符 | ACPI 地址范围类型 |
|---|---|---|
| 0 | EfiReservedMemoryType | AddressRangeReserved |
| 1 | EfiLoaderCode | AddressRangeMemory |
| 2 | EfiLoaderData | AddressRangeMemory |
| 3 | EfiBootServicesCode | AddressRangeMemory |
| 4 | EfiBootServicesData | AddressRangeMemory |
| 5 | EfiRuntimeServiceCode | AddressRangeReserved |
| 6 | EfiRuntimeServicesData | AddressRangeReserved |
| 7 | EfiConventionalMemory | AddressRangeMemory |
| 8 | EfiUnusableMemory | AddressRangeReserved |
| 9 | EfiACPIReclaimMemory | AddressRangeACPI |
| 10 | EfiACPIMemoryNVS | AddressRangeNVS |
| 11 | EfiMemoryMappedIO | AddressRangeReserved |
| 12 | EfiMemoryMappedIOPort Space | AddressRangeReserved |
| 13 | EfiPalCode | AddressRangeReserved |
| 14 | EfiPersistentMemory | AddressRangePersistentMemory |
| 15 to 0x6FFFFFFF | 保留。 | AddressRangeReserved |
| 0x70000000 to 0x7FFFFFFF | 保留供 OEM 使用 | OS 不应使用供应商定义范围内的内存类型,因为不同供应商之间可能发生冲突。 |
| 0x80000000 to 0xFFFFFFFF | 保留供由操作系统供应商提供的 UEFI OS 加载器使用 | OSV 定义 |
上表适用于支持传统 BIOS 模式和 UEFI 模式的系统固件,以及 OS 加载器。