[llvm-branch-commits] [compiler-rt-branch] r195666 - Merging r195642:

Sergey Matveev earthdok at google.com
Mon Nov 25 09:39:36 PST 2013


Author: smatveev
Date: Mon Nov 25 11:39:36 2013
New Revision: 195666

URL: http://llvm.org/viewvc/llvm-project?rev=195666&view=rev
Log:
Merging r195642:
------------------------------------------------------------------------
r195642 | smatveev | 2013-11-25 18:25:36 +0400 (Mon, 25 Nov 2013) | 5 lines

[lsan] Unbreak standalone LSan's initialization by making it more like ASan's.

No longer allow interceptors to be called during initialization, use the preinit
array (instead of initializing at the first call to an intercepted function) and
adopt the calloc() hack from ASan.
------------------------------------------------------------------------

Modified:
    compiler-rt/branches/release_34/   (props changed)
    compiler-rt/branches/release_34/lib/lsan/CMakeLists.txt
    compiler-rt/branches/release_34/lib/lsan/lsan.cc
    compiler-rt/branches/release_34/lib/lsan/lsan.h
    compiler-rt/branches/release_34/lib/lsan/lsan_interceptors.cc

Propchange: compiler-rt/branches/release_34/
------------------------------------------------------------------------------
--- svn:mergeinfo (original)
+++ svn:mergeinfo Mon Nov 25 11:39:36 2013
@@ -1 +1 @@
-/compiler-rt/trunk:195427,195433-195434,195436,195442,195570
+/compiler-rt/trunk:195427,195433-195434,195436,195442,195570,195642

Modified: compiler-rt/branches/release_34/lib/lsan/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/branches/release_34/lib/lsan/CMakeLists.txt?rev=195666&r1=195665&r2=195666&view=diff
==============================================================================
--- compiler-rt/branches/release_34/lib/lsan/CMakeLists.txt (original)
+++ compiler-rt/branches/release_34/lib/lsan/CMakeLists.txt Mon Nov 25 11:39:36 2013
@@ -9,10 +9,11 @@ set(LSAN_COMMON_SOURCES
   lsan_common_linux.cc)
 
 set(LSAN_SOURCES
-  lsan_interceptors.cc
+  lsan.cc
   lsan_allocator.cc
-  lsan_thread.cc
-  lsan.cc)
+  lsan_interceptors.cc
+  lsan_preinit.cc
+  lsan_thread.cc)
 
 set(LSAN_SRC_DIR ${CMAKE_CURRENT_SOURCE_DIR})
 

Modified: compiler-rt/branches/release_34/lib/lsan/lsan.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/branches/release_34/lib/lsan/lsan.cc?rev=195666&r1=195665&r2=195666&view=diff
==============================================================================
--- compiler-rt/branches/release_34/lib/lsan/lsan.cc (original)
+++ compiler-rt/branches/release_34/lib/lsan/lsan.cc Mon Nov 25 11:39:36 2013
@@ -20,6 +20,9 @@
 #include "lsan_common.h"
 #include "lsan_thread.h"
 
+bool lsan_inited;
+bool lsan_init_is_running;
+
 namespace __lsan {
 
 static void InitializeCommonFlags() {
@@ -32,11 +35,15 @@ static void InitializeCommonFlags() {
   ParseCommonFlagsFromString(GetEnv("LSAN_OPTIONS"));
 }
 
-void Init() {
-  static bool inited;
-  if (inited)
+}  // namespace __lsan
+
+using namespace __lsan;  // NOLINT
+
+extern "C" void __lsan_init() {
+  CHECK(!lsan_init_is_running);
+  if (lsan_inited)
     return;
-  inited = true;
+  lsan_init_is_running = true;
   SanitizerToolName = "LeakSanitizer";
   InitializeCommonFlags();
   InitializeAllocator();
@@ -58,6 +65,7 @@ void Init() {
   InitCommonLsan();
   if (common_flags()->detect_leaks && common_flags()->leak_check_at_exit)
     Atexit(DoLeakCheck);
+  lsan_inited = true;
+  lsan_init_is_running = false;
 }
 
-}  // namespace __lsan

Modified: compiler-rt/branches/release_34/lib/lsan/lsan.h
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/branches/release_34/lib/lsan/lsan.h?rev=195666&r1=195665&r2=195666&view=diff
==============================================================================
--- compiler-rt/branches/release_34/lib/lsan/lsan.h (original)
+++ compiler-rt/branches/release_34/lib/lsan/lsan.h Mon Nov 25 11:39:36 2013
@@ -17,7 +17,11 @@
 
 namespace __lsan {
 
-void Init();
 void InitializeInterceptors();
 
 }  // namespace __lsan
+
+extern bool lsan_inited;
+extern bool lsan_init_is_running;
+
+extern "C" void __lsan_init();

Modified: compiler-rt/branches/release_34/lib/lsan/lsan_interceptors.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/branches/release_34/lib/lsan/lsan_interceptors.cc?rev=195666&r1=195665&r2=195666&view=diff
==============================================================================
--- compiler-rt/branches/release_34/lib/lsan/lsan_interceptors.cc (original)
+++ compiler-rt/branches/release_34/lib/lsan/lsan_interceptors.cc Mon Nov 25 11:39:36 2013
@@ -49,6 +49,12 @@ int pthread_setspecific(unsigned key, co
                  GET_CURRENT_FRAME(), stack_top, stack_bottom, fast);        \
   }
 
+#define ENSURE_LSAN_INITED do {   \
+  CHECK(!lsan_init_is_running);   \
+  if (!lsan_inited)               \
+    __lsan_init();                \
+} while (0)
+
 ///// Malloc/free interceptors. /////
 
 const bool kAlwaysClearMemory = true;
