xref: /llvm-project/clang/test/OpenMP/simd_loop_messages.cpp (revision 405f8fc812c0067d810fa53f9dd7ba09d02f7cc5)
1 // RUN: %clang_cc1 -fsyntax-only -fopenmp -x c++ -std=c++11 -fexceptions -fcxx-exceptions -verify %s
2 // RUN: %clang_cc1 -fsyntax-only -fopenmp-simd -x c++ -std=c++11 -fexceptions -fcxx-exceptions -verify %s
3 
4 static int sii;
5 // expected-note@+1 {{defined as threadprivate or thread local}}
6 #pragma omp threadprivate(sii)
7 static int globalii;
8 
9 struct S {
10   static int ssi;
11 };
12 
13 int test_iteration_spaces() {
14   const int N = 100;
15   float a[N], b[N], c[N];
16   int ii, jj, kk;
17   float fii;
18   double dii;
19 #pragma omp simd linear(S::ssi)
20   for (S::ssi = 0; S::ssi < 10; ++S::ssi)
21     ;
22 #pragma omp simd // no messages expected
23   for (S::ssi = 0; S::ssi < 10; ++S::ssi)
24     ;
25   #pragma omp simd
26   for (int i = 0; i < 10; i+=1) {
27     c[i] = a[i] + b[i];
28   }
29   #pragma omp simd
30   for (char i = 0; i < 10; i++) {
31     c[i] = a[i] + b[i];
32   }
33   #pragma omp simd
34   for (char i = 0; i < 10; i+='\1') {
35     c[i] = a[i] + b[i];
36   }
37   #pragma omp simd
38   for (long long i = 0; i < 10; i++) {
39     c[i] = a[i] + b[i];
40   }
41   // expected-error@+2 {{expression must have integral or unscoped enumeration type, not 'double'}}
42   #pragma omp simd
43   for (long long i = 0; i < 10; i+=1.5) {
44     c[i] = a[i] + b[i];
45   }
46   #pragma omp simd
47   for (long long i = 0; i < 'z'; i+=1u) {
48     c[i] = a[i] + b[i];
49   }
50   // expected-error@+2 {{variable must be of integer or random access iterator type}}
51   #pragma omp simd
52   for (float fi = 0; fi < 10.0; fi++) {
53     c[(int)fi] = a[(int)fi] + b[(int)fi];
54   }
55   // expected-error@+2 {{variable must be of integer or random access iterator type}}
56   #pragma omp simd
57   for (double fi = 0; fi < 10.0; fi++) {
58     c[(int)fi] = a[(int)fi] + b[(int)fi];
59   }
60   // expected-error@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
61   #pragma omp simd
62   for (int &ref = ii; ref < 10; ref++) {
63   }
64   // expected-error@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
65   #pragma omp simd
66   for (int i; i < 10; i++)
67     c[i] = a[i];
68 
69   // expected-error@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
70   #pragma omp simd
71   for (int i = 0, j = 0; i < 10; ++i)
72     c[i] = a[i];
73 
74   // expected-error@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
75   #pragma omp simd
76   for (;ii < 10; ++ii)
77     c[ii] = a[ii];
78 
79   // expected-warning@+3 {{expression result unused}}
80   // expected-error@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
81   #pragma omp simd
82   for (ii + 1;ii < 10; ++ii)
83     c[ii] = a[ii];
84 
85   // expected-error@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
86   #pragma omp simd
87   for (c[ii] = 0;ii < 10; ++ii)
88     c[ii] = a[ii];
89 
90   // Ok to skip parenthesises.
91   #pragma omp simd
92   for (((ii)) = 0;ii < 10; ++ii)
93     c[ii] = a[ii];
94 
95   // expected-error@+2 {{condition of OpenMP for loop must be a relational comparison ('<', '<=', '>', or '>=') of loop variable 'i'}}
96   #pragma omp simd
97   for (int i = 0; i; i++)
98     c[i] = a[i];
99 
100   // expected-error@+3 {{condition of OpenMP for loop must be a relational comparison ('<', '<=', '>', or '>=') of loop variable 'i'}}
101   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'i'}}
102   #pragma omp simd
103   for (int i = 0; jj < kk; ii++)
104     c[i] = a[i];
105 
106   // expected-error@+2 {{condition of OpenMP for loop must be a relational comparison ('<', '<=', '>', or '>=') of loop variable 'i'}}
107   #pragma omp simd
108   for (int i = 0; !!i; i++)
109     c[i] = a[i];
110 
111   // Ok
112   #pragma omp simd
113   for (int i = 0; i != 1; i++)
114     c[i] = a[i];
115 
116   // expected-error@+2 {{condition of OpenMP for loop must be a relational comparison ('<', '<=', '>', or '>=') of loop variable 'i'}}
117   #pragma omp simd
118   for (int i = 0; ; i++)
119     c[i] = a[i];
120 
121   // Ok.
122   #pragma omp simd
123   for (int i = 11; i > 10; i--)
124     c[i] = a[i];
125 
126   // Ok.
127   #pragma omp simd
128   for (int i = 0; i < 10; ++i)
129     c[i] = a[i];
130 
131     // Ok.
132   #pragma omp simd
133   for (ii = 0; ii < 10; ++ii)
134     c[ii] = a[ii];
135 
136   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'ii'}}
137   #pragma omp simd
138   for (ii = 0; ii < 10; ++jj)
139     c[ii] = a[jj];
140 
141   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'ii'}}
142   #pragma omp simd
143   for (ii = 0; ii < 10; ++ ++ ii)
144     c[ii] = a[ii];
145 
146   // Ok but undefined behavior (in general, cannot check that incr
147   // is really loop-invariant).
148   #pragma omp simd
149   for (ii = 0; ii < 10; ii = ii + ii)
150     c[ii] = a[ii];
151 
152   // expected-error@+2 {{expression must have integral or unscoped enumeration type, not 'float'}}
153   #pragma omp simd
154   for (ii = 0; ii < 10; ii = ii + 1.0f)
155     c[ii] = a[ii];
156 
157   // Ok - step was converted to integer type.
158   #pragma omp simd
159   for (ii = 0; ii < 10; ii = ii + (int)1.1f)
160     c[ii] = a[ii];
161 
162   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'ii'}}
163   #pragma omp simd
164   for (ii = 0; ii < 10; jj = ii + 2)
165     c[ii] = a[ii];
166 
167   // expected-warning@+3 {{relational comparison result unused}}
168   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'ii'}}
169   #pragma omp simd
170   for (ii = 0; ii < 10; jj > kk + 2)
171     c[ii] = a[ii];
172 
173   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'ii'}}
174   #pragma omp simd
175   for (ii = 0; ii < 10;)
176     c[ii] = a[ii];
177 
178   // expected-warning@+3 {{expression result unused}}
179   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'ii'}}
180   #pragma omp simd
181   for (ii = 0; ii < 10; !ii)
182     c[ii] = a[ii];
183 
184   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'ii'}}
185   #pragma omp simd
186   for (ii = 0; ii < 10; ii ? ++ii : ++jj)
187     c[ii] = a[ii];
188 
189   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'ii'}}
190   #pragma omp simd
191   for (ii = 0; ii < 10; ii = ii < 10)
192     c[ii] = a[ii];
193 
194   // expected-note@+3 {{loop step is expected to be positive due to this condition}}
195   // expected-error@+2 {{increment expression must cause 'ii' to increase on each iteration of OpenMP for loop}}
196   #pragma omp simd
197   for (ii = 0; ii < 10; ii = ii + 0)
198     c[ii] = a[ii];
199 
200   // expected-note@+3 {{loop step is expected to be positive due to this condition}}
201   // expected-error@+2 {{increment expression must cause 'ii' to increase on each iteration of OpenMP for loop}}
202   #pragma omp simd
203   for (ii = 0; ii < 10; ii = ii + (int)(0.8 - 0.45))
204     c[ii] = a[ii];
205 
206   // expected-note@+3 {{loop step is expected to be positive due to this condition}}
207   // expected-error@+2 {{increment expression must cause 'ii' to increase on each iteration of OpenMP for loop}}
208   #pragma omp simd
209   for (ii = 0; (ii) < 10; ii-=25)
210     c[ii] = a[ii];
211 
212   // expected-note@+3 {{loop step is expected to be positive due to this condition}}
213   // expected-error@+2 {{increment expression must cause 'ii' to increase on each iteration of OpenMP for loop}}
214   #pragma omp simd
215   for (ii = 0; (ii < 10); ii-=0)
216     c[ii] = a[ii];
217 
218   // expected-note@+3 {{loop step is expected to be negative due to this condition}}
219   // expected-error@+2 {{increment expression must cause 'ii' to decrease on each iteration of OpenMP for loop}}
220   #pragma omp simd
221   for (ii = 0; ii > 10; (ii+=0))
222     c[ii] = a[ii];
223 
224   // expected-note@+3 {{loop step is expected to be positive due to this condition}}
225   // expected-error@+2 {{increment expression must cause 'ii' to increase on each iteration of OpenMP for loop}}
226   #pragma omp simd
227   for (ii = 0; ii < 10; (ii) = (1-1)+(ii))
228     c[ii] = a[ii];
229 
230   // expected-note@+3 {{loop step is expected to be negative due to this condition}}
231   // expected-error@+2 {{increment expression must cause 'ii' to decrease on each iteration of OpenMP for loop}}
232   #pragma omp simd
233   for ((ii = 0); ii > 10; (ii-=0))
234     c[ii] = a[ii];
235 
236   // expected-note@+3 {{loop step is expected to be positive due to this condition}}
237   // expected-error@+2 {{increment expression must cause 'ii' to increase on each iteration of OpenMP for loop}}
238   #pragma omp simd
239   for (ii = 0; (ii < 10); (ii-=0))
240     c[ii] = a[ii];
241 
242   // expected-note@+2  {{defined as private}}
243   // expected-error@+2 {{loop iteration variable in the associated loop of 'omp simd' directive may not be private, predetermined as linear}}
244   #pragma omp simd private(ii)
245   for (ii = 0; ii < 10; ii++)
246     c[ii] = a[ii];
247 
248   // expected-error@+1 {{unexpected OpenMP clause 'shared' in directive '#pragma omp simd'}}
249   #pragma omp simd shared(ii)
250   for (ii = 0; ii < 10; ii++)
251     c[ii] = a[ii];
252 
253   #pragma omp simd linear(ii)
254   for (ii = 0; ii < 10; ii++)
255     c[ii] = a[ii];
256 
257   #pragma omp simd lastprivate(ii) linear(jj) collapse(2) // expected-note {{defined as linear}}
258   for (ii = 0; ii < 10; ii++)
259   for (jj = 0; jj < 10; jj++) // expected-error {{loop iteration variable in the associated loop of 'omp simd' directive may not be linear, predetermined as lastprivate}}
260     c[ii] = a[jj];
261 
262 
263   #pragma omp parallel
264   {
265 // expected-error@+2 {{loop iteration variable in the associated loop of 'omp simd' directive may not be threadprivate or thread local, predetermined as linear}}
266     #pragma omp simd
267     for (sii = 0; sii < 10; sii+=1)
268       c[sii] = a[sii];
269   }
270 
271   #pragma omp parallel
272   {
273     #pragma omp simd
274     for (globalii = 0; globalii < 10; globalii+=1)
275       c[globalii] = a[globalii];
276   }
277 
278   #pragma omp parallel
279   {
280 #pragma omp simd collapse(2)
281     for (ii = 0; ii < 10; ii += 1)
282     for (globalii = 0; globalii < 10; globalii += 1)
283       c[globalii] += a[globalii] + ii;
284   }
285 
286   // expected-error@+2 {{statement after '#pragma omp simd' must be a for loop}}
287   #pragma omp simd
288   for (auto &item : a) {
289     item = item + 1;
290   }
291 
292   // expected-note@+3 {{loop step is expected to be positive due to this condition}}
293   // expected-error@+2 {{increment expression must cause 'i' to increase on each iteration of OpenMP for loop}}
294   #pragma omp simd
295   for (unsigned i = 9; i < 10; i--) {
296     c[i] = a[i] + b[i];
297   }
298 
299   int (*lb)[4] = nullptr;
300   #pragma omp simd
301   for (int (*p)[4] = lb; p < lb + 8; ++p) {
302   }
303 
304   // expected-warning@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
305   #pragma omp simd
306   for (int a{0}; a<10; ++a) {
307   }
308 
309   return 0;
310 }
311 
312 // Iterators allowed in openmp for-loops.
313 namespace std {
314 struct random_access_iterator_tag { };
315 template <class Iter> struct iterator_traits {
316   typedef typename Iter::difference_type difference_type;
317   typedef typename Iter::iterator_category iterator_category;
318 };
319 template <class Iter>
320 typename iterator_traits<Iter>::difference_type
321 distance(Iter first, Iter last) { return first - last; }
322 }
323 class Iter0 {
324   public:
325     Iter0() { }
326     Iter0(const Iter0 &) { }
327     Iter0 operator ++() { return *this; }
328     Iter0 operator --() { return *this; }
329     Iter0 operator + (int delta) { return *this; }
330     bool operator <(Iter0 a) { return true; }
331 };
332 // expected-note@+1 2 {{candidate function not viable: no known conversion from 'Iter1' to 'Iter0' for 1st argument}}
333 int operator -(Iter0 a, Iter0 b) { return 0; }
334 class Iter1 {
335   public:
336     Iter1(float f=0.0f, double d=0.0) { }
337     Iter1(const Iter1 &) { }
338     Iter1 operator ++() { return *this; }
339     Iter1 operator --() { return *this; }
340     bool operator <(Iter1 a) { return true; }
341     bool operator >=(Iter1 a) { return false; }
342 };
343 class GoodIter {
344   public:
345     GoodIter() { }
346     GoodIter(const GoodIter &) { }
347     GoodIter(int fst, int snd) { }
348     GoodIter &operator =(const GoodIter &that) { return *this; }
349     GoodIter &operator =(const Iter0 &that) { return *this; }
350     GoodIter &operator +=(int x) { return *this; }
351     explicit GoodIter(void *) { }
352     GoodIter operator ++() { return *this; }
353     GoodIter operator --() { return *this; }
354     bool operator !() { return true; }
355     bool operator <(GoodIter a) { return true; }
356     bool operator <=(GoodIter a) { return true; }
357     bool operator >=(GoodIter a) { return false; }
358     typedef int difference_type;
359     typedef std::random_access_iterator_tag iterator_category;
360 };
361 // expected-note@+1 2 {{candidate function not viable: no known conversion from 'Iter1' to 'GoodIter' for 1st argument}}
362 int operator -(GoodIter a, GoodIter b) { return 0; }
363 // expected-note@+1 2 {{candidate function not viable: requires single argument 'a', but 2 arguments were provided}}
364 GoodIter operator -(GoodIter a) { return a; }
365 // expected-note@+1 2 {{candidate function not viable: no known conversion from 'Iter1' to 'GoodIter' for 1st argument}}
366 GoodIter operator -(GoodIter a, int v) { return GoodIter(); }
367 GoodIter operator +(GoodIter a, int v) { return GoodIter(); }
368 // expected-note@+1 2 {{candidate function not viable: no known conversion from 'Iter1' to 'int' for 1st argument}}
369 GoodIter operator -(int v, GoodIter a) { return GoodIter(); }
370 GoodIter operator +(int v, GoodIter a) { return GoodIter(); }
371 
372 int test_with_random_access_iterator() {
373   GoodIter begin, end;
374   Iter0 begin0, end0;
375   #pragma omp simd
376   for (GoodIter I = begin; I < end; ++I)
377     ++I;
378   // expected-error@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
379   #pragma omp simd
380   for (GoodIter &I = begin; I < end; ++I)
381     ++I;
382   #pragma omp simd
383   for (GoodIter I = begin; I >= end; --I)
384     ++I;
385   // expected-warning@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
386   #pragma omp simd
387   for (GoodIter I(begin); I < end; ++I)
388     ++I;
389   // expected-warning@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
390   #pragma omp simd
391   for (GoodIter I(nullptr); I < end; ++I)
392     ++I;
393   // expected-warning@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
394   #pragma omp simd
395   for (GoodIter I(0); I < end; ++I)
396     ++I;
397   // expected-warning@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
398   #pragma omp simd
399   for (GoodIter I(1,2); I < end; ++I)
400     ++I;
401   #pragma omp simd
402   for (begin = GoodIter(0); begin < end; ++begin)
403     ++begin;
404   #pragma omp simd
405   for (begin = GoodIter(1,2); begin < end; ++begin)
406     ++begin;
407   // expected-error@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
408   #pragma omp simd
409   for (++begin; begin < end; ++begin)
410     ++begin;
411   #pragma omp simd
412   for (begin = end; begin < end; ++begin)
413     ++begin;
414   // expected-error@+2 {{condition of OpenMP for loop must be a relational comparison ('<', '<=', '>', or '>=') of loop variable 'I'}}
415   #pragma omp simd
416   for (GoodIter I = begin; I - I; ++I)
417     ++I;
418   // expected-error@+2 {{condition of OpenMP for loop must be a relational comparison ('<', '<=', '>', or '>=') of loop variable 'I'}}
419   #pragma omp simd
420   for (GoodIter I = begin; begin < end; ++I)
421     ++I;
422   // expected-error@+2 {{condition of OpenMP for loop must be a relational comparison ('<', '<=', '>', or '>=') of loop variable 'I'}}
423   #pragma omp simd
424   for (GoodIter I = begin; !I; ++I)
425     ++I;
426   // expected-note@+3 {{loop step is expected to be negative due to this condition}}
427   // expected-error@+2 {{increment expression must cause 'I' to decrease on each iteration of OpenMP for loop}}
428   #pragma omp simd
429   for (GoodIter I = begin; I >= end; I = I + 1)
430     ++I;
431   #pragma omp simd
432   for (GoodIter I = begin; I >= end; I = I - 1)
433     ++I;
434   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'I'}}
435   #pragma omp simd
436   for (GoodIter I = begin; I >= end; I = -I)
437     ++I;
438   // expected-note@+3 {{loop step is expected to be negative due to this condition}}
439   // expected-error@+2 {{increment expression must cause 'I' to decrease on each iteration of OpenMP for loop}}
440   #pragma omp simd
441   for (GoodIter I = begin; I >= end; I = 2 + I)
442     ++I;
443   // expected-error@+2 {{increment clause of OpenMP for loop must perform simple addition or subtraction on loop variable 'I'}}
444   #pragma omp simd
445   for (GoodIter I = begin; I >= end; I = 2 - I)
446     ++I;
447   #pragma omp simd
448   for (Iter0 I = begin0; I < end0; ++I)
449     ++I;
450 
451   // Initializer is constructor without params.
452   // expected-warning@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
453   #pragma omp simd
454   for (Iter0 I; I < end0; ++I)
455     ++I;
456 
457   Iter1 begin1, end1;
458   // expected-error@+3 {{invalid operands to binary expression ('Iter1' and 'Iter1')}}
459   // expected-error@+2 {{could not calculate number of iterations calling 'operator-' with upper and lower loop bounds}}
460   #pragma omp simd
461   for (Iter1 I = begin1; I < end1; ++I)
462     ++I;
463   // expected-note@+3 {{loop step is expected to be negative due to this condition}}
464   // expected-error@+2 {{increment expression must cause 'I' to decrease on each iteration of OpenMP for loop}}
465   #pragma omp simd
466   for (Iter1 I = begin1; I >= end1; ++I)
467     ++I;
468 
469   // Initializer is constructor with all default params.
470   // expected-error@+4 {{invalid operands to binary expression ('Iter1' and 'float')}}
471   // expected-error@+3 {{could not calculate number of iterations calling 'operator-' with upper and lower loop bounds}}
472   // expected-warning@+2 {{initialization clause of OpenMP for loop is not in canonical form ('var = init' or 'T var = init')}}
473   #pragma omp simd
474   for (Iter1 I; I < end1; ++I) {
475   }
476 
477   return 0;
478 }
479 
480 template <typename IT, int ST> class TC {
481   public:
482     int dotest_lt(IT begin, IT end) {
483       // expected-note@+3 {{loop step is expected to be positive due to this condition}}
484       // expected-error@+2 {{increment expression must cause 'I' to increase on each iteration of OpenMP for loop}}
485       #pragma omp simd
486       for (IT I = begin; I < end; I = I + ST) {
487         ++I;
488       }
489       // expected-note@+3 {{loop step is expected to be positive due to this condition}}
490       // expected-error@+2 {{increment expression must cause 'I' to increase on each iteration of OpenMP for loop}}
491       #pragma omp simd
492       for (IT I = begin; I <= end; I += ST) {
493         ++I;
494       }
495       #pragma omp simd
496       for (IT I = begin; I < end; ++I) {
497         ++I;
498       }
499     }
500 
501     static IT step() {
502       return IT(ST);
503     }
504 };
505 template <typename IT, int ST=0> int dotest_gt(IT begin, IT end) {
506   // expected-note@+3 2 {{loop step is expected to be negative due to this condition}}
507   // expected-error@+2 2 {{increment expression must cause 'I' to decrease on each iteration of OpenMP for loop}}
508   #pragma omp simd
509   for (IT I = begin; I >= end; I = I + ST) {
510     ++I;
511   }
512   // expected-note@+3 2 {{loop step is expected to be negative due to this condition}}
513   // expected-error@+2 2 {{increment expression must cause 'I' to decrease on each iteration of OpenMP for loop}}
514   #pragma omp simd
515   for (IT I = begin; I >= end; I += ST) {
516     ++I;
517   }
518 
519   // expected-note@+3 {{loop step is expected to be negative due to this condition}}
520   // expected-error@+2 {{increment expression must cause 'I' to decrease on each iteration of OpenMP for loop}}
521   #pragma omp simd
522   for (IT I = begin; I >= end; ++I) {
523     ++I;
524   }
525 
526   #pragma omp simd
527   for (IT I = begin; I < end; I+=TC<int,ST>::step()) {
528     ++I;
529   }
530 }
531 
532 void test_with_template() {
533   GoodIter begin, end;
534   TC<GoodIter, 100> t1;
535   TC<GoodIter, -100> t2;
536   t1.dotest_lt(begin, end);
537   t2.dotest_lt(begin, end); // expected-note {{in instantiation of member function 'TC<GoodIter, -100>::dotest_lt' requested here}}
538   dotest_gt(begin, end); // expected-note {{in instantiation of function template specialization 'dotest_gt<GoodIter, 0>' requested here}}
539   dotest_gt<unsigned, 10>(0, 100); // expected-note {{in instantiation of function template specialization 'dotest_gt<unsigned int, 10>' requested here}}
540 }
541 
542 void test_loop_break() {
543   const int N = 100;
544   float a[N], b[N], c[N];
545   #pragma omp simd
546   for (int i = 0; i < 10; i++) {
547     c[i] = a[i] + b[i];
548     for (int j = 0; j < 10; ++j) {
549       if (a[i] > b[j])
550         break; // OK in nested loop
551     }
552     switch(i) {
553       case 1:
554         b[i]++;
555         break;
556       default:
557         break;
558     }
559     if (c[i] > 10)
560       break; // expected-error {{'break' statement cannot be used in OpenMP for loop}}
561 
562     if (c[i] > 11)
563       break; // expected-error {{'break' statement cannot be used in OpenMP for loop}}
564   }
565 
566   #pragma omp simd
567   for (int i = 0; i < 10; i++) {
568     for (int j = 0; j < 10; j++) {
569       c[i] = a[i] + b[i];
570       if (c[i] > 10) {
571         if (c[i] < 20) {
572           break; // OK
573         }
574       }
575     }
576   }
577 }
578 
579 void test_loop_eh() {
580   const int N = 100;
581   float a[N], b[N], c[N];
582   #pragma omp simd
583   for (int i = 0; i < 10; i++) {
584     c[i] = a[i] + b[i];
585     try { // expected-error {{'try' statement cannot be used in OpenMP simd region}}
586       for (int j = 0; j < 10; ++j) {
587         if (a[i] > b[j])
588           throw a[i]; // expected-error {{'throw' statement cannot be used in OpenMP simd region}}
589       }
590       throw a[i]; // expected-error {{'throw' statement cannot be used in OpenMP simd region}}
591     }
592     catch (float f) {
593       if (f > 0.1)
594         throw a[i]; // expected-error {{'throw' statement cannot be used in OpenMP simd region}}
595       return; // expected-error {{cannot return from OpenMP region}}
596     }
597     switch(i) {
598       case 1:
599         b[i]++;
600         break;
601       default:
602         break;
603     }
604     for (int j = 0; j < 10; j++) {
605       if (c[i] > 10)
606         throw c[i]; // expected-error {{'throw' statement cannot be used in OpenMP simd region}}
607     }
608   }
609   if (c[9] > 10)
610     throw c[9]; // OK
611 
612   #pragma omp simd
613   for (int i = 0; i < 10; ++i) {
614     struct S {
615       void g() { throw 0; }
616     };
617   }
618 }
619 
620