Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions crates/boot/src/actions/chainload.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ pub fn chainload(context: Rc<SproutContext>, configuration: &ChainloadConfigurat
// Resolve the path to the image to chainload.
let resolved = eficore::path::resolve_path(
Some(context.root().loaded_image_path()?),
&context.stamp(&configuration.path),
context.stamp(&configuration.path),
)
.context("unable to resolve chainload path")?;

Expand All @@ -38,8 +38,7 @@ pub fn chainload(context: Rc<SproutContext>, configuration: &ChainloadConfigurat
.context("unable to open loaded image protocol")?;

// Stamp and combine the options to pass to the image.
let options =
utils::combine_options(configuration.options.iter().map(|item| context.stamp(item)));
let options = utils::combine_options(context.stamp_iter(configuration.options.iter()));

// Pass the load options to the image.
// If no options are provided, the resulting string will be empty.
Expand All @@ -50,6 +49,7 @@ pub fn chainload(context: Rc<SproutContext>, configuration: &ChainloadConfigurat
.context("unable to convert chainloader options to CString16")?,
);

// Ensure the chainloader options limit is not exceeded.
if options.num_bytes() > u32::MAX as usize {
bail!("chainloader options too large");
}
Expand Down
15 changes: 3 additions & 12 deletions crates/boot/src/actions/edera.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,20 +20,11 @@ use uefi::Guid;
/// Builds a configuration string for the Xen EFI stub using the specified `configuration`.
fn build_xen_config(context: Rc<SproutContext>, configuration: &EderaConfiguration) -> String {
// Stamp xen options and combine them.
let xen_options = utils::combine_options(
configuration
.xen_options
.iter()
.map(|item| context.stamp(item)),
);
let xen_options = utils::combine_options(context.stamp_iter(configuration.xen_options.iter()));

// Stamp kernel options and combine them.
let kernel_options = utils::combine_options(
configuration
.kernel_options
.iter()
.map(|item| context.stamp(item)),
);
let kernel_options =
utils::combine_options(context.stamp_iter(configuration.kernel_options.iter()));

// xen config file format is ini-like
[
Expand Down
9 changes: 9 additions & 0 deletions crates/boot/src/context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -269,6 +269,15 @@ impl SproutContext {
Self::stamp_values(&self.all_values(), text.as_ref()).1
}

/// Stamps all the items from the iterator `input` with all the values in this [SproutContext]
/// and it's parents. This calls [self.stamp] on each item.
pub fn stamp_iter(
&self,
input: impl Iterator<Item = impl AsRef<str>>,
) -> impl Iterator<Item = String> {
input.map(|item| self.stamp(item))
}

/// Unloads a [SproutContext] back into an owned context. This
/// may not succeed if something else is holding onto the value.
pub fn unload(self: Rc<SproutContext>) -> Option<SproutContext> {
Expand Down
2 changes: 1 addition & 1 deletion crates/boot/src/drivers.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ fn load_driver(context: Rc<SproutContext>, driver: &DriverDeclaration) -> Result
// Resolve the path to the driver image.
let resolved = eficore::path::resolve_path(
Some(context.root().loaded_image_path()?),
&context.stamp(&driver.path),
context.stamp(&driver.path),
)
.context("unable to resolve path to driver")?;

Expand Down
9 changes: 4 additions & 5 deletions crates/boot/src/generators/list.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,11 +22,10 @@ pub fn generate(

// Stamp the entry title and actions from the template.
let mut entry = list.entry.clone();
entry.actions = entry
.actions
.into_iter()
.map(|action| context.stamp(action))
.collect();

// Stamp all the actions this entry references.
entry.actions = context.stamp_iter(entry.actions.into_iter()).collect();

// Push the entry into the list with the new context.
entries.push(BootableEntry::new(
index.to_string(),
Expand Down
14 changes: 9 additions & 5 deletions crates/eficore/src/path.rs
Original file line number Diff line number Diff line change
Expand Up @@ -48,8 +48,8 @@ fn cstring16_contains_char(string: &CString16, c: char) -> bool {

/// Parses the input `path` as a [DevicePath].
/// Uses the [DevicePathFromText] protocol exclusively, and will fail if it cannot acquire the protocol.
pub fn text_to_device_path(path: &str) -> Result<PoolDevicePath> {
let path = CString16::try_from(path).context("unable to convert path to CString16")?;
pub fn text_to_device_path(path: impl AsRef<str>) -> Result<PoolDevicePath> {
let path = CString16::try_from(path.as_ref()).context("unable to convert path to CString16")?;
let device_path_from_text = uefi::boot::open_protocol_exclusive::<DevicePathFromText>(
uefi::boot::get_handle_for_protocol::<DevicePathFromText>()
.context("no device path from text protocol")?,
Expand Down Expand Up @@ -113,8 +113,13 @@ pub fn device_path_subpath(path: &DevicePath) -> Result<String> {
/// Resolve a path specified by `input` to its various components.
/// Uses `default_root_path` as the base root if one is not specified in the path.
/// Returns [ResolvedPath] which contains the resolved components.
pub fn resolve_path(default_root_path: Option<&DevicePath>, input: &str) -> Result<ResolvedPath> {
let mut path = text_to_device_path(input).context("unable to convert text to path")?;
pub fn resolve_path(
default_root_path: Option<&DevicePath>,
input: impl ToString,
) -> Result<ResolvedPath> {
let mut input = input.to_string();

let mut path = text_to_device_path(&input).context("unable to convert text to path")?;
let path_has_device = path
.node_iter()
.next()
Expand All @@ -125,7 +130,6 @@ pub fn resolve_path(default_root_path: Option<&DevicePath>, input: &str) -> Resu
.map(|it| it.to_string().contains('('))
.unwrap_or(false);
if !path_has_device {
let mut input = input.to_string();
if !input.starts_with('\\') {
input.insert(0, '\\');
}
Expand Down
2 changes: 1 addition & 1 deletion crates/eficore/src/shim.rs
Original file line number Diff line number Diff line change
Expand Up @@ -84,7 +84,7 @@ impl<'a> ShimInput<'a> {
let path = path
.to_string(DisplayOnly(false), AllowShortcuts(false))
.context("unable to convert device path to string")?;
let path = crate::path::resolve_path(None, &path.to_string())
let path = crate::path::resolve_path(None, path.to_string())
.context("unable to resolve path")?;
// Read the file path.
let data = path.read_file()?;
Expand Down
Loading