[PATCH] D50920: [tsan] Avoid calling Block_copy in the "sync" GCD interceptors

Kuba (Brecka) Mracek via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Fri Aug 17 13:40:00 PDT 2018


kubamracek created this revision.
kubamracek added reviewers: dvyukov, george.karpenkov, delcypher.
kubamracek added a project: Sanitizers.
Herald added a subscriber: Sanitizers.

The synchronous dispatch functions in GCD (dispatch_sync, dispatch_barrier_sync), don't make a copy of the passed block. To maintain binary compatibility, we should avoid doing that as well in TSan, as there's no reason to do that. The synchronous dispatch functions will not return before the block is actually executed.

rdar://problem/42242579


Repository:
  rCRT Compiler Runtime

https://reviews.llvm.org/D50920

Files:
  lib/tsan/rtl/tsan_libdispatch_mac.cc
  test/tsan/Darwin/gcd-sync-block-copy.mm


Index: test/tsan/Darwin/gcd-sync-block-copy.mm
===================================================================
--- test/tsan/Darwin/gcd-sync-block-copy.mm
+++ test/tsan/Darwin/gcd-sync-block-copy.mm
@@ -0,0 +1,32 @@
+// This test verifies that dispatch_sync() doesn't actually copy the block under TSan (without TSan, it doesn't).
+
+// RUN: %clang_tsan -fno-sanitize=thread %s -o %t -framework Foundation
+// RUN: %run %t 2>&1 | FileCheck %s
+
+// RUN: %clang_tsan %s -o %t -framework Foundation
+// RUN: %run %t 2>&1 | FileCheck %s
+
+#import <Foundation/Foundation.h>
+
+ at interface MyClass : NSObject
+ at end
+
+ at implementation MyClass
+- (instancetype)retain {
+  abort();
+}
+ at end
+
+int main(int argc, const char* argv[]) {
+  dispatch_queue_t q = dispatch_queue_create("my.queue", NULL);
+  id object = [[MyClass alloc] init];
+  dispatch_sync(q, ^{
+    NSLog(@"%@", object);
+  });
+  [object release];
+  NSLog(@"Done.");
+  return 0;
+}
+
+// CHECK: Done.
+// CHECK-NOT: WARNING: ThreadSanitizer
Index: lib/tsan/rtl/tsan_libdispatch_mac.cc
===================================================================
--- lib/tsan/rtl/tsan_libdispatch_mac.cc
+++ lib/tsan/rtl/tsan_libdispatch_mac.cc
@@ -185,11 +185,8 @@
   TSAN_INTERCEPTOR(void, name, dispatch_queue_t q,                           \
                    DISPATCH_NOESCAPE dispatch_block_t block) {               \
     SCOPED_TSAN_INTERCEPTOR(name, q, block);                                 \
-    SCOPED_TSAN_INTERCEPTOR_USER_CALLBACK_START();                           \
-    dispatch_block_t heap_block = Block_copy(block);                         \
-    SCOPED_TSAN_INTERCEPTOR_USER_CALLBACK_END();                             \
     tsan_block_context_t new_context = {                                     \
-        q, heap_block, &invoke_and_release_block, false, true, barrier, 0};  \
+        q, block, &invoke_and_release_block, false, true, barrier, 0};       \
     Release(thr, pc, (uptr)&new_context);                                    \
     SCOPED_TSAN_INTERCEPTOR_USER_CALLBACK_START();                           \
     REAL(name##_f)(q, &new_context, dispatch_callback_wrap);                 \


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D50920.161315.patch
Type: text/x-patch
Size: 2184 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20180817/3bda0046/attachment.bin>


More information about the llvm-commits mailing list