Skip to content

Commit ff3db11

Browse files
Implemented Unix memory allocation APIs.
1 parent 010d66f commit ff3db11

File tree

3 files changed

+208
-1
lines changed

3 files changed

+208
-1
lines changed

Cargo.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ nstd_heap_ptr = ["nstd_alloc", "nstd_core"]
3333
nstd_io = ["nstd_alloc", "nstd_core", "nstd_string", "nstd_vec", "std"]
3434
nstd_math = ["std"]
3535
nstd_os = []
36-
nstd_os_unix_alloc = []
36+
nstd_os_unix_alloc = ["libc", "nstd_core", "nstd_os"]
3737
nstd_os_unix_shared_lib = ["libc", "nstd_core", "nstd_os"]
3838
nstd_os_windows_alloc = [
3939
"nstd_core", "nstd_os", "windows-sys/Win32_Foundation", "windows-sys/Win32_System_Memory"

include/nstd/os/unix/alloc.h

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,64 @@
11
#ifndef NSTD_OS_UNIX_ALLOC_H
22
#define NSTD_OS_UNIX_ALLOC_H
3+
#include "../../core/def.h"
4+
#include "../../nstd.h"
5+
6+
/// Allocates a block of memory on the heap, returning a pointer to it.
7+
///
8+
/// # Parameters:
9+
///
10+
/// - `NSTDUInt size` - The number of bytes to allocate for the new block of memory.
11+
///
12+
/// # Returns
13+
///
14+
/// `NSTDAnyMut ptr` - A pointer to the newly allocated block of memory, or null on error.
15+
///
16+
/// # Safety
17+
///
18+
/// See <https://man7.org/linux/man-pages/man3/malloc.3.html>.
19+
NSTDAPI NSTDAnyMut nstd_os_unix_alloc_allocate(NSTDUInt size);
20+
21+
/// Allocates a block of zero initialized memory on the heap, returning a pointer to it.
22+
///
23+
/// # Parameters:
24+
///
25+
/// - `NSTDUInt size` - The number of bytes to allocate for the new block of memory.
26+
///
27+
/// # Returns
28+
///
29+
/// `NSTDAnyMut ptr` - A pointer to the newly allocated block of memory, or null on error.
30+
///
31+
/// # Safety
32+
///
33+
/// See <https://man7.org/linux/man-pages/man3/calloc.3p.html>.
34+
NSTDAPI NSTDAnyMut nstd_os_unix_alloc_allocate_zeroed(NSTDUInt size);
35+
36+
/// Reallocates a block of memory previously allocated by `nstd_os_unix_alloc_allocate[_zeroed]`.
37+
///
38+
/// # Parameters:
39+
///
40+
/// - `NSTDAnyMut *ptr` - A pointer to the block of memory to reallocate.
41+
///
42+
/// - `NSTDUInt new_size` - The new size of the memory block.
43+
///
44+
/// # Returns
45+
///
46+
/// `NSTDErrorCode errc` - Nonzero if reallocating fails.
47+
///
48+
/// # Safety
49+
///
50+
/// See <https://man7.org/linux/man-pages/man3/realloc.3p.html>.
51+
NSTDAPI NSTDErrorCode nstd_os_unix_alloc_reallocate(NSTDAnyMut *ptr, NSTDUInt new_size);
52+
53+
/// Deallocates a block of memory previously allocated by `nstd_os_unix_alloc_allocate[_zeroed]`.
54+
///
55+
/// # Parameters:
56+
///
57+
/// - `NSTDAnyMut *ptr` - A pointer to the block of memory to free.
58+
///
59+
/// # Safety
60+
///
61+
/// See <https://man7.org/linux/man-pages/man3/free.3p.html>.
62+
NSTDAPI void nstd_os_unix_alloc_deallocate(NSTDAnyMut *ptr);
63+
364
#endif

src/os/unix/alloc.rs

Lines changed: 146 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,147 @@
11
//! Memory allocation for Unix-like systems.
2+
use crate::{core::def::NSTDErrorCode, NSTDAnyMut, NSTDUInt, NSTD_NULL};
3+
use libc::{calloc, free, malloc, realloc};
4+
5+
/// Allocates a block of memory on the heap, returning a pointer to it.
6+
///
7+
/// # Parameters:
8+
///
9+
/// - `NSTDUInt size` - The number of bytes to allocate for the new block of memory.
10+
///
11+
/// # Returns
12+
///
13+
/// `NSTDAnyMut ptr` - A pointer to the newly allocated block of memory, or null on error.
14+
///
15+
/// # Safety
16+
///
17+
/// See <https://man7.org/linux/man-pages/man3/malloc.3.html>.
18+
///
19+
/// # Example
20+
///
21+
/// ```
22+
/// use nstd_sys::os::unix::alloc::{nstd_os_unix_alloc_allocate, nstd_os_unix_alloc_deallocate};
23+
///
24+
/// unsafe {
25+
/// let mut mem = nstd_os_unix_alloc_allocate(24);
26+
/// assert!(!mem.is_null());
27+
/// nstd_os_unix_alloc_deallocate(&mut mem);
28+
/// }
29+
/// ```
30+
#[inline]
31+
#[cfg_attr(feature = "clib", no_mangle)]
32+
pub unsafe extern "C" fn nstd_os_unix_alloc_allocate(size: NSTDUInt) -> NSTDAnyMut {
33+
malloc(size)
34+
}
35+
36+
/// Allocates a block of zero initialized memory on the heap, returning a pointer to it.
37+
///
38+
/// # Parameters:
39+
///
40+
/// - `NSTDUInt size` - The number of bytes to allocate for the new block of memory.
41+
///
42+
/// # Returns
43+
///
44+
/// `NSTDAnyMut ptr` - A pointer to the newly allocated block of memory, or null on error.
45+
///
46+
/// # Safety
47+
///
48+
/// See <https://man7.org/linux/man-pages/man3/calloc.3p.html>.
49+
///
50+
/// # Example
51+
///
52+
/// ```
53+
/// use nstd_sys::os::unix::alloc::{
54+
/// nstd_os_unix_alloc_allocate_zeroed, nstd_os_unix_alloc_deallocate,
55+
/// };
56+
///
57+
/// const SIZE: usize = core::mem::size_of::<isize>();
58+
///
59+
/// unsafe {
60+
/// let mut mem = nstd_os_unix_alloc_allocate_zeroed(SIZE);
61+
/// assert!(!mem.is_null());
62+
/// assert!(*mem.cast::<isize>() == 0);
63+
/// nstd_os_unix_alloc_deallocate(&mut mem);
64+
/// }
65+
/// ```
66+
#[inline]
67+
#[cfg_attr(feature = "clib", no_mangle)]
68+
pub unsafe extern "C" fn nstd_os_unix_alloc_allocate_zeroed(size: NSTDUInt) -> NSTDAnyMut {
69+
calloc(size, 1)
70+
}
71+
72+
/// Reallocates a block of memory previously allocated by `nstd_os_unix_alloc_allocate[_zeroed]`.
73+
///
74+
/// # Parameters:
75+
///
76+
/// - `NSTDAnyMut *ptr` - A pointer to the block of memory to reallocate.
77+
///
78+
/// - `NSTDUInt new_size` - The new size of the memory block.
79+
///
80+
/// # Returns
81+
///
82+
/// `NSTDErrorCode errc` - Nonzero if reallocating fails.
83+
///
84+
/// # Safety
85+
///
86+
/// See <https://man7.org/linux/man-pages/man3/realloc.3p.html>.
87+
///
88+
/// # Example
89+
///
90+
/// ```
91+
/// use nstd_sys::os::unix::alloc::{
92+
/// nstd_os_unix_alloc_allocate_zeroed, nstd_os_unix_alloc_deallocate,
93+
/// nstd_os_unix_alloc_reallocate,
94+
/// };
95+
///
96+
/// const SIZE: usize = core::mem::size_of::<u64>();
97+
/// const NEW_SIZE: usize = core::mem::size_of::<u32>();
98+
///
99+
/// unsafe {
100+
/// let mut mem = nstd_os_unix_alloc_allocate_zeroed(SIZE);
101+
/// assert!(!mem.is_null());
102+
/// assert!(nstd_os_unix_alloc_reallocate(&mut mem, NEW_SIZE) == 0);
103+
/// assert!(*mem.cast::<u32>() == 0);
104+
/// nstd_os_unix_alloc_deallocate(&mut mem);
105+
/// }
106+
/// ```
107+
#[inline]
108+
#[cfg_attr(feature = "clib", no_mangle)]
109+
pub unsafe extern "C" fn nstd_os_unix_alloc_reallocate(
110+
ptr: &mut NSTDAnyMut,
111+
new_size: NSTDUInt,
112+
) -> NSTDErrorCode {
113+
let new_mem = realloc(*ptr, new_size);
114+
if !new_mem.is_null() {
115+
*ptr = new_mem;
116+
return 0;
117+
}
118+
1
119+
}
120+
121+
/// Deallocates a block of memory previously allocated by `nstd_os_unix_alloc_allocate[_zeroed]`.
122+
///
123+
/// # Parameters:
124+
///
125+
/// - `NSTDAnyMut *ptr` - A pointer to the block of memory to free.
126+
///
127+
/// # Safety
128+
///
129+
/// See <https://man7.org/linux/man-pages/man3/free.3p.html>.
130+
///
131+
/// # Example
132+
///
133+
/// ```
134+
/// use nstd_sys::os::unix::alloc::{nstd_os_unix_alloc_allocate, nstd_os_unix_alloc_deallocate};
135+
///
136+
/// unsafe {
137+
/// let mut mem = nstd_os_unix_alloc_allocate(32);
138+
/// assert!(!mem.is_null());
139+
/// nstd_os_unix_alloc_deallocate(&mut mem);
140+
/// }
141+
/// ```
142+
#[inline]
143+
#[cfg_attr(feature = "clib", no_mangle)]
144+
pub unsafe extern "C" fn nstd_os_unix_alloc_deallocate(ptr: &mut NSTDAnyMut) {
145+
free(*ptr);
146+
*ptr = NSTD_NULL;
147+
}

0 commit comments

Comments
 (0)