From 0399af1019240e2d9127a588ddc8e31ff4656df0 Mon Sep 17 00:00:00 2001 From: Aliaksey Kandratsenka Date: Tue, 1 Apr 2014 21:30:27 -0700 Subject: [PATCH] added tc_malloc_skip_new_handler This is port of corresponding chromium change at: https://codereview.chromium.org/55333002/ Basic idea is that sometimes apps that use tc_set_new_mode in order to have C++ out-of-memory handler catch OOMs in malloc, need to invoke usual malloc that returns 0 on OOM. That new API is exactly for that. It'll always return NULL on OOM even if tc_new_mode is set to true. --- src/debugallocation.cc | 6 ++++++ src/gperftools/tcmalloc.h.in | 1 + src/tcmalloc.cc | 6 ++++++ src/tests/tcmalloc_unittest.cc | 5 +++++ src/windows/gperftools/tcmalloc.h | 1 + src/windows/gperftools/tcmalloc.h.in | 1 + 6 files changed, 20 insertions(+) diff --git a/src/debugallocation.cc b/src/debugallocation.cc index b7e72cf..4f03d9c 100644 --- a/src/debugallocation.cc +++ b/src/debugallocation.cc @@ -1486,3 +1486,9 @@ extern "C" PERFTOOLS_DLL_DECL struct mallinfo tc_mallinfo(void) __THROW { extern "C" PERFTOOLS_DLL_DECL size_t tc_malloc_size(void* ptr) __THROW { return MallocExtension::instance()->GetAllocatedSize(ptr); } + +extern "C" PERFTOOLS_DLL_DECL void* tc_malloc_skip_new_handler(size_t size) __THROW { + void* result = DebugAllocate(size, MallocBlock::kMallocType); + MallocHook::InvokeNewHook(result, size); + return result; +} diff --git a/src/gperftools/tcmalloc.h.in b/src/gperftools/tcmalloc.h.in index 58b3471..d43184d 100644 --- a/src/gperftools/tcmalloc.h.in +++ b/src/gperftools/tcmalloc.h.in @@ -89,6 +89,7 @@ extern "C" { const char** patch) __THROW; PERFTOOLS_DLL_DECL void* tc_malloc(size_t size) __THROW; + PERFTOOLS_DLL_DECL void* tc_malloc_skip_new_handler(size_t size) __THROW; PERFTOOLS_DLL_DECL void tc_free(void* ptr) __THROW; PERFTOOLS_DLL_DECL void* tc_realloc(void* ptr, size_t size) __THROW; PERFTOOLS_DLL_DECL void* tc_calloc(size_t nmemb, size_t size) __THROW; diff --git a/src/tcmalloc.cc b/src/tcmalloc.cc index 530e4c5..a796996 100644 --- a/src/tcmalloc.cc +++ b/src/tcmalloc.cc @@ -1735,4 +1735,10 @@ extern "C" PERFTOOLS_DLL_DECL size_t tc_malloc_size(void* ptr) __THROW { return MallocExtension::instance()->GetAllocatedSize(ptr); } +extern "C" PERFTOOLS_DLL_DECL void* tc_malloc_skip_new_handler(size_t size) __THROW { + void* result = do_malloc(size); + MallocHook::InvokeNewHook(result, size); + return result; +} + #endif // TCMALLOC_USING_DEBUGALLOCATION diff --git a/src/tests/tcmalloc_unittest.cc b/src/tests/tcmalloc_unittest.cc index 236bab6..423cae1 100644 --- a/src/tests/tcmalloc_unittest.cc +++ b/src/tests/tcmalloc_unittest.cc @@ -1132,6 +1132,11 @@ static int RunAllTests(int argc, char** argv) { free(p1); VerifyDeleteHookWasCalled(); + p1 = tc_malloc_skip_new_handler(10); + CHECK(p1 != NULL); + VerifyNewHookWasCalled(); + free(p1); + VerifyDeleteHookWasCalled(); p1 = calloc(10, 2); CHECK(p1 != NULL); diff --git a/src/windows/gperftools/tcmalloc.h b/src/windows/gperftools/tcmalloc.h index 3fa046e..0c38721 100644 --- a/src/windows/gperftools/tcmalloc.h +++ b/src/windows/gperftools/tcmalloc.h @@ -79,6 +79,7 @@ extern "C" { const char** patch) __THROW; PERFTOOLS_DLL_DECL void* tc_malloc(size_t size) __THROW; + PERFTOOLS_DLL_DECL void* tc_malloc_skip_new_handler(size_t size) __THROW; PERFTOOLS_DLL_DECL void tc_free(void* ptr) __THROW; PERFTOOLS_DLL_DECL void* tc_realloc(void* ptr, size_t size) __THROW; PERFTOOLS_DLL_DECL void* tc_calloc(size_t nmemb, size_t size) __THROW; diff --git a/src/windows/gperftools/tcmalloc.h.in b/src/windows/gperftools/tcmalloc.h.in index 193ee22..7458de1 100644 --- a/src/windows/gperftools/tcmalloc.h.in +++ b/src/windows/gperftools/tcmalloc.h.in @@ -79,6 +79,7 @@ extern "C" { const char** patch) __THROW; PERFTOOLS_DLL_DECL void* tc_malloc(size_t size) __THROW; + PERFTOOLS_DLL_DECL void* tc_malloc_skip_new_handler(size_t size) __THROW; PERFTOOLS_DLL_DECL void tc_free(void* ptr) __THROW; PERFTOOLS_DLL_DECL void* tc_realloc(void* ptr, size_t size) __THROW; PERFTOOLS_DLL_DECL void* tc_calloc(size_t nmemb, size_t size) __THROW;