blob: facd4375b0cb546d12301f458377b7b95e365d31 [file] [log] [blame]
Nico Weber1cb2d742012-03-02 22:01:22 +00001// RUN: %clang_cc1 -triple i686-linux -Wno-string-plus-int -fsyntax-only -verify -std=c++11 -pedantic %s -Wno-comment
Richard Smith59efe262011-11-11 04:05:33 +00002
Richard Smith59efe262011-11-11 04:05:33 +00003namespace StaticAssertFoldTest {
4
5int x;
Richard Smith9eed49c2011-12-09 23:00:37 +00006static_assert(++x, "test"); // expected-error {{not an integral constant expression}}
7static_assert(false, "test"); // expected-error {{test}}
Richard Smith59efe262011-11-11 04:05:33 +00008
9}
10
Richard Smith1d238ea2011-12-21 02:55:12 +000011typedef decltype(sizeof(char)) size_t;
12
13template<typename T> constexpr T id(const T &t) { return t; }
14template<typename T> constexpr T min(const T &a, const T &b) {
15 return a < b ? a : b;
16}
17template<typename T> constexpr T max(const T &a, const T &b) {
18 return a < b ? b : a;
19}
20template<typename T, size_t N> constexpr T *begin(T (&xs)[N]) { return xs; }
21template<typename T, size_t N> constexpr T *end(T (&xs)[N]) { return xs + N; }
Richard Smith59efe262011-11-11 04:05:33 +000022
23struct MemberZero {
24 constexpr int zero() { return 0; }
25};
26
27namespace DerivedToVBaseCast {
28
29 struct U { int n; };
30 struct V : U { int n; };
31 struct A : virtual V { int n; };
32 struct Aa { int n; };
33 struct B : virtual A, Aa {};
34 struct C : virtual A, Aa {};
35 struct D : B, C {};
36
37 D d;
38 constexpr B *p = &d;
39 constexpr C *q = &d;
Richard Smithf15fda02012-02-02 01:16:57 +000040
Richard Smith9eed49c2011-12-09 23:00:37 +000041 static_assert((void*)p != (void*)q, "");
42 static_assert((A*)p == (A*)q, "");
43 static_assert((Aa*)p != (Aa*)q, "");
Richard Smith59efe262011-11-11 04:05:33 +000044
45 constexpr B &pp = d;
46 constexpr C &qq = d;
Richard Smith9eed49c2011-12-09 23:00:37 +000047 static_assert((void*)&pp != (void*)&qq, "");
48 static_assert(&(A&)pp == &(A&)qq, "");
49 static_assert(&(Aa&)pp != &(Aa&)qq, "");
Richard Smith59efe262011-11-11 04:05:33 +000050
51 constexpr V *v = p;
52 constexpr V *w = q;
53 constexpr V *x = (A*)p;
Richard Smith9eed49c2011-12-09 23:00:37 +000054 static_assert(v == w, "");
55 static_assert(v == x, "");
Richard Smith59efe262011-11-11 04:05:33 +000056
Richard Smith9eed49c2011-12-09 23:00:37 +000057 static_assert((U*)&d == p, "");
58 static_assert((U*)&d == q, "");
59 static_assert((U*)&d == v, "");
60 static_assert((U*)&d == w, "");
61 static_assert((U*)&d == x, "");
Richard Smith59efe262011-11-11 04:05:33 +000062
63 struct X {};
64 struct Y1 : virtual X {};
65 struct Y2 : X {};
66 struct Z : Y1, Y2 {};
67 Z z;
Richard Smith9eed49c2011-12-09 23:00:37 +000068 static_assert((X*)(Y1*)&z != (X*)(Y2*)&z, "");
Richard Smith59efe262011-11-11 04:05:33 +000069}
70
Richard Smithf64699e2011-11-11 08:28:03 +000071namespace ConstCast {
72
73constexpr int n1 = 0;
74constexpr int n2 = const_cast<int&>(n1);
75constexpr int *n3 = const_cast<int*>(&n1);
76constexpr int n4 = *const_cast<int*>(&n1);
77constexpr const int * const *n5 = const_cast<const int* const*>(&n3);
78constexpr int **n6 = const_cast<int**>(&n3);
79constexpr int n7 = **n5;
80constexpr int n8 = **n6;
81
82}
83
Richard Smith59efe262011-11-11 04:05:33 +000084namespace TemplateArgumentConversion {
85 template<int n> struct IntParam {};
86
87 using IntParam0 = IntParam<0>;
Richard Smith1d238ea2011-12-21 02:55:12 +000088 using IntParam0 = IntParam<id(0)>;
Richard Smith61802452011-12-22 02:22:31 +000089 using IntParam0 = IntParam<MemberZero().zero>; // expected-error {{did you mean to call it with no arguments?}}
Richard Smith59efe262011-11-11 04:05:33 +000090}
91
92namespace CaseStatements {
93 void f(int n) {
94 switch (n) {
Richard Smith8ef7b202012-01-18 23:55:52 +000095 case MemberZero().zero: // expected-error {{did you mean to call it with no arguments?}} expected-note {{previous}}
96 case id(0): // expected-error {{duplicate case value '0'}}
Richard Smith59efe262011-11-11 04:05:33 +000097 return;
98 }
99 }
100}
101
102extern int &Recurse1;
Richard Smith16581332012-03-02 04:14:40 +0000103int &Recurse2 = Recurse1; // expected-note {{declared here}}
104int &Recurse1 = Recurse2;
Richard Smith099e7f62011-12-19 06:19:21 +0000105constexpr int &Recurse3 = Recurse2; // expected-error {{must be initialized by a constant expression}} expected-note {{initializer of 'Recurse2' is not a constant expression}}
106
107extern const int RecurseA;
108const int RecurseB = RecurseA; // expected-note {{declared here}}
109const int RecurseA = 10;
110constexpr int RecurseC = RecurseB; // expected-error {{must be initialized by a constant expression}} expected-note {{initializer of 'RecurseB' is not a constant expression}}
Richard Smith59efe262011-11-11 04:05:33 +0000111
112namespace MemberEnum {
113 struct WithMemberEnum {
114 enum E { A = 42 };
115 } wme;
116
Richard Smith9eed49c2011-12-09 23:00:37 +0000117 static_assert(wme.A == 42, "");
Richard Smith59efe262011-11-11 04:05:33 +0000118}
119
120namespace DefaultArguments {
121
122const int z = int();
123constexpr int Sum(int a = 0, const int &b = 0, const int *c = &z, char d = 0) {
124 return a + b + *c + d;
125}
126const int four = 4;
127constexpr int eight = 8;
128constexpr const int twentyseven = 27;
Richard Smith9eed49c2011-12-09 23:00:37 +0000129static_assert(Sum() == 0, "");
130static_assert(Sum(1) == 1, "");
131static_assert(Sum(1, four) == 5, "");
132static_assert(Sum(1, eight, &twentyseven) == 36, "");
133static_assert(Sum(1, 2, &four, eight) == 15, "");
Richard Smith59efe262011-11-11 04:05:33 +0000134
135}
136
137namespace Ellipsis {
138
139// Note, values passed through an ellipsis can't actually be used.
140constexpr int F(int a, ...) { return a; }
Richard Smith9eed49c2011-12-09 23:00:37 +0000141static_assert(F(0) == 0, "");
142static_assert(F(1, 0) == 1, "");
143static_assert(F(2, "test") == 2, "");
144static_assert(F(3, &F) == 3, "");
Richard Smith7098cbd2011-12-21 05:04:46 +0000145int k = 0; // expected-note {{here}}
146static_assert(F(4, k) == 3, ""); // expected-error {{constant expression}} expected-note {{read of non-const variable 'k'}}
Richard Smith59efe262011-11-11 04:05:33 +0000147
148}
149
150namespace Recursion {
151 constexpr int fib(int n) { return n > 1 ? fib(n-1) + fib(n-2) : n; }
Richard Smith9eed49c2011-12-09 23:00:37 +0000152 static_assert(fib(11) == 89, "");
Richard Smith59efe262011-11-11 04:05:33 +0000153
154 constexpr int gcd_inner(int a, int b) {
155 return b == 0 ? a : gcd_inner(b, a % b);
156 }
157 constexpr int gcd(int a, int b) {
158 return gcd_inner(max(a, b), min(a, b));
159 }
160
Richard Smith9eed49c2011-12-09 23:00:37 +0000161 static_assert(gcd(1749237, 5628959) == 7, "");
Richard Smith59efe262011-11-11 04:05:33 +0000162}
163
164namespace FunctionCast {
165 // When folding, we allow functions to be cast to different types. Such
166 // cast functions cannot be called, even if they're constexpr.
167 constexpr int f() { return 1; }
168 typedef double (*DoubleFn)();
169 typedef int (*IntFn)();
Richard Smithd7c56e12011-12-29 21:57:33 +0000170 int a[(int)DoubleFn(f)()]; // expected-error {{variable length array}} expected-warning{{C99 feature}}
Richard Smith59efe262011-11-11 04:05:33 +0000171 int b[(int)IntFn(f)()]; // ok
172}
173
174namespace StaticMemberFunction {
175 struct S {
176 static constexpr int k = 42;
177 static constexpr int f(int n) { return n * k + 2; }
178 } s;
179
180 constexpr int n = s.f(19);
Richard Smith9eed49c2011-12-09 23:00:37 +0000181 static_assert(S::f(19) == 800, "");
182 static_assert(s.f(19) == 800, "");
183 static_assert(n == 800, "");
Richard Smith1bf9a9e2011-11-12 22:28:03 +0000184
185 constexpr int (*sf1)(int) = &S::f;
186 constexpr int (*sf2)(int) = &s.f;
187 constexpr const int *sk = &s.k;
Richard Smith59efe262011-11-11 04:05:33 +0000188}
189
190namespace ParameterScopes {
191
192 const int k = 42;
Richard Smith83587db2012-02-15 02:18:13 +0000193 constexpr const int &ObscureTheTruth(const int &a) { return a; }
Richard Smith099e7f62011-12-19 06:19:21 +0000194 constexpr const int &MaybeReturnJunk(bool b, const int a) { // expected-note 2{{declared here}}
Richard Smith83587db2012-02-15 02:18:13 +0000195 return ObscureTheTruth(b ? a : k);
Richard Smith59efe262011-11-11 04:05:33 +0000196 }
Richard Smith9eed49c2011-12-09 23:00:37 +0000197 static_assert(MaybeReturnJunk(false, 0) == 42, ""); // ok
Richard Smith83587db2012-02-15 02:18:13 +0000198 constexpr int a = MaybeReturnJunk(true, 0); // expected-error {{constant expression}} expected-note {{read of variable whose lifetime has ended}}
Richard Smith59efe262011-11-11 04:05:33 +0000199
Richard Smith83587db2012-02-15 02:18:13 +0000200 constexpr const int MaybeReturnNonstaticRef(bool b, const int a) {
201 return ObscureTheTruth(b ? a : k);
Richard Smith59efe262011-11-11 04:05:33 +0000202 }
Richard Smith9eed49c2011-12-09 23:00:37 +0000203 static_assert(MaybeReturnNonstaticRef(false, 0) == 42, ""); // ok
Richard Smith83587db2012-02-15 02:18:13 +0000204 constexpr int b = MaybeReturnNonstaticRef(true, 0); // ok
Richard Smith59efe262011-11-11 04:05:33 +0000205
206 constexpr int InternalReturnJunk(int n) {
Richard Smith83587db2012-02-15 02:18:13 +0000207 return MaybeReturnJunk(true, n); // expected-note {{read of variable whose lifetime has ended}}
Richard Smith59efe262011-11-11 04:05:33 +0000208 }
Richard Smith099e7f62011-12-19 06:19:21 +0000209 constexpr int n3 = InternalReturnJunk(0); // expected-error {{must be initialized by a constant expression}} expected-note {{in call to 'InternalReturnJunk(0)'}}
Richard Smith59efe262011-11-11 04:05:33 +0000210
211 constexpr int LToR(int &n) { return n; }
212 constexpr int GrabCallersArgument(bool which, int a, int b) {
213 return LToR(which ? b : a);
214 }
Richard Smith9eed49c2011-12-09 23:00:37 +0000215 static_assert(GrabCallersArgument(false, 1, 2) == 1, "");
216 static_assert(GrabCallersArgument(true, 4, 8) == 8, "");
Richard Smith59efe262011-11-11 04:05:33 +0000217
218}
219
220namespace Pointers {
221
222 constexpr int f(int n, const int *a, const int *b, const int *c) {
223 return n == 0 ? 0 : *a + f(n-1, b, c, a);
224 }
225
226 const int x = 1, y = 10, z = 100;
Richard Smith9eed49c2011-12-09 23:00:37 +0000227 static_assert(f(23, &x, &y, &z) == 788, "");
Richard Smith59efe262011-11-11 04:05:33 +0000228
229 constexpr int g(int n, int a, int b, int c) {
230 return f(n, &a, &b, &c);
231 }
Richard Smith9eed49c2011-12-09 23:00:37 +0000232 static_assert(g(23, x, y, z) == 788, "");
Richard Smith59efe262011-11-11 04:05:33 +0000233
234}
235
236namespace FunctionPointers {
237
238 constexpr int Double(int n) { return 2 * n; }
239 constexpr int Triple(int n) { return 3 * n; }
240 constexpr int Twice(int (*F)(int), int n) { return F(F(n)); }
241 constexpr int Quadruple(int n) { return Twice(Double, n); }
242 constexpr auto Select(int n) -> int (*)(int) {
243 return n == 2 ? &Double : n == 3 ? &Triple : n == 4 ? &Quadruple : 0;
244 }
Richard Smith099e7f62011-12-19 06:19:21 +0000245 constexpr int Apply(int (*F)(int), int n) { return F(n); } // expected-note {{subexpression}}
Richard Smith59efe262011-11-11 04:05:33 +0000246
Richard Smith9eed49c2011-12-09 23:00:37 +0000247 static_assert(1 + Apply(Select(4), 5) + Apply(Select(3), 7) == 42, "");
Richard Smith59efe262011-11-11 04:05:33 +0000248
Richard Smith099e7f62011-12-19 06:19:21 +0000249 constexpr int Invalid = Apply(Select(0), 0); // expected-error {{must be initialized by a constant expression}} expected-note {{in call to 'Apply(0, 0)'}}
Richard Smith59efe262011-11-11 04:05:33 +0000250
251}
252
253namespace PointerComparison {
254
255int x, y;
Richard Smith9eed49c2011-12-09 23:00:37 +0000256static_assert(&x == &y, "false"); // expected-error {{false}}
257static_assert(&x != &y, "");
Richard Smith59efe262011-11-11 04:05:33 +0000258constexpr bool g1 = &x == &y;
259constexpr bool g2 = &x != &y;
260constexpr bool g3 = &x <= &y; // expected-error {{must be initialized by a constant expression}}
261constexpr bool g4 = &x >= &y; // expected-error {{must be initialized by a constant expression}}
262constexpr bool g5 = &x < &y; // expected-error {{must be initialized by a constant expression}}
263constexpr bool g6 = &x > &y; // expected-error {{must be initialized by a constant expression}}
264
265struct S { int x, y; } s;
Richard Smith9eed49c2011-12-09 23:00:37 +0000266static_assert(&s.x == &s.y, "false"); // expected-error {{false}}
267static_assert(&s.x != &s.y, "");
268static_assert(&s.x <= &s.y, "");
269static_assert(&s.x >= &s.y, "false"); // expected-error {{false}}
270static_assert(&s.x < &s.y, "");
271static_assert(&s.x > &s.y, "false"); // expected-error {{false}}
Richard Smith59efe262011-11-11 04:05:33 +0000272
Richard Smith9eed49c2011-12-09 23:00:37 +0000273static_assert(0 == &y, "false"); // expected-error {{false}}
274static_assert(0 != &y, "");
Richard Smith59efe262011-11-11 04:05:33 +0000275constexpr bool n3 = 0 <= &y; // expected-error {{must be initialized by a constant expression}}
276constexpr bool n4 = 0 >= &y; // expected-error {{must be initialized by a constant expression}}
277constexpr bool n5 = 0 < &y; // expected-error {{must be initialized by a constant expression}}
278constexpr bool n6 = 0 > &y; // expected-error {{must be initialized by a constant expression}}
279
Richard Smith9eed49c2011-12-09 23:00:37 +0000280static_assert(&x == 0, "false"); // expected-error {{false}}
281static_assert(&x != 0, "");
Richard Smith59efe262011-11-11 04:05:33 +0000282constexpr bool n9 = &x <= 0; // expected-error {{must be initialized by a constant expression}}
283constexpr bool n10 = &x >= 0; // expected-error {{must be initialized by a constant expression}}
284constexpr bool n11 = &x < 0; // expected-error {{must be initialized by a constant expression}}
285constexpr bool n12 = &x > 0; // expected-error {{must be initialized by a constant expression}}
286
Richard Smith9eed49c2011-12-09 23:00:37 +0000287static_assert(&x == &x, "");
288static_assert(&x != &x, "false"); // expected-error {{false}}
289static_assert(&x <= &x, "");
290static_assert(&x >= &x, "");
291static_assert(&x < &x, "false"); // expected-error {{false}}
292static_assert(&x > &x, "false"); // expected-error {{false}}
Richard Smith59efe262011-11-11 04:05:33 +0000293
294constexpr S* sptr = &s;
Richard Smith099e7f62011-12-19 06:19:21 +0000295constexpr bool dyncast = sptr == dynamic_cast<S*>(sptr); // expected-error {{constant expression}} expected-note {{dynamic_cast}}
Richard Smith59efe262011-11-11 04:05:33 +0000296
Richard Smith2fd59832012-02-08 08:11:33 +0000297struct U {};
Richard Smithc216a012011-12-12 12:46:16 +0000298struct Str {
Richard Smithc216a012011-12-12 12:46:16 +0000299 int a : dynamic_cast<S*>(sptr) == dynamic_cast<S*>(sptr); // \
Richard Smith244ee7b2012-01-15 03:51:30 +0000300 expected-warning {{not an integral constant expression}} \
Richard Smith4cd9b8f2011-12-12 19:10:03 +0000301 expected-note {{dynamic_cast is not allowed in a constant expression}}
Richard Smithc216a012011-12-12 12:46:16 +0000302 int b : reinterpret_cast<S*>(sptr) == reinterpret_cast<S*>(sptr); // \
Richard Smith244ee7b2012-01-15 03:51:30 +0000303 expected-warning {{not an integral constant expression}} \
Richard Smith4cd9b8f2011-12-12 19:10:03 +0000304 expected-note {{reinterpret_cast is not allowed in a constant expression}}
Richard Smithc216a012011-12-12 12:46:16 +0000305 int c : (S*)(long)(sptr) == (S*)(long)(sptr); // \
Richard Smith244ee7b2012-01-15 03:51:30 +0000306 expected-warning {{not an integral constant expression}} \
Richard Smith60f24e72011-12-12 19:33:27 +0000307 expected-note {{cast which performs the conversions of a reinterpret_cast is not allowed in a constant expression}}
Richard Smithc216a012011-12-12 12:46:16 +0000308 int d : (S*)(42) == (S*)(42); // \
Richard Smith244ee7b2012-01-15 03:51:30 +0000309 expected-warning {{not an integral constant expression}} \
Richard Smith60f24e72011-12-12 19:33:27 +0000310 expected-note {{cast which performs the conversions of a reinterpret_cast is not allowed in a constant expression}}
Richard Smithc216a012011-12-12 12:46:16 +0000311 int e : (Str*)(sptr) == (Str*)(sptr); // \
Richard Smith244ee7b2012-01-15 03:51:30 +0000312 expected-warning {{not an integral constant expression}} \
Richard Smith60f24e72011-12-12 19:33:27 +0000313 expected-note {{cast which performs the conversions of a reinterpret_cast is not allowed in a constant expression}}
Richard Smith2fd59832012-02-08 08:11:33 +0000314 int f : &(U&)(*sptr) == &(U&)(*sptr); // \
Richard Smith244ee7b2012-01-15 03:51:30 +0000315 expected-warning {{not an integral constant expression}} \
Richard Smith60f24e72011-12-12 19:33:27 +0000316 expected-note {{cast which performs the conversions of a reinterpret_cast is not allowed in a constant expression}}
Richard Smithc216a012011-12-12 12:46:16 +0000317 int g : (S*)(void*)(sptr) == sptr; // \
Richard Smith244ee7b2012-01-15 03:51:30 +0000318 expected-warning {{not an integral constant expression}} \
Richard Smith4cd9b8f2011-12-12 19:10:03 +0000319 expected-note {{cast from 'void *' is not allowed in a constant expression}}
Richard Smithc216a012011-12-12 12:46:16 +0000320};
321
Richard Smith59efe262011-11-11 04:05:33 +0000322extern char externalvar[];
Richard Smith9eed49c2011-12-09 23:00:37 +0000323constexpr bool constaddress = (void *)externalvar == (void *)0x4000UL; // expected-error {{must be initialized by a constant expression}}
Richard Smith59efe262011-11-11 04:05:33 +0000324constexpr bool litaddress = "foo" == "foo"; // expected-error {{must be initialized by a constant expression}} expected-warning {{unspecified}}
Richard Smith9eed49c2011-12-09 23:00:37 +0000325static_assert(0 != "foo", "");
Richard Smith59efe262011-11-11 04:05:33 +0000326
327}
328
329namespace MaterializeTemporary {
330
331constexpr int f(const int &r) { return r; }
332constexpr int n = f(1);
333
334constexpr bool same(const int &a, const int &b) { return &a == &b; }
335constexpr bool sameTemporary(const int &n) { return same(n, n); }
336
Richard Smith9eed49c2011-12-09 23:00:37 +0000337static_assert(n, "");
338static_assert(!same(4, 4), "");
339static_assert(same(n, n), "");
340static_assert(sameTemporary(9), "");
Richard Smith59efe262011-11-11 04:05:33 +0000341
342}
343
344constexpr int strcmp_ce(const char *p, const char *q) {
345 return (!*p || *p != *q) ? *p - *q : strcmp_ce(p+1, q+1);
346}
347
348namespace StringLiteral {
349
Richard Smith1d238ea2011-12-21 02:55:12 +0000350template<typename Char>
351constexpr int MangleChars(const Char *p) {
Richard Smith59efe262011-11-11 04:05:33 +0000352 return *p + 3 * (*p ? MangleChars(p+1) : 0);
353}
354
Richard Smith9eed49c2011-12-09 23:00:37 +0000355static_assert(MangleChars("constexpr!") == 1768383, "");
Richard Smithec789162012-01-12 18:54:33 +0000356static_assert(MangleChars(u8"constexpr!") == 1768383, "");
357static_assert(MangleChars(L"constexpr!") == 1768383, "");
Richard Smith9eed49c2011-12-09 23:00:37 +0000358static_assert(MangleChars(u"constexpr!") == 1768383, "");
359static_assert(MangleChars(U"constexpr!") == 1768383, "");
Richard Smith59efe262011-11-11 04:05:33 +0000360
361constexpr char c0 = "nought index"[0];
362constexpr char c1 = "nice index"[10];
Richard Smith7098cbd2011-12-21 05:04:46 +0000363constexpr char c2 = "nasty index"[12]; // expected-error {{must be initialized by a constant expression}} expected-warning {{is past the end}} expected-note {{read of dereferenced one-past-the-end pointer}}
Richard Smithb4e85ed2012-01-06 16:39:00 +0000364constexpr char c3 = "negative index"[-1]; // expected-error {{must be initialized by a constant expression}} expected-warning {{is before the beginning}} expected-note {{cannot refer to element -1 of array of 15 elements}}
365constexpr char c4 = ((char*)(int*)"no reinterpret_casts allowed")[14]; // expected-error {{must be initialized by a constant expression}} expected-note {{cast which performs the conversions of a reinterpret_cast}}
Richard Smith59efe262011-11-11 04:05:33 +0000366
367constexpr const char *p = "test" + 2;
Richard Smith9eed49c2011-12-09 23:00:37 +0000368static_assert(*p == 's', "");
Richard Smith59efe262011-11-11 04:05:33 +0000369
370constexpr const char *max_iter(const char *a, const char *b) {
371 return *a < *b ? b : a;
372}
373constexpr const char *max_element(const char *a, const char *b) {
374 return (a+1 >= b) ? a : max_iter(a, max_element(a+1, b));
375}
376
Richard Smith59efe262011-11-11 04:05:33 +0000377constexpr char str[] = "the quick brown fox jumped over the lazy dog";
378constexpr const char *max = max_element(begin(str), end(str));
Richard Smith9eed49c2011-12-09 23:00:37 +0000379static_assert(*max == 'z', "");
380static_assert(max == str + 38, "");
Richard Smith59efe262011-11-11 04:05:33 +0000381
Richard Smith9eed49c2011-12-09 23:00:37 +0000382static_assert(strcmp_ce("hello world", "hello world") == 0, "");
383static_assert(strcmp_ce("hello world", "hello clang") > 0, "");
384static_assert(strcmp_ce("constexpr", "test") < 0, "");
385static_assert(strcmp_ce("", " ") < 0, "");
Richard Smith59efe262011-11-11 04:05:33 +0000386
Richard Smith7098cbd2011-12-21 05:04:46 +0000387struct S {
388 int n : "foo"[4]; // expected-error {{constant expression}} expected-note {{read of dereferenced one-past-the-end pointer is not allowed in a constant expression}}
389};
390
Richard Smith974c5f92011-12-22 01:07:19 +0000391struct T {
392 char c[6];
393 constexpr T() : c{"foo"} {}
394};
395constexpr T t;
396
397static_assert(t.c[0] == 'f', "");
398static_assert(t.c[1] == 'o', "");
399static_assert(t.c[2] == 'o', "");
400static_assert(t.c[3] == 0, "");
401static_assert(t.c[4] == 0, "");
402static_assert(t.c[5] == 0, "");
403static_assert(t.c[6] == 0, ""); // expected-error {{constant expression}} expected-note {{one-past-the-end}}
404
Richard Smithec789162012-01-12 18:54:33 +0000405struct U {
406 wchar_t chars[6];
407 int n;
408} constexpr u = { { L"test" }, 0 };
409static_assert(u.chars[2] == L's', "");
410
Richard Smithf3908f22012-02-17 03:35:37 +0000411struct V {
412 char c[4];
413 constexpr V() : c("hi!") {}
414};
415static_assert(V().c[1] == "i"[0], "");
416
Richard Smith59efe262011-11-11 04:05:33 +0000417}
418
419namespace Array {
420
Richard Smith1d238ea2011-12-21 02:55:12 +0000421template<typename Iter>
422constexpr auto Sum(Iter begin, Iter end) -> decltype(+*begin) {
Richard Smith59efe262011-11-11 04:05:33 +0000423 return begin == end ? 0 : *begin + Sum(begin+1, end);
424}
Richard Smith59efe262011-11-11 04:05:33 +0000425
426constexpr int xs[] = { 1, 2, 3, 4, 5 };
427constexpr int ys[] = { 5, 4, 3, 2, 1 };
428constexpr int sum_xs = Sum(begin(xs), end(xs));
Richard Smith9eed49c2011-12-09 23:00:37 +0000429static_assert(sum_xs == 15, "");
Richard Smith59efe262011-11-11 04:05:33 +0000430
431constexpr int ZipFoldR(int (*F)(int x, int y, int c), int n,
432 const int *xs, const int *ys, int c) {
Richard Smithdaaefc52011-12-14 23:32:26 +0000433 return n ? F(
Richard Smith7098cbd2011-12-21 05:04:46 +0000434 *xs, // expected-note {{read of dereferenced one-past-the-end pointer}}
Richard Smith08d6e032011-12-16 19:06:07 +0000435 *ys,
436 ZipFoldR(F, n-1, xs+1, ys+1, c)) // \
437 expected-note {{in call to 'ZipFoldR(&SubMul, 2, &xs[4], &ys[4], 1)'}} \
438 expected-note {{in call to 'ZipFoldR(&SubMul, 1, &xs[5], &ys[5], 1)'}}
439 : c;
Richard Smith59efe262011-11-11 04:05:33 +0000440}
441constexpr int MulAdd(int x, int y, int c) { return x * y + c; }
442constexpr int InnerProduct = ZipFoldR(MulAdd, 5, xs, ys, 0);
Richard Smith9eed49c2011-12-09 23:00:37 +0000443static_assert(InnerProduct == 35, "");
Richard Smith59efe262011-11-11 04:05:33 +0000444
445constexpr int SubMul(int x, int y, int c) { return (x - y) * c; }
446constexpr int DiffProd = ZipFoldR(SubMul, 2, xs+3, ys+3, 1);
Richard Smith9eed49c2011-12-09 23:00:37 +0000447static_assert(DiffProd == 8, "");
Richard Smith08d6e032011-12-16 19:06:07 +0000448static_assert(ZipFoldR(SubMul, 3, xs+3, ys+3, 1), ""); // \
449 expected-error {{constant expression}} \
450 expected-note {{in call to 'ZipFoldR(&SubMul, 3, &xs[3], &ys[3], 1)'}}
Richard Smith59efe262011-11-11 04:05:33 +0000451
452constexpr const int *p = xs + 3;
453constexpr int xs4 = p[1]; // ok
Richard Smith7098cbd2011-12-21 05:04:46 +0000454constexpr int xs5 = p[2]; // expected-error {{constant expression}} expected-note {{read of dereferenced one-past-the-end pointer}}
Richard Smithb4e85ed2012-01-06 16:39:00 +0000455constexpr int xs6 = p[3]; // expected-error {{constant expression}} expected-note {{cannot refer to element 6}}
Richard Smith59efe262011-11-11 04:05:33 +0000456constexpr int xs0 = p[-3]; // ok
Richard Smithb4e85ed2012-01-06 16:39:00 +0000457constexpr int xs_1 = p[-4]; // expected-error {{constant expression}} expected-note {{cannot refer to element -1}}
Richard Smith59efe262011-11-11 04:05:33 +0000458
459constexpr int zs[2][2][2][2] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16 };
Richard Smith9eed49c2011-12-09 23:00:37 +0000460static_assert(zs[0][0][0][0] == 1, "");
461static_assert(zs[1][1][1][1] == 16, "");
Richard Smith7098cbd2011-12-21 05:04:46 +0000462static_assert(zs[0][0][0][2] == 3, ""); // expected-error {{constant expression}} expected-note {{read of dereferenced one-past-the-end pointer}}
Richard Smith9eed49c2011-12-09 23:00:37 +0000463static_assert((&zs[0][0][0][2])[-1] == 2, "");
464static_assert(**(**(zs + 1) + 1) == 11, "");
Richard Smithb4e85ed2012-01-06 16:39:00 +0000465static_assert(*(&(&(*(*&(&zs[2] - 1)[0] + 2 - 2))[2])[-1][-1] + 1) == 11, ""); // expected-error {{constant expression}} expected-note {{cannot refer to element -1 of array of 2 elements in a constant expression}}
466static_assert(*(&(&(*(*&(&zs[2] - 1)[0] + 2 - 2))[2])[-1][2] - 2) == 11, "");
467constexpr int err_zs_1_2_0_0 = zs[1][2][0][0]; // expected-error {{constant expression}} expected-note {{cannot access array element of pointer past the end}}
Richard Smith59efe262011-11-11 04:05:33 +0000468
Richard Smith08d6e032011-12-16 19:06:07 +0000469constexpr int fail(const int &p) {
Richard Smithb4e85ed2012-01-06 16:39:00 +0000470 return (&p)[64]; // expected-note {{cannot refer to element 64 of array of 2 elements}}
Richard Smith08d6e032011-12-16 19:06:07 +0000471}
Richard Smithb4e85ed2012-01-06 16:39:00 +0000472static_assert(fail(*(&(&(*(*&(&zs[2] - 1)[0] + 2 - 2))[2])[-1][2] - 2)) == 11, ""); // \
Richard Smith08d6e032011-12-16 19:06:07 +0000473expected-error {{static_assert expression is not an integral constant expression}} \
474expected-note {{in call to 'fail(zs[1][0][1][0])'}}
475
Richard Smithd7c56e12011-12-29 21:57:33 +0000476constexpr int arr[40] = { 1, 2, 3, [8] = 4 }; // expected-warning {{C99 feature}}
Richard Smith59efe262011-11-11 04:05:33 +0000477constexpr int SumNonzero(const int *p) {
478 return *p + (*p ? SumNonzero(p+1) : 0);
479}
480constexpr int CountZero(const int *p, const int *q) {
481 return p == q ? 0 : (*p == 0) + CountZero(p+1, q);
482}
Richard Smith9eed49c2011-12-09 23:00:37 +0000483static_assert(SumNonzero(arr) == 6, "");
484static_assert(CountZero(arr, arr + 40) == 36, "");
Richard Smith59efe262011-11-11 04:05:33 +0000485
Richard Smithe24f5fc2011-11-17 22:56:20 +0000486struct ArrayElem {
487 constexpr ArrayElem() : n(0) {}
488 int n;
489 constexpr int f() { return n; }
490};
491struct ArrayRVal {
492 constexpr ArrayRVal() {}
493 ArrayElem elems[10];
494};
Richard Smith9eed49c2011-12-09 23:00:37 +0000495static_assert(ArrayRVal().elems[3].f() == 0, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000496
Richard Smith59efe262011-11-11 04:05:33 +0000497}
498
499namespace DependentValues {
500
501struct I { int n; typedef I V[10]; };
502I::V x, y;
503template<bool B> struct S {
504 int k;
505 void f() {
506 I::V &cells = B ? x : y;
507 I &i = cells[k];
508 switch (i.n) {}
509 }
510};
511
512}
513
514namespace Class {
515
516struct A { constexpr A(int a, int b) : k(a + b) {} int k; };
517constexpr int fn(const A &a) { return a.k; }
Richard Smith9eed49c2011-12-09 23:00:37 +0000518static_assert(fn(A(4,5)) == 9, "");
Richard Smith59efe262011-11-11 04:05:33 +0000519
520struct B { int n; int m; } constexpr b = { 0, b.n }; // expected-warning {{uninitialized}}
521struct C {
522 constexpr C(C *this_) : m(42), n(this_->m) {} // ok
523 int m, n;
524};
525struct D {
526 C c;
527 constexpr D() : c(&c) {}
528};
Richard Smith9eed49c2011-12-09 23:00:37 +0000529static_assert(D().c.n == 42, "");
Richard Smith59efe262011-11-11 04:05:33 +0000530
Richard Smith61802452011-12-22 02:22:31 +0000531struct E {
Richard Smith83587db2012-02-15 02:18:13 +0000532 constexpr E() : p(&p) {}
Richard Smith59efe262011-11-11 04:05:33 +0000533 void *p;
534};
Richard Smith83587db2012-02-15 02:18:13 +0000535constexpr const E &e1 = E(); // expected-error {{constant expression}} expected-note {{reference to temporary is not a constant expression}} expected-note {{temporary created here}}
Richard Smith59efe262011-11-11 04:05:33 +0000536// This is a constant expression if we elide the copy constructor call, and
537// is not a constant expression if we don't! But we do, so it is.
Richard Smith61802452011-12-22 02:22:31 +0000538constexpr E e2 = E();
539static_assert(e2.p == &e2.p, "");
Richard Smith099e7f62011-12-19 06:19:21 +0000540constexpr E e3;
Richard Smith9eed49c2011-12-09 23:00:37 +0000541static_assert(e3.p == &e3.p, "");
Richard Smith59efe262011-11-11 04:05:33 +0000542
543extern const class F f;
544struct F {
545 constexpr F() : p(&f.p) {}
546 const void *p;
547};
Richard Smith099e7f62011-12-19 06:19:21 +0000548constexpr F f;
Richard Smith59efe262011-11-11 04:05:33 +0000549
550struct G {
551 struct T {
552 constexpr T(T *p) : u1(), u2(p) {}
553 union U1 {
554 constexpr U1() {}
555 int a, b = 42;
556 } u1;
557 union U2 {
558 constexpr U2(T *p) : c(p->u1.b) {}
559 int c, d;
560 } u2;
561 } t;
562 constexpr G() : t(&t) {}
563} constexpr g;
564
Richard Smith7098cbd2011-12-21 05:04:46 +0000565static_assert(g.t.u1.a == 42, ""); // expected-error {{constant expression}} expected-note {{read of member 'a' of union with active member 'b'}}
Richard Smith9eed49c2011-12-09 23:00:37 +0000566static_assert(g.t.u1.b == 42, "");
567static_assert(g.t.u2.c == 42, "");
Richard Smith7098cbd2011-12-21 05:04:46 +0000568static_assert(g.t.u2.d == 42, ""); // expected-error {{constant expression}} expected-note {{read of member 'd' of union with active member 'c'}}
Richard Smith59efe262011-11-11 04:05:33 +0000569
570struct S {
571 int a, b;
572 const S *p;
573 double d;
574 const char *q;
575
576 constexpr S(int n, const S *p) : a(5), b(n), p(p), d(n), q("hello") {}
577};
578
579S global(43, &global);
580
Richard Smith9eed49c2011-12-09 23:00:37 +0000581static_assert(S(15, &global).b == 15, "");
Richard Smith59efe262011-11-11 04:05:33 +0000582
583constexpr bool CheckS(const S &s) {
584 return s.a == 5 && s.b == 27 && s.p == &global && s.d == 27. && s.q[3] == 'l';
585}
Richard Smith9eed49c2011-12-09 23:00:37 +0000586static_assert(CheckS(S(27, &global)), "");
Richard Smith59efe262011-11-11 04:05:33 +0000587
588struct Arr {
589 char arr[3];
590 constexpr Arr() : arr{'x', 'y', 'z'} {}
591};
592constexpr int hash(Arr &&a) {
593 return a.arr[0] + a.arr[1] * 0x100 + a.arr[2] * 0x10000;
594}
595constexpr int k = hash(Arr());
Richard Smith9eed49c2011-12-09 23:00:37 +0000596static_assert(k == 0x007a7978, "");
Richard Smith59efe262011-11-11 04:05:33 +0000597
598
599struct AggregateInit {
600 const char &c;
601 int n;
602 double d;
603 int arr[5];
604 void *p;
605};
606
607constexpr AggregateInit agg1 = { "hello"[0] };
608
Richard Smith9eed49c2011-12-09 23:00:37 +0000609static_assert(strcmp_ce(&agg1.c, "hello") == 0, "");
610static_assert(agg1.n == 0, "");
611static_assert(agg1.d == 0.0, "");
Richard Smithb4e85ed2012-01-06 16:39:00 +0000612static_assert(agg1.arr[-1] == 0, ""); // expected-error {{constant expression}} expected-note {{cannot refer to element -1}}
Richard Smith9eed49c2011-12-09 23:00:37 +0000613static_assert(agg1.arr[0] == 0, "");
614static_assert(agg1.arr[4] == 0, "");
Richard Smith7098cbd2011-12-21 05:04:46 +0000615static_assert(agg1.arr[5] == 0, ""); // expected-error {{constant expression}} expected-note {{read of dereferenced one-past-the-end}}
Richard Smith9eed49c2011-12-09 23:00:37 +0000616static_assert(agg1.p == nullptr, "");
Richard Smith59efe262011-11-11 04:05:33 +0000617
Richard Smithfe587202012-04-15 02:50:59 +0000618static constexpr const unsigned char uc[] = { "foo" };
619static_assert(uc[0] == 'f', "");
620static_assert(uc[3] == 0, "");
621
Richard Smith59efe262011-11-11 04:05:33 +0000622namespace SimpleDerivedClass {
623
624struct B {
625 constexpr B(int n) : a(n) {}
626 int a;
627};
628struct D : B {
629 constexpr D(int n) : B(n) {}
630};
631constexpr D d(3);
Richard Smith9eed49c2011-12-09 23:00:37 +0000632static_assert(d.a == 3, "");
Richard Smith59efe262011-11-11 04:05:33 +0000633
634}
635
Richard Smithe24f5fc2011-11-17 22:56:20 +0000636struct Bottom { constexpr Bottom() {} };
637struct Base : Bottom {
Richard Smith59efe262011-11-11 04:05:33 +0000638 constexpr Base(int a = 42, const char *b = "test") : a(a), b(b) {}
639 int a;
640 const char *b;
641};
Richard Smithe24f5fc2011-11-17 22:56:20 +0000642struct Base2 : Bottom {
Richard Smith59efe262011-11-11 04:05:33 +0000643 constexpr Base2(const int &r) : r(r) {}
644 int q = 123;
Richard Smith099e7f62011-12-19 06:19:21 +0000645 const int &r;
Richard Smith59efe262011-11-11 04:05:33 +0000646};
647struct Derived : Base, Base2 {
648 constexpr Derived() : Base(76), Base2(a) {}
649 int c = r + b[1];
650};
651
652constexpr bool operator==(const Base &a, const Base &b) {
653 return a.a == b.a && strcmp_ce(a.b, b.b) == 0;
654}
655
656constexpr Base base;
657constexpr Base base2(76);
658constexpr Derived derived;
Richard Smith9eed49c2011-12-09 23:00:37 +0000659static_assert(derived.a == 76, "");
660static_assert(derived.b[2] == 's', "");
661static_assert(derived.c == 76 + 'e', "");
662static_assert(derived.q == 123, "");
663static_assert(derived.r == 76, "");
Richard Smith099e7f62011-12-19 06:19:21 +0000664static_assert(&derived.r == &derived.a, "");
Richard Smith59efe262011-11-11 04:05:33 +0000665
Richard Smith9eed49c2011-12-09 23:00:37 +0000666static_assert(!(derived == base), "");
667static_assert(derived == base2, "");
Richard Smith59efe262011-11-11 04:05:33 +0000668
Richard Smithe24f5fc2011-11-17 22:56:20 +0000669constexpr Bottom &bot1 = (Base&)derived;
670constexpr Bottom &bot2 = (Base2&)derived;
Richard Smith9eed49c2011-12-09 23:00:37 +0000671static_assert(&bot1 != &bot2, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000672
673constexpr Bottom *pb1 = (Base*)&derived;
674constexpr Bottom *pb2 = (Base2*)&derived;
Richard Smithf15fda02012-02-02 01:16:57 +0000675static_assert(&pb1 != &pb2, "");
Richard Smith9eed49c2011-12-09 23:00:37 +0000676static_assert(pb1 == &bot1, "");
677static_assert(pb2 == &bot2, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000678
Richard Smithb4e85ed2012-01-06 16:39:00 +0000679constexpr Base2 &fail = (Base2&)bot1; // expected-error {{constant expression}} expected-note {{cannot cast object of dynamic type 'const Class::Derived' to type 'Class::Base2'}}
680constexpr Base &fail2 = (Base&)*pb2; // expected-error {{constant expression}} expected-note {{cannot cast object of dynamic type 'const Class::Derived' to type 'Class::Base'}}
Richard Smithe24f5fc2011-11-17 22:56:20 +0000681constexpr Base2 &ok2 = (Base2&)bot2;
Richard Smith9eed49c2011-12-09 23:00:37 +0000682static_assert(&ok2 == &derived, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000683
Richard Smithb4e85ed2012-01-06 16:39:00 +0000684constexpr Base2 *pfail = (Base2*)pb1; // expected-error {{constant expression}} expected-note {{cannot cast object of dynamic type 'const Class::Derived' to type 'Class::Base2'}}
685constexpr Base *pfail2 = (Base*)&bot2; // expected-error {{constant expression}} expected-note {{cannot cast object of dynamic type 'const Class::Derived' to type 'Class::Base'}}
Richard Smithe24f5fc2011-11-17 22:56:20 +0000686constexpr Base2 *pok2 = (Base2*)pb2;
Richard Smith9eed49c2011-12-09 23:00:37 +0000687static_assert(pok2 == &derived, "");
688static_assert(&ok2 == pok2, "");
689static_assert((Base2*)(Derived*)(Base*)pb1 == pok2, "");
690static_assert((Derived*)(Base*)pb1 == (Derived*)pok2, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000691
692constexpr Base *nullB = 42 - 6 * 7;
Richard Smith9eed49c2011-12-09 23:00:37 +0000693static_assert((Bottom*)nullB == 0, "");
694static_assert((Derived*)nullB == 0, "");
695static_assert((void*)(Bottom*)nullB == (void*)(Derived*)nullB, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000696
Richard Smith7d580a42012-01-17 21:17:26 +0000697namespace ConversionOperators {
698
699struct T {
700 constexpr T(int n) : k(5*n - 3) {}
701 constexpr operator int() { return k; }
702 int k;
703};
704
705struct S {
706 constexpr S(int n) : k(2*n + 1) {}
707 constexpr operator int() { return k; }
708 constexpr operator T() { return T(k); }
709 int k;
710};
711
712constexpr bool check(T a, T b) { return a == b.k; }
713
714static_assert(S(5) == 11, "");
715static_assert(check(S(5), 11), "");
716
717}
718
Richard Smithe24f5fc2011-11-17 22:56:20 +0000719}
720
721namespace Temporaries {
722
723struct S {
724 constexpr S() {}
725 constexpr int f();
726};
727struct T : S {
728 constexpr T(int n) : S(), n(n) {}
729 int n;
730};
731constexpr int S::f() {
732 // 'this' must be the postfix-expression in a class member access expression,
733 // so we can't just use
734 // return static_cast<T*>(this)->n;
735 return this->*(int(S::*))&T::n;
736}
737// The T temporary is implicitly cast to an S subobject, but we can recover the
738// T full-object via a base-to-derived cast, or a derived-to-base-casted member
739// pointer.
Richard Smith9eed49c2011-12-09 23:00:37 +0000740static_assert(T(3).f() == 3, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000741
742constexpr int f(const S &s) {
743 return static_cast<const T&>(s).n;
744}
745constexpr int n = f(T(5));
Richard Smith9eed49c2011-12-09 23:00:37 +0000746static_assert(f(T(5)) == 5, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000747
Richard Smithf2e4cd72012-01-26 04:47:34 +0000748constexpr bool b(int n) { return &n; }
749static_assert(b(0), "");
750
Richard Smith59efe262011-11-11 04:05:33 +0000751}
752
753namespace Union {
754
755union U {
756 int a;
757 int b;
758};
759
Richard Smithd7c56e12011-12-29 21:57:33 +0000760constexpr U u[4] = { { .a = 0 }, { .b = 1 }, { .a = 2 }, { .b = 3 } }; // expected-warning 4{{C99 feature}}
Richard Smith9eed49c2011-12-09 23:00:37 +0000761static_assert(u[0].a == 0, "");
Richard Smith7098cbd2011-12-21 05:04:46 +0000762static_assert(u[0].b, ""); // expected-error {{constant expression}} expected-note {{read of member 'b' of union with active member 'a'}}
Richard Smith9eed49c2011-12-09 23:00:37 +0000763static_assert(u[1].b == 1, "");
Richard Smith7098cbd2011-12-21 05:04:46 +0000764static_assert((&u[1].b)[1] == 2, ""); // expected-error {{constant expression}} expected-note {{read of dereferenced one-past-the-end pointer}}
Richard Smithb4e85ed2012-01-06 16:39:00 +0000765static_assert(*(&(u[1].b) + 1 + 1) == 3, ""); // expected-error {{constant expression}} expected-note {{cannot refer to element 2 of non-array object}}
Richard Smith9eed49c2011-12-09 23:00:37 +0000766static_assert((&(u[1]) + 1 + 1)->b == 3, "");
Richard Smith59efe262011-11-11 04:05:33 +0000767
Richard Smithec789162012-01-12 18:54:33 +0000768constexpr U v = {};
769static_assert(v.a == 0, "");
770
771union Empty {};
772constexpr Empty e = {};
773
Richard Smith610a60c2012-01-10 04:32:03 +0000774// Make sure we handle trivial copy constructors for unions.
775constexpr U x = {42};
776constexpr U y = x;
777static_assert(y.a == 42, "");
778static_assert(y.b == 42, ""); // expected-error {{constant expression}} expected-note {{'b' of union with active member 'a'}}
779
Richard Smith59efe262011-11-11 04:05:33 +0000780}
781
Richard Smithe24f5fc2011-11-17 22:56:20 +0000782namespace MemberPointer {
783 struct A {
784 constexpr A(int n) : n(n) {}
785 int n;
786 constexpr int f() { return n + 3; }
787 };
788 constexpr A a(7);
Richard Smith9eed49c2011-12-09 23:00:37 +0000789 static_assert(A(5).*&A::n == 5, "");
790 static_assert((&a)->*&A::n == 7, "");
791 static_assert((A(8).*&A::f)() == 11, "");
792 static_assert(((&a)->*&A::f)() == 10, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000793
794 struct B : A {
795 constexpr B(int n, int m) : A(n), m(m) {}
796 int m;
797 constexpr int g() { return n + m + 1; }
798 };
799 constexpr B b(9, 13);
Richard Smith9eed49c2011-12-09 23:00:37 +0000800 static_assert(B(4, 11).*&A::n == 4, "");
801 static_assert(B(4, 11).*&B::m == 11, "");
802 static_assert(B(4, 11).*(int(A::*))&B::m == 11, "");
803 static_assert((&b)->*&A::n == 9, "");
804 static_assert((&b)->*&B::m == 13, "");
805 static_assert((&b)->*(int(A::*))&B::m == 13, "");
806 static_assert((B(4, 11).*&A::f)() == 7, "");
807 static_assert((B(4, 11).*&B::g)() == 16, "");
808 static_assert((B(4, 11).*(int(A::*)()const)&B::g)() == 16, "");
809 static_assert(((&b)->*&A::f)() == 12, "");
810 static_assert(((&b)->*&B::g)() == 23, "");
811 static_assert(((&b)->*(int(A::*)()const)&B::g)() == 23, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000812
813 struct S {
814 constexpr S(int m, int n, int (S::*pf)() const, int S::*pn) :
815 m(m), n(n), pf(pf), pn(pn) {}
816 constexpr S() : m(), n(), pf(&S::f), pn(&S::n) {}
817
818 constexpr int f() { return this->*pn; }
819 virtual int g() const;
820
821 int m, n;
822 int (S::*pf)() const;
823 int S::*pn;
824 };
825
826 constexpr int S::*pm = &S::m;
827 constexpr int S::*pn = &S::n;
828 constexpr int (S::*pf)() const = &S::f;
829 constexpr int (S::*pg)() const = &S::g;
830
831 constexpr S s(2, 5, &S::f, &S::m);
832
Richard Smith9eed49c2011-12-09 23:00:37 +0000833 static_assert((s.*&S::f)() == 2, "");
834 static_assert((s.*s.pf)() == 2, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000835
Richard Smithb02e4622012-02-01 01:42:44 +0000836 static_assert(pf == &S::f, "");
837 static_assert(pf == s.*&S::pf, "");
838 static_assert(pm == &S::m, "");
839 static_assert(pm != pn, "");
840 static_assert(s.pn != pn, "");
841 static_assert(s.pn == pm, "");
842 static_assert(pg != nullptr, "");
843 static_assert(pf != nullptr, "");
844 static_assert((int S::*)nullptr == nullptr, "");
845 static_assert(pg == pg, ""); // expected-error {{constant expression}} expected-note {{comparison of pointer to virtual member function 'g' has unspecified value}}
846 static_assert(pf != pg, ""); // expected-error {{constant expression}} expected-note {{comparison of pointer to virtual member function 'g' has unspecified value}}
847
Richard Smithe24f5fc2011-11-17 22:56:20 +0000848 template<int n> struct T : T<n-1> {};
849 template<> struct T<0> { int n; };
850 template<> struct T<30> : T<29> { int m; };
851
852 T<17> t17;
853 T<30> t30;
854
855 constexpr int (T<10>::*deepn) = &T<0>::n;
Richard Smith9eed49c2011-12-09 23:00:37 +0000856 static_assert(&(t17.*deepn) == &t17.n, "");
Richard Smithb02e4622012-02-01 01:42:44 +0000857 static_assert(deepn == &T<2>::n, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000858
859 constexpr int (T<15>::*deepm) = (int(T<10>::*))&T<30>::m;
860 constexpr int *pbad = &(t17.*deepm); // expected-error {{constant expression}}
Richard Smith9eed49c2011-12-09 23:00:37 +0000861 static_assert(&(t30.*deepm) == &t30.m, "");
Richard Smithb02e4622012-02-01 01:42:44 +0000862 static_assert(deepm == &T<50>::m, "");
863 static_assert(deepm != deepn, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000864
865 constexpr T<5> *p17_5 = &t17;
866 constexpr T<13> *p17_13 = (T<13>*)p17_5;
Richard Smithb4e85ed2012-01-06 16:39:00 +0000867 constexpr T<23> *p17_23 = (T<23>*)p17_13; // expected-error {{constant expression}} expected-note {{cannot cast object of dynamic type 'T<17>' to type 'T<23>'}}
Richard Smith9eed49c2011-12-09 23:00:37 +0000868 static_assert(&(p17_5->*(int(T<3>::*))deepn) == &t17.n, "");
869 static_assert(&(p17_13->*deepn) == &t17.n, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000870 constexpr int *pbad2 = &(p17_13->*(int(T<9>::*))deepm); // expected-error {{constant expression}}
871
872 constexpr T<5> *p30_5 = &t30;
873 constexpr T<23> *p30_23 = (T<23>*)p30_5;
874 constexpr T<13> *p30_13 = p30_23;
Richard Smith9eed49c2011-12-09 23:00:37 +0000875 static_assert(&(p30_5->*(int(T<3>::*))deepn) == &t30.n, "");
876 static_assert(&(p30_13->*deepn) == &t30.n, "");
877 static_assert(&(p30_23->*deepn) == &t30.n, "");
878 static_assert(&(p30_5->*(int(T<2>::*))deepm) == &t30.m, "");
879 static_assert(&(((T<17>*)p30_13)->*deepm) == &t30.m, "");
880 static_assert(&(p30_23->*deepm) == &t30.m, "");
Richard Smithb02e4622012-02-01 01:42:44 +0000881
882 struct Base { int n; };
883 template<int N> struct Mid : Base {};
884 struct Derived : Mid<0>, Mid<1> {};
885 static_assert(&Mid<0>::n == &Mid<1>::n, "");
886 static_assert((int Derived::*)(int Mid<0>::*)&Mid<0>::n !=
887 (int Derived::*)(int Mid<1>::*)&Mid<1>::n, "");
888 static_assert(&Mid<0>::n == (int Mid<0>::*)&Base::n, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000889}
890
891namespace ArrayBaseDerived {
892
893 struct Base {
894 constexpr Base() {}
895 int n = 0;
896 };
897 struct Derived : Base {
898 constexpr Derived() {}
899 constexpr const int *f() { return &n; }
900 };
901
902 constexpr Derived a[10];
903 constexpr Derived *pd3 = const_cast<Derived*>(&a[3]);
904 constexpr Base *pb3 = const_cast<Derived*>(&a[3]);
Richard Smith9eed49c2011-12-09 23:00:37 +0000905 static_assert(pb3 == pd3, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000906
907 // pb3 does not point to an array element.
908 constexpr Base *pb4 = pb3 + 1; // ok, one-past-the-end pointer.
Richard Smithb4e85ed2012-01-06 16:39:00 +0000909 constexpr int pb4n = pb4->n; // expected-error {{constant expression}} expected-note {{cannot access field of pointer past the end}}
910 constexpr Base *err_pb5 = pb3 + 2; // expected-error {{constant expression}} expected-note {{cannot refer to element 2}} expected-note {{here}}
911 constexpr int err_pb5n = err_pb5->n; // expected-error {{constant expression}} expected-note {{initializer of 'err_pb5' is not a constant expression}}
912 constexpr Base *err_pb2 = pb3 - 1; // expected-error {{constant expression}} expected-note {{cannot refer to element -1}} expected-note {{here}}
913 constexpr int err_pb2n = err_pb2->n; // expected-error {{constant expression}} expected-note {{initializer of 'err_pb2'}}
Richard Smithe24f5fc2011-11-17 22:56:20 +0000914 constexpr Base *pb3a = pb4 - 1;
915
916 // pb4 does not point to a Derived.
Richard Smithb4e85ed2012-01-06 16:39:00 +0000917 constexpr Derived *err_pd4 = (Derived*)pb4; // expected-error {{constant expression}} expected-note {{cannot access derived class of pointer past the end}}
Richard Smithe24f5fc2011-11-17 22:56:20 +0000918 constexpr Derived *pd3a = (Derived*)pb3a;
919 constexpr int pd3n = pd3a->n;
920
921 // pd3a still points to the Derived array.
922 constexpr Derived *pd6 = pd3a + 3;
Richard Smith9eed49c2011-12-09 23:00:37 +0000923 static_assert(pd6 == &a[6], "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000924 constexpr Derived *pd9 = pd6 + 3;
925 constexpr Derived *pd10 = pd6 + 4;
926 constexpr int pd9n = pd9->n; // ok
Richard Smithb4e85ed2012-01-06 16:39:00 +0000927 constexpr int err_pd10n = pd10->n; // expected-error {{constant expression}} expected-note {{cannot access base class of pointer past the end}}
Richard Smithe24f5fc2011-11-17 22:56:20 +0000928 constexpr int pd0n = pd10[-10].n;
Richard Smithb4e85ed2012-01-06 16:39:00 +0000929 constexpr int err_pdminus1n = pd10[-11].n; // expected-error {{constant expression}} expected-note {{cannot refer to element -1 of}}
Richard Smithe24f5fc2011-11-17 22:56:20 +0000930
931 constexpr Base *pb9 = pd9;
932 constexpr const int *(Base::*pfb)() const =
933 static_cast<const int *(Base::*)() const>(&Derived::f);
Richard Smith9eed49c2011-12-09 23:00:37 +0000934 static_assert((pb9->*pfb)() == &a[9].n, "");
Richard Smithe24f5fc2011-11-17 22:56:20 +0000935}
936
Richard Smith59efe262011-11-11 04:05:33 +0000937namespace Complex {
938
939class complex {
940 int re, im;
941public:
942 constexpr complex(int re = 0, int im = 0) : re(re), im(im) {}
943 constexpr complex(const complex &o) : re(o.re), im(o.im) {}
944 constexpr complex operator-() const { return complex(-re, -im); }
945 friend constexpr complex operator+(const complex &l, const complex &r) {
946 return complex(l.re + r.re, l.im + r.im);
947 }
948 friend constexpr complex operator-(const complex &l, const complex &r) {
949 return l + -r;
950 }
951 friend constexpr complex operator*(const complex &l, const complex &r) {
952 return complex(l.re * r.re - l.im * r.im, l.re * r.im + l.im * r.re);
953 }
954 friend constexpr bool operator==(const complex &l, const complex &r) {
955 return l.re == r.re && l.im == r.im;
956 }
957 constexpr bool operator!=(const complex &r) const {
958 return re != r.re || im != r.im;
959 }
960 constexpr int real() const { return re; }
961 constexpr int imag() const { return im; }
962};
963
964constexpr complex i = complex(0, 1);
965constexpr complex k = (3 + 4*i) * (6 - 4*i);
Richard Smith9eed49c2011-12-09 23:00:37 +0000966static_assert(complex(1,0).real() == 1, "");
967static_assert(complex(1,0).imag() == 0, "");
968static_assert(((complex)1).imag() == 0, "");
969static_assert(k.real() == 34, "");
970static_assert(k.imag() == 12, "");
971static_assert(k - 34 == 12*i, "");
972static_assert((complex)1 == complex(1), "");
973static_assert((complex)1 != complex(0, 1), "");
974static_assert(complex(1) == complex(1), "");
975static_assert(complex(1) != complex(0, 1), "");
Richard Smith59efe262011-11-11 04:05:33 +0000976constexpr complex makeComplex(int re, int im) { return complex(re, im); }
Richard Smith9eed49c2011-12-09 23:00:37 +0000977static_assert(makeComplex(1,0) == complex(1), "");
978static_assert(makeComplex(1,0) != complex(0, 1), "");
Richard Smith59efe262011-11-11 04:05:33 +0000979
980class complex_wrap : public complex {
981public:
982 constexpr complex_wrap(int re, int im = 0) : complex(re, im) {}
983 constexpr complex_wrap(const complex_wrap &o) : complex(o) {}
984};
985
Richard Smith9eed49c2011-12-09 23:00:37 +0000986static_assert((complex_wrap)1 == complex(1), "");
987static_assert((complex)1 != complex_wrap(0, 1), "");
988static_assert(complex(1) == complex_wrap(1), "");
989static_assert(complex_wrap(1) != complex(0, 1), "");
Richard Smith59efe262011-11-11 04:05:33 +0000990constexpr complex_wrap makeComplexWrap(int re, int im) {
991 return complex_wrap(re, im);
992}
Richard Smith9eed49c2011-12-09 23:00:37 +0000993static_assert(makeComplexWrap(1,0) == complex(1), "");
994static_assert(makeComplexWrap(1,0) != complex(0, 1), "");
Richard Smith59efe262011-11-11 04:05:33 +0000995
996}
Eli Friedmanf59ff8c2011-12-17 02:24:21 +0000997
998namespace PR11595 {
999 struct A { constexpr bool operator==(int x) { return true; } };
Richard Smithaf2c7a12011-12-19 22:01:37 +00001000 struct B { B(); A& x; };
1001 static_assert(B().x == 3, ""); // expected-error {{constant expression}} expected-note {{non-literal type 'PR11595::B' cannot be used in a constant expression}}
1002
Richard Smith745f5142012-01-27 01:14:48 +00001003 constexpr bool f(int k) { // expected-error {{constexpr function never produces a constant expression}}
Richard Smithaf2c7a12011-12-19 22:01:37 +00001004 return B().x == k; // expected-note {{non-literal type 'PR11595::B' cannot be used in a constant expression}}
1005 }
Eli Friedmanf59ff8c2011-12-17 02:24:21 +00001006}
Richard Smithbc6abe92011-12-19 22:12:41 +00001007
1008namespace ExprWithCleanups {
1009 struct A { A(); ~A(); int get(); };
1010 constexpr int get(bool FromA) { return FromA ? A().get() : 1; }
1011 constexpr int n = get(false);
1012}
Richard Smith7098cbd2011-12-21 05:04:46 +00001013
1014namespace Volatile {
1015
1016volatile constexpr int n1 = 0; // expected-note {{here}}
1017volatile const int n2 = 0; // expected-note {{here}}
1018int n3 = 37; // expected-note {{declared here}}
1019
Richard Smith9ec71972012-02-05 01:23:16 +00001020constexpr int m1 = n1; // expected-error {{constant expression}} expected-note {{read of volatile-qualified type 'const volatile int'}}
1021constexpr int m2 = n2; // expected-error {{constant expression}} expected-note {{read of volatile-qualified type 'const volatile int'}}
1022constexpr int m1b = const_cast<const int&>(n1); // expected-error {{constant expression}} expected-note {{read of volatile object 'n1'}}
1023constexpr int m2b = const_cast<const int&>(n2); // expected-error {{constant expression}} expected-note {{read of volatile object 'n2'}}
Richard Smith7098cbd2011-12-21 05:04:46 +00001024
1025struct T { int n; };
1026const T t = { 42 }; // expected-note {{declared here}}
1027
1028constexpr int f(volatile int &&r) {
Richard Smith9ec71972012-02-05 01:23:16 +00001029 return r; // expected-note {{read of volatile-qualified type 'volatile int'}}
1030}
1031constexpr int g(volatile int &&r) {
1032 return const_cast<int&>(r); // expected-note {{read of volatile temporary is not allowed in a constant expression}}
Richard Smith7098cbd2011-12-21 05:04:46 +00001033}
1034struct S {
Richard Smith9ec71972012-02-05 01:23:16 +00001035 int j : f(0); // expected-error {{constant expression}} expected-note {{in call to 'f(0)'}}
1036 int k : g(0); // expected-error {{constant expression}} expected-note {{temporary created here}} expected-note {{in call to 'g(0)'}}
Richard Smith7098cbd2011-12-21 05:04:46 +00001037 int l : n3; // expected-error {{constant expression}} expected-note {{read of non-const variable}}
1038 int m : t.n; // expected-error {{constant expression}} expected-note {{read of non-constexpr variable}}
1039};
1040
1041}
Richard Smithdd4b3502011-12-25 21:17:58 +00001042
1043namespace ExternConstexpr {
1044 extern constexpr int n = 0;
1045 extern constexpr int m; // expected-error {{constexpr variable declaration must be a definition}}
1046 void f() {
1047 extern constexpr int i; // expected-error {{constexpr variable declaration must be a definition}}
1048 constexpr int j = 0;
1049 constexpr int k; // expected-error {{default initialization of an object of const type}}
1050 }
1051}
Eli Friedman7ead5c72012-01-10 04:58:17 +00001052
1053namespace ComplexConstexpr {
1054 constexpr _Complex float test1 = {};
1055 constexpr _Complex float test2 = {1};
1056 constexpr _Complex double test3 = {1,2};
1057 constexpr _Complex int test4 = {4};
1058 constexpr _Complex int test5 = 4;
1059 constexpr _Complex int test6 = {5,6};
Eli Friedmanf6c17a42012-01-13 23:34:56 +00001060 typedef _Complex float fcomplex;
1061 constexpr fcomplex test7 = fcomplex();
Richard Smith86024012012-02-18 22:04:06 +00001062
1063 constexpr const double &t2r = __real test3;
1064 constexpr const double &t2i = __imag test3;
1065 static_assert(&t2r + 1 == &t2i, "");
1066 static_assert(t2r == 1.0, "");
1067 static_assert(t2i == 2.0, "");
1068 constexpr const double *t2p = &t2r;
1069 static_assert(t2p[-1] == 0.0, ""); // expected-error {{constant expr}} expected-note {{cannot refer to element -1 of array of 2 elements}}
1070 static_assert(t2p[0] == 1.0, "");
1071 static_assert(t2p[1] == 2.0, "");
1072 static_assert(t2p[2] == 0.0, ""); // expected-error {{constant expr}} expected-note {{one-past-the-end pointer}}
1073 static_assert(t2p[3] == 0.0, ""); // expected-error {{constant expr}} expected-note {{cannot refer to element 3 of array of 2 elements}}
1074 constexpr _Complex float *p = 0;
1075 constexpr float pr = __real *p; // expected-error {{constant expr}} expected-note {{cannot access real component of null}}
1076 constexpr float pi = __imag *p; // expected-error {{constant expr}} expected-note {{cannot access imaginary component of null}}
1077 constexpr const _Complex double *q = &test3 + 1;
1078 constexpr double qr = __real *q; // expected-error {{constant expr}} expected-note {{cannot access real component of pointer past the end}}
1079 constexpr double qi = __imag *q; // expected-error {{constant expr}} expected-note {{cannot access imaginary component of pointer past the end}}
1080
1081 static_assert(__real test6 == 5, "");
1082 static_assert(__imag test6 == 6, "");
1083 static_assert(&__imag test6 == &__real test6 + 1, "");
Eli Friedman7ead5c72012-01-10 04:58:17 +00001084}
Eli Friedman6b3014b2012-01-18 02:54:10 +00001085
1086namespace InstantiateCaseStmt {
1087 template<int x> constexpr int f() { return x; }
1088 template<int x> int g(int c) { switch(c) { case f<x>(): return 1; } return 0; }
1089 int gg(int c) { return g<4>(c); }
1090}
Richard Smith495f42a2012-01-24 05:40:50 +00001091
1092namespace ConvertedConstantExpr {
1093 extern int &m;
1094 extern int &n;
1095
1096 constexpr int k = 4;
1097 int &m = const_cast<int&>(k);
1098
1099 // If we have nothing more interesting to say, ensure we don't produce a
1100 // useless note and instead just point to the non-constant subexpression.
1101 enum class E {
1102 em = m,
1103 en = n, // expected-error {{not a constant expression}}
1104 eo = (m +
1105 n // expected-error {{not a constant expression}}
1106 ),
1107 eq = reinterpret_cast<int>((int*)0) // expected-error {{not a constant expression}} expected-note {{reinterpret_cast}}
1108 };
1109}
Richard Smithd9b02e72012-01-25 22:15:11 +00001110
1111namespace IndirectField {
1112 struct S {
1113 struct { // expected-warning {{GNU extension}}
1114 union {
1115 struct { // expected-warning {{GNU extension}}
1116 int a;
1117 int b;
1118 };
1119 int c;
1120 };
1121 int d;
1122 };
1123 union {
1124 int e;
1125 int f;
1126 };
1127 constexpr S(int a, int b, int d, int e) : a(a), b(b), d(d), e(e) {}
1128 constexpr S(int c, int d, int f) : c(c), d(d), f(f) {}
1129 };
1130
1131 constexpr S s1(1, 2, 3, 4);
1132 constexpr S s2(5, 6, 7);
1133
1134 // FIXME: The diagnostics here do a very poor job of explaining which unnamed
1135 // member is active and which is requested.
1136 static_assert(s1.a == 1, "");
1137 static_assert(s1.b == 2, "");
1138 static_assert(s1.c == 0, ""); // expected-error {{constant expression}} expected-note {{union with active member}}
1139 static_assert(s1.d == 3, "");
1140 static_assert(s1.e == 4, "");
1141 static_assert(s1.f == 0, ""); // expected-error {{constant expression}} expected-note {{union with active member}}
1142
1143 static_assert(s2.a == 0, ""); // expected-error {{constant expression}} expected-note {{union with active member}}
1144 static_assert(s2.b == 0, ""); // expected-error {{constant expression}} expected-note {{union with active member}}
1145 static_assert(s2.c == 5, "");
1146 static_assert(s2.d == 6, "");
1147 static_assert(s2.e == 0, ""); // expected-error {{constant expression}} expected-note {{union with active member}}
1148 static_assert(s2.f == 7, "");
1149}
Richard Smithf15fda02012-02-02 01:16:57 +00001150
Richard Smithb4e5e282012-02-09 03:29:58 +00001151// DR1405: don't allow reading mutable members in constant expressions.
1152namespace MutableMembers {
1153 struct MM {
1154 mutable int n; // expected-note 3{{declared here}}
1155 } constexpr mm = { 4 };
1156 constexpr int mmn = mm.n; // expected-error {{constant expression}} expected-note {{read of mutable member 'n' is not allowed in a constant expression}}
1157 int x = (mm.n = 1, 3);
1158 constexpr int mmn2 = mm.n; // expected-error {{constant expression}} expected-note {{read of mutable member 'n' is not allowed in a constant expression}}
1159
1160 // Here's one reason why allowing this would be a disaster...
1161 template<int n> struct Id { int k = n; };
1162 int f() {
1163 constexpr MM m = { 0 };
1164 ++m.n;
1165 return Id<m.n>().k; // expected-error {{not a constant expression}} expected-note {{read of mutable member 'n' is not allowed in a constant expression}}
1166 }
1167
1168 struct A { int n; };
1169 struct B { mutable A a; }; // expected-note {{here}}
1170 struct C { B b; };
1171 constexpr C c[3] = {};
1172 constexpr int k = c[1].b.a.n; // expected-error {{constant expression}} expected-note {{mutable}}
1173}
1174
Richard Smithf15fda02012-02-02 01:16:57 +00001175namespace Fold {
1176
1177 // This macro forces its argument to be constant-folded, even if it's not
1178 // otherwise a constant expression.
1179 #define fold(x) (__builtin_constant_p(x) ? (x) : (x))
1180
1181 constexpr int n = (int)(char*)123; // expected-error {{constant expression}} expected-note {{reinterpret_cast}}
1182 constexpr int m = fold((int)(char*)123); // ok
1183 static_assert(m == 123, "");
1184
1185 #undef fold
1186
1187}
Richard Smith83587db2012-02-15 02:18:13 +00001188
1189namespace DR1454 {
1190
1191constexpr const int &f(const int &n) { return n; }
1192constexpr int k1 = f(0); // ok
1193
1194struct Wrap {
1195 const int &value;
1196};
1197constexpr const Wrap &g(const Wrap &w) { return w; }
1198constexpr int k2 = g({0}).value; // ok
1199
1200constexpr const int &i = 0; // expected-error {{constant expression}} expected-note {{temporary}} expected-note 2{{here}}
1201constexpr const int j = i; // expected-error {{constant expression}} expected-note {{initializer of 'i' is not a constant expression}}
1202
1203}
Richard Smith74e1ad92012-02-16 02:46:34 +00001204
1205namespace RecursiveOpaqueExpr {
1206 template<typename Iter>
1207 constexpr auto LastNonzero(Iter p, Iter q) -> decltype(+*p) {
1208 return p != q ? (LastNonzero(p+1, q) ?: *p) : 0; // expected-warning {{GNU}}
1209 }
1210
1211 constexpr int arr1[] = { 1, 0, 0, 3, 0, 2, 0, 4, 0, 0 };
1212 static_assert(LastNonzero(begin(arr1), end(arr1)) == 4, "");
1213
1214 constexpr int arr2[] = { 1, 0, 0, 3, 0, 2, 0, 4, 0, 5 };
1215 static_assert(LastNonzero(begin(arr2), end(arr2)) == 5, "");
Richard Smithe92b1f42012-06-26 08:12:11 +00001216
1217 constexpr int arr3[] = {
1218 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0,
1219 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0,
1220 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0,
1221 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0,
1222 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0,
1223 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0,
1224 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0,
1225 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
1226 static_assert(LastNonzero(begin(arr3), end(arr3)) == 2, "");
Richard Smith74e1ad92012-02-16 02:46:34 +00001227}
1228
1229namespace VLASizeof {
1230
1231 void f(int k) {
1232 int arr[k]; // expected-warning {{C99}}
1233 constexpr int n = 1 +
1234 sizeof(arr) // expected-error {{constant expression}}
1235 * 3;
1236 }
1237}
Richard Smithb78ae972012-02-18 04:58:18 +00001238
1239namespace CompoundLiteral {
1240 // FIXME:
1241 // We don't model the semantics of this correctly: the compound literal is
1242 // represented as a prvalue in the AST, but actually behaves like an lvalue.
1243 // We treat the compound literal as a temporary and refuse to produce a
1244 // pointer to it. This is OK: we're not required to treat this as a constant
1245 // in C++, and in C we model compound literals as lvalues.
1246 constexpr int *p = (int*)(int[1]){0}; // expected-warning {{C99}} expected-error {{constant expression}} expected-note 2{{temporary}}
1247}
Richard Smith4b1f6842012-03-13 20:58:32 +00001248
1249namespace Vector {
1250 typedef int __attribute__((vector_size(16))) VI4;
1251 constexpr VI4 f(int n) {
1252 return VI4 { n * 3, n + 4, n - 5, n / 6 };
1253 }
1254 constexpr auto v1 = f(10);
1255
1256 typedef double __attribute__((vector_size(32))) VD4;
1257 constexpr VD4 g(int n) {
1258 return (VD4) { n / 2.0, n + 1.5, n - 5.4, n * 0.9 }; // expected-warning {{C99}}
1259 }
1260 constexpr auto v2 = g(4);
1261}
John McCall8d59dee2012-05-01 00:38:49 +00001262
1263// PR12626, redux
1264namespace InvalidClasses {
1265 void test0() {
1266 struct X; // expected-note {{forward declaration}}
1267 struct Y { bool b; X x; }; // expected-error {{field has incomplete type}}
1268 Y y;
1269 auto& b = y.b;
1270 }
1271}
Richard Smithdbbeccc2012-05-15 05:04:02 +00001272
Richard Smith622da852012-07-02 06:15:40 +00001273// Constructors can be implicitly constexpr, even for a non-literal type.
1274namespace ImplicitConstexpr {
1275 struct Q { Q() = default; Q(const Q&) = default; Q(Q&&) = default; ~Q(); }; // expected-note 3{{here}}
1276 struct R { constexpr R(); constexpr R(const R&); constexpr R(R&&); ~R(); };
1277 struct S { R r; }; // expected-note 3{{here}}
1278 struct T { T(const T&); T(T &&); ~T(); };
1279 struct U { T t; }; // expected-note 3{{here}}
1280 static_assert(!__is_literal_type(Q), "");
1281 static_assert(!__is_literal_type(R), "");
1282 static_assert(!__is_literal_type(S), "");
1283 static_assert(!__is_literal_type(T), "");
1284 static_assert(!__is_literal_type(U), "");
1285 struct Test {
1286 friend Q::Q() noexcept; // expected-error {{follows constexpr}}
1287 friend Q::Q(Q&&) noexcept; // expected-error {{follows constexpr}}
1288 friend Q::Q(const Q&) noexcept; // expected-error {{follows constexpr}}
1289 friend S::S() noexcept; // expected-error {{follows constexpr}}
1290 friend S::S(S&&) noexcept; // expected-error {{follows constexpr}}
1291 friend S::S(const S&) noexcept; // expected-error {{follows constexpr}}
1292 friend constexpr U::U() noexcept; // expected-error {{follows non-constexpr}}
1293 friend constexpr U::U(U&&) noexcept; // expected-error {{follows non-constexpr}}
1294 friend constexpr U::U(const U&) noexcept; // expected-error {{follows non-constexpr}}
1295 };
1296}
1297
Richard Smithdbbeccc2012-05-15 05:04:02 +00001298// Indirectly test that an implicit lvalue to xvalue conversion performed for
1299// an NRVO move operation isn't implemented as CK_LValueToRValue.
1300namespace PR12826 {
1301 struct Foo {};
1302 constexpr Foo id(Foo x) { return x; }
1303 constexpr Foo res(id(Foo()));
1304}
Richard Smithf4bb8d02012-07-05 08:39:21 +00001305
1306namespace PR13273 {
1307 struct U {
1308 int t;
1309 U() = default;
1310 };
1311
1312 struct S : U {
1313 S() = default;
1314 };
1315
1316 // S's default constructor isn't constexpr, because U's default constructor
1317 // doesn't initialize 't', but it's trivial, so value-initialization doesn't
1318 // actually call it.
1319 static_assert(S{}.t == 0, "");
1320}