capypad
0 day streak
rust / expert
Snippet

Implementing a Custom Global Allocator

Rust allows overriding the default memory allocator for the entire program. By implementing the GlobalAlloc trait and using the #[global_allocator] attribute, you can inject custom logic into every allocation and deallocation, which is useful for memory profiling, telemetry, or specialized embedded requirements.

snippet.rs
rust
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
use std::alloc::{GlobalAlloc, Layout, System};
 
struct TrackingAllocator;
 
unsafe impl GlobalAlloc for TrackingAllocator {
unsafe fn alloc(&self, layout: Layout) -> *mut u8 {
println!("Allocating {} bytes", layout.size());
System.alloc(layout)
}
 
unsafe fn dealloc(&self, ptr: *mut u8, layout: Layout) {
println!("Deallocating {} bytes", layout.size());
System.dealloc(ptr, layout)
}
}
 
#[global_allocator]
static GLOBAL: TrackingAllocator = TrackingAllocator;
Breakdown
1
unsafe impl GlobalAlloc
Implementing this trait is unsafe because it must correctly manage raw pointers.
2
System.alloc(layout)
Delegates the actual memory work to the underlying system allocator (e.g., jemalloc or libc).
3
#[global_allocator]
A compiler attribute that registers the static variable as the program-wide allocator.