1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
use core::alloc::{GlobalAlloc, Layout};
use core::ptr::NonNull;
use crate::kernel::{KERNEL, State};
use crate::alloc::allocator::Allocator;
use crate::{log, syscall};
use crate::sched;
pub struct Wrapper { }
impl Wrapper {
pub(crate) const fn new() -> Self {
Wrapper { }
}
pub(crate) fn alloc_handler(layout: Layout) -> *mut u8 {
Self::with_allocator(|a| {
match a {
None => 0 as *mut _,
Some(a) => {
match a.alloc(layout) {
Ok(mut addr) => unsafe { &mut addr.as_mut()[0] as *mut _ },
Err(_) => 0 as *mut _,
}
}
}
})
}
pub(crate) fn dealloc_handler(ptr: *mut u8, layout: Layout) {
Self::with_allocator(|a| {
if let Some(alloc) = a {
unsafe { alloc.dealloc(NonNull::new_unchecked(ptr), layout); }
}
})
}
fn with_allocator<F, R>(f: F) -> R
where F: FnOnce(Option<&dyn Allocator>) -> R
{
match KERNEL.state() {
State::Startup => {
match KERNEL.process() {
None => {
log::error!("Cannot allocate memory outside process.");
f(None)
},
Some(p) => {
f(Some(p.allocator()))
}
}
}
State::Running => {
sched::with_callee(|t| {
f(Some(t.process().allocator()))
})
}
}
}
}
unsafe impl GlobalAlloc for Wrapper {
unsafe fn alloc(&self, layout: Layout) -> *mut u8 {
syscall::alloc(layout)
}
unsafe fn dealloc(&self, ptr: *mut u8, layout: Layout) {
syscall::dealloc(ptr, layout)
}
}