Skip to content

aarch64: reserve low memory for UEFI device space - #4372

Open
Henry Li (henryli001) wants to merge 1 commit into
microsoft:mainfrom
henryli001:lihl/aarch64-uefi-low-memory-layout
Open

aarch64: reserve low memory for UEFI device space#4372
Henry Li (henryli001) wants to merge 1 commit into
microsoft:mainfrom
henryli001:lihl/aarch64-uefi-low-memory-layout

Conversation

@henryli001

@henryli001 Henry Li (henryli001) commented Sep 3, 2026

Copy link
Copy Markdown

Summary

Give ARM64 UEFI guests a split low/high RAM layout that leaves the device-space region unbacked.

Changes

  • Keep a 32 MiB firmware RAM window at GPA 0.
  • Place the remaining UEFI RAM above 1 GiB.
  • Reserve the intervening range for device space so VFIO mappings do not collide with the GIC MSI reserved IOVA region.
  • Leave direct Linux boot unchanged.

This is the memory-layout portion split out of #4344 for independent review.

Scope

The layout applies to ARM64 UEFI boots and leaves direct Linux boot unchanged.
Within UEFI it is unconditional: backing the device-space gap would reintroduce
the reserved-IOVA collision this layout prevents. A mode can still be added if
a concrete compatibility case requires the legacy contiguous layout.

Validation

  • OPENVMM_GUEST_TARGET=aarch64 cargo check -p openvmm_core
  • cargo test -p openvmm_core --lib worker::memory_layout (25 passed)
  • cargo xtask fmt --only-diffed
  • Booted an Ubuntu 24.04 UEFI guest with 112 vCPUs and four GB200 VFIO devices.

Keep a 32 MiB firmware RAM window at GPA 0 and place the remaining UEFI RAM above 1 GiB. Reserve the intervening range for device space so VFIO mappings do not collide with the GIC MSI reserved IOVA region, while leaving direct Linux boot unchanged.

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Changes recommended

The aarch64 layout selection currently applies to all non-Linux load modes (not just UEFI), which is broader than the stated scope and may unintentionally change IGVM/other boot paths.

Once you've addressed the issues Copilot identified, you can request another Copilot review.

Pull request overview

This PR adjusts the ARM64 guest RAM placement for UEFI boots to keep a small RAM window at GPA 0 while moving the remaining RAM above 1 GiB, leaving the intervening region unbacked so VFIO/iommufd device mappings don’t collide with the host MSI doorbell IOVA reservation.

Changes:

  • Extend the memory layout resolver to support a split RAM layout via a new low_ram_window_size input (low RAM at GPA 0 + bulk RAM above ram_start_address).
  • Update aarch64 VM initialization to request a 32 MiB low RAM window for UEFI while keeping Linux direct boot behavior (bulk RAM above 1 GiB).
  • Add unit tests validating the new low RAM window behavior and that the MSI doorbell range remains unbacked.
File summaries
File Description
openvmm/openvmm_core/src/worker/memory_layout.rs Adds low_ram_window_size support, reserves a low-memory device-space gap, allocates a small RAM prefix at GPA 0, and includes tests for the new layout.
openvmm/openvmm_core/src/worker/dispatch.rs Sets ram_start_address/low_ram_window_size for aarch64 so UEFI gets a 32 MiB low RAM window while RAM otherwise starts at 1 GiB.
Review details
  • Files reviewed: 2/2 changed files
  • Comments generated: 1
  • Review effort level: Lite

💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment on lines +1175 to +1185
let (ram_start_address, low_ram_window_size) = if cfg!(guest_arch = "aarch64") {
let start = 1024 * 1024 * 1024;
let low_window = if matches!(cfg.load_mode, LoadMode::Linux { .. }) {
0
} else {
32 * 1024 * 1024
};
(start, low_window)
} else {
(0, 0)
};
// GPA 0 to reach DXE, so retain a small low window and resume bulk RAM
// at 1 GiB, leaving the MSI doorbell range unbacked.
let (ram_start_address, low_ram_window_size) = if cfg!(guest_arch = "aarch64") {
let start = 1024 * 1024 * 1024;

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we will want this to be configurable to support different allocation modes for UEFI. Or do we think it's reasonable to just do this everywhere on aarch64? John/others thoughts?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants