[PATCH 10/12] gpu: nova-core: mm: Add GpuMm centralized memory manager
Eliot Courtney <[email protected]> Wed, 05 Aug 2026 14:44:57 +0900
| Newsgroups | gmane.linux.kernel,gmane.linux.kernel.rust,gmane.comp.video.dri.devel,gmane.linux.documentation |
|---|---|
| Message-ID | <[email protected]> |
From: Joel Fernandes <[email protected]> Introduce GpuMm as the centralized GPU memory manager. At this point in the series, GpuMm only owns the PRAMIN window for direct VRAM access; the buddy allocator and TLB manager are added later when those backing types become available. This provides a clean ownership model where GpuMm provides accessor methods for its components that can be used for memory management operations, and lets follow-on patches (such as the PRAMIN aperture self-tests) reference `pramin_mut()` cleanly. Signed-off-by: Joel Fernandes <[email protected]> [ecourtney: squash the total VRAM end patch, drop its dev_info print] [ecourtney: take the maximum FB limit before adding one, fail with EINVAL] [ecourtney: rebase for the Bar0 lifetime and ownership changes, drop Arcs] [ecourtney: source the chipset through gsp_resources] [ecourtney: build the VRAM region in new(), pramin() becomes pramin_mut()] [ecourtney: declare mm before gsp_resources, doc wording cleanups] Signed-off-by: Eliot Courtney <[email protected]> --- drivers/gpu/nova-core/gpu.rs | 18 +++++++++++++++- drivers/gpu/nova-core/gsp/commands.rs | 4 ++++ drivers/gpu/nova-core/gsp/fw/commands.rs | 5 +++++ drivers/gpu/nova-core/mm.rs | 35 ++++++++++++++++++++++++++++++++ 4 files changed, 61 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/nova-core/gpu.rs b/drivers/gpu/nova-core/gpu.rs index 42a4cd7971fa..e29e07488e78 100644 --- a/drivers/gpu/nova-core/gpu.rs +++ b/drivers/gpu/nova-core/gpu.rs @@ -29,6 +29,10 @@ Gsp, GspBootContext, // }, + mm::{ + GpuMm, + VramAddress, // + }, regs, vgpu::VgpuManager, // }; @@ -283,6 +287,11 @@ pub(crate) struct Gpu<'gpu> { spec: Spec, /// Static GPU information as provided by the GSP. gsp_static_info: GetGspStaticInfoReply, + /// GPU memory manager owning memory management resources. + /// + /// Must be kept declared *before* `gsp_resources`, so that its components are dropped while + /// the GSP is still operational. + mm: GpuMm<'gpu>, /// GSP and its resources. #[pin] gsp_resources: GspResources<'gpu>, @@ -410,7 +419,14 @@ pub(crate) fn new( } info - } + }, + + // Create GPU memory manager owning memory management resources. + mm: GpuMm::new( + bar, + gsp_resources.spec.chipset, + VramAddress::from_raw(gsp_static_info.total_fb_end), + )?, }) } } diff --git a/drivers/gpu/nova-core/gsp/commands.rs b/drivers/gpu/nova-core/gsp/commands.rs index ffc25fd8c47b..eea1c9ed4684 100644 --- a/drivers/gpu/nova-core/gsp/commands.rs +++ b/drivers/gpu/nova-core/gsp/commands.rs @@ -216,6 +216,8 @@ pub(crate) struct GetGspStaticInfoReply { gpu_name: [u8; 64], /// Usable FB (VRAM) regions for driver memory allocation. pub(crate) usable_fb_regions: KVec<Range<u64>>, + /// Exclusive end of the FB physical address space. + pub(crate) total_fb_end: u64, } impl MessageFromGsp for GetGspStaticInfoReply { @@ -231,10 +233,12 @@ fn read( for region in msg.usable_fb_regions() { usable_fb_regions.push(region, GFP_KERNEL)?; } + let total_fb_end = msg.total_fb_end().ok_or(EINVAL)?; Ok(GetGspStaticInfoReply { gpu_name: msg.gpu_name_str(), usable_fb_regions, + total_fb_end, }) } } diff --git a/drivers/gpu/nova-core/gsp/fw/commands.rs b/drivers/gpu/nova-core/gsp/fw/commands.rs index 6dc31d1bf5ae..6e85442a4b13 100644 --- a/drivers/gpu/nova-core/gsp/fw/commands.rs +++ b/drivers/gpu/nova-core/gsp/fw/commands.rs @@ -165,6 +165,11 @@ pub(crate) fn usable_fb_regions(&self) -> impl Iterator<Item = Range<u64>> + '_ } }) } + + /// Computes the exclusive end of the FB physical address space. + pub(crate) fn total_fb_end(&self) -> Option<u64> { + self.fb_regions().map(|reg| reg.limit).max()?.checked_add(1) + } } // SAFETY: Padding is explicit and will not contain uninitialized data. diff --git a/drivers/gpu/nova-core/mm.rs b/drivers/gpu/nova-core/mm.rs index ef5b1cad56c3..58dce211a337 100644 --- a/drivers/gpu/nova-core/mm.rs +++ b/drivers/gpu/nova-core/mm.rs @@ -19,10 +19,45 @@ }, }; +use crate::{ + driver::Bar0, + gpu::Chipset, // +}; + mod hal; mod pramin; mod regs; +/// GPU Memory Manager - owns all core MM components. +/// +/// Provides centralized ownership of memory management resources: +/// - [`pramin::Pramin`] for direct VRAM access. +pub(crate) struct GpuMm<'gpu> { + pramin: pramin::Pramin<'gpu>, +} + +impl<'gpu> GpuMm<'gpu> { + /// Creates the GPU memory manager. + pub(crate) fn new( + bar: Bar0<'gpu>, + chipset: Chipset, + total_fb_end: VramAddress, + ) -> Result<Self> { + // PRAMIN covers all physical VRAM (including GSP-reserved areas + // above the usable region, e.g. the BAR1 page directory). + let vram_region = VramAddress::ZERO..total_fb_end; + + Ok(Self { + pramin: pramin::Pramin::new(bar, chipset, vram_region)?, + }) + } + + /// Access the [`pramin::Pramin`]. + fn pramin_mut(&mut self) -> &mut pramin::Pramin<'gpu> { + &mut self.pramin + } +} + /// Physical VRAM address in GPU video memory. #[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord)] #[repr(transparent)] -- 2.55.0