xref: /linux/drivers/gpu/nova-core/fb/hal/gh100.rs (revision 570f7e331f5febb30f1384817463c7e42b65ca7d)
1 // SPDX-License-Identifier: GPL-2.0
2 // SPDX-FileCopyrightText: Copyright (c) 2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
3 
4 use kernel::{
5     io::Io,
6     num::Bounded,
7     prelude::*,
8     sizes::SizeConstants, //
9 };
10 
11 use crate::{
12     driver::Bar0,
13     fb::{
14         hal::FbHal,
15         regs, //
16     },
17 };
18 
19 struct Gh100;
20 
21 fn read_sysmem_flush_page_gh100(bar: Bar0<'_>) -> u64 {
22     let lo = u64::from(bar.read(regs::NV_PFB_FBHUB_PCIE_FLUSH_SYSMEM_ADDR_LO).adr());
23     let hi = u64::from(bar.read(regs::NV_PFB_FBHUB_PCIE_FLUSH_SYSMEM_ADDR_HI).adr());
24 
25     (hi << 32) | lo
26 }
27 
28 /// Write the sysmem flush page address through the Hopper FBHUB registers.
29 fn write_sysmem_flush_page_gh100(bar: Bar0<'_>, addr: Bounded<u64, 52>) {
30     // Write HI first. The hardware will trigger the flush on the LO write.
31     bar.write_reg(
32         regs::NV_PFB_FBHUB_PCIE_FLUSH_SYSMEM_ADDR_HI::zeroed()
33             .with_adr(addr.shr::<32, 20>().cast::<u32>()),
34     );
35     bar.write_reg(
36         // CAST: lower 32 bits. Hardware ignores bits 7:0.
37         regs::NV_PFB_FBHUB_PCIE_FLUSH_SYSMEM_ADDR_LO::zeroed().with_adr(*addr as u32),
38     );
39 }
40 
41 impl FbHal for Gh100 {
42     fn read_sysmem_flush_page(&self, bar: Bar0<'_>) -> u64 {
43         read_sysmem_flush_page_gh100(bar)
44     }
45 
46     fn write_sysmem_flush_page(&self, bar: Bar0<'_>, addr: u64) -> Result {
47         let addr = Bounded::<u64, 52>::try_new(addr).ok_or(EINVAL)?;
48 
49         write_sysmem_flush_page_gh100(bar, addr);
50 
51         Ok(())
52     }
53 
54     fn supports_display(&self, bar: Bar0<'_>) -> bool {
55         super::ga100::display_enabled_ga100(bar)
56     }
57 
58     fn vidmem_size(&self, bar: Bar0<'_>) -> u64 {
59         super::ga102::vidmem_size_ga102(bar)
60     }
61 
62     fn pmu_reserved_size(&self) -> u32 {
63         super::tu102::pmu_reserved_size_tu102()
64     }
65 
66     fn non_wpr_heap_size(&self) -> u64 {
67         // Non-WPR heap for Hopper (see Open RM: kgspCalculateFbLayout_GH100).
68         u64::SZ_2M
69     }
70 
71     fn frts_size(&self) -> u64 {
72         super::tu102::frts_size_tu102()
73     }
74 }
75 
76 const GH100: Gh100 = Gh100;
77 pub(super) const GH100_HAL: &dyn FbHal = &GH100;
78