[PATCH v2 1/7] nova-core: doc: Add code comments related to devinit

Joel Fernandes
2025-05-03T04:08:19Z

Add several code comments to reduce acronym soup and explain how devinit magic
and bootflow works before driver loads. These are essential for debug and
development of the nova driver.

Signed-off-by: Joel Fernandes <joelagnelf at nvidia.com>
---
 drivers/gpu/nova-core/devinit.rs | 34 ++++++++++++++++++++++++++++----
 drivers/gpu/nova-core/regs.rs    | 16 +++++++++++++--
 2 files changed, 44 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/nova-core/devinit.rs b/drivers/gpu/nova-core/devinit.rs
index 31a313a0652c..21fc9b96d498 100644
--- a/drivers/gpu/nova-core/devinit.rs
+++ b/drivers/gpu/nova-core/devinit.rs
@@ -1,6 +1,19 @@
 // SPDX-License-Identifier: GPL-2.0

 //! Methods for device initialization.
+//!
+//! A clarification about devinit terminology:
+//! devinit is a sequence of register read/writes after reset that performs
tasks
+//! such as:
+//! 1. Programming VRAM memory controller timings.
+//! 2. Power sequencing.
+//! 3. Clock and PLL configuration.
+//! 4. Thermal management.
+//!
+//! devinit itself is a 'script' which is interpreted by the PMU
microcontroller of
+//! the GPU by an interpreter program.
+//!
+//! Note that the devinit sequence also needs to run during suspend/resume at
runtime.

 use kernel::bindings;
 use kernel::devres::Devres;
@@ -9,15 +22,28 @@
 use crate::driver::Bar0;
 use crate::regs;

-/// Wait for devinit FW completion.
+/// Wait for gfw (GPU firmware) boot completion signal (GFW_BOOT).
 ///
-/// Upon reset, the GPU runs some firmware code to setup its core parameters.
Most of the GPU is
-/// considered unusable until this step is completed, so it must be waited on
very early during
-/// driver initialization.
+/// Upon reset, several microcontrollers (such as PMU, SEC2, GSP etc) on the
GPU run some GPU
+/// firmware (gfw) code to setup its core parameters. Most of the GPU is
considered unusable until
+/// this step is completed, so it must be waited on very early during driver
initialization.
+///
+/// The GPU firmware (gfw) code includes several components that execute before
the driver loads.
+/// These components are located in the VBIOS ROM and are executed in a
sequence on these different
+/// microcontrollers. The devinit sequence itself runs on the PMU, and the
FWSEC runs on the GSP.
+///
+/// This function specifically waits for a signal indicating core
initialization is complete before
+/// which not much can be done. This signal is setup by the FWSEC running on
the GSP in Heavy-secured
+/// mode.
 pub(crate) fn wait_gfw_boot_completion(bar: &Devres<Bar0>) ->
Result<()> {
     let mut timeout = 2000;

     loop {
+        // Before accessing the completion status in
[`crate::regs::NV_PGC6_AON_SECURE_SCRATCH_GROUP_05`],
+        // we must first check
[`crate::regs::NV_PGC6_AON_SECURE_SCRATCH_GROUP_05_PRIV_LEVEL_MASK`].
+        // This is because the register is accessible only after secure
firmware (FWSEC) lowers the
+        // privilege level to allow CPU (LS/Light-secured) access. We can only
safely read the status
+        // register from CPU (LS/Light-secured) once mask indicates privilege
level has been lowered.
         let gfw_booted              with_bar!(
                 bar,
diff --git a/drivers/gpu/nova-core/regs.rs b/drivers/gpu/nova-core/regs.rs
index 3acec36f2d57..a2b506883654 100644
--- a/drivers/gpu/nova-core/regs.rs
+++ b/drivers/gpu/nova-core/regs.rs
@@ -74,8 +74,20 @@ pub(crate) fn chipset(self) -> Result<Chipset,
Error> {
     31:4    hi_val as u32;
 });

-/* PGC6 */
-
+/*
+ * PGC6 register space.
+ *
+ * GC6 is a GPU low-power state where VRAM is in self-refresh and the GPU
+ * is powered down (except for power rails needed to keep self-refresh working
+ * and important registers and hardware blocks).
+ *
+ * These scratch registers are "always-on" even in a low-power state
and have a
+ * designated group number.
+ */
+
+// Privilege level mask register.
+// It dictates whether the host CPU has privilege to access the
+// PGC6_AON_SECURE_SCRATCH_GROUP_05 register (which it needs to read GFW_BOOT).
 register!(NV_PGC6_AON_SECURE_SCRATCH_GROUP_05_PRIV_LEVEL_MASK @ 0x00118128 {
     0:0     read_protection_level0 as bool;
 });
--
2.43.0