From a8980cdc3da9d53ea86d534061a032d996484b30 Mon Sep 17 00:00:00 2001 From: German Maglione Date: Tue, 28 May 2024 17:15:54 +0200 Subject: [PATCH] Add SMBIOS OEM String support Signed-off-by: German Maglione --- src/cmdline.rs | 4 ++++ src/context.rs | 36 ++++++++++++++++++++++++++++++++++-- 2 files changed, 38 insertions(+), 2 deletions(-) diff --git a/src/cmdline.rs b/src/cmdline.rs index 241d041..2640fa5 100644 --- a/src/cmdline.rs +++ b/src/cmdline.rs @@ -34,6 +34,10 @@ pub struct Args { /// GUI option for compatibility with vfkit (ignored). #[arg(long, default_value_t = false)] pub gui: bool, + + /// SMBIOS OEM String + #[arg(long = "oem-string")] + pub oem_strings: Option>, } /// Parse a string into a vector of substrings, all of which are separated by commas. diff --git a/src/context.rs b/src/context.rs index eea2ab5..5ac003f 100644 --- a/src/context.rs +++ b/src/context.rs @@ -7,15 +7,17 @@ use crate::{ virtio::KrunContextSet, }; -use std::{convert::TryFrom, thread}; +use std::ffi::{c_char, CString}; +use std::{convert::TryFrom, ptr, thread}; -use anyhow::anyhow; +use anyhow::{anyhow, Context}; #[link(name = "krun-efi")] extern "C" { fn krun_create_ctx() -> i32; fn krun_set_gpu_options(ctx_id: u32, virgl_flags: u32) -> i32; fn krun_set_vm_config(ctx_id: u32, num_vcpus: u8, ram_mib: u32) -> i32; + fn krun_set_smbios_oem_strings(ctx_id: u32, oem_strings: *const *const c_char) -> i32; fn krun_start_enter(ctx_id: u32) -> i32; } @@ -67,6 +69,8 @@ impl TryFrom for KrunContext { unsafe { device.krun_ctx_set(id)? } } + set_smbios_oem_strings(id, &args.oem_strings)?; + Ok(Self { id, args }) } } @@ -89,3 +93,31 @@ impl KrunContext { Ok(()) } } + +fn set_smbios_oem_strings( + ctx_id: u32, + oem_strings: &Option>, +) -> Result<(), anyhow::Error> { + let Some(oem_strings) = oem_strings else { + return Ok(()); + }; + + if oem_strings.len() > u8::MAX as usize { + return Err(anyhow!("invalid number of SMBIOS OEM strings")); + } + + let mut cstr_vec = Vec::with_capacity(oem_strings.len()); + for s in oem_strings { + let cs = CString::new(s.as_str()).context("invalid SMBIOS OEM string")?; + cstr_vec.push(cs); + } + let mut ptr_vec: Vec<_> = cstr_vec.iter().map(|s| s.as_ptr()).collect(); + // libkrun requires an NULL terminator to indicate the end of the array + ptr_vec.push(ptr::null()); + + let ret = unsafe { krun_set_smbios_oem_strings(ctx_id, ptr_vec.as_ptr()) }; + if ret < 0 { + return Err(anyhow!("unable to set SMBIOS OEM Strings")); + } + Ok(()) +}