summaryrefslogtreecommitdiff
path: root/drivers/gpu/nova-core/gpu.rs
diff options
context:
space:
mode:
authorJohn Hubbard <jhubbard@nvidia.com>2025-11-14 17:09:21 -0800
committerAlexandre Courbot <acourbot@nvidia.com>2025-11-15 23:11:27 +0900
commit0ecc08e2c450d9d3aebfc0c093db444d77557469 (patch)
treebd5eff6dbf99071e4507a750669956e208fffa8e /drivers/gpu/nova-core/gpu.rs
parent4d980333a66341a764a64a29df668aac1cd6ec41 (diff)
gpu: nova-core: add boot42 support for next-gen GPUs
NVIDIA GPUs are moving away from using NV_PMC_BOOT_0 to contain architecture and revision details, and will instead use NV_PMC_BOOT_42 in the future. NV_PMC_BOOT_0 will contain a specific set of values that will mean "go read NV_PMC_BOOT_42 instead". Change the selection logic in Nova so that it will claim Turing and later GPUs. This will work for the foreseeable future, without any further code changes here, because all NVIDIA GPUs are considered, from the oldest supported on Linux (NV04), through the future GPUs. Add some comment documentation to explain, chronologically, how boot0 and boot42 change with the GPU eras, and how that affects the selection logic. Cc: Alexandre Courbot <acourbot@nvidia.com> Cc: Danilo Krummrich <dakr@kernel.org> Cc: Timur Tabi <ttabi@nvidia.com> Reviewed-by: Joel Fernandes <joelagnelf@nvidia.com> Signed-off-by: John Hubbard <jhubbard@nvidia.com> [acourbot@nvidia.com: remove unneeded `From<BOOT_0> for Revision` implementation.] Signed-off-by: Alexandre Courbot <acourbot@nvidia.com> Message-ID: <20251115010923.1192144-4-jhubbard@nvidia.com>
Diffstat (limited to 'drivers/gpu/nova-core/gpu.rs')
-rw-r--r--drivers/gpu/nova-core/gpu.rs36
1 files changed, 29 insertions, 7 deletions
diff --git a/drivers/gpu/nova-core/gpu.rs b/drivers/gpu/nova-core/gpu.rs
index 88a6d7af9f37..3e3375f8fe99 100644
--- a/drivers/gpu/nova-core/gpu.rs
+++ b/drivers/gpu/nova-core/gpu.rs
@@ -160,8 +160,8 @@ pub(crate) struct Revision {
minor: u8,
}
-impl From<regs::NV_PMC_BOOT_0> for Revision {
- fn from(boot0: regs::NV_PMC_BOOT_0) -> Self {
+impl From<regs::NV_PMC_BOOT_42> for Revision {
+ fn from(boot0: regs::NV_PMC_BOOT_42) -> Self {
Self {
major: boot0.major_revision(),
minor: boot0.minor_revision(),
@@ -183,19 +183,41 @@ pub(crate) struct Spec {
impl Spec {
fn new(bar: &Bar0) -> Result<Spec> {
+ // Some brief notes about boot0 and boot42, in chronological order:
+ //
+ // NV04 through NV50:
+ //
+ // Not supported by Nova. boot0 is necessary and sufficient to identify these GPUs.
+ // boot42 may not even exist on some of these GPUs.
+ //
+ // Fermi through Volta:
+ //
+ // Not supported by Nova. boot0 is still sufficient to identify these GPUs, but boot42
+ // is also guaranteed to be both present and accurate.
+ //
+ // Turing and later:
+ //
+ // Supported by Nova. Identified by first checking boot0 to ensure that the GPU is not
+ // from an earlier (pre-Fermi) era, and then using boot42 to precisely identify the GPU.
+ // Somewhere in the Rubin timeframe, boot0 will no longer have space to add new GPU IDs.
+
let boot0 = regs::NV_PMC_BOOT_0::read(bar);
- Spec::try_from(boot0)
+ if boot0.is_older_than_fermi() {
+ return Err(ENODEV);
+ }
+
+ Spec::try_from(regs::NV_PMC_BOOT_42::read(bar))
}
}
-impl TryFrom<regs::NV_PMC_BOOT_0> for Spec {
+impl TryFrom<regs::NV_PMC_BOOT_42> for Spec {
type Error = Error;
- fn try_from(boot0: regs::NV_PMC_BOOT_0) -> Result<Self> {
+ fn try_from(boot42: regs::NV_PMC_BOOT_42) -> Result<Self> {
Ok(Self {
- chipset: boot0.chipset()?,
- revision: boot0.into(),
+ chipset: boot42.chipset()?,
+ revision: boot42.into(),
})
}
}