pub struct BoundedAllocator<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> { /* private fields */ }Expand description
Static pre-allocated bounded global allocator.
Generic parameters
MAX_BLOCKS— maximum number of simultaneously-live blocks.BLOCK_SIZE— maximum bytes per allocation. Should be a multiple of 64 to avoid intra-block padding.BITMAP_WORDS— must be(MAX_BLOCKS + 63) / 64. Use thedeclare_global_allocator!/bounded_allocator!macros to compute it automatically.
Implementations§
Source§impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
Sourcepub const fn new() -> Self
pub const fn new() -> Self
Construct a fresh allocator. Intended for use as a static
initialiser.
All bitmap words are initialised to all-ones, meaning every
block is free. The few tail bits past MAX_BLOCKS in the
last word are also set, but the bit-scan refuses to allocate
them (block index >= MAX_BLOCKS rejection).
Sourcepub fn lock(&self)
pub fn lock(&self)
Engage lock-after-init mode. Every subsequent alloc call
panics immediately. One-way: there is no unlock method.
Sourcepub fn is_locked(&self) -> bool
pub fn is_locked(&self) -> bool
Is the allocator locked? See Self::lock.
Sourcepub fn alloc_count(&self) -> usize
pub fn alloc_count(&self) -> usize
Total successful alloc calls since process start.
Examples found in repository?
examples/fail_closed.rs (line 48)
33fn main() {
34 println!("taktora-bounded-alloc fail_closed demo");
35 println!("arena: {MAX_BLOCKS} blocks × {BLOCK_SIZE} bytes");
36 println!(
37 "blocks already in use after Rust runtime startup: {}",
38 ALLOC.live_blocks()
39 );
40 println!();
41
42 let mut held: Vec<Box<[u8; 1024]>> = Vec::new();
43 for i in 0_u32..64 {
44 let b: Box<[u8; 1024]> = Box::new([(i & 0xff) as u8; 1024]);
45 held.push(b);
46 println!(
47 "iter {i}: alloc_count={}, live={}, peak={}, held={}",
48 ALLOC.alloc_count(),
49 ALLOC.live_blocks(),
50 ALLOC.peak_blocks_used(),
51 held.len()
52 );
53 }
54
55 // Unreachable: an allocation past the cap returns null, and
56 // Rust's default alloc_error_handler aborts the process.
57 println!("unexpectedly reached end of main (cap was not exhausted)");
58}Sourcepub fn dealloc_count(&self) -> usize
pub fn dealloc_count(&self) -> usize
Total dealloc calls since process start.
Sourcepub fn peak_blocks_used(&self) -> usize
pub fn peak_blocks_used(&self) -> usize
High-water mark of simultaneously-live blocks.
Examples found in repository?
examples/fail_closed.rs (line 50)
33fn main() {
34 println!("taktora-bounded-alloc fail_closed demo");
35 println!("arena: {MAX_BLOCKS} blocks × {BLOCK_SIZE} bytes");
36 println!(
37 "blocks already in use after Rust runtime startup: {}",
38 ALLOC.live_blocks()
39 );
40 println!();
41
42 let mut held: Vec<Box<[u8; 1024]>> = Vec::new();
43 for i in 0_u32..64 {
44 let b: Box<[u8; 1024]> = Box::new([(i & 0xff) as u8; 1024]);
45 held.push(b);
46 println!(
47 "iter {i}: alloc_count={}, live={}, peak={}, held={}",
48 ALLOC.alloc_count(),
49 ALLOC.live_blocks(),
50 ALLOC.peak_blocks_used(),
51 held.len()
52 );
53 }
54
55 // Unreachable: an allocation past the cap returns null, and
56 // Rust's default alloc_error_handler aborts the process.
57 println!("unexpectedly reached end of main (cap was not exhausted)");
58}Sourcepub fn live_blocks(&self) -> usize
pub fn live_blocks(&self) -> usize
Currently-live block count.
Examples found in repository?
examples/fail_closed.rs (line 38)
33fn main() {
34 println!("taktora-bounded-alloc fail_closed demo");
35 println!("arena: {MAX_BLOCKS} blocks × {BLOCK_SIZE} bytes");
36 println!(
37 "blocks already in use after Rust runtime startup: {}",
38 ALLOC.live_blocks()
39 );
40 println!();
41
42 let mut held: Vec<Box<[u8; 1024]>> = Vec::new();
43 for i in 0_u32..64 {
44 let b: Box<[u8; 1024]> = Box::new([(i & 0xff) as u8; 1024]);
45 held.push(b);
46 println!(
47 "iter {i}: alloc_count={}, live={}, peak={}, held={}",
48 ALLOC.alloc_count(),
49 ALLOC.live_blocks(),
50 ALLOC.peak_blocks_used(),
51 held.len()
52 );
53 }
54
55 // Unreachable: an allocation past the cap returns null, and
56 // Rust's default alloc_error_handler aborts the process.
57 println!("unexpectedly reached end of main (cap was not exhausted)");
58}Sourcepub const fn capacity_bytes(&self) -> usize
pub const fn capacity_bytes(&self) -> usize
Total arena bytes addressed by this allocator.
Trait Implementations§
Source§impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> Default for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> Default for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
Source§impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> GlobalAlloc for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> GlobalAlloc for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
Source§unsafe fn alloc(&self, layout: Layout) -> *mut u8
unsafe fn alloc(&self, layout: Layout) -> *mut u8
Allocates memory as described by the given
layout. Read moreAuto Trait Implementations§
impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> !Freeze for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> !RefUnwindSafe for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> Send for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> Sync for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> Unpin for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> UnsafeUnpin for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
impl<const MAX_BLOCKS: usize, const BLOCK_SIZE: usize, const BITMAP_WORDS: usize> UnwindSafe for BoundedAllocator<MAX_BLOCKS, BLOCK_SIZE, BITMAP_WORDS>
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Mutably borrows from an owned value. Read more