1// RUN: %clang_tsan %s -o %t -framework Foundation 2// RUN: %env_tsan_opts=ignore_interceptors_accesses=1 %run %t 2>&1 | FileCheck %s 3 4#import <Foundation/Foundation.h> 5 6long my_global = 0; 7 8int main(int argc, const char *argv[]) { 9 fprintf(stderr, "Hello world.\n"); 10 11 dispatch_queue_t queue = dispatch_queue_create("my.queue", DISPATCH_QUEUE_CONCURRENT); 12 dispatch_semaphore_t sem = dispatch_semaphore_create(0); 13 NSString *ns_path = [NSTemporaryDirectory() stringByAppendingPathComponent:[NSString stringWithFormat:@"temp-gcd-io.%d", getpid()]]; 14 const char *path = ns_path.fileSystemRepresentation; 15 dispatch_io_t channel; 16 17 dispatch_fd_t fd = open(path, O_CREAT | O_WRONLY, 0666); 18 my_global++; 19 channel = dispatch_io_create(DISPATCH_IO_STREAM, fd, queue, ^(int error) { 20 my_global++; 21 dispatch_semaphore_signal(sem); 22 }); 23 if (! channel) abort(); 24 my_global++; 25 dispatch_io_close(channel, 0); 26 dispatch_semaphore_wait(sem, DISPATCH_TIME_FOREVER); 27 28 my_global++; 29 channel = dispatch_io_create_with_path(DISPATCH_IO_STREAM, path, O_CREAT | O_WRONLY, 0666, queue, ^(int error) { 30 my_global++; 31 dispatch_semaphore_signal(sem); 32 }); 33 if (! channel) abort(); 34 my_global++; 35 dispatch_io_close(channel, 0); 36 dispatch_semaphore_wait(sem, DISPATCH_TIME_FOREVER); 37 38 my_global++; 39 dispatch_io_t other_channel = dispatch_io_create_with_path(DISPATCH_IO_STREAM, path, O_CREAT | O_WRONLY, 0666, queue, ^(int error) { }); 40 channel = dispatch_io_create_with_io(DISPATCH_IO_STREAM, other_channel, queue, ^(int error) { 41 my_global++; 42 dispatch_semaphore_signal(sem); 43 }); 44 if (! channel) abort(); 45 my_global++; 46 dispatch_io_close(channel, 0); 47 dispatch_io_close(other_channel, 0); 48 dispatch_semaphore_wait(sem, DISPATCH_TIME_FOREVER); 49 50 fprintf(stderr, "Done.\n"); 51 return 0; 52} 53 54// CHECK: Hello world. 55// CHECK-NOT: WARNING: ThreadSanitizer 56// CHECK: Done. 57