diff --git a/include/mimalloc/prim.h b/include/mimalloc/prim.h index 97d8b45d..68f0871e 100644 --- a/include/mimalloc/prim.h +++ b/include/mimalloc/prim.h @@ -104,12 +104,13 @@ void _mi_prim_thread_associate_default_heap(mi_heap_t* heap); //------------------------------------------------------------------- -// Thread id +// Thread id: `_mi_prim_thread_id()` // // Getting the thread id should be performant as it is called in the // fast path of `_mi_free` and we specialize for various platforms as // inlined definitions. Regular code should call `init.c:_mi_thread_id()`. -// We only require _mi_prim_thread_id() to return a unique id for each thread. +// We only require _mi_prim_thread_id() to return a unique id +// for each thread (unequal to zero). //------------------------------------------------------------------- static inline mi_threadid_t _mi_prim_thread_id(void) mi_attr_noexcept; diff --git a/src/init.c b/src/init.c index b402a3df..fcfcb659 100644 --- a/src/init.c +++ b/src/init.c @@ -409,15 +409,24 @@ void mi_thread_done(void) mi_attr_noexcept { _mi_thread_done(NULL); } +#include + void _mi_thread_done(mi_heap_t* heap) { - mi_atomic_decrement_relaxed(&thread_count); - _mi_stat_decrease(&_mi_stats_main.threads, 1); - + // calling with NULL implies using the default heap if (heap == NULL) { heap = mi_prim_get_default_heap(); if (heap == NULL) return; } + + // prevent re-entrancy through heap_done/heap_set_default_direct (issue #699) + if (!mi_heap_is_initialized(heap)) { + return; + } + + // adjust stats + mi_atomic_decrement_relaxed(&thread_count); + _mi_stat_decrease(&_mi_stats_main.threads, 1); // check thread-id as on Windows shutdown with FLS the main (exit) thread may call this on thread-local heaps... if (heap->thread_id != _mi_thread_id()) return; diff --git a/src/prim/unix/prim.c b/src/prim/unix/prim.c index 0ac69f1a..ac23e5ca 100644 --- a/src/prim/unix/prim.c +++ b/src/prim/unix/prim.c @@ -629,8 +629,8 @@ bool _mi_prim_getenv(const char* name, char* result, size_t result_size) { if (len == 0) return false; char** env = mi_get_environ(); if (env == NULL) return false; - // compare up to 256 entries - for (int i = 0; i < 256 && env[i] != NULL; i++) { + // compare up to 64K entries + for (int i = 0; i < 64*MI_KiB && env[i] != NULL; i++) { const char* s = env[i]; if (_mi_strnicmp(name, s, len) == 0 && s[len] == '=') { // case insensitive // found it diff --git a/test/main-override.cpp b/test/main-override.cpp index 65df79f1..18ec610c 100644 --- a/test/main-override.cpp +++ b/test/main-override.cpp @@ -39,12 +39,16 @@ static void strdup_test(); // issue #445 static void bench_alloc_large(void); // issue #xxx static void test_large_migrate(void); // issue #691 static void heap_thread_free_huge(); +static void test_std_string(); // issue #697 static void test_stl_allocators(); int main() { mi_stats_reset(); // ignore earlier allocations + + // test_std_string(); + // heap_thread_free_huge(); /* heap_thread_free_huge(); heap_thread_free_large(); @@ -237,6 +241,13 @@ static void heap_no_delete() { } +// Issue #697 +static void test_std_string() { + std::string path = "/Users/xxxx/Library/Developer/Xcode/DerivedData/xxxxxxxxxx/Build/Intermediates.noindex/xxxxxxxxxxx/arm64/XX_lto.o/0.arm64.lto.o"; + std::string path1 = "/Users/xxxx/Library/Developer/Xcode/DerivedData/xxxxxxxxxx/Build/Intermediates.noindex/xxxxxxxxxxx/arm64/XX_lto.o/1.arm64.lto.o"; + std::cout << path + "\n>>> " + path1 + "\n>>> " << std::endl; +} + // Issue #204 static volatile void* global_p;