mirror of
https://github.com/edera-dev/sprout.git
synced 2025-12-19 13:50:16 +00:00
feat(bootloader-interface): add support for LoaderFeatures
This commit is contained in:
1
Cargo.lock
generated
1
Cargo.lock
generated
@@ -119,6 +119,7 @@ name = "edera-sprout"
|
|||||||
version = "0.0.16"
|
version = "0.0.16"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"anyhow",
|
"anyhow",
|
||||||
|
"bitflags",
|
||||||
"image",
|
"image",
|
||||||
"log",
|
"log",
|
||||||
"serde",
|
"serde",
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ edition = "2024"
|
|||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
anyhow = "1.0.100"
|
anyhow = "1.0.100"
|
||||||
|
bitflags = "2.10.0"
|
||||||
toml = "0.9.8"
|
toml = "0.9.8"
|
||||||
log = "0.4.28"
|
log = "0.4.28"
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
|
use crate::integrations::bootloader_interface::bitflags::LoaderFeatures;
|
||||||
use crate::platform::timer::PlatformTimer;
|
use crate::platform::timer::PlatformTimer;
|
||||||
use crate::utils::device_path_subpath;
|
use crate::utils::device_path_subpath;
|
||||||
use crate::utils::variables::{VariableClass, VariableController};
|
use crate::utils::variables::{VariableClass, VariableController};
|
||||||
@@ -6,6 +7,9 @@ use uefi::proto::device_path::DevicePath;
|
|||||||
use uefi::{Guid, guid};
|
use uefi::{Guid, guid};
|
||||||
use uefi_raw::table::runtime::VariableVendor;
|
use uefi_raw::table::runtime::VariableVendor;
|
||||||
|
|
||||||
|
/// bitflags: LoaderFeatures bitflags.
|
||||||
|
mod bitflags;
|
||||||
|
|
||||||
/// The name of the bootloader to tell the system.
|
/// The name of the bootloader to tell the system.
|
||||||
const LOADER_NAME: &str = "Sprout";
|
const LOADER_NAME: &str = "Sprout";
|
||||||
|
|
||||||
@@ -18,6 +22,11 @@ impl BootloaderInterface {
|
|||||||
"4a67b082-0a4c-41cf-b6c7-440b29bb8c4f"
|
"4a67b082-0a4c-41cf-b6c7-440b29bb8c4f"
|
||||||
)));
|
)));
|
||||||
|
|
||||||
|
/// The feature we support in Sprout.
|
||||||
|
fn features() -> LoaderFeatures {
|
||||||
|
LoaderFeatures::LoadDriver | LoaderFeatures::Tpm2ActivePcrBanks | LoaderFeatures::RetainShim
|
||||||
|
}
|
||||||
|
|
||||||
/// Tell the system that Sprout was initialized at the current time.
|
/// Tell the system that Sprout was initialized at the current time.
|
||||||
pub fn mark_init(timer: &PlatformTimer) -> Result<()> {
|
pub fn mark_init(timer: &PlatformTimer) -> Result<()> {
|
||||||
Self::mark_time("LoaderTimeInitUSec", timer)
|
Self::mark_time("LoaderTimeInitUSec", timer)
|
||||||
@@ -45,13 +54,26 @@ impl BootloaderInterface {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Tell the system what loader is being used.
|
/// Tell the system what loader is being used and our features.
|
||||||
pub fn set_loader_info() -> Result<()> {
|
pub fn set_loader_info() -> Result<()> {
|
||||||
Self::VENDOR.set_cstr16(
|
// Set the LoaderInfo variable with the name of the loader.
|
||||||
"LoaderInfo",
|
Self::VENDOR
|
||||||
LOADER_NAME,
|
.set_cstr16(
|
||||||
VariableClass::BootAndRuntimeTemporary,
|
"LoaderInfo",
|
||||||
)
|
LOADER_NAME,
|
||||||
|
VariableClass::BootAndRuntimeTemporary,
|
||||||
|
)
|
||||||
|
.context("unable to set loader info variable")?;
|
||||||
|
|
||||||
|
// Set the LoaderFeatures variable with the features we support.
|
||||||
|
Self::VENDOR
|
||||||
|
.set_u64le(
|
||||||
|
"LoaderFeatures",
|
||||||
|
Self::features().bits(),
|
||||||
|
VariableClass::BootAndRuntimeTemporary,
|
||||||
|
)
|
||||||
|
.context("unable to set loader features variable")?;
|
||||||
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Tell the system the relative path to the partition root of the current bootloader.
|
/// Tell the system the relative path to the partition root of the current bootloader.
|
||||||
|
|||||||
46
src/integrations/bootloader_interface/bitflags.rs
Normal file
46
src/integrations/bootloader_interface/bitflags.rs
Normal file
@@ -0,0 +1,46 @@
|
|||||||
|
use bitflags::bitflags;
|
||||||
|
|
||||||
|
bitflags! {
|
||||||
|
/// Feature bitflags for the bootloader interface.
|
||||||
|
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
|
||||||
|
pub struct LoaderFeatures: u64 {
|
||||||
|
/// Bootloader supports LoaderConfigTimeout.
|
||||||
|
const ConfigTimeout = 1 << 0;
|
||||||
|
/// Bootloader supports LoaderConfigTimeoutOneShot.
|
||||||
|
const ConfigTimeoutOneShot = 1 << 1;
|
||||||
|
/// Bootloader supports LoaderEntryDefault.
|
||||||
|
const EntryDefault = 1 << 2;
|
||||||
|
/// Bootloader supports LoaderEntryOneShot.
|
||||||
|
const EntryOneShot = 1 << 3;
|
||||||
|
/// Bootloader supports boot counting.
|
||||||
|
const BootCounting = 1 << 4;
|
||||||
|
/// Bootloader supports detection from XBOOTLDR partitions.
|
||||||
|
const Xbootldr = 1 << 5;
|
||||||
|
/// Bootloader supports handling of random seeds.
|
||||||
|
const RandomSeed = 1 << 6;
|
||||||
|
/// Bootloader supports loading drivers.
|
||||||
|
const LoadDriver = 1 << 7;
|
||||||
|
/// Bootloader supports sort keys.
|
||||||
|
const SortKey = 1 << 8;
|
||||||
|
/// Bootloader supports saved entries.
|
||||||
|
const SavedEntry = 1 << 9;
|
||||||
|
/// Bootloader supports device trees.
|
||||||
|
const DeviceTree = 1 << 10;
|
||||||
|
/// Bootloader supports secure boot enroll.
|
||||||
|
const SecureBootEnroll = 1 << 11;
|
||||||
|
/// Bootloader retains the shim.
|
||||||
|
const RetainShim = 1 << 12;
|
||||||
|
/// Bootloader supports disabling the menu via menu timeout variable.
|
||||||
|
const MenuDisable = 1 << 13;
|
||||||
|
/// Bootloader supports multi-profile UKI.
|
||||||
|
const MultiProfileUki = 1 << 14;
|
||||||
|
/// Bootloader reports URLs.
|
||||||
|
const ReportUrl = 1 << 15;
|
||||||
|
/// Bootloader supports type-1 UKIs.
|
||||||
|
const Type1Uki = 1 << 16;
|
||||||
|
/// Bootloader supports type-1 UKI urls.
|
||||||
|
const Type1UkiUrl = 1 << 17;
|
||||||
|
/// Bootloader indicates TPM2 active PCR banks.
|
||||||
|
const Tpm2ActivePcrBanks = 1 << 18;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -98,4 +98,10 @@ impl VariableController {
|
|||||||
pub fn set_bool(&self, key: &str, value: bool, class: VariableClass) -> Result<()> {
|
pub fn set_bool(&self, key: &str, value: bool, class: VariableClass) -> Result<()> {
|
||||||
self.set(key, &[value as u8], class)
|
self.set(key, &[value as u8], class)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Set the u64 little-endian variable specified by `key` to `value`.
|
||||||
|
/// The variable `class` controls the attributes for the variable.
|
||||||
|
pub fn set_u64le(&self, key: &str, value: u64, class: VariableClass) -> Result<()> {
|
||||||
|
self.set(key, &value.to_le_bytes(), class)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user