1 // { dg-do compile }
2 // { dg-options "-O3 -g" }
3
4 template <typename T>
max(T & a,T & b)5 T &max (T &a, T &b)
6 {
7 if (a < b) return b; else return a;
8 }
9 int foo (double);
10 struct S
11 {
12 struct T
13 {
14 int dims, count;
TS::T15 T (int, int) : dims (), count () {}
16 };
17 T *rep;
SS18 S () {}
SS19 S (int r, int c) : rep (new T (r, c)) {}
~SS20 ~S () { delete rep; }
21 };
22 template <typename T>
23 struct U
24 {
25 static T epsilon () throw ();
26 };
27 template <class T>
28 struct V
29 {
30 struct W
31 {
32 T * data;
33 int count;
WV::W34 W (int n) : data (new T[n]), count () {}
35 };
36 V::W *rep;
37 S dimensions;
38 int slice_len;
VV39 V (S s) : rep (new V <T>::W (get_size (s))) {}
capacityV40 int capacity () { return slice_len; }
41 int get_size (S);
42 };
43 template <class T>
44 struct Z : public V <T>
45 {
ZZ46 Z () : V <T> (S (0, 0)) {}
ZZ47 Z (int r, int c) : V <T> (S (r, c)) {}
48 };
49 template <class T>
50 struct A : public Z <T>
51 {
AA52 A () : Z <T> () {}
AA53 A (int n, int m) : Z <T> (n, m) {}
54 };
55 template <class T>
56 struct B : public V <T>
57 {
58 };
59 struct C : public A <double>
60 {
CC61 C () : A <double> () {}
CC62 C (int r, int c) : A <double> (r, c) {}
63 };
64 struct D : public B <double>
65 {
66 };
67 template <class T>
68 struct E
69 {
70 };
71 template <class T>
72 struct G : public E <T>
73 {
74 };
75 struct H : public G <double>
76 {
77 };
78 template <class R>
79 struct I
80 {
81 R scl, sum;
accumI82 void accum (R val)
83 {
84 R t = __builtin_fabs (val);
85 if (scl == t)
86 sum += 1;
87 }
operator RI88 operator R () { __builtin_sqrt (sum); return R (); }
89 };
90 template <class R>
91 struct J
92 {
accumJ93 template < class U > void accum (U val) {}
operator RJ94 operator R () { return R (); }
95 };
96 template <class R>
97 struct K
98 {
99 R max;
accumK100 template <class U> void accum (U val)
101 {
102 double z = __builtin_fabs (val);
103 max = ::max (max, z);
104 }
operator RK105 operator R () { return max; }
106 };
107 template <class R>
108 struct L
109 {
110 unsigned num;
accumL111 template <class U> void accum (U) {}
operator RL112 operator R () { return num; }
113 };
114 template <class T, class R, class S>
bar(V<T> & v,R & res,S acc)115 void bar (V <T> &v, R &res, S acc)
116 {
117 for (int i = 0; i < v.capacity (); i++)
118 acc.accum ((i));
119 res = acc;
120 }
121 template <class T, class R>
bar(B<T> & v,R)122 void bar (B <T> &v, R)
123 {
124 R res;
125 bar (v, res, I <R> ());
126 }
127 template <class T, class R>
bar(A<T> & v,R p)128 R bar (A <T> &v, R p)
129 {
130 R res;
131 if (p == 2)
132 bar (v, res, I <R> ());
133 else if (p == 1)
134 bar (v, res, J <R> ());
135 else if (p == sizeof (float) ? (p) : foo (p))
136 {
137 if (p > 0)
138 bar (v, res, K <R> ());
139 }
140 else if (p == 0)
141 bar (v, res, L <R> ());
142 return res;
143 }
144 template <class CT, class VectorT, class R>
145 void
baz(CT m,R p,R tol,int maxiter,VectorT)146 baz (CT m, R p, R tol, int maxiter, VectorT)
147 {
148 VectorT y (0, 0), z (0, 1);
149 R q = 0;
150 R gamma = 0, gamma1 = 0;
151 gamma = bar (y, p);
152 (void) (bar (z, q) <= (gamma1 <= gamma));
153 }
154 int a = 100;
155 template <class CT, class VectorT, class R>
156 void
test(CT m,R p,VectorT)157 test (CT m, R p, VectorT)
158 {
159 VectorT x;
160 R sqrteps (U <R>::epsilon ());
161 baz (m, p, sqrteps, a, x);
162 }
163 void
fn(D x,double p)164 fn (D x, double p)
165 {
166 bar (x, p);
167 }
168 void
fn(H x,double p)169 fn (H x, double p)
170 {
171 test (x, p, C ());
172 }
173