1 // RUN: %clang_cc1 -verify -fopenmp -I %S/Inputs -ast-print %s | FileCheck %s
2 // RUN: %clang_cc1 -fopenmp -x c++ -std=c++11 -I %S/Inputs -emit-pch -o %t %s
3 // RUN: %clang_cc1 -fopenmp -std=c++11 -include-pch %t -fsyntax-only -I %S/Inputs -verify %s -ast-print | FileCheck %s
4 
5 // RUN: %clang_cc1 -verify -fopenmp -I %S/Inputs -ast-print %s | FileCheck %s --check-prefix=CHECK --check-prefix=OMP50
6 // RUN: %clang_cc1 -verify -fopenmp -fopenmp-version=51 -I %S/Inputs -ast-print %s | FileCheck %s --check-prefix=CHECK --check-prefix=OMP51
7 // RUN: %clang_cc1 -fopenmp -x c++ -std=c++11 -I %S/Inputs -emit-pch -o %t %s
8 // RUN: %clang_cc1 -fopenmp -std=c++11 -include-pch %t -fsyntax-only -I %S/Inputs -verify %s -ast-print | FileCheck %s --check-prefix=CHECK --check-prefix=OMP50
9 // RUN: %clang_cc1 -fopenmp -fopenmp-version=51 -x c++ -std=c++11 -I %S/Inputs -emit-pch -o %t %s
10 // RUN: %clang_cc1 -fopenmp -fopenmp-version=51 -std=c++11 -include-pch %t -fsyntax-only -I %S/Inputs -verify %s -ast-print | FileCheck %s --check-prefix=CHECK --check-prefix=OMP51
11 
12 // RUN: %clang_cc1 -verify -fopenmp-simd -I %S/Inputs -ast-print %s | FileCheck %s
13 // RUN: %clang_cc1 -fopenmp-simd -x c++ -std=c++11 -I %S/Inputs -emit-pch -o %t %s
14 // RUN: %clang_cc1 -fopenmp-simd -std=c++11 -include-pch %t -fsyntax-only -I %S/Inputs -verify %s -ast-print | FileCheck %s
15 // expected-no-diagnostics
16 
17 #ifndef HEADER
18 #define HEADER
19 
20 #if _OPENMP == 201811
21 void bar();
22 #pragma omp declare target to(bar) device_type(any)
23 // OMP50: #pragma omp declare target{{$}}
24 // OMP50: void bar();
25 // OMP50: #pragma omp end declare target{{$}}
26 void baz();
27 #pragma omp declare target to(baz) device_type(nohost)
28 // OMP50: #pragma omp declare target device_type(nohost){{$}}
29 // OMP50: void baz();
30 // OMP50: #pragma omp end declare target{{$}}
31 void bazz();
32 #pragma omp declare target to(bazz) device_type(host)
33 // OMP50: #pragma omp declare target device_type(host){{$}}
34 // OMP50: void bazz();
35 // OMP50: #pragma omp end declare target{{$}}
36 #endif // _OPENMP
37 
38 #if _OPENMP == 202011
39 extern "C" {
boo_c()40 void boo_c() {}
41 #pragma omp declare target to(boo_c) indirect
42 // OMP51: #pragma omp declare target indirect
43 // OMP51: void boo_c() {
44 // OMP51: }
45 // OMP51: #pragma omp end declare target
46 #pragma omp declare target indirect
yoo()47 void yoo(){}
48 #pragma omp end declare target
49 // OMP51: #pragma omp declare target indirect
50 // OMP51: void yoo() {
51 // OMP51: }
52 // OMP51: #pragma omp end declare target
53 }
54 extern "C++" {
boo_cpp()55 void boo_cpp() {}
56 #pragma omp declare target to(boo_cpp) indirect
57 // OMP51: #pragma omp declare target indirect
58 // OMP51: void boo_cpp() {
59 // OMP51: }
60 // OMP51: #pragma omp end declare target
61 
f()62 constexpr bool f() {return false;}
63 #pragma omp begin declare target indirect(f())
zoo()64 void zoo() {}
65 void xoo();
66 #pragma omp end declare target
67 #pragma omp declare target to(zoo) indirect(false)
68 // OMP51: #pragma omp declare target indirect(f())
69 // OMP51: #pragma omp declare target indirect(false)
70 // OMP51: void zoo() {
71 // OMP51: }
72 // OMP51: #pragma omp end declare target
73 // OMP51: #pragma omp declare target indirect(f())
74 // OMP51: void xoo();
75 // OMP51: #pragma omp end declare target
76 
77 }
78 #endif // _OPENMP
79 
80 int out_decl_target = 0;
81 #pragma omp declare target (out_decl_target)
82 
83 // CHECK: #pragma omp declare target{{$}}
84 // CHECK: int out_decl_target = 0;
85 // CHECK: #pragma omp end declare target{{$}}
86 // CHECK: #pragma omp declare target{{$}}
87 // CHECK: void lambda()
88 // CHECK: #pragma omp end declare target{{$}}
89 
90 #pragma omp declare target
lambda()91 void lambda () {
92 #ifdef __cpp_lambdas
93   (void)[&] { ++out_decl_target; };
94 #else
95   #pragma clang __debug captured
96   (void)out_decl_target;
97 #endif
98 };
99 #pragma omp end declare target
100 
101 #pragma omp declare target
102 // CHECK: #pragma omp declare target{{$}}
foo()103 void foo() {}
104 // CHECK-NEXT: void foo()
105 #pragma omp end declare target
106 // CHECK: #pragma omp end declare target{{$}}
107 
108 extern "C" {
109 #pragma omp declare target
110 // CHECK: #pragma omp declare target
foo_c()111 void foo_c() {}
112 // CHECK-NEXT: void foo_c()
113 #pragma omp end declare target
114 // CHECK: #pragma omp end declare target
115 }
116 
117 extern "C++" {
118 #pragma omp declare target
119 // CHECK: #pragma omp declare target
foo_cpp()120 void foo_cpp() {}
121 // CHECK-NEXT: void foo_cpp()
122 #pragma omp end declare target
123 // CHECK: #pragma omp end declare target
124 }
125 
126 #pragma omp declare target
127 template <class T>
128 struct C {
129 // CHECK: template <class T> struct C {
130 // CHECK: #pragma omp declare target
131 // CHECK-NEXT: static T ts;
132 // CHECK-NEXT: #pragma omp end declare target
133 
134 // CHECK: template<> struct C<int>
135   T t;
136 // CHECK-NEXT: int t;
137   static T ts;
138 // CHECK-NEXT: #pragma omp declare target
139 // CHECK-NEXT: static int ts;
140 // CHECK: #pragma omp end declare target
141 
CC142   C(T t) : t(t) {
143   }
144 // CHECK: #pragma omp declare target
145 // CHECK-NEXT: C(int t) : t(t) {
146 // CHECK-NEXT: }
147 // CHECK: #pragma omp end declare target
148 
fooC149   T foo() {
150     return t;
151   }
152 // CHECK: #pragma omp declare target
153 // CHECK-NEXT: int foo() {
154 // CHECK-NEXT: return this->t;
155 // CHECK-NEXT: }
156 // CHECK: #pragma omp end declare target
157 };
158 
159 template<class T>
160 T C<T>::ts = 1;
161 // CHECK: #pragma omp declare target
162 // CHECK: T ts = 1;
163 // CHECK: #pragma omp end declare target
164 
165 // CHECK: #pragma omp declare target
166 // CHECK: int test1()
test1()167 int test1() {
168   C<int> c(1);
169   return c.foo() + c.ts;
170 }
171 #pragma omp end declare target
172 // CHECK: #pragma omp end declare target
173 
174 int a1;
f1()175 void f1() {
176 }
177 #pragma omp declare target (a1, f1)
178 // CHECK: #pragma omp declare target{{$}}
179 // CHECK: int a1;
180 // CHECK: #pragma omp end declare target{{$}}
181 // CHECK: #pragma omp declare target{{$}}
182 // CHECK: void f1()
183 // CHECK: #pragma omp end declare target{{$}}
184 
185 int b1, b2, b3;
f2()186 void f2() {
187 }
188 #pragma omp declare target to(b1) to(b2), to(b3, f2)
189 // CHECK: #pragma omp declare target{{$}}
190 // CHECK: int b1;
191 // CHECK: #pragma omp end declare target{{$}}
192 // CHECK: #pragma omp declare target{{$}}
193 // CHECK: int b2;
194 // CHECK: #pragma omp end declare target{{$}}
195 // CHECK: #pragma omp declare target{{$}}
196 // CHECK: int b3;
197 // CHECK: #pragma omp end declare target{{$}}
198 // CHECK: #pragma omp declare target{{$}}
199 // CHECK: void f2()
200 // CHECK: #pragma omp end declare target{{$}}
201 
202 int c1, c2, c3;
203 #pragma omp declare target link(c1) link(c2), link(c3)
204 // CHECK: #pragma omp declare target link{{$}}
205 // CHECK: int c1;
206 // CHECK: #pragma omp end declare target{{$}}
207 // CHECK: #pragma omp declare target link{{$}}
208 // CHECK: int c2;
209 // CHECK: #pragma omp end declare target{{$}}
210 // CHECK: #pragma omp declare target link{{$}}
211 // CHECK: int c3;
212 // CHECK: #pragma omp end declare target{{$}}
213 
214 struct SSSt {
215 #pragma omp declare target
216   static int a;
217   int b;
218 #pragma omp end declare target
219 };
220 
221 // CHECK: struct SSSt {
222 // CHECK: #pragma omp declare target
223 // CHECK: static int a;
224 // CHECK: #pragma omp end declare target
225 // CHECK: int b;
226 
227 template <class T>
228 struct SSSTt {
229 #pragma omp declare target
230   static T a;
231   int b;
232 #pragma omp end declare target
233 };
234 
235 // CHECK: template <class T> struct SSSTt {
236 // CHECK: #pragma omp declare target
237 // CHECK: static T a;
238 // CHECK: #pragma omp end declare target
239 // CHECK: int b;
240 
241 #pragma omp declare target
242 template <typename T>
baz()243 T baz() { return T(); }
244 #pragma omp end declare target
245 
246 template <>
baz()247 int baz() { return 1; }
248 
249 // CHECK: #pragma omp declare target
250 // CHECK: template <typename T> T baz() {
251 // CHECK:     return T();
252 // CHECK: }
253 // CHECK: #pragma omp end declare target
254 // CHECK: #pragma omp declare target
255 // CHECK: template<> float baz<float>() {
256 // CHECK:     return float();
257 // CHECK: }
258 // CHECK: template<> int baz<int>() {
259 // CHECK:     return 1;
260 // CHECK: }
261 // CHECK: #pragma omp end declare target
262 
263 #pragma omp declare target
264   #include "declare_target_include.h"
265   void xyz();
266 #pragma omp end declare target
267 
268 // CHECK: #pragma omp declare target
269 // CHECK: void zyx();
270 // CHECK: #pragma omp end declare target
271 // CHECK: #pragma omp declare target
272 // CHECK: void xyz();
273 // CHECK: #pragma omp end declare target
274 
275 #pragma omp declare target
276   #pragma omp declare target
277     void abc();
278   #pragma omp end declare target
279   void cba();
280 #pragma omp end declare target
281 
282 // CHECK: #pragma omp declare target
283 // CHECK: void abc();
284 // CHECK: #pragma omp end declare target
285 // CHECK: #pragma omp declare target
286 // CHECK: void cba();
287 // CHECK: #pragma omp end declare target
288 
289 #pragma omp declare target
abc1()290 int abc1() { return 1; }
291 #pragma omp declare target to(abc1) device_type(nohost)
292 #pragma omp end declare target
293 
294 // CHECK-NEXT: #pragma omp declare target
295 // CHECK-NEXT: #pragma omp declare target device_type(nohost)
296 // CHECK-NEXT: int abc1() {
297 // CHECK-NEXT: return 1;
298 // CHECK-NEXT: }
299 // CHECK-NEXT: #pragma omp end declare target
300 
301 #pragma omp declare target
302 int inner_link;
303 #pragma omp declare target link(inner_link)
304 #pragma omp end declare target
305 
306 // CHECK-NEXT: #pragma omp declare target
307 // CHECK-NEXT: #pragma omp declare target link
308 // CHECK-NEXT: int inner_link;
309 // CHECK-NEXT: #pragma omp end declare target
310 
main(int argc,char ** argv)311 int main (int argc, char **argv) {
312   foo();
313   foo_c();
314   foo_cpp();
315   test1();
316   baz<float>();
317   baz<int>();
318   return (0);
319 }
320 
321 // CHECK: #pragma omp declare target
322 // CHECK-NEXT: int ts = 1;
323 // CHECK-NEXT: #pragma omp end declare target
324 
325 // Do not expect anything here since the region is empty.
326 #pragma omp declare target
327 #pragma omp end declare target
328 
329 #endif
330