You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
80 lines
2.5 KiB
80 lines
2.5 KiB
#ifndef ALLOCATOR_INTERNAL_H
|
|
#define ALLOCATOR_INTERNAL_H
|
|
|
|
#include <stdint.h>
|
|
|
|
// No enum because these need to be 1 byte
|
|
const char RT_FREESPACE = 0;
|
|
const char RT_TREE_NODE = 1;
|
|
const char RT_WATERMARK = 2;
|
|
|
|
const char COLOR_RED = 0;
|
|
const char COLOR_BLACK = 1;
|
|
|
|
const uintptr_t MIN_NEW_MEM_SIZE = 4096;
|
|
|
|
typedef struct Arena {
|
|
struct FreeSpace *root_freespace;
|
|
struct TreeAlloc *root_treealloc;
|
|
void *(*get_new_region)(uintptr_t);
|
|
void (*error)(char*);
|
|
} Arena;
|
|
|
|
// All three of these types should be memory-compatible with each other
|
|
|
|
// Before I forget to write it down: It is assumed that the beginning of every allocation region (or
|
|
// free space region) is aligned to the alignment of all three of these types (or WatermarkAlloc since
|
|
// it has at least all the fields of the other one). This allows for the allocation record to appear
|
|
// at the beginning of the region and still be aligned. As a consequence, all sizes are a multiple of
|
|
// the alignment.
|
|
|
|
typedef struct TreeAlloc {
|
|
char type; // Should be RT_TREE_NODE
|
|
char color;
|
|
struct TreeAlloc *parent;
|
|
struct TreeAlloc *left;
|
|
struct TreeAlloc *right;
|
|
uintptr_t size;
|
|
struct TreeAlloc *before;
|
|
struct TreeAlloc *after;
|
|
} TreeAlloc;
|
|
|
|
typedef struct FreeSpace {
|
|
char type; // Should be RT_FREESPACE
|
|
char color;
|
|
struct FreeSpace *parent;
|
|
struct FreeSpace *left;
|
|
struct FreeSpace *right;
|
|
uintptr_t size;
|
|
} FreeSpace;
|
|
|
|
typedef struct WatermarkAlloc {
|
|
char type; // Should be RT_WATERMARK
|
|
char color;
|
|
struct TreeAlloc *parent;
|
|
struct TreeAlloc *left;
|
|
struct TreeAlloc *right;
|
|
uintptr_t size;
|
|
struct TreeAlloc *before;
|
|
struct TreeAlloc *after;
|
|
int num_allocs;
|
|
void *next_alloc;
|
|
} WatermarkAlloc;
|
|
|
|
void* align_after(void* address, uintptr_t align);
|
|
uintptr_t lcm(uintptr_t a, uintptr_t b);
|
|
uintptr_t gcd(uintptr_t a, uintptr_t b);
|
|
TreeAlloc *search_by_address(TreeAlloc *root, void *address);
|
|
TreeAlloc *search_by_size(TreeAlloc *root, uintptr_t padding, uintptr_t align, uintptr_t size);
|
|
TreeAlloc *get_sibling(TreeAlloc *p, TreeAlloc *ta);
|
|
void rotate_left(TreeAlloc **root_ptr, TreeAlloc *ta);
|
|
void rotate_right(TreeAlloc **root_ptr, TreeAlloc *ta);
|
|
void repair_tree_after_insert(TreeAlloc **root_ptr, TreeAlloc *ta);
|
|
void remove_node(TreeAlloc** root_ptr, TreeAlloc* node);
|
|
void insert_singleton(TreeAlloc **root_ptr, TreeAlloc *to_insert);
|
|
void insert_by_size(TreeAlloc** root_ptr, TreeAlloc* to_insert);
|
|
void insert_by_addr(TreeAlloc** root_ptr, TreeAlloc* to_insert);
|
|
void unalloc(Arena *arena, void *addr);
|
|
void *alloc(Arena *arena, uintptr_t size, uintptr_t align);
|
|
|
|
#endif
|