@@ -58,38 +64,49 @@ namespace std {
 }
 
 INTERCEPTOR(void*, malloc, uptr size) {
-  Init();
+  ENSURE_LSAN_INITED;
   GET_STACK_TRACE;
   return Allocate(stack, size, 1, kAlwaysClearMemory);
 }
 
 INTERCEPTOR(void, free, void *p) {
-  Init();
+  ENSURE_LSAN_INITED;
   Deallocate(p);
 }
 
 INTERCEPTOR(void*, calloc, uptr nmemb, uptr size) {
+  if (lsan_init_is_running) {
+    // Hack: dlsym calls calloc before REAL(calloc) is retrieved from dlsym.
+    const uptr kCallocPoolSize = 1024;
+    static uptr calloc_memory_for_dlsym[kCallocPoolSize];
+    static uptr allocated;
+    uptr size_in_words = ((nmemb * size) + kWordSize - 1) / kWordSize;
+    void *mem = (void*)&calloc_memory_for_dlsym[allocated];
+    allocated += size_in_words;
+    CHECK(allocated < kCallocPoolSize);
+    return mem;
+  }
   if (CallocShouldReturnNullDueToOverflow(size, nmemb)) return 0;
-  Init();
+  ENSURE_LSAN_INITED;
   GET_STACK_TRACE;
   size *= nmemb;
   return Allocate(stack, size, 1, true);
 }
 
 INTERCEPTOR(void*, realloc, void *q, uptr size) {
-  Init();
+  ENSURE_LSAN_INITED;
   GET_STACK_TRACE;
   return Reallocate(stack, q, size, 1);
 }
 
 INTERCEPTOR(void*, memalign, uptr alignment, uptr size) {
-  Init();
+  ENSURE_LSAN_INITED;
   GET_STACK_TRACE;
   return Allocate(stack, size, alignment, kAlwaysClearMemory);
 }
 
 INTERCEPTOR(int, posix_memalign, void **memptr, uptr alignment, uptr size) {
-  Init();
+  ENSURE_LSAN_INITED;
   GET_STACK_TRACE;
   *memptr = Allocate(stack, size, alignment, kAlwaysClearMemory);
   // FIXME: Return ENOMEM if user requested more than max alloc size.
@@ -97,7 +114,7 @@ INTERCEPTOR(int, posix_memalign, void **
 }
 
 INTERCEPTOR(void*, valloc, uptr size) {
-  Init();
+  ENSURE_LSAN_INITED;
   GET_STACK_TRACE;
   if (size == 0)
     size = GetPageSizeCached();
@@ -105,7 +122,7 @@ INTERCEPTOR(void*, valloc, uptr size) {
 }
 
 INTERCEPTOR(uptr, malloc_usable_size, void *ptr) {
-  Init();
+  ENSURE_LSAN_INITED;
   return GetMallocUsableSize(ptr);
 }
 
@@ -124,7 +141,7 @@ INTERCEPTOR(int, mallopt, int cmd, int v
 }
 
 INTERCEPTOR(void*, pvalloc, uptr size) {
-  Init();
+  ENSURE_LSAN_INITED;
   GET_STACK_TRACE;
   uptr PageSize = GetPageSizeCached();
   size = RoundUpTo(size, PageSize);
@@ -138,7 +155,7 @@ INTERCEPTOR(void*, pvalloc, uptr size) {
 INTERCEPTOR(void, cfree, void *p) ALIAS("free");
 
 #define OPERATOR_NEW_BODY                              \
-  Init();                                              \
+  ENSURE_LSAN_INITED;                                  \
   GET_STACK_TRACE;                                     \
   return Allocate(stack, size, 1, kAlwaysClearMemory);
 
@@ -152,7 +169,7 @@ INTERCEPTOR_ATTRIBUTE
 void *operator new[](uptr size, std::nothrow_t const&) { OPERATOR_NEW_BODY; }
 
 #define OPERATOR_DELETE_BODY \
-  Init();                    \
+  ENSURE_LSAN_INITED;        \
   Deallocate(ptr);
 
 INTERCEPTOR_ATTRIBUTE
@@ -214,7 +231,7 @@ extern "C" void *__lsan_thread_start_fun
 
 INTERCEPTOR(int, pthread_create, void *th, void *attr,
             void *(*callback)(void *), void *param) {
-  Init();
+  ENSURE_LSAN_INITED;
   EnsureMainThreadIDIsCorrect();
   __sanitizer_pthread_attr_t myattr;
   if (attr == 0) {
@@ -242,7 +259,7 @@ INTERCEPTOR(int, pthread_create, void *t
 }
 
 INTERCEPTOR(int, pthread_join, void *th, void **ret) {
-  Init();
+  ENSURE_LSAN_INITED;
   int tid = ThreadTid((uptr)th);
   int res = REAL(pthread_join)(th, ret);
   if (res == 0)





More information about the llvm-branch-commits mailing list