|
| 1 | +//! TODO |
| 2 | +
|
| 3 | +// TODO |
| 4 | +#![allow(clippy::missing_safety_doc)] |
| 5 | + |
| 6 | +use crate::table::boot::MemoryDescriptor; |
| 7 | +use crate::table::runtime::{ |
| 8 | + ResetType, RuntimeServices, Time, TimeCapabilities, VariableAttributes, VariableStorageInfo, |
| 9 | + VariableVendor, |
| 10 | +}; |
| 11 | +use crate::{system, CStr16, Result, Status}; |
| 12 | +use core::ptr::NonNull; |
| 13 | + |
| 14 | +#[cfg(feature = "alloc")] |
| 15 | +use {crate::table::runtime::VariableKey, alloc::boxed::Box, alloc::vec::Vec}; |
| 16 | + |
| 17 | +fn runtime_services() -> NonNull<RuntimeServices> { |
| 18 | + let st = unsafe { system::system_table().as_mut() }; |
| 19 | + NonNull::new(st.runtime_services.cast()).expect("runtime services are not active") |
| 20 | +} |
| 21 | + |
| 22 | +/// Query the current time and date information |
| 23 | +pub fn get_time() -> Result<Time> { |
| 24 | + unsafe { runtime_services().as_mut() }.get_time() |
| 25 | +} |
| 26 | + |
| 27 | +/// Query the current time and date information and the RTC capabilities |
| 28 | +pub fn get_time_and_caps() -> Result<(Time, TimeCapabilities)> { |
| 29 | + unsafe { runtime_services().as_mut() }.get_time_and_caps() |
| 30 | +} |
| 31 | + |
| 32 | +/// Sets the current local time and date information |
| 33 | +/// |
| 34 | +/// During runtime, if a PC-AT CMOS device is present in the platform, the |
| 35 | +/// caller must synchronize access to the device before calling `set_time`. |
| 36 | +/// |
| 37 | +/// # Safety |
| 38 | +/// |
| 39 | +/// Undefined behavior could happen if multiple tasks try to |
| 40 | +/// use this function at the same time without synchronisation. |
| 41 | +pub unsafe fn set_time(time: &Time) -> Result { |
| 42 | + unsafe { runtime_services().as_mut() }.set_time(time) |
| 43 | +} |
| 44 | + |
| 45 | +/// Get the size (in bytes) of a variable. This can be used to find out how |
| 46 | +/// big of a buffer should be passed in to `get_variable`. |
| 47 | +pub fn get_variable_size(name: &CStr16, vendor: &VariableVendor) -> Result<usize> { |
| 48 | + unsafe { runtime_services().as_mut() }.get_variable_size(name, vendor) |
| 49 | +} |
| 50 | + |
| 51 | +/// Get the contents and attributes of a variable. The size of `buf` must |
| 52 | +/// be at least as big as the variable's size, although it can be |
| 53 | +/// larger. If it is too small, `BUFFER_TOO_SMALL` is returned. |
| 54 | +/// |
| 55 | +/// On success, a tuple containing the variable's value (a slice of `buf`) |
| 56 | +/// and the variable's attributes is returned. |
| 57 | +pub fn get_variable<'a>( |
| 58 | + name: &CStr16, |
| 59 | + vendor: &VariableVendor, |
| 60 | + buf: &'a mut [u8], |
| 61 | +) -> Result<(&'a [u8], VariableAttributes)> { |
| 62 | + unsafe { runtime_services().as_mut() }.get_variable(name, vendor, buf) |
| 63 | +} |
| 64 | + |
| 65 | +/// Get the contents and attributes of a variable. |
| 66 | +#[cfg(feature = "alloc")] |
| 67 | +pub fn get_variable_boxed( |
| 68 | + name: &CStr16, |
| 69 | + vendor: &VariableVendor, |
| 70 | +) -> Result<(Box<[u8]>, VariableAttributes)> { |
| 71 | + unsafe { runtime_services().as_mut() }.get_variable_boxed(name, vendor) |
| 72 | +} |
| 73 | + |
| 74 | +/// Get the names and vendor GUIDs of all currently-set variables. |
| 75 | +#[cfg(feature = "alloc")] |
| 76 | +pub fn variable_keys() -> Result<Vec<VariableKey>> { |
| 77 | + unsafe { runtime_services().as_mut() }.variable_keys() |
| 78 | +} |
| 79 | + |
| 80 | +/// Set the value of a variable. This can be used to create a new variable, |
| 81 | +/// update an existing variable, or (when the size of `data` is zero) |
| 82 | +/// delete a variable. |
| 83 | +/// |
| 84 | +/// # Warnings |
| 85 | +/// |
| 86 | +/// The [`Status::WARN_RESET_REQUIRED`] warning will be returned when using |
| 87 | +/// this function to transition the Secure Boot mode to setup mode or audit |
| 88 | +/// mode if the firmware requires a reboot for that operation. |
| 89 | +pub fn set_variable( |
| 90 | + name: &CStr16, |
| 91 | + vendor: &VariableVendor, |
| 92 | + attributes: VariableAttributes, |
| 93 | + data: &[u8], |
| 94 | +) -> Result { |
| 95 | + unsafe { runtime_services().as_mut() }.set_variable(name, vendor, attributes, data) |
| 96 | +} |
| 97 | + |
| 98 | +/// Deletes a UEFI variable. |
| 99 | +pub fn delete_variable(name: &CStr16, vendor: &VariableVendor) -> Result { |
| 100 | + unsafe { runtime_services().as_mut() }.delete_variable(name, vendor) |
| 101 | +} |
| 102 | + |
| 103 | +/// Get information about UEFI variable storage space for the type |
| 104 | +/// of variable specified in `attributes`. |
| 105 | +/// |
| 106 | +/// This operation is only supported starting with UEFI 2.0; earlier |
| 107 | +/// versions will fail with [`Status::UNSUPPORTED`]. |
| 108 | +/// |
| 109 | +/// See [`VariableStorageInfo`] for details of the information returned. |
| 110 | +pub fn query_variable_info(attributes: VariableAttributes) -> Result<VariableStorageInfo> { |
| 111 | + unsafe { runtime_services().as_mut() }.query_variable_info(attributes) |
| 112 | +} |
| 113 | + |
| 114 | +/// Resets the computer. |
| 115 | +pub fn reset(rt: ResetType, status: Status, data: Option<&[u8]>) -> ! { |
| 116 | + unsafe { runtime_services().as_mut() }.reset(rt, status, data) |
| 117 | +} |
| 118 | + |
| 119 | +/// TODO |
| 120 | +pub unsafe fn set_virtual_address_map( |
| 121 | + map_size: usize, |
| 122 | + desc_size: usize, |
| 123 | + desc_version: u32, |
| 124 | + virtual_map: *mut MemoryDescriptor, |
| 125 | +) -> Status { |
| 126 | + unsafe { runtime_services().as_mut() }.set_virtual_address_map( |
| 127 | + map_size, |
| 128 | + desc_size, |
| 129 | + desc_version, |
| 130 | + virtual_map, |
| 131 | + ) |
| 132 | +} |
0 commit comments