aloc/
lib.rs

1#![no_std]
2extern crate core;
3use core::alloc::{GlobalAlloc, Layout};
4use core::cell::UnsafeCell;
5use core::mem::MaybeUninit;
6use core::ptr::null_mut;
7
8pub struct Heap<const P: usize> {
9    playarea: usize,
10    len:      UnsafeCell<usize>,
11    header:   UnsafeCell<[MaybeUninit<(*mut u8, usize)>; P]>
12}
13
14fn is_allocated(pointer: *mut u8, size: usize) -> bool {
15    if (pointer..pointer.wrapping_add(size)).contains(&pointer) {
16	true
17    } else {
18	false
19    }
20}
21
22impl<const P: usize> Heap<P> {
23    const HEADER_ITEM: MaybeUninit<(*mut u8, usize)> = MaybeUninit::uninit();
24    const HEADER_INIT: [MaybeUninit<(*mut u8, usize)>; P] = [Self::HEADER_ITEM; P];
25
26    pub const fn new() -> Self {
27	Heap {
28	    playarea: P,
29	    len: UnsafeCell::new(0),
30	    header: UnsafeCell::new(Self::HEADER_INIT)
31	}
32    }
33}
34
35unsafe impl<const P: usize> GlobalAlloc for Heap<P> {
36    unsafe fn alloc(&self, layout: Layout) -> *mut u8 {
37	let size = layout.size();
38	let mut ptr = null_mut();
39	for pointer in 0..self.playarea {
40	    if !is_allocated(pointer as *mut u8, size) {
41		ptr = pointer as *mut u8;
42		break;
43	    }
44	};
45	let header_mut = self.header.get();
46	*header_mut.as_mut().unwrap().get_unchecked_mut(*self.len.get())  = MaybeUninit::new((ptr, size));
47	*self.len.get() += 1;
48
49	ptr
50    }
51
52    unsafe fn dealloc(&self, ptr: *mut u8, layout: Layout) {}
53}
54
55unsafe impl<const P: usize> Sync for Heap<P> {}