#ifndef __MAGAZINE_RACK_H
#define __MAGAZINE_RACK_H
typedef void *region_t;
typedef region_t *rgnhdl_t;
#define INITIAL_NUM_REGIONS_SHIFT 6 // log2(INITIAL_NUM_REGIONS)
#define INITIAL_NUM_REGIONS (1 << INITIAL_NUM_REGIONS_SHIFT) // Must be a power of 2!
#define HASHRING_OPEN_ENTRY ((region_t)0) // Initial value and sentinel marking end of collision chain
#define HASHRING_REGION_DEALLOCATED ((region_t)-1) // Region at this slot reclaimed by OS
#define HASH_BLOCKS_ALIGN TINY_BLOCKS_ALIGN // MIN( TINY_BLOCKS_ALIGN, SMALL_BLOCKS_ALIGN, ... )
typedef struct region_hash_generation {
size_t num_regions_allocated;
size_t num_regions_allocated_shift; region_t *hashed_regions; struct region_hash_generation *nextgen;
} region_hash_generation_t;
OS_ENUM(rack_type, uint32_t,
RACK_TYPE_NONE = 0,
RACK_TYPE_TINY,
RACK_TYPE_SMALL,
RACK_TYPE_MEDIUM,
);
typedef struct rack_s {
_malloc_lock_s region_lock MALLOC_CACHE_ALIGN;
rack_type_t type;
size_t num_regions;
size_t num_regions_dealloc;
region_hash_generation_t *region_generation;
region_hash_generation_t rg[2];
region_t initial_regions[INITIAL_NUM_REGIONS];
int num_magazines;
unsigned num_magazines_mask;
int num_magazines_mask_shift;
uint32_t debug_flags;
magazine_t *magazines;
uintptr_t cookie;
uintptr_t last_madvise;
} rack_t;
MALLOC_NOEXPORT
void
rack_init(rack_t *rack, rack_type_t type, uint32_t num_magazines, uint32_t debug_flags);
MALLOC_NOEXPORT
void
rack_destroy_regions(rack_t *rack, size_t region_size);
MALLOC_NOEXPORT
void
rack_destroy(rack_t *rack);
MALLOC_NOEXPORT
void
rack_region_insert(rack_t *rack, region_t region);
#endif // __MAGAZINE_RACK_H