[compiler-rt] r208707 - [libsanitizer] Use internal_fork() to spawn the symbolizer process.

Alexander Potapenko glider at google.com
Tue May 13 09:17:55 PDT 2014


Author: glider
Date: Tue May 13 11:17:54 2014
New Revision: 208707

URL: http://llvm.org/viewvc/llvm-project?rev=208707&view=rev
Log:
[libsanitizer] Use internal_fork() to spawn the symbolizer process.
This should fix https://code.google.com/p/thread-sanitizer/issues/detail?id=61

Added:
    compiler-rt/trunk/test/tsan/pthread_atfork_deadlock.c
Modified:
    compiler-rt/trunk/lib/sanitizer_common/sanitizer_libc.h
    compiler-rt/trunk/lib/sanitizer_common/sanitizer_linux.cc
    compiler-rt/trunk/lib/sanitizer_common/sanitizer_mac.cc
    compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_posix_libcdep.cc

Modified: compiler-rt/trunk/lib/sanitizer_common/sanitizer_libc.h
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_libc.h?rev=208707&r1=208706&r2=208707&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_libc.h (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_libc.h Tue May 13 11:17:54 2014
@@ -91,6 +91,8 @@ uptr internal_waitpid(int pid, int *stat
 uptr internal_getpid();
 uptr internal_getppid();
 
+uptr internal_fork();
+
 // Threading
 uptr internal_sched_yield();
 

Modified: compiler-rt/trunk/lib/sanitizer_common/sanitizer_linux.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_linux.cc?rev=208707&r1=208706&r2=208707&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_linux.cc (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_linux.cc Tue May 13 11:17:54 2014
@@ -501,6 +501,10 @@ uptr internal_sigaltstack(const struct s
   return internal_syscall(SYSCALL(sigaltstack), (uptr)ss, (uptr)oss);
 }
 
+uptr internal_fork() {
+  return internal_syscall(SYSCALL(fork));
+}
+
 #if SANITIZER_LINUX
 // Doesn't set sa_restorer, use with caution (see below).
 int internal_sigaction_norestorer(int signum, const void *act, void *oldact) {

Modified: compiler-rt/trunk/lib/sanitizer_common/sanitizer_mac.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_mac.cc?rev=208707&r1=208706&r2=208707&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_mac.cc (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_mac.cc Tue May 13 11:17:54 2014
@@ -126,6 +126,11 @@ int internal_sigaction(int signum, const
                    (struct sigaction *)act, (struct sigaction *)oldact);
 }
 
+int internal_fork() {
+  // TODO(glider): this may call user's pthread_atfork() handlers which is bad.
+  return fork();
+}
+
 // ----------------- sanitizer_common.h
 bool FileExists(const char *filename) {
   struct stat st;

Modified: compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_posix_libcdep.cc
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_posix_libcdep.cc?rev=208707&r1=208706&r2=208707&view=diff
==============================================================================
--- compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_posix_libcdep.cc (original)
+++ compiler-rt/trunk/lib/sanitizer_common/sanitizer_symbolizer_posix_libcdep.cc Tue May 13 11:17:54 2014
@@ -234,7 +234,8 @@ class SymbolizerProcess : public Externa
     CHECK(infd);
     CHECK(outfd);
 
-    int pid = fork();
+    // Real fork() may call user callbacks registered with pthread_atfork().
+    int pid = internal_fork();
     if (pid == -1) {
       // Fork() failed.
       internal_close(infd[0]);

Added: compiler-rt/trunk/test/tsan/pthread_atfork_deadlock.c
URL: http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/test/tsan/pthread_atfork_deadlock.c?rev=208707&view=auto
==============================================================================
--- compiler-rt/trunk/test/tsan/pthread_atfork_deadlock.c (added)
+++ compiler-rt/trunk/test/tsan/pthread_atfork_deadlock.c Tue May 13 11:17:54 2014
@@ -0,0 +1,31 @@
+// RUN: %clang_tsan -O1 %s -o %t && not %run %t 2>&1 | FileCheck %s
+// Regression test for
+// https://code.google.com/p/thread-sanitizer/issues/detail?id=61
+// When the data race was reported, pthread_atfork() handler used to be
+// executed which caused another race report in the same thread, which resulted
+// in a deadlock.
+#include <pthread.h>
+#include <stdio.h>
+
+int glob = 0;
+
+void *worker(void *unused) {
+  glob++;
+  return NULL;
+}
+
+void atfork() {
+  fprintf(stderr, "ATFORK\n");
+  glob++;
+}
+
+int main() {
+  pthread_atfork(atfork, NULL, NULL);
+  pthread_t t;
+  pthread_create(&t, NULL, worker, NULL);
+  glob++;
+  pthread_join(t, NULL);
+  // CHECK: ThreadSanitizer: data race
+  // CHECK-NOT: ATFORK
+  return 0;
+}





More information about the llvm-commits mailing list