1 // RUN: %libomp-compile-and-run
2
3 #include <stdio.h>
4 #include <stdlib.h>
5 #include <omp.h>
6
7 int a;
8
inc_a()9 void inc_a() {
10 #pragma omp atomic
11 a++;
12 }
13
root_team_detached()14 void root_team_detached() {
15 a = 0;
16 omp_event_handle_t ev;
17 #pragma omp task detach(ev)
18 inc_a();
19 omp_fulfill_event(ev);
20 if (a != 1) {
21 fprintf(stderr, "error: root_team_detached(): a != 1\n");
22 exit(EXIT_FAILURE);
23 }
24 }
25
root_team_hidden_helpers()26 void root_team_hidden_helpers() {
27 a = 0;
28 #pragma omp target nowait
29 inc_a();
30
31 #pragma omp taskwait
32
33 if (a != 1) {
34 fprintf(stderr, "error: root_team_hidden_helpers(): a != 1\n");
35 exit(EXIT_FAILURE);
36 }
37 }
38
parallel_detached(int nth1)39 void parallel_detached(int nth1) {
40 a = 0;
41 omp_event_handle_t *evs =
42 (omp_event_handle_t *)malloc(sizeof(omp_event_handle_t) * nth1);
43 #pragma omp parallel num_threads(nth1)
44 {
45 int tid = omp_get_thread_num();
46 omp_event_handle_t e = evs[tid];
47 #pragma omp task detach(e)
48 inc_a();
49 omp_fulfill_event(e);
50 }
51 free(evs);
52 if (a != nth1) {
53 fprintf(stderr, "error: parallel_detached(): a (%d) != %d\n", a, nth1);
54 exit(EXIT_FAILURE);
55 }
56 }
57
parallel_hidden_helpers(int nth1)58 void parallel_hidden_helpers(int nth1) {
59 a = 0;
60 #pragma omp parallel num_threads(nth1)
61 {
62 #pragma omp target nowait
63 inc_a();
64 }
65 if (a != nth1) {
66 fprintf(stderr, "error: parallel_hidden_helpers(): a (%d) != %d\n", a,
67 nth1);
68 exit(EXIT_FAILURE);
69 }
70 }
71
nested_parallel_detached(int nth1,int nth2)72 void nested_parallel_detached(int nth1, int nth2) {
73 a = 0;
74 omp_event_handle_t **evs =
75 (omp_event_handle_t **)malloc(sizeof(omp_event_handle_t *) * nth1);
76 #pragma omp parallel num_threads(nth1)
77 {
78 int tid = omp_get_thread_num();
79 evs[tid] = (omp_event_handle_t *)malloc(sizeof(omp_event_handle_t) * nth2);
80 #pragma omp parallel num_threads(nth2) shared(tid)
81 {
82 int tid2 = omp_get_thread_num();
83 omp_event_handle_t e = evs[tid][tid2];
84 #pragma omp task detach(e)
85 inc_a();
86 omp_fulfill_event(e);
87 }
88 free(evs[tid]);
89 }
90 free(evs);
91 if (a != nth1 * nth2) {
92 fprintf(stderr, "error: nested_parallel_detached(): a (%d) != %d * %d\n", a,
93 nth1, nth2);
94 exit(EXIT_FAILURE);
95 }
96 }
97
nested_parallel_hidden_helpers(int nth1,int nth2)98 void nested_parallel_hidden_helpers(int nth1, int nth2) {
99 a = 0;
100 #pragma omp parallel num_threads(nth1)
101 {
102 #pragma omp parallel num_threads(nth2)
103 {
104 #pragma omp target nowait
105 inc_a();
106 }
107 }
108 if (a != nth1 * nth2) {
109 fprintf(stderr,
110 "error: nested_parallel_hidden_helpers(): a (%d) != %d * %d\n", a,
111 nth1, nth2);
112 exit(EXIT_FAILURE);
113 }
114 }
115
main()116 int main() {
117 int i, nth1, nth2;
118
119 omp_set_max_active_levels(2);
120 omp_set_dynamic(0);
121
122 for (i = 0; i < 10; ++i)
123 root_team_detached();
124
125 for (i = 0; i < 10; ++i)
126 root_team_hidden_helpers();
127
128 for (i = 0; i < 10; ++i)
129 for (nth1 = 1; nth1 <= 4; ++nth1)
130 parallel_detached(nth1);
131
132 for (i = 0; i < 10; ++i)
133 for (nth1 = 1; nth1 <= 4; ++nth1)
134 parallel_hidden_helpers(nth1);
135
136 for (i = 0; i < 10; ++i)
137 for (nth1 = 1; nth1 <= 4; ++nth1)
138 for (nth2 = 1; nth2 <= 4; ++nth2)
139 nested_parallel_detached(nth1, nth2);
140
141 for (i = 0; i < 10; ++i)
142 for (nth1 = 1; nth1 <= 4; ++nth1)
143 for (nth2 = 1; nth2 <= 4; ++nth2)
144 nested_parallel_hidden_helpers(nth1, nth2);
145
146 return 0;
147 }
148