1da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany// Mini-benchmark for tsan: shared memory reads. 2da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany#include <pthread.h> 3da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany#include <stdio.h> 4da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany#include <stdlib.h> 5da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany#include <assert.h> 6da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany 7da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryanyint len; 8da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryanyint *a; 9da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryanyconst int kNumIter = 1000; 10da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany 11da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany__attribute__((noinline)) 12da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryanyvoid Run(int idx) { 13da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany for (int i = 0, n = len; i < n; i++) 14da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany if (a[i] != i) abort(); 15da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany} 16da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany 17da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryanyvoid *Thread(void *arg) { 18da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany long idx = (long)arg; 19da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany printf("Thread %ld started\n", idx); 20da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany for (int i = 0; i < kNumIter; i++) 21da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany Run(idx); 22da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany printf("Thread %ld done\n", idx); 23da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany return 0; 24da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany} 25da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany 26da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryanyint main(int argc, char **argv) { 27da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany int n_threads = 0; 28da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany if (argc != 3) { 29da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany n_threads = 4; 30da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany len = 1000000; 31da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany } else { 32da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany n_threads = atoi(argv[1]); 33da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany assert(n_threads > 0 && n_threads <= 32); 34da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany len = atoi(argv[2]); 35da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany } 36da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany printf("%s: n_threads=%d len=%d iter=%d\n", 37da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany __FILE__, n_threads, len, kNumIter); 38da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany a = new int[len]; 39da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany for (int i = 0, n = len; i < n; i++) 40da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany a[i] = i; 41da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany pthread_t *t = new pthread_t[n_threads]; 42da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany for (int i = 0; i < n_threads; i++) { 43da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany pthread_create(&t[i], 0, Thread, (void*)i); 44da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany } 45da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany for (int i = 0; i < n_threads; i++) { 46da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany pthread_join(t[i], 0); 47da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany } 48da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany delete [] t; 49da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany delete [] a; 50da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany return 0; 51da4edd850db1a333c15fc3b0abc01a2e8d2f08feKostya Serebryany} 52