1 // PR c++/60228
2 // { dg-additional-options "-std=c++11" }
3 
4 extern "C" void abort ();
5 
6 struct A
7 {
8   typedef int T;
9   #pragma omp declare reduction (y : T : [&omp_out, &omp_in]() { omp_out += omp_in; return 0; }()) initializer (omp_priv = [omp_orig]() { return omp_orig; }())
10   static void foo ();
11 };
12 
13 template <typename T>
14 struct B
15 {
16   #pragma omp declare reduction (y : T : [&omp_out, &omp_in]() { omp_out += omp_in; return 0; }()) initializer (omp_priv = [omp_orig]() { return omp_orig; }())
17   static void foo ();
18 };
19 
20 void
foo()21 A::foo ()
22 {
23   int r = 0, s = 0;
24   #pragma omp parallel for reduction (y : r, s)
25   for (int i = 0; i < 64; i++)
26     {
27       r++;
28       s += i;
29     }
30   if (r != 64 || s != (64 * 63) / 2)
31     abort ();
32 }
33 
34 template <typename T>
35 void
foo()36 B<T>::foo ()
37 {
38   T r = 0, s = 0;
39   #pragma omp parallel for reduction (y : r, s)
40   for (int i = 0; i < 64; i++)
41     {
42       r++;
43       s += i;
44     }
45   if (r != 64 || s != (64 * 63) / 2)
46     abort ();
47 }
48 
49 int
main()50 main ()
51 {
52   A::foo ();
53   B<short>::foo ();
54 }
55