[compiler-rt] r217929 - tsan: fix crash when a program registers zillions of atexit callbacks

Dmitry Vyukov dvyukov at google.com
Tue Sep 16 17:12:50 PDT 2014


Author: dvyukov
Date: Tue Sep 16 19:12:50 2014
New Revision: 217929

URL: http://llvm.org/viewvc/llvm-project?rev=217929&view=rev
Log:
tsan: fix crash when a program registers zillions of atexit callbacks
I don't remember that crash on mmap in internal allocator
ever yielded anything useful, only crashes in rare wierd untested situations.
One of the reasons for crash was to catch if tsan starts allocating
clocks using mmap. Tsan does not allocate clocks using internal_alloc anymore.
Solve it once and for all by allowing mmaps.


Added:
    compiler-rt/trunk/test/tsan/atexit2.cc
Modified:
    compiler-rt/trunk/lib/sanitizer_common/sanitizer_allocator_internal.h
    compiler-rt/trunk/lib/sanitizer_common/tests/sanitizer_allocator_test.cc
    compiler-rt/trunk/lib/tsan/rtl/tsan_mman.cc

Modified: compiler-rt/trunk/lib/sanitizer_common/sanitizer_allocator_internal.h
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_allocator_internal.h?rev=217929&r1=217928&r2=217929&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_allocator_internal.h (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_allocator_internal.h Tue Sep 16 19:12:50 2014
@@ -42,20 +42,8 @@ typedef SizeClassAllocator32<
 typedef SizeClassAllocatorLocalCache<PrimaryInternalAllocator>
     InternalAllocatorCache;
 
-// We don't want our internal allocator to do any map/unmap operations from
-// LargeMmapAllocator.
-struct CrashOnMapUnmap {
-  void OnMap(uptr p, uptr size) const {
-    RAW_CHECK_MSG(0, "Unexpected mmap in InternalAllocator!\n");
-  }
-  void OnUnmap(uptr p, uptr size) const {
-    RAW_CHECK_MSG(0, "Unexpected munmap in InternalAllocator!\n");
-  }
-};
-
 typedef CombinedAllocator<PrimaryInternalAllocator, InternalAllocatorCache,
-                          LargeMmapAllocator<CrashOnMapUnmap> >
-    InternalAllocator;
+                          LargeMmapAllocator<> > InternalAllocator;
 
 void *InternalAlloc(uptr size, InternalAllocatorCache *cache = 0);
 void InternalFree(void *p, InternalAllocatorCache *cache = 0);

Modified: compiler-rt/trunk/lib/sanitizer_common/tests/sanitizer_allocator_test.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/tests/sanitizer_allocator_test.cc?rev=217929&r1=217928&r2=217929&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/tests/sanitizer_allocator_test.cc (original)
+++ compiler-rt/trunk/lib/sanitizer_common/tests/sanitizer_allocator_test.cc Tue Sep 16 19:12:50 2014
@@ -629,9 +629,9 @@ TEST(Allocator, Stress) {
   }
 }
 
-TEST(Allocator, InternalAllocFailure) {
-  EXPECT_DEATH(Ident(InternalAlloc(10 << 20)),
-               "Unexpected mmap in InternalAllocator!");
+TEST(Allocator, LargeAlloc) {
+  void *p = InternalAlloc(10 << 20);
+  InternalFree(p);
 }
 
 TEST(Allocator, ScopedBuffer) {

Modified: compiler-rt/trunk/lib/tsan/rtl/tsan_mman.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/tsan/rtl/tsan_mman.cc?rev=217929&r1=217928&r2=217929&view=diff
==============================================================================
--- compiler-rt/trunk/lib/tsan/rtl/tsan_mman.cc (original)
+++ compiler-rt/trunk/lib/tsan/rtl/tsan_mman.cc Tue Sep 16 19:12:50 2014
@@ -153,7 +153,6 @@ void invoke_free_hook(void *ptr) {
 
 void *internal_alloc(MBlockType typ, uptr sz) {
   ThreadState *thr = cur_thread();
-  CHECK_LE(sz, InternalSizeClassMap::kMaxSize);
   if (thr->nomalloc) {
     thr->nomalloc = 0;  // CHECK calls internal_malloc().
     CHECK(0);

Added: compiler-rt/trunk/test/tsan/atexit2.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/test/tsan/atexit2.cc?rev=217929&view=auto
==============================================================================
--- compiler-rt/trunk/test/tsan/atexit2.cc (added)
+++ compiler-rt/trunk/test/tsan/atexit2.cc Tue Sep 16 19:12:50 2014
@@ -0,0 +1,26 @@
+// RUN: %clang_tsan -O1 %s -o %t && %run %t 2>&1 | FileCheck %s
+
+#include <stdio.h>
+#include <stdlib.h>
+
+int n;
+const int N = 10000;
+
+static void atexit1() {
+  n++;
+}
+
+static void atexit0() {
+  fprintf(stderr, "run count: %d\n", n);
+}
+
+int main() {
+  atexit(atexit0);
+  for (int i = 0; i < N; i++)
+    atexit(atexit1);
+}
+
+// CHECK-NOT: FATAL: ThreadSanitizer
+// CHECK-NOT: WARNING: ThreadSanitizer
+// CHECK: run count: 10000
+





More information about the llvm-commits mailing list