36#ifdef WITH_MEM_VALGRIND
37# include "valgrind/memcheck.h"
43# define POISON_REDZONE_SIZE 32
45# define POISON_REDZONE_SIZE 0
50#define MAKE_ID(a, b, c, d) (int(d) << 24 | int(c) << 16 | (b) << 8 | (a))
51#define MAKE_ID_8(a, b, c, d, e, f, g, h) \
52 (int64_t(h) << 56 | int64_t(g) << 48 | int64_t(f) << 40 | int64_t(e) << 32 | int64_t(d) << 24 | \
53 int64_t(c) << 16 | int64_t(b) << 8 | (a))
62 ((sizeof(void *) > sizeof(int32_t)) ? MAKE_ID_8('e', 'e', 'r', 'f', 'f', 'r', 'e', 'e') : \
63 MAKE_ID('e', 'f', 'f', 'e'))
68#define USEDWORD MAKE_ID('u', 's', 'e', 'd')
127#define MEMPOOL_ELEM_SIZE_MIN (sizeof(void *) * 2)
129#define CHUNK_DATA(chunk) \
130 ((BLI_freenode *)(CHECK_TYPE_INLINE(chunk, BLI_mempool_chunk *), (void *)((chunk) + 1)))
132#define NODE_STEP_NEXT(node) ((BLI_freenode *)((char *)(node) + esize))
133#define NODE_STEP_PREV(node) ((BLI_freenode *)((char *)(node) - esize))
136#define CHUNK_OVERHEAD uint(MEM_SIZE_OVERHEAD + sizeof(BLI_mempool_chunk))
158 while (index-- && head) {
172 return (elem_num <= pchunk) ? 1 : ((elem_num / pchunk) + 1);
207 mpchunk->
next =
nullptr;
211 pool->
free = curnode;
221#ifdef WITH_MEM_VALGRIND
228#ifdef WITH_MEM_VALGRIND
229 VALGRIND_MAKE_MEM_UNDEFINED(curnode, pool->
esize);
239#ifdef WITH_MEM_VALGRIND
244#ifdef WITH_MEM_VALGRIND
245 VALGRIND_MAKE_MEM_UNDEFINED(curnode, pool->
esize);
258#ifdef WITH_MEM_VALGRIND
260 VALGRIND_MAKE_MEM_UNDEFINED(curnode, pool->
esize);
267#ifdef WITH_MEM_VALGRIND
271 curnode->
next =
nullptr;
273#ifdef WITH_MEM_VALGRIND
274 VALGRIND_MAKE_MEM_UNDEFINED(curnode, pool->
esize);
280#ifdef WITH_MEM_VALGRIND
285#ifdef WITH_MEM_VALGRIND
286 VALGRIND_MAKE_MEM_UNDEFINED(last_tail, pool->
esize);
300#ifdef WITH_MEM_VALGRIND
310 for (; mpchunk; mpchunk = mpchunk_next) {
311 mpchunk_next = mpchunk->
next;
352 pool->
csize = esize * pchunk;
355#if defined(USE_CHUNK_POW2) && !defined(NDEBUG)
364 pool->
free =
nullptr;
370 for (
i = 0;
i < maxchunks;
i++) {
376#ifdef WITH_MEM_VALGRIND
393 free_pop = pool->
free;
396#ifdef WITH_MEM_VALGRIND
417#ifdef WITH_MEM_VALGRIND
421 return (
void *)free_pop;
441 for (chunk = pool->
chunks; chunk; chunk = chunk->
next) {
448 BLI_assert_msg(0,
"Attempt to free data which is not in pool.\n");
467 pool->
free = newhead;
473#ifdef WITH_MEM_VALGRIND
474 VALGRIND_MEMPOOL_FREE(pool, addr);
486 first->
next =
nullptr;
490#ifdef WITH_MEM_VALGRIND
495 pool->
free = curnode;
512 curnode->
next =
nullptr;
515#ifdef WITH_MEM_VALGRIND
516 VALGRIND_MEMPOOL_FREE(pool,
CHUNK_DATA(first));
534 if (index < pool->totused) {
556 char *p =
static_cast<char *
>(
data);
563 memcpy(p, elem,
size_t(esize));
571 char *
data =
static_cast<char *
>(
604 for (
size_t i = 1;
i < iter_num;
i++) {
607 ((*curchunk_threaded_shared) ? (*curchunk_threaded_shared)->next :
nullptr);
649 ret = bli_mempool_iternext(iter);
670# ifdef WITH_MEM_VALGRIND
682# ifdef WITH_MEM_VALGRIND
689# ifdef WITH_MEM_VALGRIND
719# ifdef WITH_MEM_VALGRIND
742# ifdef WITH_MEM_VALGRIND
757# ifdef WITH_MEM_VALGRIND
772# ifdef WITH_MEM_VALGRIND
796#ifdef WITH_MEM_VALGRIND
801 if (elem_num_reserve == -1) {
810 if (mpchunk && mpchunk->
next) {
812 mpchunk_next = mpchunk->
next;
813 mpchunk->
next =
nullptr;
814 mpchunk = mpchunk_next;
817 mpchunk_next = mpchunk->
next;
819 }
while ((mpchunk = mpchunk_next));
823 pool->
free =
nullptr;
825 chunks_temp = pool->
chunks;
829 while ((mpchunk = chunks_temp)) {
830 chunks_temp = mpchunk->
next;
844#ifdef WITH_MEM_VALGRIND
#define BLI_asan_unpoison(addr, size)
#define BLI_asan_poison(addr, size)
#define BLI_assert_msg(a, msg)
MINLINE unsigned int power_of_2_max_u(unsigned int x)
#define VALGRIND_MEMPOOL_ALLOC(pool, addr, size)
#define VALGRIND_CREATE_MEMPOOL(pool, rzB, is_zeroed)
#define VALGRIND_DESTROY_MEMPOOL(pool)
#define MEMPOOL_ELEM_SIZE_MIN
void BLI_mempool_clear_ex(BLI_mempool *pool, const int elem_num_reserve)
#define NODE_STEP_PREV(node)
static bool mempool_debug_memset
ParallelMempoolTaskData * mempool_iter_threadsafe_create(BLI_mempool *pool, const size_t iter_num)
void * BLI_mempool_findelem(BLI_mempool *pool, uint index)
#define CHUNK_DATA(chunk)
void BLI_mempool_as_array(BLI_mempool *pool, void *data)
static void mempool_asan_lock(BLI_mempool *pool)
void mempool_iter_threadsafe_destroy(ParallelMempoolTaskData *iter_arr)
void * BLI_mempool_as_arrayN(BLI_mempool *pool, const char *allocstr)
void * BLI_mempool_alloc(BLI_mempool *pool)
int BLI_mempool_len(const BLI_mempool *pool)
void BLI_mempool_free(BLI_mempool *pool, void *addr)
void BLI_mempool_clear(BLI_mempool *pool)
static BLI_mempool_chunk * mempool_chunk_alloc(const BLI_mempool *pool)
static void mempool_threadsafe_iternew(BLI_mempool *pool, BLI_mempool_threadsafe_iter *ts_iter)
void BLI_mempool_iternew(BLI_mempool *pool, BLI_mempool_iter *iter)
static void mempool_asan_unlock(BLI_mempool *pool)
static void mempool_chunk_free(BLI_mempool_chunk *mpchunk, BLI_mempool *pool)
void * mempool_iter_threadsafe_step(BLI_mempool_threadsafe_iter *ts_iter)
void * BLI_mempool_calloc(BLI_mempool *pool)
void BLI_mempool_destroy(BLI_mempool *pool)
void * BLI_mempool_iterstep(BLI_mempool_iter *iter)
void BLI_mempool_set_memory_debug()
#define POISON_REDZONE_SIZE
static BLI_freenode * mempool_chunk_add(BLI_mempool *pool, BLI_mempool_chunk *mpchunk, BLI_freenode *last_tail)
BLI_mempool * BLI_mempool_create(uint esize, uint elem_num, uint pchunk, uint flag)
static void mempool_chunk_free_all(BLI_mempool_chunk *mpchunk, BLI_mempool *pool)
#define NODE_STEP_NEXT(node)
BLI_INLINE BLI_mempool_chunk * mempool_chunk_find(BLI_mempool_chunk *head, uint index)
BLI_INLINE uint mempool_maxchunks(const uint elem_num, const uint pchunk)
void BLI_mutex_init(ThreadMutex *mutex)
void BLI_mutex_lock(ThreadMutex *mutex)
void BLI_mutex_unlock(ThreadMutex *mutex)
pthread_mutex_t ThreadMutex
#define ARRAY_HAS_ITEM(arr_item, arr_start, arr_len)
#define POINTER_OFFSET(v, ofs)
Read Guarded memory(de)allocation.
#define MEM_SIZE_OVERHEAD
Provides wrapper around system-specific atomic primitives, and some extensions (faked-atomic operatio...
ATOMIC_INLINE void * atomic_cas_ptr(void **v, void *old, void *_new)
BMesh const char void * data
void * MEM_mallocN(size_t len, const char *str)
void * MEM_calloc_arrayN(size_t len, size_t size, const char *str)
void * MEM_callocN(size_t len, const char *str)
void * MEM_malloc_arrayN(size_t len, size_t size, const char *str)
void MEM_freeN(void *vmemh)
struct BLI_mempool_chunk * curchunk
struct BLI_mempool_chunk ** curchunk_threaded_shared
BLI_mempool_chunk * chunks
BLI_mempool_chunk * chunk_tail
BLI_mempool_threadsafe_iter ts_iter