Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit be11de0

Browse files
wangrunji0408GabrielMajeri
authored andcommitted
Implement alignment for allocator
1 parent 4c4049e commit be11de0

File tree

2 files changed

+36
-4
lines changed

2 files changed

+36
-4
lines changed

‎src/alloc.rs

Lines changed: 24 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -52,16 +52,33 @@ pub fn exit_boot_services() {
5252
/// Only valid for as long as the UEFI boot services are available.
5353
pub struct Allocator;
5454

55+
#[allow(clippy::cast_ptr_alignment)]
5556
unsafe impl GlobalAlloc for Allocator {
5657
unsafe fn alloc(&self, layout: Layout) -> *mut u8 {
5758
let mem_ty = MemoryType::LOADER_DATA;
5859
let size = layout.size();
5960
let align = layout.align();
6061

61-
// TODO: add support for other alignments.
6262
if align > 8 {
63-
// Unsupported alignment for allocation, UEFI can only allocate 8-byte aligned addresses
64-
ptr::null_mut()
63+
// allocate more space for alignment
64+
let ptr = if let Ok(ptr) = boot_services()
65+
.as_ref()
66+
.allocate_pool(mem_ty, size + align)
67+
.warning_as_error()
68+
{
69+
ptr
70+
} else {
71+
return ptr::null_mut();
72+
};
73+
// calculate align offset
74+
let mut offset = ptr.align_offset(align);
75+
if offset == 0 {
76+
offset = align;
77+
}
78+
let return_ptr = ptr.add(offset);
79+
// store allocated pointer before the struct
80+
(return_ptr as *mut *mut u8).sub(1).write(ptr);
81+
return_ptr
6582
} else {
6683
boot_services()
6784
.as_ref()
@@ -71,7 +88,10 @@ unsafe impl GlobalAlloc for Allocator {
7188
}
7289
}
7390

74-
unsafe fn dealloc(&self, ptr: *mut u8, _layout: Layout) {
91+
unsafe fn dealloc(&self, mut ptr: *mut u8, layout: Layout) {
92+
if layout.align() > 8 {
93+
ptr = (ptr as *const *mut u8).sub(1).read();
94+
}
7595
boot_services()
7696
.as_ref()
7797
.free_pool(ptr)

‎uefi-test-runner/src/boot/memory.rs

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ pub fn test(bt: &BootServices) {
99

1010
allocate_pages(bt);
1111
vec_alloc();
12+
alloc_alignment();
1213
memmove(bt);
1314

1415
memory_map(bt);
@@ -47,6 +48,17 @@ fn vec_alloc() {
4748
assert_eq!(values[..], [-5, 0, 4, 16, 23], "Failed to sort vector");
4849
}
4950

51+
// Simple test to ensure our custom allocator works with correct alignment.
52+
fn alloc_alignment() {
53+
info!("Allocating a structure with alignment to 0x100");
54+
55+
#[repr(align(0x100))]
56+
struct Block([u8; 0x100]);
57+
58+
let value = vec![Block([1; 0x100])];
59+
assert_eq!(value.as_ptr() as usize % 0x100, 0, "Wrong alignment");
60+
}
61+
5062
// Test that the `memmove` / `memset` functions work.
5163
fn memmove(bt: &BootServices) {
5264
info!("Testing the `memmove` / `memset` functions");

0 commit comments

Comments
(0)

AltStyle によって変換されたページ (->オリジナル) /