1 // { dg-do run } 2 // { dg-require-effective-target tls_runtime } 3 4 #include <omp.h> 5 #include <assert.h> 6 7 #define N 10 8 #define THR 4 9 10 struct B 11 { 12 B& operator=(const B &); 13 }; 14 15 static B *base; 16 static B *threadbase; 17 static int singlethread; 18 #pragma omp threadprivate(threadbase) 19 20 static unsigned cmask[THR]; 21 22 B& B::operator= (const B &b) 23 { 24 unsigned sindex = &b - base; 25 unsigned tindex = this - threadbase; 26 assert(sindex < N); 27 assert(sindex == tindex); 28 cmask[omp_get_thread_num ()] |= 1u << tindex; 29 return *this; 30 } 31 foo()32void foo() 33 { 34 #pragma omp parallel 35 { 36 B b[N]; 37 threadbase = b; 38 #pragma omp single copyprivate(b) 39 { 40 assert(omp_get_num_threads () == THR); 41 singlethread = omp_get_thread_num (); 42 base = b; 43 } 44 } 45 } 46 main()47int main() 48 { 49 omp_set_dynamic (0); 50 omp_set_num_threads (THR); 51 foo(); 52 53 for (int i = 0; i < THR; ++i) 54 if (i == singlethread) 55 assert(cmask[singlethread] == 0); 56 else 57 assert(cmask[i] == (1u << N) - 1); 58 59 return 0; 60 } 61