- Sponsor
-
Notifications
You must be signed in to change notification settings - Fork 170
doc: improved documentation for boot allocation functions #1665
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change | ||||
---|---|---|---|---|---|---|
|
@@ -120,28 +120,43 @@ pub unsafe fn raise_tpl(tpl: Tpl) -> TplGuard { | |||||
} | ||||||
} | ||||||
|
||||||
/// Allocates memory pages from the system. | ||||||
/// Allocates a consecutive set of memory pages using the UEFI allocator. | ||||||
/// | ||||||
/// UEFI OS loaders should allocate memory of the type `LoaderData`. | ||||||
/// The caller is responsible to free the memory using [`free_pages`]. | ||||||
/// | ||||||
/// # Arguments | ||||||
/// - `allocation_type`: The [`AllocateType`] to alter the allocation strategy. | ||||||
/// - `memory_type`: The [`MemoryType`] used to persist the allocation in the | ||||||
/// UEFI memory map. Typically, UEFI OS loaders should allocate memory of | ||||||
/// type [`MemoryType::LOADER_DATA`]. | ||||||
///- `size`: Amount of bytes to allocate. | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
|
||||||
/// | ||||||
/// # Safety | ||||||
/// Using this function is safe but reading on initialized memory is not. | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
(Reference: https://doc.rust-lang.org/nomicon/unchecked-uninit.html "It is illegal to construct a reference to uninitialized data") There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yikes, typos/weird wording from my side. Thanks |
||||||
/// Please look into the example code. | ||||||
/// | ||||||
/// # Errors | ||||||
/// | ||||||
/// * [`Status::OUT_OF_RESOURCES`]: allocation failed. | ||||||
/// * [`Status::INVALID_PARAMETER`]: `mem_ty` is [`MemoryType::PERSISTENT_MEMORY`], | ||||||
/// [`MemoryType::UNACCEPTED`], or in the range [`MemoryType::MAX`]`..=0x6fff_ffff`. | ||||||
/// * [`Status::NOT_FOUND`]: the requested pages could not be found. | ||||||
pub fn allocate_pages(ty: AllocateType, mem_ty: MemoryType, count: usize) -> Result<NonNull<u8>> { | ||||||
pub fn allocate_pages( | ||||||
allocation_type: AllocateType, | ||||||
memory_type: MemoryType, | ||||||
count: usize, | ||||||
) -> Result<NonNull<u8>> { | ||||||
let bt = boot_services_raw_panicking(); | ||||||
let bt = unsafe { bt.as_ref() }; | ||||||
|
||||||
let (ty, initial_addr) = match ty { | ||||||
let (ty, initial_addr) = match allocation_type { | ||||||
AllocateType::AnyPages => (0, 0), | ||||||
AllocateType::MaxAddress(addr) => (1, addr), | ||||||
AllocateType::Address(addr) => (2, addr), | ||||||
}; | ||||||
|
||||||
let mut addr1 = initial_addr; | ||||||
unsafe { (bt.allocate_pages)(ty, mem_ty, count, &mut addr1) }.to_result()?; | ||||||
unsafe { (bt.allocate_pages)(ty, memory_type, count, &mut addr1) }.to_result()?; | ||||||
|
||||||
// The UEFI spec allows `allocate_pages` to return a valid allocation at | ||||||
// address zero. Rust does not allow writes through a null pointer (which | ||||||
|
@@ -155,7 +170,7 @@ pub fn allocate_pages(ty: AllocateType, mem_ty: MemoryType, count: usize) -> Res | |||||
// not yet been freed, so if this allocation succeeds it should be at a | ||||||
// non-zero address. | ||||||
let mut addr2 = initial_addr; | ||||||
let r = unsafe { (bt.allocate_pages)(ty, mem_ty, count, &mut addr2) }.to_result(); | ||||||
let r = unsafe { (bt.allocate_pages)(ty, memory_type, count, &mut addr2) }.to_result(); | ||||||
|
||||||
// Free the original allocation (ignoring errors). | ||||||
let _unused = unsafe { (bt.free_pages)(addr1, count) }; | ||||||
|
@@ -189,22 +204,31 @@ pub unsafe fn free_pages(ptr: NonNull<u8>, count: usize) -> Result { | |||||
unsafe { (bt.free_pages)(addr, count) }.to_result() | ||||||
} | ||||||
|
||||||
/// Allocates from a memory pool. The pointer will be 8-byte aligned. | ||||||
/// Allocates a consecutive region of bytes using the UEFI allocator. The buffer | ||||||
/// will be 8-byte aligned. | ||||||
/// | ||||||
/// The caller is responsible to free the memory using [`free_pool`]. | ||||||
/// | ||||||
/// # Arguments | ||||||
/// - `memory_type`: The [`MemoryType`] used to persist the allocation in the | ||||||
/// UEFI memory map. Typically, UEFI OS loaders should allocate memory of | ||||||
/// type [`MemoryType::LOADER_DATA`]. | ||||||
///- `size`: Amount of bytes to allocate. | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
(This is a nitpicky grammar thing, "number" should be used for countable things) |
||||||
/// | ||||||
/// # Errors | ||||||
/// | ||||||
/// * [`Status::OUT_OF_RESOURCES`]: allocation failed. | ||||||
/// * [`Status::INVALID_PARAMETER`]: `mem_ty` is [`MemoryType::PERSISTENT_MEMORY`], | ||||||
/// [`MemoryType::UNACCEPTED`], or in the range [`MemoryType::MAX`]`..=0x6fff_ffff`. | ||||||
pub fn allocate_pool(mem_ty: MemoryType, size: usize) -> Result<NonNull<u8>> { | ||||||
pub fn allocate_pool(memory_type: MemoryType, size: usize) -> Result<NonNull<u8>> { | ||||||
let bt = boot_services_raw_panicking(); | ||||||
let bt = unsafe { bt.as_ref() }; | ||||||
|
||||||
let mut buffer = ptr::null_mut(); | ||||||
let ptr = | ||||||
unsafe { (bt.allocate_pool)(mem_ty, size, &mut buffer) }.to_result_with_val(|| buffer)?; | ||||||
let ptr = unsafe { (bt.allocate_pool)(memory_type, size, &mut buffer) } | ||||||
.to_result_with_val(|| buffer)?; | ||||||
|
||||||
Ok(NonNull::new(ptr).expect("allocate_pool must not return a null pointer if successful")) | ||||||
NonNull::new(ptr).ok_or(Status::OUT_OF_RESOURCES.into()) | ||||||
} | ||||||
|
||||||
/// Frees memory allocated by [`allocate_pool`]. | ||||||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.