From fa4433b1649a075543d3e3a610d6be9e3b826cc8 Mon Sep 17 00:00:00 2001 From: Krish Dandiwala Date: Thu, 23 Jul 2026 14:13:45 -0400 Subject: [PATCH 1/2] feat: minimal SMC GB300 support --- src/model/service_root.rs | 15 ++++++++++- src/nvidia_gbx00.rs | 53 +++++++++++++++++++++++++++++++++------ 2 files changed, 59 insertions(+), 9 deletions(-) diff --git a/src/model/service_root.rs b/src/model/service_root.rs index d461f5f5d..999fd6264 100644 --- a/src/model/service_root.rs +++ b/src/model/service_root.rs @@ -114,7 +114,10 @@ impl ServiceRoot { _ => RedfishVendor::NvidiaDpu, }, "wiwynn" => RedfishVendor::NvidiaGBx00, - "supermicro" => RedfishVendor::Supermicro, + "supermicro" => match self.product.as_deref() { + Some("GB NVL") => RedfishVendor::NvidiaGBx00, + _ => RedfishVendor::Supermicro, + }, "lite-on technology corp." => RedfishVendor::LiteOnPowerShelf, "delta" => RedfishVendor::DeltaPowerShelf, _ => RedfishVendor::Unknown, @@ -156,6 +159,16 @@ mod test { assert_eq!(result.vendor().unwrap(), RedfishVendor::NvidiaGBx00); } + #[test] + fn test_supermicro_gb300_service_root() { + let result = ServiceRoot { + vendor: Some("Supermicro".to_string()), + product: Some("GB NVL".to_string()), + ..Default::default() + }; + assert_eq!(result.vendor().unwrap(), RedfishVendor::NvidiaGBx00); + } + #[test] fn test_nvidia_bluefield_service_root() { let result = ServiceRoot { diff --git a/src/nvidia_gbx00.rs b/src/nvidia_gbx00.rs index d2b4126d5..8f55cc560 100644 --- a/src/nvidia_gbx00.rs +++ b/src/nvidia_gbx00.rs @@ -66,6 +66,20 @@ impl Bmc { pub fn new(s: RedfishStandard) -> Result { Ok(Bmc { s }) } + + async fn is_gb300(&self) -> Result { + let systems = self + .s + .get_collection(ODataId::from("/redfish/v1/Systems")) + .await? + .try_get::()?; + Ok(systems.members.iter().any(|system| { + system + .model + .as_deref() + .is_some_and(|model| model.contains("GB300")) + })) + } } #[derive(Copy, Clone)] @@ -521,9 +535,15 @@ impl Redfish for Bmc { >, ) -> crate::RedfishFuture<'a, Result, RedfishError>> { Box::pin(async move { - self.disable_secure_boot().await?; + let is_gb300 = self.is_gb300().await?; - let bios_attrs = self.machine_setup_attrs().await?; + // The Supermicro GB300 SecureBoot resource does not expose + // SecureBootEnable, so there is no supported setting to change. + if !is_gb300 { + self.disable_secure_boot().await?; + } + + let bios_attrs = self.machine_setup_attrs(is_gb300).await?; let mut attrs = HashMap::new(); attrs.extend(bios_attrs); let body = HashMap::from([("Attributes", attrs)]); @@ -1172,6 +1192,11 @@ impl Redfish for Bmc { fn enable_infinite_boot<'a>(&'a self) -> crate::RedfishFuture<'a, Result<(), RedfishError>> { Box::pin(async move { + if self.is_gb300().await? { + return Err(RedfishError::NotSupported( + "Supermicro GB300 does not expose EmbeddedUefiShell".to_string(), + )); + } let attrs: HashMap = HashMap::from([("EmbeddedUefiShell".to_string(), "Disabled".into())]); let body = HashMap::from([("Attributes", attrs)]); @@ -1184,6 +1209,9 @@ impl Redfish for Bmc { &'a self, ) -> crate::RedfishFuture<'a, Result, RedfishError>> { Box::pin(async move { + if self.is_gb300().await? { + return Ok(None); + } let embedded_uefi_shell = self.get_embedded_uefi_shell_status().await?; // Infinite boot is enabled when EmbeddedUefiShell is disabled Ok(Some(embedded_uefi_shell == EnabledDisabled::Disabled)) @@ -1362,7 +1390,8 @@ impl Bmc { } let bios = self.s.bios_attributes().await?; - let expected_attrs = self.machine_setup_attrs().await?; + let is_gb300 = self.is_gb300().await?; + let expected_attrs = self.machine_setup_attrs(is_gb300).await?; for (key, expected) in expected_attrs { let Some(actual) = bios.get(&key) else { diffs.push(MachineSetupDiff { @@ -1491,14 +1520,22 @@ impl Bmc { Ok(log_entries) } - async fn machine_setup_attrs(&self) -> Result, RedfishError> { + async fn machine_setup_attrs( + &self, + is_gb300: bool, + ) -> Result, RedfishError> { let mut bios_attrs: Vec<(String, serde_json::Value)> = vec![]; - // Enabled TPM - bios_attrs.push(("TPM".into(), "Enabled".into())); + if is_gb300 { + // This platform exposes the TPM through the AMI BIOS name. + bios_attrs.push(("SecurityDeviceSupport".into(), "Enabled".into())); + } else { + // Enable TPM. + bios_attrs.push(("TPM".into(), "Enabled".into())); - // Disabled EmbeddedUefiShell (infinite boot workaround) - bios_attrs.push(("EmbeddedUefiShell".into(), "Disabled".into())); + // Disable EmbeddedUefiShell (infinite boot workaround). + bios_attrs.push(("EmbeddedUefiShell".into(), "Disabled".into())); + } // Enable Option ROM so that the DPU will show up in the Host's network devce list // Otherwise, we will never see the DPU's Host PF MAC in the boot option list From dfbcb57f9170d31f964bee99d7173c2a3fa807c3 Mon Sep 17 00:00:00 2001 From: Krish Dandiwala Date: Thu, 23 Jul 2026 14:28:12 -0400 Subject: [PATCH 2/2] fix: secure boot unsupported --- src/nvidia_gbx00.rs | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/src/nvidia_gbx00.rs b/src/nvidia_gbx00.rs index 8f55cc560..79cf8962e 100644 --- a/src/nvidia_gbx00.rs +++ b/src/nvidia_gbx00.rs @@ -860,11 +860,25 @@ impl Redfish for Bmc { } fn enable_secure_boot<'a>(&'a self) -> crate::RedfishFuture<'a, Result<(), RedfishError>> { - Box::pin(async move { self.s.enable_secure_boot().await }) + Box::pin(async move { + if self.is_gb300().await? { + return Err(RedfishError::NotSupported( + "Supermicro GB300 does not expose SecureBootEnable".to_string(), + )); + } + self.s.enable_secure_boot().await + }) } fn disable_secure_boot<'a>(&'a self) -> crate::RedfishFuture<'a, Result<(), RedfishError>> { - Box::pin(async move { self.s.disable_secure_boot().await }) + Box::pin(async move { + if self.is_gb300().await? { + return Err(RedfishError::NotSupported( + "Supermicro GB300 does not expose SecureBootEnable".to_string(), + )); + } + self.s.disable_secure_boot().await + }) } fn get_secure_boot_certificate<'a>(