Skip to content

Enable display-aware static BAR1 with full coverage - #36

Open
xycjscs wants to merge 1 commit into
aikitoria:610.43.03-p2pfrom
xycjscs:fix/display-aware-static-bar1-full-coverage
Open

Enable display-aware static BAR1 with full coverage#36
xycjscs wants to merge 1 commit into
aikitoria:610.43.03-p2pfrom
xycjscs:fix/display-aware-static-bar1-full-coverage

Conversation

@xycjscs

@xycjscs xycjscs commented Aug 5, 2026

Copy link
Copy Markdown

Summary

Enable static BAR1 under the existing AUTO policy when the runtime BAR1 geometry can fully cover
the aligned client-visible framebuffer after console and mailbox reservations.

This fixes BAR1-based PCIe P2P on display-attached GPUs without globally forcing static BAR1 and
without enabling partial framebuffer coverage.

The change is intentionally minimal:

  • retain the existing AUTO default;

  • retain explicit registry override precedence;

  • apply the new calculation only to devices that already advertise BAR1 P2P by default;

  • require complete runtime coverage of the aligned client-visible framebuffer;

  • continue reserving capacity for UserD, MMIO, doorbells, console mappings, mailboxes, and
    alignment;

  • modify only kbusIsStaticBar1Supported_TU102().

Problem

The issue was reproduced on this system:

  • 3× NVIDIA GeForce RTX 5090 (GB202)
  • 32 GiB BAR1 per GPU
  • 256 GiB system RAM
  • GPU0 attached to a display and used by Xorg/GNOME
  • GPU1 and GPU2 used as headless compute GPUs
  • Linux 7.0.0-28-generic
  • NVIDIA driver 610.43.03
  • IOMMU passthrough enabled with iommu=pt

P2P worked between all three GPUs before the system memory upgrade.

After upgrading to 256 GiB RAM and the resulting platform PCIe/MMIO resource-layout change, P2P
remained functional between the two headless GPUs but failed for every pair involving the display-
attached GPU:

  • GPU0 ↔ GPU1: broken
  • GPU0 ↔ GPU2: broken
  • GPU1 ↔ GPU2: working

CUDA still reported peer-access capability for every pair, so the connectivity matrix did not
reveal the failure.

Observed failure

p2pBandwidthLatencyTest reported implausible values for GPU pairs involving GPU0:

Pair Reported result
━━━━━━━━━━━━━ ━━━━━━━━━━━━━━━━━━━━━━━━━
GPU0 ↔ GPU1 approximately 128 GB/s
───────────── ─────────────────────────
GPU0 ↔ GPU2 approximately 128 GB/s
───────────── ─────────────────────────
GPU1 ↔ GPU2 approximately 14.3 GB/s

The approximately 128 GB/s values were not real PCIe bandwidth. The affected P2P mappings did not
reference valid peer framebuffer addresses.

The kernel also emitted repeated assertions:

Assertion failed: ((base & RM_PAGE_MASK) == 0) @ kern_bus.c:298
Assertion failed: remoteWMBoxLocalAddr != ~0ULL @ kern_bus_gm200.c:89

Runtime diagnostics showed that static BAR1 was enabled on both headless GPUs but disabled on the
display GPU:

GPU0 static BAR1: disabled
GPU1 static BAR1: enabled
GPU2 static BAR1: enabled

Pairs involving GPU0 consequently did not use the valid BAR1 P2P path.

Root cause

The existing AUTO calculation begins with the complete framebuffer address-space size:

requiredAutoBar1Size = fbSizeAligned;

It then adds capacity for:

  • UserD mappings for all channels;
  • MMIO mappings;
  • doorbells;
  • console reservations;
  • mailbox reservations;
  • 512 MiB static BAR1 alignment.

This is conservative because the static BAR1 mapping created by
kbusEnableStaticBar1Mapping_TU102() does not map the complete framebuffer address space. It maps
only the aligned client-visible framebuffer returned by:

memmgrGetClientFbAddrSpaceSize()

On the affected display GPU, the relevant runtime geometry was approximately:

BAR1 aperture: 32 GiB
Static BAR1 offset: 0x20000000 (512 MiB)
Aligned client FB mapping: 0x7d9400000

The aligned client framebuffer fits completely after the display/console offset:

staticBar1Offset + clientFbSizeAligned < bar1VASizeAligned

However, the original AUTO estimate based on the complete framebuffer address space rejected the
configuration before the actual client-visible geometry could be used.

Implementation

