Skip to main content

alloc_no_stdlib/
lib.rs

1#![no_std]
2// The only unsafe code in this crate is the C calloc/malloc backing store,
3// which is gated behind the "unsafe" feature. Assert that the default build
4// contains no unsafe code at all.
5#![cfg_attr(not(feature="unsafe"), forbid(unsafe_code))]
6
7#[macro_use]
8mod allocated_memory;
9mod stack_allocator;
10mod allocated_stack_memory;
11#[macro_use]
12pub mod init;
13pub use allocated_memory::SliceWrapper;
14pub use allocated_memory::SliceWrapperMut;
15pub use allocated_memory::AllocatedSlice;
16
17pub use allocated_stack_memory::AllocatedStackMemory;
18pub use stack_allocator::Allocator;
19pub use stack_allocator::StackAllocator;
20
21use core::default::Default;
22pub fn bzero<T : Default> (data : &mut [T]) {
23    for iter in data.iter_mut() {
24        *iter = T::default();
25    }
26}
27
28pub fn uninitialized<T> (_data : &mut[T]) {}
29
30
31
32#[cfg(feature="unsafe")]
33#[derive(Debug)]
34pub struct CallocBackingStore<'a, T : 'a> {
35    pub raw_data : *mut u8,
36    pub data : &'a mut[T],
37    free : unsafe extern "C" fn(*mut u8),
38}
39
40#[cfg(feature="unsafe")]
41pub enum AllocatorC {
42   Calloc(unsafe extern "C" fn(usize, usize) -> *mut u8),
43   Malloc(unsafe extern "C" fn(usize) -> *mut u8),
44   Custom(fn(usize) -> *mut u8),
45}
46#[cfg(feature="unsafe")]
47impl<'a, T : 'a> CallocBackingStore<'a, T> {
48  pub unsafe fn new(num_elements : usize, alloc : AllocatorC, free : unsafe extern "C" fn (*mut u8), should_free : bool) -> Self{
49     let retval : *mut u8 = if num_elements == 0 {core::ptr::null_mut()} else {
50        match alloc {
51           AllocatorC::Calloc(calloc) => calloc(num_elements, core::mem::size_of::<T>()),
52           AllocatorC::Malloc(malloc) => malloc(num_elements *core::mem::size_of::<T>()),
53           AllocatorC::Custom(malloc) => malloc(num_elements *core::mem::size_of::<T>()),
54        }
55     };
56     if num_elements == 0 || retval.is_null() {
57        return CallocBackingStore::<'a, T>{
58         raw_data : core::ptr::null_mut(),
59         data : &mut[],
60         free : free,
61       }
62     }
63     let raw_data : *mut T = core::mem::transmute(retval);
64     if should_free {
65       return CallocBackingStore::<'a, T>{
66         raw_data : retval,
67         data : core::slice::from_raw_parts_mut(raw_data,
68                                                num_elements),
69         free : free,
70       };
71     } else {
72       let null_ptr : *const u8 = core::ptr::null();
73       return CallocBackingStore::<'a, T>{
74         raw_data : core::mem::transmute(null_ptr),//retval,
75         data : core::slice::from_raw_parts_mut(raw_data,
76                                                num_elements),
77         free : free,
78       };
79    }
80  }
81}
82#[cfg(feature="unsafe")]
83impl<'a, T:'a> Drop for CallocBackingStore<'a, T> {
84  fn drop(self :&mut Self) {
85//      core::mem::forget(core::mem::replace(self.data, &mut[]));
86    core::mem::forget(core::mem::replace(&mut self.data, &mut[]));
87    if !self.raw_data.is_null() {
88      let local_free = self.free;
89      unsafe {(local_free)(self.raw_data)};
90
91    }
92  }
93}