A robust, thread-safe implementation of dynamic memory allocation functions for UNIX systems, implementing the standard malloc interface with additional features for memory management and debugging.
This project implements the following memory allocation functions:
- malloc: Allocate memory of specified size
- free: Deallocate previously allocated memory
- realloc: Resize allocated memory
- calloc: Allocate and zero-initialize memory
- show_alloc_mem: Basic allocation visualization
- show_alloc_mem_ex: Detailed memory state with hex dumps
This custom malloc implementation is fully compatible with the standard C library malloc. It follows the same function signatures and behavior as defined in the C standard:
void *malloc(size_t size);
void free(void *ptr);
void *realloc(void *ptr, size_t size);
void *calloc(size_t nmemb, size_t size);
void show_alloc_mem(void);
void show_alloc_mem_ex(void);
Programs using standard memory allocation functions can use this implementation without any code modifications:
- Function parameters and return values match the standard malloc implementation
- Error handling follows the same conventions (returning NULL on failure)
- Memory alignment meets standard requirements
- Thread safety is maintained as in the system implementation
- All edge cases (NULL pointers, zero sizes) are handled correctly
- Simply use one of the linking methods described in the "Using the Library" section to replace the system malloc with this implementation in your programs.
Key features include:
- Zone-based allocation strategy for efficient memory management
- Thread-safe implementation using POSIX mutexes
- Memory visualization tools
- Memory defragmentation
- Minimal system calls for performance optimization
Memory is organized into three zone types:
- TINY: For allocations from 1 to 128 bytes
- SMALL: For allocations from 129 to 1024 bytes
- LARGE: For allocations larger than 1024 bytes
Zones are pre-allocated to minimize system calls, with each zone containing at least 100 allocations.
- Memory is mapped using
mmap
at program initialization - Zones are divided into blocks with metadata headers
- First-fit algorithm is used to find available blocks
- Blocks are split when significantly larger than requested size
- Adjacent free blocks are merged during defragmentation
Thread safety is ensured using a global mutex (g_malloc_mutex
) that protects all critical sections in the allocation and freeing operations.
Each allocated block contains:
- Metadata header (size, status, magic number)
- User data area
- Proper alignment (16-byte)
- Calculate required size including metadata and alignment
- Find appropriate zone type (TINY, SMALL, LARGE)
- Search for a free block of sufficient size
- Split block if necessary
- Mark block as allocated and return pointer to user data area
- Validate the pointer to ensure it's a proper allocation
- Mark the block as free
- Merge with adjacent free blocks when possible
- Perform zone defragmentation when fragmentation exceeds threshold
- Unmap LARGE zones when they become empty
# Clone the repository
git clone git@github.com:c-bertran/malloc.git
cd malloc
# Build the shared library
make
This creates a shared library file (libft_malloc_.so) and a symbolic link (libft_malloc.so).
# Run a program with your malloc implementation
env LD_PRELOAD=./libft_malloc.so <program>
# Compile your program with the custom malloc
gcc -o myprogram myprogram.c -L/path/to/malloc -lft_malloc
To enable debug output:
# Build with debug output enabled
make CFLAGS="-Wall -Wextra -Werror -fPIC -DDEBUG_MALLOC=1"
- basic: Simple malloc/free, calloc, realloc tests
- edge_cases: NULL pointers, zero-size, very large allocations
- performance: Many allocations, fragmentation handling
- thread: Thread-safety tests with concurrent allocations
- absurd: Extreme test cases to stress the implementation
- advanced: Real-world allocation patterns, stability tests
- gnl: Get Next Line test for real program allocation patterns
# Build library and run all tests
make test
# Run specific test suite
cd tests
make basic
make edge
make performance
make thread
make absurd
make advanced
make gnl
The tests verify:
- Memory integrity
- Thread safety
- Performance under load
- Edge case handling
- Memory leak detection
- Stability in long-running scenarios
- Memory Visualization