Skip to content

Commit 9c6fdab

Browse files
committed
allow borrows of calloc data
update the docs and tried two passes of calloc/malloc allocators where the data was not reallocated in between
1 parent 8d8d83d commit 9c6fdab

File tree

6 files changed

+66
-37
lines changed

6 files changed

+66
-37
lines changed

README.md

Lines changed: 14 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ declare_stack_allocator_struct!(StackAllocatedFreelist4, 4, stack);
3939
...
4040
4141
// in the code where the memory must be used, first the array needs to be readied
42-
define_allocator_memory_pool!(stack_buffer, 4, u8, [0; 65536], stack);
42+
let mut stack_buffer = define_allocator_memory_pool!(4, u8, [0; 65536], stack);
4343
// then an allocator needs to be made and pointed to the stack_buffer on the stack
4444
// the final argument tells the system if free'd data should be zero'd before being
4545
// reused by a subsequent call to alloc_cell
@@ -66,7 +66,7 @@ at this point
6666
```
6767
declare_stack_allocator_struct!(HeapAllocatedFreelist, heap);
6868
...
69-
define_allocator_memory_pool!(heap_global_buffer, 4096, u8, [0; 6 * 1024 * 1024], heap);
69+
let mut heap_global_buffer = define_allocator_memory_pool!(4096, u8, [0; 6 * 1024 * 1024], heap);
7070
let mut ags = HeapAllocatedFreelist::<u8>::new_allocator(4096, &mut heap_global_buffer, bzero);
7171
{
7272
let mut x = ags.alloc_cell(9999);
@@ -86,13 +86,19 @@ In this version, the number of cells are fixed to the parameter specified in the
8686
(4096 in this example)
8787

8888
```
89+
extern {
90+
fn calloc(n_elem : usize, el_size : usize) -> *mut u8;
91+
fn malloc(len : usize) -> *mut u8;
92+
fn free(item : *mut u8);
93+
}
94+
8995
declare_stack_allocator_struct!(CallocAllocatedFreelist4096, 4096, calloc);
9096
...
9197
9298
// the buffer is defined with 200 megs of zero'd memory from calloc
93-
define_allocator_memory_pool!(calloc_global_buffer, 4096, u8, [0; 200 * 1024 * 1024], calloc);
99+
let mut calloc_global_buffer = unsafe {define_allocator_memory_pool!(4096, u8, [0; 200 * 1024 * 1024], calloc)};
94100
// and assigned to a new_allocator
95-
let mut ags = CallocAllocatedFreelist4096::<u8>::new_allocator(calloc_global_buffer, bzero);
101+
let mut ags = CallocAllocatedFreelist4096::<u8>::new_allocator(&mut calloc_global_buffer.data, bzero);
96102
{
97103
let mut x = ags.alloc_cell(9999);
98104
x.slice_mut()[0] = 4;
@@ -118,12 +124,14 @@ since multiple allocators may get access to global_buffer.
118124

119125
```
120126
declare_stack_allocator_struct!(GlobalAllocatedFreelist, 16, global);
121-
define_allocator_memory_pool!(global_buffer, 16, u8, [0; 1024 * 1024 * 100], global);
127+
define_allocator_memory_pool!(16, u8, [0; 1024 * 1024 * 100], global, global_buffer);
122128
123129
...
124130
// this references a global buffer
125131
let mut ags = GlobalAllocatedFreelist::<u8>::new_allocator(bzero);
126-
bind_global_buffers_to_allocator!(ags, global_buffer, u8);
132+
unsafe {
133+
bind_global_buffers_to_allocator!(ags, global_buffer, u8);
134+
}
127135
{
128136
let mut x = ags.alloc_cell(9999);
129137
x.slice_mut()[0] = 4;

src/bin/example.rs

Lines changed: 7 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -29,21 +29,11 @@ declare_stack_allocator_struct!(StackAllocatedFreelist16, 16, stack);
2929
declare_stack_allocator_struct!(BoxAllocatedFreelist, heap);
3030

3131
fn main() {
32-
//let mut global_buffer : [u8; 1024 * 4096] = [0;4096*1024];
33-
//let max_memory_pool_size : usize = 1024 * 1024 * 200;
34-
35-
//// let global_buffer_vec : Vec<u8> = vec![0; max_memory_pool_size];
36-
//// //let global_buffer_vec = std::iter::repeat(0u8).take(max_memory_pool_size).collect::<Vec<u8>>();
37-
//// let mut global_buffer_box = global_buffer_vec.into_boxed_slice();
38-
39-
//// let mut global_buffer = &mut *global_buffer_box;
40-
//let allocated_mem = unsafe {calloc(max_memory_pool_size, core::mem::size_of::<u8>())};
41-
//let global_ptr : *mut u8 = unsafe {core::mem::transmute(allocated_mem)};
42-
//let mut global_buffer = unsafe {core::slice::from_raw_parts_mut(global_ptr, max_memory_pool_size)};
43-
//trace_macros!(true);
44-
let global_buffer = unsafe {define_allocator_memory_pool!(4, u8, [0; 1024 * 1024 * 200], calloc)};
45-
//let global_buffer = alloc_no_stdlib::CallocBackingStore<u8>(1024 * 1024 * 200, alloc_no_stdlib::AllocatorC::Calloc(calloc), free, true);
46-
let mut ags = CallocAllocatedFreelist4::<u8>::new_allocator(global_buffer, bzero);
32+
let mut global_buffer = unsafe {define_allocator_memory_pool!(4, u8, [0; 1024 * 1024 * 200], calloc)};
33+
{
34+
let mut gbref = &mut global_buffer;
35+
{
36+
let mut ags = CallocAllocatedFreelist4::<u8>::new_allocator(gbref.data, bzero);
4737

4838
{
4939
let mut x = ags.alloc_cell(9999);
@@ -64,6 +54,8 @@ fn main() {
6454
println!("x[0] = {:?} z[0] = {:?} z[1] = {:?} r3[0] = {:?} r3[1] = {:?}", x.mem[0], z.mem[0], z.mem[1], reget_three[0], reget_three.slice()[1]);
6555
let mut _z = ags.alloc_cell(1);
6656
}
57+
}
58+
}
6759
let mut zero_global_buffer = define_allocator_memory_pool!(4, u8, [0; 1024 * 1024 * 20], heap);
6860

6961
let mut boxallocator = BoxAllocatedFreelist::<u8>::new_allocator(1024 * 1024, &mut zero_global_buffer, bzero);

src/init.rs

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,7 @@ macro_rules! define_stack_allocator_traits(
7272

7373
impl<'a, T: 'a> Default for $name<'a, T> {
7474
fn default() -> Self {
75-
return $name::<'a, T>{freelist : static_array!(&mut[]; $freelist_size), backing_store : None};
75+
return $name::<'a, T>{freelist : static_array!(&mut[]; $freelist_size)};
7676
}
7777
}
7878
define_stack_allocator_traits!($name, generic);
@@ -125,7 +125,7 @@ macro_rules! declare_stack_allocator_struct(
125125

126126
(@new_calloc_method $name : ident, $freelist_size : tt) => {
127127
impl<'a, T: 'a> $name<'a, T> {
128-
fn new_allocator(mut global_buffer : alloc_no_stdlib::CallocBackingStore<'a, T>,
128+
fn new_allocator(mut global_buffer : &'a mut [T],
129129
initializer : fn(&mut[T])) -> StackAllocator<'a, T, $name<'a, T> > {
130130
let mut retval = StackAllocator::<T, $name<T> > {
131131
nop : &mut [],
@@ -134,8 +134,7 @@ macro_rules! declare_stack_allocator_struct(
134134
free_list_overflow_count : 0,
135135
initialize : initializer,
136136
};
137-
retval.free_cell(AllocatedStackMemory::<T>{mem:core::mem::replace(&mut global_buffer.data, &mut[])});
138-
retval.system_resources.backing_store = Some(global_buffer);
137+
retval.free_cell(AllocatedStackMemory::<T>{mem:core::mem::replace(&mut global_buffer, &mut[])});
139138
return retval;
140139
}
141140
}
@@ -146,7 +145,6 @@ macro_rules! declare_stack_allocator_struct(
146145
($name :ident, $freelist_size : tt, calloc) => {
147146
struct $name<'a, T : 'a> {
148147
freelist : [&'a mut [T]; declare_stack_allocator_struct!(@as_expr $freelist_size)],
149-
backing_store : Option<alloc_no_stdlib::CallocBackingStore<'a, T> >,
150148
}
151149
define_stack_allocator_traits!($name,
152150
$freelist_size,

src/lib.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
#![no_std]
22

3-
//#[macro_use]
4-
//extern crate std;
3+
#[macro_use]
4+
extern crate std;
55
mod allocated_memory;
66
mod stack_allocator;
77
mod allocated_stack_memory;

src/stack_allocator.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@ impl<'a, T : 'a, U : allocated_memory::AllocatedSlice<&'a mut[T]> >
3636
type AllocatedMemory = AllocatedStackMemory<'a, T>;
3737
fn alloc_cell(self : &mut StackAllocator<'a, T, U>,
3838
len : usize) -> AllocatedStackMemory<'a, T> {
39+
println!("Allocated {:}", len);
3940
if len == 0 {
4041
return AllocatedStackMemory::<'a, T>::default();
4142
}
@@ -80,6 +81,7 @@ impl<'a, T : 'a, U : allocated_memory::AllocatedSlice<&'a mut[T]> >
8081
if val.slice().len() == 0 {
8182
return;
8283
}
84+
println!("Freed {:}", val.slice().len());
8385
if self.free_list_start > 0 {
8486
self.free_list_start -=1;
8587
core::mem::replace(&mut self.system_resources.slice_mut()[self.free_list_start],

tests/lib.rs

Lines changed: 38 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -164,8 +164,8 @@ fn uninitialized_heap_pool_test() {
164164
fn uninitialized_calloc_pool_test() {
165165

166166
{
167-
let calloc_global_buffer = unsafe{define_allocator_memory_pool!(4096, u8, [0; 200 * 1024 * 1024], calloc)};
168-
let mut ags = CallocAllocatedFreelist4096::<u8>::new_allocator(calloc_global_buffer, uninitialized);
167+
let mut calloc_global_buffer = unsafe{define_allocator_memory_pool!(4096, u8, [0; 200 * 1024 * 1024], calloc)};
168+
let mut ags = CallocAllocatedFreelist4096::<u8>::new_allocator(&mut calloc_global_buffer.data, uninitialized);
169169
{
170170
let mut x = ags.alloc_cell(9999);
171171
x.slice_mut()[0] = 4;
@@ -197,7 +197,7 @@ fn uninitialized_global_pool_test() {
197197
{
198198
let mut ags = GlobalAllocatedFreelist::<u8>::new_allocator(uninitialized);
199199
unsafe {
200-
bind_global_buffers_to_allocator!(ags, global_buffer, u8);
200+
bind_global_buffers_to_allocator!(ags, global_buffer, u8);
201201
}
202202
{
203203
let mut x = ags.alloc_cell(9999);
@@ -362,8 +362,8 @@ fn heap_pool_test() {
362362
fn calloc_pool_test() {
363363

364364
{
365-
let calloc_global_buffer = unsafe {define_allocator_memory_pool!(4096, u8, [0; 200 * 1024 * 1024], calloc)};
366-
let mut ags = CallocAllocatedFreelist4096::<u8>::new_allocator(calloc_global_buffer, bzero);
365+
let mut calloc_global_buffer = unsafe {define_allocator_memory_pool!(4096, u8, [0; 200 * 1024 * 1024], calloc)};
366+
let mut ags = CallocAllocatedFreelist4096::<u8>::new_allocator(&mut calloc_global_buffer.data, bzero);
367367
{
368368
let mut x = ags.alloc_cell(9999);
369369
x.slice_mut()[0] = 4;
@@ -396,8 +396,8 @@ fn calloc_pool_test() {
396396
fn calloc_leak_pool_test() {
397397

398398
{
399-
let calloc_global_buffer = unsafe{define_allocator_memory_pool!(4096, u8, [0; 200 * 1024 * 1024], calloc_no_free)};
400-
let mut ags = CallocAllocatedFreelist4096::<u8>::new_allocator(calloc_global_buffer, bzero);
399+
let mut calloc_global_buffer = unsafe{define_allocator_memory_pool!(4096, u8, [0; 200 * 1024 * 1024], calloc_no_free)};
400+
let mut ags = CallocAllocatedFreelist4096::<u8>::new_allocator(&mut calloc_global_buffer.data, bzero);
401401
{
402402
let mut x = ags.alloc_cell(9999);
403403
x.slice_mut()[0] = 4;
@@ -429,8 +429,9 @@ fn calloc_leak_pool_test() {
429429
fn malloc_pool_test() {
430430

431431
{
432-
let malloc_global_buffer = unsafe {define_allocator_memory_pool!(4096, u8, [0; 200 * 1024 * 1024], malloc)};
433-
let mut ags = MallocAllocatedFreelist4096::<u8>::new_allocator(malloc_global_buffer, bzero);
432+
let mut malloc_global_buffer = unsafe {define_allocator_memory_pool!(4096, u8, [0; 200 * 1024 * 1024], malloc)};
433+
{
434+
let mut ags = MallocAllocatedFreelist4096::<u8>::new_allocator(&mut malloc_global_buffer.data, bzero);
434435
{
435436
let mut x = ags.alloc_cell(9999);
436437
x.slice_mut()[0] = 4;
@@ -455,6 +456,34 @@ fn malloc_pool_test() {
455456
let mut _z = ags.alloc_cell(1);
456457
}
457458
}
459+
{
460+
let mut ags = MallocAllocatedFreelist4096::<u8>::new_allocator(&mut malloc_global_buffer.data, bzero);
461+
{
462+
let mut x = ags.alloc_cell(9999);
463+
x.slice_mut()[0] = 4;
464+
let mut y = ags.alloc_cell(4);
465+
y[0] = 5;
466+
ags.free_cell(y);
467+
468+
let mut three = ags.alloc_cell(3);
469+
three[0] = 6;
470+
ags.free_cell(three);
471+
472+
let mut z = ags.alloc_cell(4);
473+
z.slice_mut()[1] = 8;
474+
let mut reget_three = ags.alloc_cell(4);
475+
reget_three.slice_mut()[1] = 9;
476+
//y.mem[0] = 6; // <-- this is an error (use after free)
477+
assert_eq!(x[0], 4);
478+
assert_eq!(z[0], 0);
479+
assert_eq!(z[1], 8);
480+
assert_eq!(reget_three[0], 0);
481+
assert_eq!(reget_three[1], 9);
482+
let mut _z = ags.alloc_cell(1);
483+
}
484+
}
485+
drop(malloc_global_buffer);
486+
}
458487
}
459488

460489

0 commit comments

Comments
 (0)