#![no_std]
#![deny(missing_docs)]
#![allow(dead_code)]
#![allow(clippy::missing_safety_doc)]
use core::cmp;
use core::ptr;
mod common;
mod dlmalloc;
mod dlverbose;
#[cfg(all(feature = "global", not(test)))]
mod global;
#[cfg(all(feature = "global", not(test)))]
pub use self::global::GlobalDlmalloc;
#[cfg(all(feature = "global", not(test)))]
pub use global::get_alloced_mem_size;
pub struct Dlmalloc(dlmalloc::Dlmalloc);
pub const DLMALLOC_INIT: Dlmalloc = Dlmalloc(dlmalloc::DLMALLOC_INIT);
#[cfg(target_arch = "wasm32")]
#[path = "wasm.rs"]
mod sys;
#[cfg(target_os = "macos")]
#[path = "macos.rs"]
mod sys;
#[cfg(target_os = "linux")]
#[path = "linux.rs"]
mod sys;
#[cfg(target_os = "windows")]
#[path = "windows.rs"]
mod sys;
#[allow(clippy::new_without_default)]
impl Dlmalloc {
pub fn new() -> Dlmalloc {
DLMALLOC_INIT
}
#[inline]
pub unsafe fn malloc(&mut self, size: usize, align: usize) -> *mut u8 {
if align <= self.0.malloc_alignment() {
self.0.malloc(size)
} else {
self.0.memalign(align, size)
}
}
#[inline]
pub unsafe fn calloc(&mut self, size: usize, align: usize) -> *mut u8 {
dlverbose!("DL CALLOC");
let ptr = self.malloc(size, align);
if !ptr.is_null() {
ptr::write_bytes(ptr, 0, size);
}
ptr
}
#[inline]
pub unsafe fn free(&mut self, ptr: *mut u8, _size: usize, _align: usize) {
self.0.free(ptr)
}
#[inline]
pub unsafe fn realloc(
&mut self,
ptr: *mut u8,
old_size: usize,
old_align: usize,
new_size: usize,
) -> *mut u8 {
if old_align <= self.0.malloc_alignment() {
self.0.realloc(ptr, new_size)
} else {
let res = self.malloc(new_size, old_align);
if !res.is_null() {
let size = cmp::min(old_size, new_size);
ptr::copy_nonoverlapping(ptr, res, size);
self.free(ptr, old_size, old_align);
}
res
}
}
pub unsafe fn get_alloced_mem_size(&self) -> usize {
self.0.get_alloced_mem_size()
}
}