The revised AUTO policy calculates:

clientFbSizeAligned =
RM_ALIGN_DOWN(memmgrGetClientFbAddrSpaceSize(...),
RM_PAGE_SIZE_2M);

staticBar1Offset =
NV_ALIGN_UP(consoleSize + mailboxSize,
RM_PAGE_SIZE_512M);

maxStaticMapSize =
bar1VASizeAligned - staticBar1Offset;

Display-aware sizing is selected only when:

PDB_PROP_KBUS_SUPPORT_BAR1_P2P_BY_DEFAULT &&
clientFbSizeAligned != 0 &&
maxStaticMapSize >= clientFbSizeAligned

This requires complete coverage. The change does not permit a static mapping that covers only part
of the client-visible framebuffer.

When complete coverage is available, the AUTO calculation uses the same aligned client-visible
framebuffer size that the mapping function will actually map.

Dynamic BAR1 requirements remain part of the capacity calculation:

dynamicBar1Size = UserD + MMIO + doorbell

The space between the console/mailbox mappings and the 512 MiB-aligned static mapping is treated
as usable alignment padding. Dynamic mappings can consume that gap; only the amount exceeding the
gap adds to the total required aperture size.

If full runtime coverage is unavailable, the device continues to use the original conservative
AUTO calculation.

Why not globally force static BAR1?

An earlier fix changed the default policy from AUTO to ENABLE. That restored P2P on this machine,
but the forced path intentionally bypasses parts of AUTO's capacity policy.

Changing the global default could create BAR1 pressure on other device and property
configurations.

This implementation instead:

  • preserves the global AUTO policy;
  • preserves existing registry behavior;
  • retains dynamic BAR1 capacity checks;
  • enables display-aware placement only when runtime geometry proves complete framebuffer coverage;
  • avoids changing behavior for unsupported or partial-coverage configurations.

Scope

This is a minimal extraction of the complete-coverage policy discussed in #35.

It intentionally does not include:

  • the GB206 partial-window exception;
  • partial static BAR1 mappings;
  • static/dynamic boundary behavior changes;
  • UVM coherence changes;
  • PCI P2PDMA registration changes;
  • hugetlb changes;
  • IOVA lifetime changes;
  • external BAR1 PTE changes;
  • mailbox transaction and rollback changes.

Those changes may be useful independently, but they are not required to fix the fully covered
GB202 display-attached configuration reproduced here.

Validation

The complete NVIDIA kernel-module build passed.

The new AUTO policy was then installed and tested after reboot on the original three-GPU RTX 5090
system.

Measured unidirectional P2P write bandwidth:

Pair Before After
━━━━━━━━━━━━━ ━━━━━━━━━━━━━━━━━━━ ━━━━━━━━━━━━
GPU0 → GPU1 invalid ~128 GB/s 14.30 GB/s
───────────── ─────────────────── ────────────
GPU1 → GPU0 invalid ~128 GB/s 14.33 GB/s
───────────── ─────────────────── ────────────
GPU0 → GPU2 invalid ~128 GB/s 28.53 GB/s
───────────── ─────────────────── ────────────
GPU2 → GPU0 invalid ~122 GB/s 28.07 GB/s
───────────── ─────────────────── ────────────
GPU1 → GPU2 14.33 GB/s 14.33 GB/s
───────────── ─────────────────── ────────────
GPU2 → GPU1 14.32 GB/s 14.32 GB/s

Measured bidirectional P2P bandwidth:

Pair Result
━━━━━━━━━━━━━ ━━━━━━━━━━━━━━━━━━━━━━━━━
GPU0 ↔ GPU1 approximately 28.2 GB/s
───────────── ─────────────────────────
GPU0 ↔ GPU2 approximately 56 GB/s
───────────── ─────────────────────────
GPU1 ↔ GPU2 approximately 28.3 GB/s

The different bandwidths are consistent with the motherboard PCIe topology.

Peer-write GPU latency remained below 0.5 μs.

Post-reboot validation confirmed:

  • all three GPU pairs support real peer communication;
  • the display-attached GPU uses a valid static BAR1 mapping under AUTO;
  • no approximately 128 GB/s invalid results remain;
  • no mailbox assertions occur;
  • no NVIDIA Xids occur;
  • no IOMMU or PCIe AER errors occur;
  • the existing headless GPU0-independent P2P path remains unchanged.

Relationship to other PRs

The RTX 5090 results provide GB202 hardware validation for the full-coverage runtime policy.

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.

1 participant