1*67e74705SXin Li // RUN: %clang_cc1 -triple i686-linux -Wno-string-plus-int -Wno-pointer-arith -Wno-zero-length-array -fsyntax-only -fcxx-exceptions -verify -std=c++11 -pedantic %s -Wno-comment -Wno-tautological-pointer-compare -Wno-bool-conversion
2*67e74705SXin Li
3*67e74705SXin Li namespace StaticAssertFoldTest {
4*67e74705SXin Li
5*67e74705SXin Li int x;
6*67e74705SXin Li static_assert(++x, "test"); // expected-error {{not an integral constant expression}}
7*67e74705SXin Li static_assert(false, "test"); // expected-error {{test}}
8*67e74705SXin Li
9*67e74705SXin Li }
10*67e74705SXin Li
11*67e74705SXin Li typedef decltype(sizeof(char)) size_t;
12*67e74705SXin Li
id(const T & t)13*67e74705SXin Li template<typename T> constexpr T id(const T &t) { return t; }
min(const T & a,const T & b)14*67e74705SXin Li template<typename T> constexpr T min(const T &a, const T &b) {
15*67e74705SXin Li return a < b ? a : b;
16*67e74705SXin Li }
max(const T & a,const T & b)17*67e74705SXin Li template<typename T> constexpr T max(const T &a, const T &b) {
18*67e74705SXin Li return a < b ? b : a;
19*67e74705SXin Li }
begin(T (& xs)[N])20*67e74705SXin Li template<typename T, size_t N> constexpr T *begin(T (&xs)[N]) { return xs; }
end(T (& xs)[N])21*67e74705SXin Li template<typename T, size_t N> constexpr T *end(T (&xs)[N]) { return xs + N; }
22*67e74705SXin Li
23*67e74705SXin Li struct MemberZero {
zeroMemberZero24*67e74705SXin Li constexpr int zero() const { return 0; }
25*67e74705SXin Li };
26*67e74705SXin Li
27*67e74705SXin Li namespace DerivedToVBaseCast {
28*67e74705SXin Li
29*67e74705SXin Li struct U { int n; };
30*67e74705SXin Li struct V : U { int n; };
31*67e74705SXin Li struct A : virtual V { int n; };
32*67e74705SXin Li struct Aa { int n; };
33*67e74705SXin Li struct B : virtual A, Aa {};
34*67e74705SXin Li struct C : virtual A, Aa {};
35*67e74705SXin Li struct D : B, C {};
36*67e74705SXin Li
37*67e74705SXin Li D d;
38*67e74705SXin Li constexpr B *p = &d;
39*67e74705SXin Li constexpr C *q = &d;
40*67e74705SXin Li
41*67e74705SXin Li static_assert((void*)p != (void*)q, "");
42*67e74705SXin Li static_assert((A*)p == (A*)q, "");
43*67e74705SXin Li static_assert((Aa*)p != (Aa*)q, "");
44*67e74705SXin Li
45*67e74705SXin Li constexpr B &pp = d;
46*67e74705SXin Li constexpr C &qq = d;
47*67e74705SXin Li static_assert((void*)&pp != (void*)&qq, "");
48*67e74705SXin Li static_assert(&(A&)pp == &(A&)qq, "");
49*67e74705SXin Li static_assert(&(Aa&)pp != &(Aa&)qq, "");
50*67e74705SXin Li
51*67e74705SXin Li constexpr V *v = p;
52*67e74705SXin Li constexpr V *w = q;
53*67e74705SXin Li constexpr V *x = (A*)p;
54*67e74705SXin Li static_assert(v == w, "");
55*67e74705SXin Li static_assert(v == x, "");
56*67e74705SXin Li
57*67e74705SXin Li static_assert((U*)&d == p, "");
58*67e74705SXin Li static_assert((U*)&d == q, "");
59*67e74705SXin Li static_assert((U*)&d == v, "");
60*67e74705SXin Li static_assert((U*)&d == w, "");
61*67e74705SXin Li static_assert((U*)&d == x, "");
62*67e74705SXin Li
63*67e74705SXin Li struct X {};
64*67e74705SXin Li struct Y1 : virtual X {};
65*67e74705SXin Li struct Y2 : X {};
66*67e74705SXin Li struct Z : Y1, Y2 {};
67*67e74705SXin Li Z z;
68*67e74705SXin Li static_assert((X*)(Y1*)&z != (X*)(Y2*)&z, "");
69*67e74705SXin Li }
70*67e74705SXin Li
71*67e74705SXin Li namespace ConstCast {
72*67e74705SXin Li
73*67e74705SXin Li constexpr int n1 = 0;
74*67e74705SXin Li constexpr int n2 = const_cast<int&>(n1);
75*67e74705SXin Li constexpr int *n3 = const_cast<int*>(&n1);
76*67e74705SXin Li constexpr int n4 = *const_cast<int*>(&n1);
77*67e74705SXin Li constexpr const int * const *n5 = const_cast<const int* const*>(&n3);
78*67e74705SXin Li constexpr int **n6 = const_cast<int**>(&n3);
79*67e74705SXin Li constexpr int n7 = **n5;
80*67e74705SXin Li constexpr int n8 = **n6;
81*67e74705SXin Li
82*67e74705SXin Li // const_cast from prvalue to xvalue.
83*67e74705SXin Li struct A { int n; };
84*67e74705SXin Li constexpr int n9 = (const_cast<A&&>(A{123})).n;
85*67e74705SXin Li static_assert(n9 == 123, "");
86*67e74705SXin Li
87*67e74705SXin Li }
88*67e74705SXin Li
89*67e74705SXin Li namespace TemplateArgumentConversion {
90*67e74705SXin Li template<int n> struct IntParam {};
91*67e74705SXin Li
92*67e74705SXin Li using IntParam0 = IntParam<0>;
93*67e74705SXin Li using IntParam0 = IntParam<id(0)>;
94*67e74705SXin Li using IntParam0 = IntParam<MemberZero().zero>; // expected-error {{did you mean to call it with no arguments?}}
95*67e74705SXin Li }
96*67e74705SXin Li
97*67e74705SXin Li namespace CaseStatements {
98*67e74705SXin Li int x;
f(int n)99*67e74705SXin Li void f(int n) {
100*67e74705SXin Li switch (n) {
101*67e74705SXin Li case MemberZero().zero: // expected-error {{did you mean to call it with no arguments?}} expected-note {{previous}}
102*67e74705SXin Li case id(0): // expected-error {{duplicate case value '0'}}
103*67e74705SXin Li return;
104*67e74705SXin Li case __builtin_constant_p(true) ? (__SIZE_TYPE__)&x : 0:; // expected-error {{constant}}
105*67e74705SXin Li }
106*67e74705SXin Li }
107*67e74705SXin Li }
108*67e74705SXin Li
109*67e74705SXin Li extern int &Recurse1;
110*67e74705SXin Li int &Recurse2 = Recurse1; // expected-note {{declared here}}
111*67e74705SXin Li int &Recurse1 = Recurse2;
112*67e74705SXin Li constexpr int &Recurse3 = Recurse2; // expected-error {{must be initialized by a constant expression}} expected-note {{initializer of 'Recurse2' is not a constant expression}}
113*67e74705SXin Li
114*67e74705SXin Li extern const int RecurseA;
115*67e74705SXin Li const int RecurseB = RecurseA; // expected-note {{declared here}}
116*67e74705SXin Li const int RecurseA = 10;
117*67e74705SXin Li constexpr int RecurseC = RecurseB; // expected-error {{must be initialized by a constant expression}} expected-note {{initializer of 'RecurseB' is not a constant expression}}
118*67e74705SXin Li
119*67e74705SXin Li namespace MemberEnum {
120*67e74705SXin Li struct WithMemberEnum {
121*67e74705SXin Li enum E { A = 42 };
122*67e74705SXin Li } wme;
123*67e74705SXin Li
124*67e74705SXin Li static_assert(wme.A == 42, "");
125*67e74705SXin Li }
126*67e74705SXin Li
127*67e74705SXin Li namespace DefaultArguments {
128*67e74705SXin Li
129*67e74705SXin Li const int z = int();
Sum(int a=0,const int & b=0,const int * c=& z,char d=0)130*67e74705SXin Li constexpr int Sum(int a = 0, const int &b = 0, const int *c = &z, char d = 0) {
131*67e74705SXin Li return a + b + *c + d;
132*67e74705SXin Li }
133*67e74705SXin Li const int four = 4;
134*67e74705SXin Li constexpr int eight = 8;
135*67e74705SXin Li constexpr const int twentyseven = 27;
136*67e74705SXin Li static_assert(Sum() == 0, "");
137*67e74705SXin Li static_assert(Sum(1) == 1, "");
138*67e74705SXin Li static_assert(Sum(1, four) == 5, "");
139*67e74705SXin Li static_assert(Sum(1, eight, &twentyseven) == 36, "");
140*67e74705SXin Li static_assert(Sum(1, 2, &four, eight) == 15, "");
141*67e74705SXin Li
142*67e74705SXin Li }
143*67e74705SXin Li
144*67e74705SXin Li namespace Ellipsis {
145*67e74705SXin Li
146*67e74705SXin Li // Note, values passed through an ellipsis can't actually be used.
F(int a,...)147*67e74705SXin Li constexpr int F(int a, ...) { return a; }
148*67e74705SXin Li static_assert(F(0) == 0, "");
149*67e74705SXin Li static_assert(F(1, 0) == 1, "");
150*67e74705SXin Li static_assert(F(2, "test") == 2, "");
151*67e74705SXin Li static_assert(F(3, &F) == 3, "");
152*67e74705SXin Li int k = 0; // expected-note {{here}}
153*67e74705SXin Li static_assert(F(4, k) == 3, ""); // expected-error {{constant expression}} expected-note {{read of non-const variable 'k'}}
154*67e74705SXin Li
155*67e74705SXin Li }
156*67e74705SXin Li
157*67e74705SXin Li namespace Recursion {
fib(int n)158*67e74705SXin Li constexpr int fib(int n) { return n > 1 ? fib(n-1) + fib(n-2) : n; }
159*67e74705SXin Li static_assert(fib(11) == 89, "");
160*67e74705SXin Li
gcd_inner(int a,int b)161*67e74705SXin Li constexpr int gcd_inner(int a, int b) {
162*67e74705SXin Li return b == 0 ? a : gcd_inner(b, a % b);
163*67e74705SXin Li }
gcd(int a,int b)164*67e74705SXin Li constexpr int gcd(int a, int b) {
165*67e74705SXin Li return gcd_inner(max(a, b), min(a, b));
166*67e74705SXin Li }
167*67e74705SXin Li
168*67e74705SXin Li static_assert(gcd(1749237, 5628959) == 7, "");
169*67e74705SXin Li }
170*67e74705SXin Li
171*67e74705SXin Li namespace FunctionCast {
172*67e74705SXin Li // When folding, we allow functions to be cast to different types. Such
173*67e74705SXin Li // cast functions cannot be called, even if they're constexpr.
f()174*67e74705SXin Li constexpr int f() { return 1; }
175*67e74705SXin Li typedef double (*DoubleFn)();
176*67e74705SXin Li typedef int (*IntFn)();
177*67e74705SXin Li int a[(int)DoubleFn(f)()]; // expected-error {{variable length array}} expected-warning{{C99 feature}}
178*67e74705SXin Li int b[(int)IntFn(f)()]; // ok
179*67e74705SXin Li }
180*67e74705SXin Li
181*67e74705SXin Li namespace StaticMemberFunction {
182*67e74705SXin Li struct S {
183*67e74705SXin Li static constexpr int k = 42;
fStaticMemberFunction::S184*67e74705SXin Li static constexpr int f(int n) { return n * k + 2; }
185*67e74705SXin Li } s;
186*67e74705SXin Li
187*67e74705SXin Li constexpr int n = s.f(19);
188*67e74705SXin Li static_assert(S::f(19) == 800, "");
189*67e74705SXin Li static_assert(s.f(19) == 800, "");
190*67e74705SXin Li static_assert(n == 800, "");
191*67e74705SXin Li
192*67e74705SXin Li constexpr int (*sf1)(int) = &S::f;
193*67e74705SXin Li constexpr int (*sf2)(int) = &s.f;
194*67e74705SXin Li constexpr const int *sk = &s.k;
195*67e74705SXin Li }
196*67e74705SXin Li
197*67e74705SXin Li namespace ParameterScopes {
198*67e74705SXin Li
199*67e74705SXin Li const int k = 42;
ObscureTheTruth(const int & a)200*67e74705SXin Li constexpr const int &ObscureTheTruth(const int &a) { return a; }
MaybeReturnJunk(bool b,const int a)201*67e74705SXin Li constexpr const int &MaybeReturnJunk(bool b, const int a) { // expected-note 2{{declared here}}
202*67e74705SXin Li return ObscureTheTruth(b ? a : k);
203*67e74705SXin Li }
204*67e74705SXin Li static_assert(MaybeReturnJunk(false, 0) == 42, ""); // ok
205*67e74705SXin Li constexpr int a = MaybeReturnJunk(true, 0); // expected-error {{constant expression}} expected-note {{read of variable whose lifetime has ended}}
206*67e74705SXin Li
MaybeReturnNonstaticRef(bool b,const int a)207*67e74705SXin Li constexpr const int MaybeReturnNonstaticRef(bool b, const int a) {
208*67e74705SXin Li return ObscureTheTruth(b ? a : k);
209*67e74705SXin Li }
210*67e74705SXin Li static_assert(MaybeReturnNonstaticRef(false, 0) == 42, ""); // ok
211*67e74705SXin Li constexpr int b = MaybeReturnNonstaticRef(true, 0); // ok
212*67e74705SXin Li
InternalReturnJunk(int n)213*67e74705SXin Li constexpr int InternalReturnJunk(int n) {
214*67e74705SXin Li return MaybeReturnJunk(true, n); // expected-note {{read of variable whose lifetime has ended}}
215*67e74705SXin Li }
216*67e74705SXin Li constexpr int n3 = InternalReturnJunk(0); // expected-error {{must be initialized by a constant expression}} expected-note {{in call to 'InternalReturnJunk(0)'}}
217*67e74705SXin Li
LToR(int & n)218*67e74705SXin Li constexpr int LToR(int &n) { return n; }
GrabCallersArgument(bool which,int a,int b)219*67e74705SXin Li constexpr int GrabCallersArgument(bool which, int a, int b) {
220*67e74705SXin Li return LToR(which ? b : a);
221*67e74705SXin Li }
222*67e74705SXin Li static_assert(GrabCallersArgument(false, 1, 2) == 1, "");
223*67e74705SXin Li static_assert(GrabCallersArgument(true, 4, 8) == 8, "");
224*67e74705SXin Li
225*67e74705SXin Li }
226*67e74705SXin Li
227*67e74705SXin Li namespace Pointers {
228*67e74705SXin Li
f(int n,const int * a,const int * b,const int * c)229*67e74705SXin Li constexpr int f(int n, const int *a, const int *b, const int *c) {
230*67e74705SXin Li return n == 0 ? 0 : *a + f(n-1, b, c, a);
231*67e74705SXin Li }
232*67e74705SXin Li
233*67e74705SXin Li const int x = 1, y = 10, z = 100;
234*67e74705SXin Li static_assert(f(23, &x, &y, &z) == 788, "");
235*67e74705SXin Li
g(int n,int a,int b,int c)236*67e74705SXin Li constexpr int g(int n, int a, int b, int c) {
237*67e74705SXin Li return f(n, &a, &b, &c);
238*67e74705SXin Li }
239*67e74705SXin Li static_assert(g(23, x, y, z) == 788, "");
240*67e74705SXin Li
241*67e74705SXin Li }
242*67e74705SXin Li
243*67e74705SXin Li namespace FunctionPointers {
244*67e74705SXin Li
Double(int n)245*67e74705SXin Li constexpr int Double(int n) { return 2 * n; }
Triple(int n)246*67e74705SXin Li constexpr int Triple(int n) { return 3 * n; }
Twice(int (* F)(int),int n)247*67e74705SXin Li constexpr int Twice(int (*F)(int), int n) { return F(F(n)); }
Quadruple(int n)248*67e74705SXin Li constexpr int Quadruple(int n) { return Twice(Double, n); }
Select(int n)249*67e74705SXin Li constexpr auto Select(int n) -> int (*)(int) {
250*67e74705SXin Li return n == 2 ? &Double : n == 3 ? &Triple : n == 4 ? &Quadruple : 0;
251*67e74705SXin Li }
Apply(int (* F)(int),int n)252*67e74705SXin Li constexpr int Apply(int (*F)(int), int n) { return F(n); } // expected-note {{subexpression}}
253*67e74705SXin Li
254*67e74705SXin Li static_assert(1 + Apply(Select(4), 5) + Apply(Select(3), 7) == 42, "");
255*67e74705SXin Li
256*67e74705SXin Li constexpr int Invalid = Apply(Select(0), 0); // expected-error {{must be initialized by a constant expression}} expected-note {{in call to 'Apply(0, 0)'}}
257*67e74705SXin Li
258*67e74705SXin Li }
259*67e74705SXin Li
260*67e74705SXin Li namespace PointerComparison {
261*67e74705SXin Li
262*67e74705SXin Li int x, y;
263*67e74705SXin Li static_assert(&x == &y, "false"); // expected-error {{false}}
264*67e74705SXin Li static_assert(&x != &y, "");
265*67e74705SXin Li constexpr bool g1 = &x == &y;
266*67e74705SXin Li constexpr bool g2 = &x != &y;
267*67e74705SXin Li constexpr bool g3 = &x <= &y; // expected-error {{must be initialized by a constant expression}}
268*67e74705SXin Li constexpr bool g4 = &x >= &y; // expected-error {{must be initialized by a constant expression}}
269*67e74705SXin Li constexpr bool g5 = &x < &y; // expected-error {{must be initialized by a constant expression}}
270*67e74705SXin Li constexpr bool g6 = &x > &y; // expected-error {{must be initialized by a constant expression}}
271*67e74705SXin Li
272*67e74705SXin Li struct S { int x, y; } s;
273*67e74705SXin Li static_assert(&s.x == &s.y, "false"); // expected-error {{false}}
274*67e74705SXin Li static_assert(&s.x != &s.y, "");
275*67e74705SXin Li static_assert(&s.x <= &s.y, "");
276*67e74705SXin Li static_assert(&s.x >= &s.y, "false"); // expected-error {{false}}
277*67e74705SXin Li static_assert(&s.x < &s.y, "");
278*67e74705SXin Li static_assert(&s.x > &s.y, "false"); // expected-error {{false}}
279*67e74705SXin Li
280*67e74705SXin Li static_assert(0 == &y, "false"); // expected-error {{false}}
281*67e74705SXin Li static_assert(0 != &y, "");
282*67e74705SXin Li constexpr bool n3 = 0 <= &y; // expected-error {{must be initialized by a constant expression}}
283*67e74705SXin Li constexpr bool n4 = 0 >= &y; // expected-error {{must be initialized by a constant expression}}
284*67e74705SXin Li constexpr bool n5 = 0 < &y; // expected-error {{must be initialized by a constant expression}}
285*67e74705SXin Li constexpr bool n6 = 0 > &y; // expected-error {{must be initialized by a constant expression}}
286*67e74705SXin Li
287*67e74705SXin Li static_assert(&x == 0, "false"); // expected-error {{false}}
288*67e74705SXin Li static_assert(&x != 0, "");
289*67e74705SXin Li constexpr bool n9 = &x <= 0; // expected-error {{must be initialized by a constant expression}}
290*67e74705SXin Li constexpr bool n10 = &x >= 0; // expected-error {{must be initialized by a constant expression}}
291*67e74705SXin Li constexpr bool n11 = &x < 0; // expected-error {{must be initialized by a constant expression}}
292*67e74705SXin Li constexpr bool n12 = &x > 0; // expected-error {{must be initialized by a constant expression}}
293*67e74705SXin Li
294*67e74705SXin Li static_assert(&x == &x, "");
295*67e74705SXin Li static_assert(&x != &x, "false"); // expected-error {{false}}
296*67e74705SXin Li static_assert(&x <= &x, "");
297*67e74705SXin Li static_assert(&x >= &x, "");
298*67e74705SXin Li static_assert(&x < &x, "false"); // expected-error {{false}}
299*67e74705SXin Li static_assert(&x > &x, "false"); // expected-error {{false}}
300*67e74705SXin Li
301*67e74705SXin Li constexpr S* sptr = &s;
302*67e74705SXin Li constexpr bool dyncast = sptr == dynamic_cast<S*>(sptr); // expected-error {{constant expression}} expected-note {{dynamic_cast}}
303*67e74705SXin Li
304*67e74705SXin Li struct U {};
305*67e74705SXin Li struct Str {
306*67e74705SXin Li int a : dynamic_cast<S*>(sptr) == dynamic_cast<S*>(sptr); // \
307*67e74705SXin Li expected-warning {{not an integral constant expression}} \
308*67e74705SXin Li expected-note {{dynamic_cast is not allowed in a constant expression}}
309*67e74705SXin Li int b : reinterpret_cast<S*>(sptr) == reinterpret_cast<S*>(sptr); // \
310*67e74705SXin Li expected-warning {{not an integral constant expression}} \
311*67e74705SXin Li expected-note {{reinterpret_cast is not allowed in a constant expression}}
312*67e74705SXin Li int c : (S*)(long)(sptr) == (S*)(long)(sptr); // \
313*67e74705SXin Li expected-warning {{not an integral constant expression}} \
314*67e74705SXin Li expected-note {{cast that performs the conversions of a reinterpret_cast is not allowed in a constant expression}}
315*67e74705SXin Li int d : (S*)(42) == (S*)(42); // \
316*67e74705SXin Li expected-warning {{not an integral constant expression}} \
317*67e74705SXin Li expected-note {{cast that performs the conversions of a reinterpret_cast is not allowed in a constant expression}}
318*67e74705SXin Li int e : (Str*)(sptr) == (Str*)(sptr); // \
319*67e74705SXin Li expected-warning {{not an integral constant expression}} \
320*67e74705SXin Li expected-note {{cast that performs the conversions of a reinterpret_cast is not allowed in a constant expression}}
321*67e74705SXin Li int f : &(U&)(*sptr) == &(U&)(*sptr); // \
322*67e74705SXin Li expected-warning {{not an integral constant expression}} \
323*67e74705SXin Li expected-note {{cast that performs the conversions of a reinterpret_cast is not allowed in a constant expression}}
324*67e74705SXin Li int g : (S*)(void*)(sptr) == sptr; // \
325*67e74705SXin Li expected-warning {{not an integral constant expression}} \
326*67e74705SXin Li expected-note {{cast from 'void *' is not allowed in a constant expression}}
327*67e74705SXin Li };
328*67e74705SXin Li
329*67e74705SXin Li extern char externalvar[];
330*67e74705SXin Li constexpr bool constaddress = (void *)externalvar == (void *)0x4000UL; // expected-error {{must be initialized by a constant expression}} expected-note {{reinterpret_cast}}
331*67e74705SXin Li constexpr bool litaddress = "foo" == "foo"; // expected-error {{must be initialized by a constant expression}} expected-warning {{unspecified}}
332*67e74705SXin Li static_assert(0 != "foo", "");
333*67e74705SXin Li
334*67e74705SXin Li }
335*67e74705SXin Li
336*67e74705SXin Li namespace MaterializeTemporary {
337*67e74705SXin Li
f(const int & r)338*67e74705SXin Li constexpr int f(const int &r) { return r; }
339*67e74705SXin Li constexpr int n = f(1);
340*67e74705SXin Li
same(const int & a,const int & b)341*67e74705SXin Li constexpr bool same(const int &a, const int &b) { return &a == &b; }
sameTemporary(const int & n)342*67e74705SXin Li constexpr bool sameTemporary(const int &n) { return same(n, n); }
343*67e74705SXin Li
344*67e74705SXin Li static_assert(n, "");
345*67e74705SXin Li static_assert(!same(4, 4), "");
346*67e74705SXin Li static_assert(same(n, n), "");
347*67e74705SXin Li static_assert(sameTemporary(9), "");
348*67e74705SXin Li
349*67e74705SXin Li struct A { int &&r; };
350*67e74705SXin Li struct B { A &&a1; A &&a2; };
351*67e74705SXin Li
352*67e74705SXin Li constexpr B b1 { { 1 }, { 2 } }; // expected-note {{temporary created here}}
353*67e74705SXin Li static_assert(&b1.a1 != &b1.a2, "");
354*67e74705SXin Li static_assert(&b1.a1.r != &b1.a2.r, ""); // expected-error {{constant expression}} expected-note {{outside the expression that created the temporary}}
355*67e74705SXin Li
356*67e74705SXin Li constexpr B &&b2 { { 3 }, { 4 } }; // expected-note {{temporary created here}}
357*67e74705SXin Li static_assert(&b1 != &b2, "");
358*67e74705SXin Li static_assert(&b1.a1 != &b2.a1, ""); // expected-error {{constant expression}} expected-note {{outside the expression that created the temporary}}
359*67e74705SXin Li
360*67e74705SXin Li constexpr thread_local B b3 { { 1 }, { 2 } }; // expected-error {{constant expression}} expected-note {{reference to temporary}} expected-note {{here}}
foo()361*67e74705SXin Li void foo() {
362*67e74705SXin Li constexpr static B b1 { { 1 }, { 2 } }; // ok
363*67e74705SXin Li constexpr thread_local B b2 { { 1 }, { 2 } }; // expected-error {{constant expression}} expected-note {{reference to temporary}} expected-note {{here}}
364*67e74705SXin Li constexpr B b3 { { 1 }, { 2 } }; // expected-error {{constant expression}} expected-note {{reference to temporary}} expected-note {{here}}
365*67e74705SXin Li }
366*67e74705SXin Li
367*67e74705SXin Li constexpr B &&b4 = ((1, 2), 3, 4, B { {10}, {{20}} }); // expected-warning 4{{unused}}
368*67e74705SXin Li static_assert(&b4 != &b2, "");
369*67e74705SXin Li
370*67e74705SXin Li // Proposed DR: copy-elision doesn't trigger lifetime extension.
371*67e74705SXin Li constexpr B b5 = B{ {0}, {0} }; // expected-error {{constant expression}} expected-note {{reference to temporary}} expected-note {{here}}
372*67e74705SXin Li
373*67e74705SXin Li namespace NestedNonStatic {
374*67e74705SXin Li // Proposed DR: for a reference constant expression to refer to a static
375*67e74705SXin Li // storage duration temporary, that temporary must itself be initialized
376*67e74705SXin Li // by a constant expression (a core constant expression is not enough).
377*67e74705SXin Li struct A { int &&r; };
378*67e74705SXin Li struct B { A &&a; };
379*67e74705SXin Li constexpr B a = { A{0} }; // ok
380*67e74705SXin Li constexpr B b = { A(A{0}) }; // expected-error {{constant expression}} expected-note {{reference to temporary}} expected-note {{here}}
381*67e74705SXin Li }
382*67e74705SXin Li
383*67e74705SXin Li namespace FakeInitList {
384*67e74705SXin Li struct init_list_3_ints { const int (&x)[3]; };
385*67e74705SXin Li struct init_list_2_init_list_3_ints { const init_list_3_ints (&x)[2]; };
386*67e74705SXin Li constexpr init_list_2_init_list_3_ints ils = { { { { 1, 2, 3 } }, { { 4, 5, 6 } } } };
387*67e74705SXin Li }
388*67e74705SXin Li
389*67e74705SXin Li }
390*67e74705SXin Li
strcmp_ce(const char * p,const char * q)391*67e74705SXin Li constexpr int strcmp_ce(const char *p, const char *q) {
392*67e74705SXin Li return (!*p || *p != *q) ? *p - *q : strcmp_ce(p+1, q+1);
393*67e74705SXin Li }
394*67e74705SXin Li
395*67e74705SXin Li namespace StringLiteral {
396*67e74705SXin Li
397*67e74705SXin Li template<typename Char>
MangleChars(const Char * p)398*67e74705SXin Li constexpr int MangleChars(const Char *p) {
399*67e74705SXin Li return *p + 3 * (*p ? MangleChars(p+1) : 0);
400*67e74705SXin Li }
401*67e74705SXin Li
402*67e74705SXin Li static_assert(MangleChars("constexpr!") == 1768383, "");
403*67e74705SXin Li static_assert(MangleChars(u8"constexpr!") == 1768383, "");
404*67e74705SXin Li static_assert(MangleChars(L"constexpr!") == 1768383, "");
405*67e74705SXin Li static_assert(MangleChars(u"constexpr!") == 1768383, "");
406*67e74705SXin Li static_assert(MangleChars(U"constexpr!") == 1768383, "");
407*67e74705SXin Li
408*67e74705SXin Li constexpr char c0 = "nought index"[0];
409*67e74705SXin Li constexpr char c1 = "nice index"[10];
410*67e74705SXin Li constexpr 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}}
411*67e74705SXin Li constexpr 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}}
412*67e74705SXin Li constexpr char c4 = ((char*)(int*)"no reinterpret_casts allowed")[14]; // expected-error {{must be initialized by a constant expression}} expected-note {{cast that performs the conversions of a reinterpret_cast}}
413*67e74705SXin Li
414*67e74705SXin Li constexpr const char *p = "test" + 2;
415*67e74705SXin Li static_assert(*p == 's', "");
416*67e74705SXin Li
max_iter(const char * a,const char * b)417*67e74705SXin Li constexpr const char *max_iter(const char *a, const char *b) {
418*67e74705SXin Li return *a < *b ? b : a;
419*67e74705SXin Li }
max_element(const char * a,const char * b)420*67e74705SXin Li constexpr const char *max_element(const char *a, const char *b) {
421*67e74705SXin Li return (a+1 >= b) ? a : max_iter(a, max_element(a+1, b));
422*67e74705SXin Li }
423*67e74705SXin Li
424*67e74705SXin Li constexpr char str[] = "the quick brown fox jumped over the lazy dog";
425*67e74705SXin Li constexpr const char *max = max_element(begin(str), end(str));
426*67e74705SXin Li static_assert(*max == 'z', "");
427*67e74705SXin Li static_assert(max == str + 38, "");
428*67e74705SXin Li
429*67e74705SXin Li static_assert(strcmp_ce("hello world", "hello world") == 0, "");
430*67e74705SXin Li static_assert(strcmp_ce("hello world", "hello clang") > 0, "");
431*67e74705SXin Li static_assert(strcmp_ce("constexpr", "test") < 0, "");
432*67e74705SXin Li static_assert(strcmp_ce("", " ") < 0, "");
433*67e74705SXin Li
434*67e74705SXin Li struct S {
435*67e74705SXin Li 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}}
436*67e74705SXin Li };
437*67e74705SXin Li
438*67e74705SXin Li struct T {
439*67e74705SXin Li char c[6];
TStringLiteral::T440*67e74705SXin Li constexpr T() : c{"foo"} {}
441*67e74705SXin Li };
442*67e74705SXin Li constexpr T t;
443*67e74705SXin Li
444*67e74705SXin Li static_assert(t.c[0] == 'f', "");
445*67e74705SXin Li static_assert(t.c[1] == 'o', "");
446*67e74705SXin Li static_assert(t.c[2] == 'o', "");
447*67e74705SXin Li static_assert(t.c[3] == 0, "");
448*67e74705SXin Li static_assert(t.c[4] == 0, "");
449*67e74705SXin Li static_assert(t.c[5] == 0, "");
450*67e74705SXin Li static_assert(t.c[6] == 0, ""); // expected-error {{constant expression}} expected-note {{one-past-the-end}}
451*67e74705SXin Li
452*67e74705SXin Li struct U {
453*67e74705SXin Li wchar_t chars[6];
454*67e74705SXin Li int n;
455*67e74705SXin Li } constexpr u = { { L"test" }, 0 };
456*67e74705SXin Li static_assert(u.chars[2] == L's', "");
457*67e74705SXin Li
458*67e74705SXin Li struct V {
459*67e74705SXin Li char c[4];
VStringLiteral::V460*67e74705SXin Li constexpr V() : c("hi!") {}
461*67e74705SXin Li };
462*67e74705SXin Li static_assert(V().c[1] == "i"[0], "");
463*67e74705SXin Li
464*67e74705SXin Li namespace Parens {
465*67e74705SXin Li constexpr unsigned char a[] = ("foo"), b[] = {"foo"}, c[] = {("foo")},
466*67e74705SXin Li d[4] = ("foo"), e[5] = {"foo"}, f[6] = {("foo")};
467*67e74705SXin Li static_assert(a[0] == 'f', "");
468*67e74705SXin Li static_assert(b[1] == 'o', "");
469*67e74705SXin Li static_assert(c[2] == 'o', "");
470*67e74705SXin Li static_assert(d[0] == 'f', "");
471*67e74705SXin Li static_assert(e[1] == 'o', "");
472*67e74705SXin Li static_assert(f[2] == 'o', "");
473*67e74705SXin Li static_assert(f[5] == 0, "");
474*67e74705SXin Li static_assert(f[6] == 0, ""); // expected-error {{constant expression}} expected-note {{one-past-the-end}}
475*67e74705SXin Li }
476*67e74705SXin Li
477*67e74705SXin Li }
478*67e74705SXin Li
479*67e74705SXin Li namespace Array {
480*67e74705SXin Li
481*67e74705SXin Li template<typename Iter>
Sum(Iter begin,Iter end)482*67e74705SXin Li constexpr auto Sum(Iter begin, Iter end) -> decltype(+*begin) {
483*67e74705SXin Li return begin == end ? 0 : *begin + Sum(begin+1, end);
484*67e74705SXin Li }
485*67e74705SXin Li
486*67e74705SXin Li constexpr int xs[] = { 1, 2, 3, 4, 5 };
487*67e74705SXin Li constexpr int ys[] = { 5, 4, 3, 2, 1 };
488*67e74705SXin Li constexpr int sum_xs = Sum(begin(xs), end(xs));
489*67e74705SXin Li static_assert(sum_xs == 15, "");
490*67e74705SXin Li
ZipFoldR(int (* F)(int x,int y,int c),int n,const int * xs,const int * ys,int c)491*67e74705SXin Li constexpr int ZipFoldR(int (*F)(int x, int y, int c), int n,
492*67e74705SXin Li const int *xs, const int *ys, int c) {
493*67e74705SXin Li return n ? F(
494*67e74705SXin Li *xs, // expected-note {{read of dereferenced one-past-the-end pointer}}
495*67e74705SXin Li *ys,
496*67e74705SXin Li ZipFoldR(F, n-1, xs+1, ys+1, c)) // \
497*67e74705SXin Li expected-note {{in call to 'ZipFoldR(&SubMul, 2, &xs[4], &ys[4], 1)'}} \
498*67e74705SXin Li expected-note {{in call to 'ZipFoldR(&SubMul, 1, &xs[5], &ys[5], 1)'}}
499*67e74705SXin Li : c;
500*67e74705SXin Li }
MulAdd(int x,int y,int c)501*67e74705SXin Li constexpr int MulAdd(int x, int y, int c) { return x * y + c; }
502*67e74705SXin Li constexpr int InnerProduct = ZipFoldR(MulAdd, 5, xs, ys, 0);
503*67e74705SXin Li static_assert(InnerProduct == 35, "");
504*67e74705SXin Li
SubMul(int x,int y,int c)505*67e74705SXin Li constexpr int SubMul(int x, int y, int c) { return (x - y) * c; }
506*67e74705SXin Li constexpr int DiffProd = ZipFoldR(SubMul, 2, xs+3, ys+3, 1);
507*67e74705SXin Li static_assert(DiffProd == 8, "");
508*67e74705SXin Li static_assert(ZipFoldR(SubMul, 3, xs+3, ys+3, 1), ""); // \
509*67e74705SXin Li expected-error {{constant expression}} \
510*67e74705SXin Li expected-note {{in call to 'ZipFoldR(&SubMul, 3, &xs[3], &ys[3], 1)'}}
511*67e74705SXin Li
512*67e74705SXin Li constexpr const int *p = xs + 3;
513*67e74705SXin Li constexpr int xs4 = p[1]; // ok
514*67e74705SXin Li constexpr int xs5 = p[2]; // expected-error {{constant expression}} expected-note {{read of dereferenced one-past-the-end pointer}}
515*67e74705SXin Li constexpr int xs6 = p[3]; // expected-error {{constant expression}} expected-note {{cannot refer to element 6}}
516*67e74705SXin Li constexpr int xs0 = p[-3]; // ok
517*67e74705SXin Li constexpr int xs_1 = p[-4]; // expected-error {{constant expression}} expected-note {{cannot refer to element -1}}
518*67e74705SXin Li
519*67e74705SXin Li constexpr int zs[2][2][2][2] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16 };
520*67e74705SXin Li static_assert(zs[0][0][0][0] == 1, "");
521*67e74705SXin Li static_assert(zs[1][1][1][1] == 16, "");
522*67e74705SXin Li static_assert(zs[0][0][0][2] == 3, ""); // expected-error {{constant expression}} expected-note {{read of dereferenced one-past-the-end pointer}}
523*67e74705SXin Li static_assert((&zs[0][0][0][2])[-1] == 2, "");
524*67e74705SXin Li static_assert(**(**(zs + 1) + 1) == 11, "");
525*67e74705SXin Li static_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}}
526*67e74705SXin Li static_assert(*(&(&(*(*&(&zs[2] - 1)[0] + 2 - 2))[2])[-1][2] - 2) == 11, "");
527*67e74705SXin Li constexpr 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}}
528*67e74705SXin Li
fail(const int & p)529*67e74705SXin Li constexpr int fail(const int &p) {
530*67e74705SXin Li return (&p)[64]; // expected-note {{cannot refer to element 64 of array of 2 elements}}
531*67e74705SXin Li }
532*67e74705SXin Li static_assert(fail(*(&(&(*(*&(&zs[2] - 1)[0] + 2 - 2))[2])[-1][2] - 2)) == 11, ""); // \
533*67e74705SXin Li expected-error {{static_assert expression is not an integral constant expression}} \
534*67e74705SXin Li expected-note {{in call to 'fail(zs[1][0][1][0])'}}
535*67e74705SXin Li
536*67e74705SXin Li constexpr int arr[40] = { 1, 2, 3, [8] = 4 }; // expected-warning {{C99 feature}}
SumNonzero(const int * p)537*67e74705SXin Li constexpr int SumNonzero(const int *p) {
538*67e74705SXin Li return *p + (*p ? SumNonzero(p+1) : 0);
539*67e74705SXin Li }
CountZero(const int * p,const int * q)540*67e74705SXin Li constexpr int CountZero(const int *p, const int *q) {
541*67e74705SXin Li return p == q ? 0 : (*p == 0) + CountZero(p+1, q);
542*67e74705SXin Li }
543*67e74705SXin Li static_assert(SumNonzero(arr) == 6, "");
544*67e74705SXin Li static_assert(CountZero(arr, arr + 40) == 36, "");
545*67e74705SXin Li
546*67e74705SXin Li struct ArrayElem {
ArrayElemArray::ArrayElem547*67e74705SXin Li constexpr ArrayElem() : n(0) {}
548*67e74705SXin Li int n;
fArray::ArrayElem549*67e74705SXin Li constexpr int f() const { return n; }
550*67e74705SXin Li };
551*67e74705SXin Li struct ArrayRVal {
ArrayRValArray::ArrayRVal552*67e74705SXin Li constexpr ArrayRVal() {}
553*67e74705SXin Li ArrayElem elems[10];
554*67e74705SXin Li };
555*67e74705SXin Li static_assert(ArrayRVal().elems[3].f() == 0, "");
556*67e74705SXin Li
557*67e74705SXin Li constexpr int selfref[2][2][2] = {
558*67e74705SXin Li selfref[1][1][1] + 1, selfref[0][0][0] + 1,
559*67e74705SXin Li selfref[1][0][1] + 1, selfref[0][1][0] + 1,
560*67e74705SXin Li selfref[1][0][0] + 1, selfref[0][1][1] + 1 };
561*67e74705SXin Li static_assert(selfref[0][0][0] == 1, "");
562*67e74705SXin Li static_assert(selfref[0][0][1] == 2, "");
563*67e74705SXin Li static_assert(selfref[0][1][0] == 1, "");
564*67e74705SXin Li static_assert(selfref[0][1][1] == 2, "");
565*67e74705SXin Li static_assert(selfref[1][0][0] == 1, "");
566*67e74705SXin Li static_assert(selfref[1][0][1] == 3, "");
567*67e74705SXin Li static_assert(selfref[1][1][0] == 0, "");
568*67e74705SXin Li static_assert(selfref[1][1][1] == 0, "");
569*67e74705SXin Li
570*67e74705SXin Li struct TrivialDefCtor { int n; };
571*67e74705SXin Li typedef TrivialDefCtor TDCArray[2][2];
572*67e74705SXin Li static_assert(TDCArray{}[1][1].n == 0, "");
573*67e74705SXin Li
574*67e74705SXin Li struct NonAggregateTDC : TrivialDefCtor {};
575*67e74705SXin Li typedef NonAggregateTDC NATDCArray[2][2];
576*67e74705SXin Li static_assert(NATDCArray{}[1][1].n == 0, "");
577*67e74705SXin Li
578*67e74705SXin Li }
579*67e74705SXin Li
580*67e74705SXin Li namespace DependentValues {
581*67e74705SXin Li
582*67e74705SXin Li struct I { int n; typedef I V[10]; };
583*67e74705SXin Li I::V x, y;
584*67e74705SXin Li int g();
585*67e74705SXin Li template<bool B, typename T> struct S : T {
586*67e74705SXin Li int k;
fDependentValues::S587*67e74705SXin Li void f() {
588*67e74705SXin Li I::V &cells = B ? x : y;
589*67e74705SXin Li I &i = cells[k];
590*67e74705SXin Li switch (i.n) {}
591*67e74705SXin Li
592*67e74705SXin Li // FIXME: We should be able to diagnose this.
593*67e74705SXin Li constexpr int n = g();
594*67e74705SXin Li
595*67e74705SXin Li constexpr int m = this->g(); // ok, could be constexpr
596*67e74705SXin Li }
597*67e74705SXin Li };
598*67e74705SXin Li
599*67e74705SXin Li }
600*67e74705SXin Li
601*67e74705SXin Li namespace Class {
602*67e74705SXin Li
AClass::A603*67e74705SXin Li struct A { constexpr A(int a, int b) : k(a + b) {} int k; };
fn(const A & a)604*67e74705SXin Li constexpr int fn(const A &a) { return a.k; }
605*67e74705SXin Li static_assert(fn(A(4,5)) == 9, "");
606*67e74705SXin Li
607*67e74705SXin Li struct B { int n; int m; } constexpr b = { 0, b.n };
608*67e74705SXin Li struct C {
CClass::C609*67e74705SXin Li constexpr C(C *this_) : m(42), n(this_->m) {} // ok
610*67e74705SXin Li int m, n;
611*67e74705SXin Li };
612*67e74705SXin Li struct D {
613*67e74705SXin Li C c;
DClass::D614*67e74705SXin Li constexpr D() : c(&c) {}
615*67e74705SXin Li };
616*67e74705SXin Li static_assert(D().c.n == 42, "");
617*67e74705SXin Li
618*67e74705SXin Li struct E {
EClass::E619*67e74705SXin Li constexpr E() : p(&p) {}
620*67e74705SXin Li void *p;
621*67e74705SXin Li };
622*67e74705SXin Li constexpr const E &e1 = E();
623*67e74705SXin Li // This is a constant expression if we elide the copy constructor call, and
624*67e74705SXin Li // is not a constant expression if we don't! But we do, so it is.
625*67e74705SXin Li constexpr E e2 = E();
626*67e74705SXin Li static_assert(e2.p == &e2.p, "");
627*67e74705SXin Li constexpr E e3;
628*67e74705SXin Li static_assert(e3.p == &e3.p, "");
629*67e74705SXin Li
630*67e74705SXin Li extern const class F f;
631*67e74705SXin Li struct F {
FClass::F632*67e74705SXin Li constexpr F() : p(&f.p) {}
633*67e74705SXin Li const void *p;
634*67e74705SXin Li };
635*67e74705SXin Li constexpr F f;
636*67e74705SXin Li
637*67e74705SXin Li struct G {
638*67e74705SXin Li struct T {
TClass::G::T639*67e74705SXin Li constexpr T(T *p) : u1(), u2(p) {}
640*67e74705SXin Li union U1 {
U1()641*67e74705SXin Li constexpr U1() {}
642*67e74705SXin Li int a, b = 42;
643*67e74705SXin Li } u1;
644*67e74705SXin Li union U2 {
U2(T * p)645*67e74705SXin Li constexpr U2(T *p) : c(p->u1.b) {}
646*67e74705SXin Li int c, d;
647*67e74705SXin Li } u2;
648*67e74705SXin Li } t;
GClass::G649*67e74705SXin Li constexpr G() : t(&t) {}
650*67e74705SXin Li } constexpr g;
651*67e74705SXin Li
652*67e74705SXin Li static_assert(g.t.u1.a == 42, ""); // expected-error {{constant expression}} expected-note {{read of member 'a' of union with active member 'b'}}
653*67e74705SXin Li static_assert(g.t.u1.b == 42, "");
654*67e74705SXin Li static_assert(g.t.u2.c == 42, "");
655*67e74705SXin Li static_assert(g.t.u2.d == 42, ""); // expected-error {{constant expression}} expected-note {{read of member 'd' of union with active member 'c'}}
656*67e74705SXin Li
657*67e74705SXin Li struct S {
658*67e74705SXin Li int a, b;
659*67e74705SXin Li const S *p;
660*67e74705SXin Li double d;
661*67e74705SXin Li const char *q;
662*67e74705SXin Li
SClass::S663*67e74705SXin Li constexpr S(int n, const S *p) : a(5), b(n), p(p), d(n), q("hello") {}
664*67e74705SXin Li };
665*67e74705SXin Li
666*67e74705SXin Li S global(43, &global);
667*67e74705SXin Li
668*67e74705SXin Li static_assert(S(15, &global).b == 15, "");
669*67e74705SXin Li
CheckS(const S & s)670*67e74705SXin Li constexpr bool CheckS(const S &s) {
671*67e74705SXin Li return s.a == 5 && s.b == 27 && s.p == &global && s.d == 27. && s.q[3] == 'l';
672*67e74705SXin Li }
673*67e74705SXin Li static_assert(CheckS(S(27, &global)), "");
674*67e74705SXin Li
675*67e74705SXin Li struct Arr {
676*67e74705SXin Li char arr[3];
ArrClass::Arr677*67e74705SXin Li constexpr Arr() : arr{'x', 'y', 'z'} {}
678*67e74705SXin Li };
hash(Arr && a)679*67e74705SXin Li constexpr int hash(Arr &&a) {
680*67e74705SXin Li return a.arr[0] + a.arr[1] * 0x100 + a.arr[2] * 0x10000;
681*67e74705SXin Li }
682*67e74705SXin Li constexpr int k = hash(Arr());
683*67e74705SXin Li static_assert(k == 0x007a7978, "");
684*67e74705SXin Li
685*67e74705SXin Li
686*67e74705SXin Li struct AggregateInit {
687*67e74705SXin Li const char &c;
688*67e74705SXin Li int n;
689*67e74705SXin Li double d;
690*67e74705SXin Li int arr[5];
691*67e74705SXin Li void *p;
692*67e74705SXin Li };
693*67e74705SXin Li
694*67e74705SXin Li constexpr AggregateInit agg1 = { "hello"[0] };
695*67e74705SXin Li
696*67e74705SXin Li static_assert(strcmp_ce(&agg1.c, "hello") == 0, "");
697*67e74705SXin Li static_assert(agg1.n == 0, "");
698*67e74705SXin Li static_assert(agg1.d == 0.0, "");
699*67e74705SXin Li static_assert(agg1.arr[-1] == 0, ""); // expected-error {{constant expression}} expected-note {{cannot refer to element -1}}
700*67e74705SXin Li static_assert(agg1.arr[0] == 0, "");
701*67e74705SXin Li static_assert(agg1.arr[4] == 0, "");
702*67e74705SXin Li static_assert(agg1.arr[5] == 0, ""); // expected-error {{constant expression}} expected-note {{read of dereferenced one-past-the-end}}
703*67e74705SXin Li static_assert(agg1.p == nullptr, "");
704*67e74705SXin Li
705*67e74705SXin Li static constexpr const unsigned char uc[] = { "foo" };
706*67e74705SXin Li static_assert(uc[0] == 'f', "");
707*67e74705SXin Li static_assert(uc[3] == 0, "");
708*67e74705SXin Li
709*67e74705SXin Li namespace SimpleDerivedClass {
710*67e74705SXin Li
711*67e74705SXin Li struct B {
BClass::SimpleDerivedClass::B712*67e74705SXin Li constexpr B(int n) : a(n) {}
713*67e74705SXin Li int a;
714*67e74705SXin Li };
715*67e74705SXin Li struct D : B {
DClass::SimpleDerivedClass::D716*67e74705SXin Li constexpr D(int n) : B(n) {}
717*67e74705SXin Li };
718*67e74705SXin Li constexpr D d(3);
719*67e74705SXin Li static_assert(d.a == 3, "");
720*67e74705SXin Li
721*67e74705SXin Li }
722*67e74705SXin Li
BottomClass::Bottom723*67e74705SXin Li struct Bottom { constexpr Bottom() {} };
724*67e74705SXin Li struct Base : Bottom {
BaseClass::Base725*67e74705SXin Li constexpr Base(int a = 42, const char *b = "test") : a(a), b(b) {}
726*67e74705SXin Li int a;
727*67e74705SXin Li const char *b;
728*67e74705SXin Li };
729*67e74705SXin Li struct Base2 : Bottom {
Base2Class::Base2730*67e74705SXin Li constexpr Base2(const int &r) : r(r) {}
731*67e74705SXin Li int q = 123;
732*67e74705SXin Li const int &r;
733*67e74705SXin Li };
734*67e74705SXin Li struct Derived : Base, Base2 {
DerivedClass::Derived735*67e74705SXin Li constexpr Derived() : Base(76), Base2(a) {}
736*67e74705SXin Li int c = r + b[1];
737*67e74705SXin Li };
738*67e74705SXin Li
operator ==(const Base & a,const Base & b)739*67e74705SXin Li constexpr bool operator==(const Base &a, const Base &b) {
740*67e74705SXin Li return a.a == b.a && strcmp_ce(a.b, b.b) == 0;
741*67e74705SXin Li }
742*67e74705SXin Li
743*67e74705SXin Li constexpr Base base;
744*67e74705SXin Li constexpr Base base2(76);
745*67e74705SXin Li constexpr Derived derived;
746*67e74705SXin Li static_assert(derived.a == 76, "");
747*67e74705SXin Li static_assert(derived.b[2] == 's', "");
748*67e74705SXin Li static_assert(derived.c == 76 + 'e', "");
749*67e74705SXin Li static_assert(derived.q == 123, "");
750*67e74705SXin Li static_assert(derived.r == 76, "");
751*67e74705SXin Li static_assert(&derived.r == &derived.a, "");
752*67e74705SXin Li
753*67e74705SXin Li static_assert(!(derived == base), "");
754*67e74705SXin Li static_assert(derived == base2, "");
755*67e74705SXin Li
756*67e74705SXin Li constexpr Bottom &bot1 = (Base&)derived;
757*67e74705SXin Li constexpr Bottom &bot2 = (Base2&)derived;
758*67e74705SXin Li static_assert(&bot1 != &bot2, "");
759*67e74705SXin Li
760*67e74705SXin Li constexpr Bottom *pb1 = (Base*)&derived;
761*67e74705SXin Li constexpr Bottom *pb2 = (Base2*)&derived;
762*67e74705SXin Li static_assert(&pb1 != &pb2, "");
763*67e74705SXin Li static_assert(pb1 == &bot1, "");
764*67e74705SXin Li static_assert(pb2 == &bot2, "");
765*67e74705SXin Li
766*67e74705SXin Li constexpr Base2 &fail = (Base2&)bot1; // expected-error {{constant expression}} expected-note {{cannot cast object of dynamic type 'const Class::Derived' to type 'Class::Base2'}}
767*67e74705SXin Li constexpr Base &fail2 = (Base&)*pb2; // expected-error {{constant expression}} expected-note {{cannot cast object of dynamic type 'const Class::Derived' to type 'Class::Base'}}
768*67e74705SXin Li constexpr Base2 &ok2 = (Base2&)bot2;
769*67e74705SXin Li static_assert(&ok2 == &derived, "");
770*67e74705SXin Li
771*67e74705SXin Li constexpr Base2 *pfail = (Base2*)pb1; // expected-error {{constant expression}} expected-note {{cannot cast object of dynamic type 'const Class::Derived' to type 'Class::Base2'}}
772*67e74705SXin Li constexpr Base *pfail2 = (Base*)&bot2; // expected-error {{constant expression}} expected-note {{cannot cast object of dynamic type 'const Class::Derived' to type 'Class::Base'}}
773*67e74705SXin Li constexpr Base2 *pok2 = (Base2*)pb2;
774*67e74705SXin Li static_assert(pok2 == &derived, "");
775*67e74705SXin Li static_assert(&ok2 == pok2, "");
776*67e74705SXin Li static_assert((Base2*)(Derived*)(Base*)pb1 == pok2, "");
777*67e74705SXin Li static_assert((Derived*)(Base*)pb1 == (Derived*)pok2, "");
778*67e74705SXin Li
779*67e74705SXin Li // Core issue 903: we do not perform constant evaluation when checking for a
780*67e74705SXin Li // null pointer in C++11. Just check for an integer literal with value 0.
781*67e74705SXin Li constexpr Base *nullB = 42 - 6 * 7; // expected-error {{cannot initialize a variable of type 'Class::Base *const' with an rvalue of type 'int'}}
782*67e74705SXin Li constexpr Base *nullB1 = 0;
783*67e74705SXin Li static_assert((Bottom*)nullB == 0, "");
784*67e74705SXin Li static_assert((Derived*)nullB == 0, "");
785*67e74705SXin Li static_assert((void*)(Bottom*)nullB == (void*)(Derived*)nullB, "");
786*67e74705SXin Li Base *nullB2 = '\0'; // expected-error {{cannot initialize a variable of type 'Class::Base *' with an rvalue of type 'char'}}
787*67e74705SXin Li Base *nullB3 = (0);
788*67e74705SXin Li Base *nullB4 = false; // expected-error {{cannot initialize a variable of type 'Class::Base *' with an rvalue of type 'bool'}}
789*67e74705SXin Li Base *nullB5 = ((0ULL));
790*67e74705SXin Li Base *nullB6 = 0.; // expected-error {{cannot initialize a variable of type 'Class::Base *' with an rvalue of type 'double'}}
791*67e74705SXin Li enum Null { kNull };
792*67e74705SXin Li Base *nullB7 = kNull; // expected-error {{cannot initialize a variable of type 'Class::Base *' with an rvalue of type 'Class::Null'}}
793*67e74705SXin Li static_assert(nullB1 == (1 - 1), ""); // expected-error {{comparison between pointer and integer}}
794*67e74705SXin Li
795*67e74705SXin Li
796*67e74705SXin Li
797*67e74705SXin Li namespace ConversionOperators {
798*67e74705SXin Li
799*67e74705SXin Li struct T {
TClass::ConversionOperators::T800*67e74705SXin Li constexpr T(int n) : k(5*n - 3) {}
operator intClass::ConversionOperators::T801*67e74705SXin Li constexpr operator int() const { return k; }
802*67e74705SXin Li int k;
803*67e74705SXin Li };
804*67e74705SXin Li
805*67e74705SXin Li struct S {
SClass::ConversionOperators::S806*67e74705SXin Li constexpr S(int n) : k(2*n + 1) {}
operator intClass::ConversionOperators::S807*67e74705SXin Li constexpr operator int() const { return k; }
operator TClass::ConversionOperators::S808*67e74705SXin Li constexpr operator T() const { return T(k); }
809*67e74705SXin Li int k;
810*67e74705SXin Li };
811*67e74705SXin Li
check(T a,T b)812*67e74705SXin Li constexpr bool check(T a, T b) { return a == b.k; }
813*67e74705SXin Li
814*67e74705SXin Li static_assert(S(5) == 11, "");
815*67e74705SXin Li static_assert(check(S(5), 11), "");
816*67e74705SXin Li
817*67e74705SXin Li namespace PR14171 {
818*67e74705SXin Li
819*67e74705SXin Li struct X {
820*67e74705SXin Li constexpr (operator int)() const { return 0; }
821*67e74705SXin Li };
822*67e74705SXin Li static_assert(X() == 0, "");
823*67e74705SXin Li
824*67e74705SXin Li }
825*67e74705SXin Li
826*67e74705SXin Li }
827*67e74705SXin Li
828*67e74705SXin Li struct This {
fClass::This829*67e74705SXin Li constexpr int f() const { return 0; }
gClass::This830*67e74705SXin Li static constexpr int g() { return 0; }
hClass::This831*67e74705SXin Li void h() {
832*67e74705SXin Li constexpr int x = f(); // expected-error {{must be initialized by a constant}}
833*67e74705SXin Li // expected-note@-1 {{implicit use of 'this' pointer is only allowed within the evaluation of a call to a 'constexpr' member function}}
834*67e74705SXin Li constexpr int y = this->f(); // expected-error {{must be initialized by a constant}}
835*67e74705SXin Li // expected-note-re@-1 {{{{^}}use of 'this' pointer}}
836*67e74705SXin Li constexpr int z = g();
837*67e74705SXin Li static_assert(z == 0, "");
838*67e74705SXin Li }
839*67e74705SXin Li };
840*67e74705SXin Li
841*67e74705SXin Li }
842*67e74705SXin Li
843*67e74705SXin Li namespace Temporaries {
844*67e74705SXin Li
845*67e74705SXin Li struct S {
STemporaries::S846*67e74705SXin Li constexpr S() {}
847*67e74705SXin Li constexpr int f() const;
848*67e74705SXin Li constexpr int g() const;
849*67e74705SXin Li };
850*67e74705SXin Li struct T : S {
TTemporaries::T851*67e74705SXin Li constexpr T(int n) : S(), n(n) {}
852*67e74705SXin Li int n;
853*67e74705SXin Li };
f() const854*67e74705SXin Li constexpr int S::f() const {
855*67e74705SXin Li return static_cast<const T*>(this)->n; // expected-note {{cannot cast}}
856*67e74705SXin Li }
g() const857*67e74705SXin Li constexpr int S::g() const {
858*67e74705SXin Li // FIXME: Better diagnostic for this.
859*67e74705SXin Li return this->*(int(S::*))&T::n; // expected-note {{subexpression}}
860*67e74705SXin Li }
861*67e74705SXin Li // The T temporary is implicitly cast to an S subobject, but we can recover the
862*67e74705SXin Li // T full-object via a base-to-derived cast, or a derived-to-base-casted member
863*67e74705SXin Li // pointer.
864*67e74705SXin Li static_assert(S().f(), ""); // expected-error {{constant expression}} expected-note {{in call to '&Temporaries::S()->f()'}}
865*67e74705SXin Li static_assert(S().g(), ""); // expected-error {{constant expression}} expected-note {{in call to '&Temporaries::S()->g()'}}
866*67e74705SXin Li static_assert(T(3).f() == 3, "");
867*67e74705SXin Li static_assert(T(4).g() == 4, "");
868*67e74705SXin Li
f(const S & s)869*67e74705SXin Li constexpr int f(const S &s) {
870*67e74705SXin Li return static_cast<const T&>(s).n;
871*67e74705SXin Li }
872*67e74705SXin Li constexpr int n = f(T(5));
873*67e74705SXin Li static_assert(f(T(5)) == 5, "");
874*67e74705SXin Li
b(int n)875*67e74705SXin Li constexpr bool b(int n) { return &n; }
876*67e74705SXin Li static_assert(b(0), "");
877*67e74705SXin Li
878*67e74705SXin Li struct NonLiteral {
879*67e74705SXin Li NonLiteral();
880*67e74705SXin Li int f();
881*67e74705SXin Li };
882*67e74705SXin Li constexpr int k = NonLiteral().f(); // expected-error {{constant expression}} expected-note {{non-literal type 'Temporaries::NonLiteral'}}
883*67e74705SXin Li
884*67e74705SXin Li }
885*67e74705SXin Li
886*67e74705SXin Li namespace Union {
887*67e74705SXin Li
888*67e74705SXin Li union U {
889*67e74705SXin Li int a;
890*67e74705SXin Li int b;
891*67e74705SXin Li };
892*67e74705SXin Li
893*67e74705SXin Li constexpr U u[4] = { { .a = 0 }, { .b = 1 }, { .a = 2 }, { .b = 3 } }; // expected-warning 4{{C99 feature}}
894*67e74705SXin Li static_assert(u[0].a == 0, "");
895*67e74705SXin Li static_assert(u[0].b, ""); // expected-error {{constant expression}} expected-note {{read of member 'b' of union with active member 'a'}}
896*67e74705SXin Li static_assert(u[1].b == 1, "");
897*67e74705SXin Li static_assert((&u[1].b)[1] == 2, ""); // expected-error {{constant expression}} expected-note {{read of dereferenced one-past-the-end pointer}}
898*67e74705SXin Li static_assert(*(&(u[1].b) + 1 + 1) == 3, ""); // expected-error {{constant expression}} expected-note {{cannot refer to element 2 of non-array object}}
899*67e74705SXin Li static_assert((&(u[1]) + 1 + 1)->b == 3, "");
900*67e74705SXin Li
901*67e74705SXin Li constexpr U v = {};
902*67e74705SXin Li static_assert(v.a == 0, "");
903*67e74705SXin Li
904*67e74705SXin Li union Empty {};
905*67e74705SXin Li constexpr Empty e = {};
906*67e74705SXin Li
907*67e74705SXin Li // Make sure we handle trivial copy constructors for unions.
908*67e74705SXin Li constexpr U x = {42};
909*67e74705SXin Li constexpr U y = x;
910*67e74705SXin Li static_assert(y.a == 42, "");
911*67e74705SXin Li static_assert(y.b == 42, ""); // expected-error {{constant expression}} expected-note {{'b' of union with active member 'a'}}
912*67e74705SXin Li
913*67e74705SXin Li }
914*67e74705SXin Li
915*67e74705SXin Li namespace MemberPointer {
916*67e74705SXin Li struct A {
AMemberPointer::A917*67e74705SXin Li constexpr A(int n) : n(n) {}
918*67e74705SXin Li int n;
fMemberPointer::A919*67e74705SXin Li constexpr int f() const { return n + 3; }
920*67e74705SXin Li };
921*67e74705SXin Li constexpr A a(7);
922*67e74705SXin Li static_assert(A(5).*&A::n == 5, "");
923*67e74705SXin Li static_assert((&a)->*&A::n == 7, "");
924*67e74705SXin Li static_assert((A(8).*&A::f)() == 11, "");
925*67e74705SXin Li static_assert(((&a)->*&A::f)() == 10, "");
926*67e74705SXin Li
927*67e74705SXin Li struct B : A {
BMemberPointer::B928*67e74705SXin Li constexpr B(int n, int m) : A(n), m(m) {}
929*67e74705SXin Li int m;
gMemberPointer::B930*67e74705SXin Li constexpr int g() const { return n + m + 1; }
931*67e74705SXin Li };
932*67e74705SXin Li constexpr B b(9, 13);
933*67e74705SXin Li static_assert(B(4, 11).*&A::n == 4, "");
934*67e74705SXin Li static_assert(B(4, 11).*&B::m == 11, "");
935*67e74705SXin Li static_assert(B(4, 11).*(int(A::*))&B::m == 11, "");
936*67e74705SXin Li static_assert((&b)->*&A::n == 9, "");
937*67e74705SXin Li static_assert((&b)->*&B::m == 13, "");
938*67e74705SXin Li static_assert((&b)->*(int(A::*))&B::m == 13, "");
939*67e74705SXin Li static_assert((B(4, 11).*&A::f)() == 7, "");
940*67e74705SXin Li static_assert((B(4, 11).*&B::g)() == 16, "");
941*67e74705SXin Li static_assert((B(4, 11).*(int(A::*)()const)&B::g)() == 16, "");
942*67e74705SXin Li static_assert(((&b)->*&A::f)() == 12, "");
943*67e74705SXin Li static_assert(((&b)->*&B::g)() == 23, "");
944*67e74705SXin Li static_assert(((&b)->*(int(A::*)()const)&B::g)() == 23, "");
945*67e74705SXin Li
946*67e74705SXin Li struct S {
SMemberPointer::S947*67e74705SXin Li constexpr S(int m, int n, int (S::*pf)() const, int S::*pn) :
948*67e74705SXin Li m(m), n(n), pf(pf), pn(pn) {}
SMemberPointer::S949*67e74705SXin Li constexpr S() : m(), n(), pf(&S::f), pn(&S::n) {}
950*67e74705SXin Li
fMemberPointer::S951*67e74705SXin Li constexpr int f() const { return this->*pn; }
952*67e74705SXin Li virtual int g() const;
953*67e74705SXin Li
954*67e74705SXin Li int m, n;
955*67e74705SXin Li int (S::*pf)() const;
956*67e74705SXin Li int S::*pn;
957*67e74705SXin Li };
958*67e74705SXin Li
959*67e74705SXin Li constexpr int S::*pm = &S::m;
960*67e74705SXin Li constexpr int S::*pn = &S::n;
961*67e74705SXin Li constexpr int (S::*pf)() const = &S::f;
962*67e74705SXin Li constexpr int (S::*pg)() const = &S::g;
963*67e74705SXin Li
964*67e74705SXin Li constexpr S s(2, 5, &S::f, &S::m);
965*67e74705SXin Li
966*67e74705SXin Li static_assert((s.*&S::f)() == 2, "");
967*67e74705SXin Li static_assert((s.*s.pf)() == 2, "");
968*67e74705SXin Li
969*67e74705SXin Li static_assert(pf == &S::f, "");
970*67e74705SXin Li static_assert(pf == s.*&S::pf, "");
971*67e74705SXin Li static_assert(pm == &S::m, "");
972*67e74705SXin Li static_assert(pm != pn, "");
973*67e74705SXin Li static_assert(s.pn != pn, "");
974*67e74705SXin Li static_assert(s.pn == pm, "");
975*67e74705SXin Li static_assert(pg != nullptr, "");
976*67e74705SXin Li static_assert(pf != nullptr, "");
977*67e74705SXin Li static_assert((int S::*)nullptr == nullptr, "");
978*67e74705SXin Li static_assert(pg == pg, ""); // expected-error {{constant expression}} expected-note {{comparison of pointer to virtual member function 'g' has unspecified value}}
979*67e74705SXin Li static_assert(pf != pg, ""); // expected-error {{constant expression}} expected-note {{comparison of pointer to virtual member function 'g' has unspecified value}}
980*67e74705SXin Li
981*67e74705SXin Li template<int n> struct T : T<n-1> {};
982*67e74705SXin Li template<> struct T<0> { int n; };
983*67e74705SXin Li template<> struct T<30> : T<29> { int m; };
984*67e74705SXin Li
985*67e74705SXin Li T<17> t17;
986*67e74705SXin Li T<30> t30;
987*67e74705SXin Li
988*67e74705SXin Li constexpr int (T<10>::*deepn) = &T<0>::n;
989*67e74705SXin Li static_assert(&(t17.*deepn) == &t17.n, "");
990*67e74705SXin Li static_assert(deepn == &T<2>::n, "");
991*67e74705SXin Li
992*67e74705SXin Li constexpr int (T<15>::*deepm) = (int(T<10>::*))&T<30>::m;
993*67e74705SXin Li constexpr int *pbad = &(t17.*deepm); // expected-error {{constant expression}}
994*67e74705SXin Li static_assert(&(t30.*deepm) == &t30.m, "");
995*67e74705SXin Li static_assert(deepm == &T<50>::m, "");
996*67e74705SXin Li static_assert(deepm != deepn, "");
997*67e74705SXin Li
998*67e74705SXin Li constexpr T<5> *p17_5 = &t17;
999*67e74705SXin Li constexpr T<13> *p17_13 = (T<13>*)p17_5;
1000*67e74705SXin Li 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>'}}
1001*67e74705SXin Li static_assert(&(p17_5->*(int(T<3>::*))deepn) == &t17.n, "");
1002*67e74705SXin Li static_assert(&(p17_13->*deepn) == &t17.n, "");
1003*67e74705SXin Li constexpr int *pbad2 = &(p17_13->*(int(T<9>::*))deepm); // expected-error {{constant expression}}
1004*67e74705SXin Li
1005*67e74705SXin Li constexpr T<5> *p30_5 = &t30;
1006*67e74705SXin Li constexpr T<23> *p30_23 = (T<23>*)p30_5;
1007*67e74705SXin Li constexpr T<13> *p30_13 = p30_23;
1008*67e74705SXin Li static_assert(&(p30_5->*(int(T<3>::*))deepn) == &t30.n, "");
1009*67e74705SXin Li static_assert(&(p30_13->*deepn) == &t30.n, "");
1010*67e74705SXin Li static_assert(&(p30_23->*deepn) == &t30.n, "");
1011*67e74705SXin Li static_assert(&(p30_5->*(int(T<2>::*))deepm) == &t30.m, "");
1012*67e74705SXin Li static_assert(&(((T<17>*)p30_13)->*deepm) == &t30.m, "");
1013*67e74705SXin Li static_assert(&(p30_23->*deepm) == &t30.m, "");
1014*67e74705SXin Li
1015*67e74705SXin Li struct Base { int n; };
1016*67e74705SXin Li template<int N> struct Mid : Base {};
1017*67e74705SXin Li struct Derived : Mid<0>, Mid<1> {};
1018*67e74705SXin Li static_assert(&Mid<0>::n == &Mid<1>::n, "");
1019*67e74705SXin Li static_assert((int Derived::*)(int Mid<0>::*)&Mid<0>::n !=
1020*67e74705SXin Li (int Derived::*)(int Mid<1>::*)&Mid<1>::n, "");
1021*67e74705SXin Li static_assert(&Mid<0>::n == (int Mid<0>::*)&Base::n, "");
1022*67e74705SXin Li }
1023*67e74705SXin Li
1024*67e74705SXin Li namespace ArrayBaseDerived {
1025*67e74705SXin Li
1026*67e74705SXin Li struct Base {
BaseArrayBaseDerived::Base1027*67e74705SXin Li constexpr Base() {}
1028*67e74705SXin Li int n = 0;
1029*67e74705SXin Li };
1030*67e74705SXin Li struct Derived : Base {
DerivedArrayBaseDerived::Derived1031*67e74705SXin Li constexpr Derived() {}
fArrayBaseDerived::Derived1032*67e74705SXin Li constexpr const int *f() const { return &n; }
1033*67e74705SXin Li };
1034*67e74705SXin Li
1035*67e74705SXin Li constexpr Derived a[10];
1036*67e74705SXin Li constexpr Derived *pd3 = const_cast<Derived*>(&a[3]);
1037*67e74705SXin Li constexpr Base *pb3 = const_cast<Derived*>(&a[3]);
1038*67e74705SXin Li static_assert(pb3 == pd3, "");
1039*67e74705SXin Li
1040*67e74705SXin Li // pb3 does not point to an array element.
1041*67e74705SXin Li constexpr Base *pb4 = pb3 + 1; // ok, one-past-the-end pointer.
1042*67e74705SXin Li constexpr int pb4n = pb4->n; // expected-error {{constant expression}} expected-note {{cannot access field of pointer past the end}}
1043*67e74705SXin Li constexpr Base *err_pb5 = pb3 + 2; // expected-error {{constant expression}} expected-note {{cannot refer to element 2}} expected-note {{here}}
1044*67e74705SXin Li constexpr int err_pb5n = err_pb5->n; // expected-error {{constant expression}} expected-note {{initializer of 'err_pb5' is not a constant expression}}
1045*67e74705SXin Li constexpr Base *err_pb2 = pb3 - 1; // expected-error {{constant expression}} expected-note {{cannot refer to element -1}} expected-note {{here}}
1046*67e74705SXin Li constexpr int err_pb2n = err_pb2->n; // expected-error {{constant expression}} expected-note {{initializer of 'err_pb2'}}
1047*67e74705SXin Li constexpr Base *pb3a = pb4 - 1;
1048*67e74705SXin Li
1049*67e74705SXin Li // pb4 does not point to a Derived.
1050*67e74705SXin Li constexpr Derived *err_pd4 = (Derived*)pb4; // expected-error {{constant expression}} expected-note {{cannot access derived class of pointer past the end}}
1051*67e74705SXin Li constexpr Derived *pd3a = (Derived*)pb3a;
1052*67e74705SXin Li constexpr int pd3n = pd3a->n;
1053*67e74705SXin Li
1054*67e74705SXin Li // pd3a still points to the Derived array.
1055*67e74705SXin Li constexpr Derived *pd6 = pd3a + 3;
1056*67e74705SXin Li static_assert(pd6 == &a[6], "");
1057*67e74705SXin Li constexpr Derived *pd9 = pd6 + 3;
1058*67e74705SXin Li constexpr Derived *pd10 = pd6 + 4;
1059*67e74705SXin Li constexpr int pd9n = pd9->n; // ok
1060*67e74705SXin Li constexpr int err_pd10n = pd10->n; // expected-error {{constant expression}} expected-note {{cannot access base class of pointer past the end}}
1061*67e74705SXin Li constexpr int pd0n = pd10[-10].n;
1062*67e74705SXin Li constexpr int err_pdminus1n = pd10[-11].n; // expected-error {{constant expression}} expected-note {{cannot refer to element -1 of}}
1063*67e74705SXin Li
1064*67e74705SXin Li constexpr Base *pb9 = pd9;
1065*67e74705SXin Li constexpr const int *(Base::*pfb)() const =
1066*67e74705SXin Li static_cast<const int *(Base::*)() const>(&Derived::f);
1067*67e74705SXin Li static_assert((pb9->*pfb)() == &a[9].n, "");
1068*67e74705SXin Li }
1069*67e74705SXin Li
1070*67e74705SXin Li namespace Complex {
1071*67e74705SXin Li
1072*67e74705SXin Li class complex {
1073*67e74705SXin Li int re, im;
1074*67e74705SXin Li public:
complex(int re=0,int im=0)1075*67e74705SXin Li constexpr complex(int re = 0, int im = 0) : re(re), im(im) {}
complex(const complex & o)1076*67e74705SXin Li constexpr complex(const complex &o) : re(o.re), im(o.im) {}
operator -() const1077*67e74705SXin Li constexpr complex operator-() const { return complex(-re, -im); }
operator +(const complex & l,const complex & r)1078*67e74705SXin Li friend constexpr complex operator+(const complex &l, const complex &r) {
1079*67e74705SXin Li return complex(l.re + r.re, l.im + r.im);
1080*67e74705SXin Li }
operator -(const complex & l,const complex & r)1081*67e74705SXin Li friend constexpr complex operator-(const complex &l, const complex &r) {
1082*67e74705SXin Li return l + -r;
1083*67e74705SXin Li }
operator *(const complex & l,const complex & r)1084*67e74705SXin Li friend constexpr complex operator*(const complex &l, const complex &r) {
1085*67e74705SXin Li return complex(l.re * r.re - l.im * r.im, l.re * r.im + l.im * r.re);
1086*67e74705SXin Li }
operator ==(const complex & l,const complex & r)1087*67e74705SXin Li friend constexpr bool operator==(const complex &l, const complex &r) {
1088*67e74705SXin Li return l.re == r.re && l.im == r.im;
1089*67e74705SXin Li }
operator !=(const complex & r) const1090*67e74705SXin Li constexpr bool operator!=(const complex &r) const {
1091*67e74705SXin Li return re != r.re || im != r.im;
1092*67e74705SXin Li }
real() const1093*67e74705SXin Li constexpr int real() const { return re; }
imag() const1094*67e74705SXin Li constexpr int imag() const { return im; }
1095*67e74705SXin Li };
1096*67e74705SXin Li
1097*67e74705SXin Li constexpr complex i = complex(0, 1);
1098*67e74705SXin Li constexpr complex k = (3 + 4*i) * (6 - 4*i);
1099*67e74705SXin Li static_assert(complex(1,0).real() == 1, "");
1100*67e74705SXin Li static_assert(complex(1,0).imag() == 0, "");
1101*67e74705SXin Li static_assert(((complex)1).imag() == 0, "");
1102*67e74705SXin Li static_assert(k.real() == 34, "");
1103*67e74705SXin Li static_assert(k.imag() == 12, "");
1104*67e74705SXin Li static_assert(k - 34 == 12*i, "");
1105*67e74705SXin Li static_assert((complex)1 == complex(1), "");
1106*67e74705SXin Li static_assert((complex)1 != complex(0, 1), "");
1107*67e74705SXin Li static_assert(complex(1) == complex(1), "");
1108*67e74705SXin Li static_assert(complex(1) != complex(0, 1), "");
makeComplex(int re,int im)1109*67e74705SXin Li constexpr complex makeComplex(int re, int im) { return complex(re, im); }
1110*67e74705SXin Li static_assert(makeComplex(1,0) == complex(1), "");
1111*67e74705SXin Li static_assert(makeComplex(1,0) != complex(0, 1), "");
1112*67e74705SXin Li
1113*67e74705SXin Li class complex_wrap : public complex {
1114*67e74705SXin Li public:
complex_wrap(int re,int im=0)1115*67e74705SXin Li constexpr complex_wrap(int re, int im = 0) : complex(re, im) {}
complex_wrap(const complex_wrap & o)1116*67e74705SXin Li constexpr complex_wrap(const complex_wrap &o) : complex(o) {}
1117*67e74705SXin Li };
1118*67e74705SXin Li
1119*67e74705SXin Li static_assert((complex_wrap)1 == complex(1), "");
1120*67e74705SXin Li static_assert((complex)1 != complex_wrap(0, 1), "");
1121*67e74705SXin Li static_assert(complex(1) == complex_wrap(1), "");
1122*67e74705SXin Li static_assert(complex_wrap(1) != complex(0, 1), "");
makeComplexWrap(int re,int im)1123*67e74705SXin Li constexpr complex_wrap makeComplexWrap(int re, int im) {
1124*67e74705SXin Li return complex_wrap(re, im);
1125*67e74705SXin Li }
1126*67e74705SXin Li static_assert(makeComplexWrap(1,0) == complex(1), "");
1127*67e74705SXin Li static_assert(makeComplexWrap(1,0) != complex(0, 1), "");
1128*67e74705SXin Li
1129*67e74705SXin Li }
1130*67e74705SXin Li
1131*67e74705SXin Li namespace PR11595 {
operator ==PR11595::A1132*67e74705SXin Li struct A { constexpr bool operator==(int x) const { return true; } };
1133*67e74705SXin Li struct B { B(); A& x; };
1134*67e74705SXin Li static_assert(B().x == 3, ""); // expected-error {{constant expression}} expected-note {{non-literal type 'PR11595::B' cannot be used in a constant expression}}
1135*67e74705SXin Li
f(int k)1136*67e74705SXin Li constexpr bool f(int k) { // expected-error {{constexpr function never produces a constant expression}}
1137*67e74705SXin Li return B().x == k; // expected-note {{non-literal type 'PR11595::B' cannot be used in a constant expression}}
1138*67e74705SXin Li }
1139*67e74705SXin Li }
1140*67e74705SXin Li
1141*67e74705SXin Li namespace ExprWithCleanups {
1142*67e74705SXin Li struct A { A(); ~A(); int get(); };
get(bool FromA)1143*67e74705SXin Li constexpr int get(bool FromA) { return FromA ? A().get() : 1; }
1144*67e74705SXin Li constexpr int n = get(false);
1145*67e74705SXin Li }
1146*67e74705SXin Li
1147*67e74705SXin Li namespace Volatile {
1148*67e74705SXin Li
1149*67e74705SXin Li volatile constexpr int n1 = 0; // expected-note {{here}}
1150*67e74705SXin Li volatile const int n2 = 0; // expected-note {{here}}
1151*67e74705SXin Li int n3 = 37; // expected-note {{declared here}}
1152*67e74705SXin Li
1153*67e74705SXin Li constexpr int m1 = n1; // expected-error {{constant expression}} expected-note {{read of volatile-qualified type 'const volatile int'}}
1154*67e74705SXin Li constexpr int m2 = n2; // expected-error {{constant expression}} expected-note {{read of volatile-qualified type 'const volatile int'}}
1155*67e74705SXin Li constexpr int m1b = const_cast<const int&>(n1); // expected-error {{constant expression}} expected-note {{read of volatile object 'n1'}}
1156*67e74705SXin Li constexpr int m2b = const_cast<const int&>(n2); // expected-error {{constant expression}} expected-note {{read of volatile object 'n2'}}
1157*67e74705SXin Li
1158*67e74705SXin Li struct T { int n; };
1159*67e74705SXin Li const T t = { 42 }; // expected-note {{declared here}}
1160*67e74705SXin Li
f(volatile int && r)1161*67e74705SXin Li constexpr int f(volatile int &&r) {
1162*67e74705SXin Li return r; // expected-note {{read of volatile-qualified type 'volatile int'}}
1163*67e74705SXin Li }
g(volatile int && r)1164*67e74705SXin Li constexpr int g(volatile int &&r) {
1165*67e74705SXin Li return const_cast<int&>(r); // expected-note {{read of volatile temporary is not allowed in a constant expression}}
1166*67e74705SXin Li }
1167*67e74705SXin Li struct S {
1168*67e74705SXin Li int j : f(0); // expected-error {{constant expression}} expected-note {{in call to 'f(0)'}}
1169*67e74705SXin Li int k : g(0); // expected-error {{constant expression}} expected-note {{temporary created here}} expected-note {{in call to 'g(0)'}}
1170*67e74705SXin Li int l : n3; // expected-error {{constant expression}} expected-note {{read of non-const variable}}
1171*67e74705SXin Li int m : t.n; // expected-error {{constant expression}} expected-note {{read of non-constexpr variable}}
1172*67e74705SXin Li };
1173*67e74705SXin Li
1174*67e74705SXin Li }
1175*67e74705SXin Li
1176*67e74705SXin Li namespace ExternConstexpr {
1177*67e74705SXin Li extern constexpr int n = 0;
1178*67e74705SXin Li extern constexpr int m; // expected-error {{constexpr variable declaration must be a definition}}
f()1179*67e74705SXin Li void f() {
1180*67e74705SXin Li extern constexpr int i; // expected-error {{constexpr variable declaration must be a definition}}
1181*67e74705SXin Li constexpr int j = 0;
1182*67e74705SXin Li constexpr int k; // expected-error {{default initialization of an object of const type}}
1183*67e74705SXin Li }
1184*67e74705SXin Li
1185*67e74705SXin Li extern const int q;
g()1186*67e74705SXin Li constexpr int g() { return q; }
1187*67e74705SXin Li constexpr int q = g();
1188*67e74705SXin Li static_assert(q == 0, "zero-initialization should precede static initialization");
1189*67e74705SXin Li
1190*67e74705SXin Li extern int r; // expected-note {{here}}
h()1191*67e74705SXin Li constexpr int h() { return r; } // expected-error {{never produces a constant}} expected-note {{read of non-const}}
1192*67e74705SXin Li
1193*67e74705SXin Li struct S { int n; };
1194*67e74705SXin Li extern const S s;
x()1195*67e74705SXin Li constexpr int x() { return s.n; }
1196*67e74705SXin Li constexpr S s = {x()};
1197*67e74705SXin Li static_assert(s.n == 0, "zero-initialization should precede static initialization");
1198*67e74705SXin Li }
1199*67e74705SXin Li
1200*67e74705SXin Li namespace ComplexConstexpr {
1201*67e74705SXin Li constexpr _Complex float test1 = {};
1202*67e74705SXin Li constexpr _Complex float test2 = {1};
1203*67e74705SXin Li constexpr _Complex double test3 = {1,2};
1204*67e74705SXin Li constexpr _Complex int test4 = {4};
1205*67e74705SXin Li constexpr _Complex int test5 = 4;
1206*67e74705SXin Li constexpr _Complex int test6 = {5,6};
1207*67e74705SXin Li typedef _Complex float fcomplex;
1208*67e74705SXin Li constexpr fcomplex test7 = fcomplex();
1209*67e74705SXin Li
1210*67e74705SXin Li constexpr const double &t2r = __real test3;
1211*67e74705SXin Li constexpr const double &t2i = __imag test3;
1212*67e74705SXin Li static_assert(&t2r + 1 == &t2i, "");
1213*67e74705SXin Li static_assert(t2r == 1.0, "");
1214*67e74705SXin Li static_assert(t2i == 2.0, "");
1215*67e74705SXin Li constexpr const double *t2p = &t2r;
1216*67e74705SXin Li static_assert(t2p[-1] == 0.0, ""); // expected-error {{constant expr}} expected-note {{cannot refer to element -1 of array of 2 elements}}
1217*67e74705SXin Li static_assert(t2p[0] == 1.0, "");
1218*67e74705SXin Li static_assert(t2p[1] == 2.0, "");
1219*67e74705SXin Li static_assert(t2p[2] == 0.0, ""); // expected-error {{constant expr}} expected-note {{one-past-the-end pointer}}
1220*67e74705SXin Li static_assert(t2p[3] == 0.0, ""); // expected-error {{constant expr}} expected-note {{cannot refer to element 3 of array of 2 elements}}
1221*67e74705SXin Li constexpr _Complex float *p = 0;
1222*67e74705SXin Li constexpr float pr = __real *p; // expected-error {{constant expr}} expected-note {{cannot access real component of null}}
1223*67e74705SXin Li constexpr float pi = __imag *p; // expected-error {{constant expr}} expected-note {{cannot access imaginary component of null}}
1224*67e74705SXin Li constexpr const _Complex double *q = &test3 + 1;
1225*67e74705SXin Li constexpr double qr = __real *q; // expected-error {{constant expr}} expected-note {{cannot access real component of pointer past the end}}
1226*67e74705SXin Li constexpr double qi = __imag *q; // expected-error {{constant expr}} expected-note {{cannot access imaginary component of pointer past the end}}
1227*67e74705SXin Li
1228*67e74705SXin Li static_assert(__real test6 == 5, "");
1229*67e74705SXin Li static_assert(__imag test6 == 6, "");
1230*67e74705SXin Li static_assert(&__imag test6 == &__real test6 + 1, "");
1231*67e74705SXin Li }
1232*67e74705SXin Li
1233*67e74705SXin Li // _Atomic(T) is exactly like T for the purposes of constant expression
1234*67e74705SXin Li // evaluation..
1235*67e74705SXin Li namespace Atomic {
1236*67e74705SXin Li constexpr _Atomic int n = 3;
1237*67e74705SXin Li
1238*67e74705SXin Li struct S { _Atomic(double) d; };
1239*67e74705SXin Li constexpr S s = { 0.5 };
1240*67e74705SXin Li constexpr double d1 = s.d;
1241*67e74705SXin Li constexpr double d2 = n;
1242*67e74705SXin Li constexpr _Atomic double d3 = n;
1243*67e74705SXin Li
1244*67e74705SXin Li constexpr _Atomic(int) n2 = d3;
1245*67e74705SXin Li static_assert(d1 == 0.5, "");
1246*67e74705SXin Li static_assert(d3 == 3.0, "");
1247*67e74705SXin Li
1248*67e74705SXin Li namespace PR16056 {
1249*67e74705SXin Li struct TestVar {
1250*67e74705SXin Li _Atomic(int) value;
TestVarAtomic::PR16056::TestVar1251*67e74705SXin Li constexpr TestVar(int value) : value(value) {}
1252*67e74705SXin Li };
1253*67e74705SXin Li constexpr TestVar testVar{-1};
1254*67e74705SXin Li static_assert(testVar.value == -1, "");
1255*67e74705SXin Li }
1256*67e74705SXin Li }
1257*67e74705SXin Li
1258*67e74705SXin Li namespace InstantiateCaseStmt {
f()1259*67e74705SXin Li template<int x> constexpr int f() { return x; }
g(int c)1260*67e74705SXin Li template<int x> int g(int c) { switch(c) { case f<x>(): return 1; } return 0; }
gg(int c)1261*67e74705SXin Li int gg(int c) { return g<4>(c); }
1262*67e74705SXin Li }
1263*67e74705SXin Li
1264*67e74705SXin Li namespace ConvertedConstantExpr {
1265*67e74705SXin Li extern int &m;
1266*67e74705SXin Li extern int &n;
1267*67e74705SXin Li
1268*67e74705SXin Li constexpr int k = 4;
1269*67e74705SXin Li int &m = const_cast<int&>(k);
1270*67e74705SXin Li
1271*67e74705SXin Li // If we have nothing more interesting to say, ensure we don't produce a
1272*67e74705SXin Li // useless note and instead just point to the non-constant subexpression.
1273*67e74705SXin Li enum class E {
1274*67e74705SXin Li em = m,
1275*67e74705SXin Li en = n, // expected-error {{not a constant expression}}
1276*67e74705SXin Li eo = (m +
1277*67e74705SXin Li n // expected-error {{not a constant expression}}
1278*67e74705SXin Li ),
1279*67e74705SXin Li eq = reinterpret_cast<int>((int*)0) // expected-error {{not a constant expression}} expected-note {{reinterpret_cast}}
1280*67e74705SXin Li };
1281*67e74705SXin Li }
1282*67e74705SXin Li
1283*67e74705SXin Li namespace IndirectField {
1284*67e74705SXin Li struct S {
1285*67e74705SXin Li struct { // expected-warning {{GNU extension}}
1286*67e74705SXin Li union { // expected-warning {{declared in an anonymous struct}}
1287*67e74705SXin Li struct { // expected-warning {{GNU extension}} expected-warning {{declared in an anonymous union}}
1288*67e74705SXin Li int a;
1289*67e74705SXin Li int b;
1290*67e74705SXin Li };
1291*67e74705SXin Li int c;
1292*67e74705SXin Li };
1293*67e74705SXin Li int d;
1294*67e74705SXin Li };
1295*67e74705SXin Li union {
1296*67e74705SXin Li int e;
1297*67e74705SXin Li int f;
1298*67e74705SXin Li };
SIndirectField::S1299*67e74705SXin Li constexpr S(int a, int b, int d, int e) : a(a), b(b), d(d), e(e) {}
SIndirectField::S1300*67e74705SXin Li constexpr S(int c, int d, int f) : c(c), d(d), f(f) {}
1301*67e74705SXin Li };
1302*67e74705SXin Li
1303*67e74705SXin Li constexpr S s1(1, 2, 3, 4);
1304*67e74705SXin Li constexpr S s2(5, 6, 7);
1305*67e74705SXin Li
1306*67e74705SXin Li // FIXME: The diagnostics here do a very poor job of explaining which unnamed
1307*67e74705SXin Li // member is active and which is requested.
1308*67e74705SXin Li static_assert(s1.a == 1, "");
1309*67e74705SXin Li static_assert(s1.b == 2, "");
1310*67e74705SXin Li static_assert(s1.c == 0, ""); // expected-error {{constant expression}} expected-note {{union with active member}}
1311*67e74705SXin Li static_assert(s1.d == 3, "");
1312*67e74705SXin Li static_assert(s1.e == 4, "");
1313*67e74705SXin Li static_assert(s1.f == 0, ""); // expected-error {{constant expression}} expected-note {{union with active member}}
1314*67e74705SXin Li
1315*67e74705SXin Li static_assert(s2.a == 0, ""); // expected-error {{constant expression}} expected-note {{union with active member}}
1316*67e74705SXin Li static_assert(s2.b == 0, ""); // expected-error {{constant expression}} expected-note {{union with active member}}
1317*67e74705SXin Li static_assert(s2.c == 5, "");
1318*67e74705SXin Li static_assert(s2.d == 6, "");
1319*67e74705SXin Li static_assert(s2.e == 0, ""); // expected-error {{constant expression}} expected-note {{union with active member}}
1320*67e74705SXin Li static_assert(s2.f == 7, "");
1321*67e74705SXin Li }
1322*67e74705SXin Li
1323*67e74705SXin Li // DR1405: don't allow reading mutable members in constant expressions.
1324*67e74705SXin Li namespace MutableMembers {
1325*67e74705SXin Li struct MM {
1326*67e74705SXin Li mutable int n; // expected-note 3{{declared here}}
1327*67e74705SXin Li } constexpr mm = { 4 };
1328*67e74705SXin Li constexpr int mmn = mm.n; // expected-error {{constant expression}} expected-note {{read of mutable member 'n' is not allowed in a constant expression}}
1329*67e74705SXin Li int x = (mm.n = 1, 3);
1330*67e74705SXin Li constexpr int mmn2 = mm.n; // expected-error {{constant expression}} expected-note {{read of mutable member 'n' is not allowed in a constant expression}}
1331*67e74705SXin Li
1332*67e74705SXin Li // Here's one reason why allowing this would be a disaster...
1333*67e74705SXin Li template<int n> struct Id { int k = n; };
f()1334*67e74705SXin Li int f() {
1335*67e74705SXin Li constexpr MM m = { 0 };
1336*67e74705SXin Li ++m.n;
1337*67e74705SXin Li 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}}
1338*67e74705SXin Li }
1339*67e74705SXin Li
1340*67e74705SXin Li struct A { int n; };
1341*67e74705SXin Li struct B { mutable A a; }; // expected-note {{here}}
1342*67e74705SXin Li struct C { B b; };
1343*67e74705SXin Li constexpr C c[3] = {};
1344*67e74705SXin Li constexpr int k = c[1].b.a.n; // expected-error {{constant expression}} expected-note {{mutable}}
1345*67e74705SXin Li
1346*67e74705SXin Li struct D { int x; mutable int y; }; // expected-note {{here}}
1347*67e74705SXin Li constexpr D d1 = { 1, 2 };
1348*67e74705SXin Li int l = ++d1.y;
1349*67e74705SXin Li constexpr D d2 = d1; // expected-error {{constant}} expected-note {{mutable}} expected-note {{in call}}
1350*67e74705SXin Li
1351*67e74705SXin Li struct E {
1352*67e74705SXin Li union {
1353*67e74705SXin Li int a;
1354*67e74705SXin Li mutable int b; // expected-note {{here}}
1355*67e74705SXin Li };
1356*67e74705SXin Li };
1357*67e74705SXin Li constexpr E e1 = {{1}};
1358*67e74705SXin Li constexpr E e2 = e1; // expected-error {{constant}} expected-note {{mutable}} expected-note {{in call}}
1359*67e74705SXin Li
1360*67e74705SXin Li struct F {
1361*67e74705SXin Li union U { };
1362*67e74705SXin Li mutable U u;
1363*67e74705SXin Li struct X { };
1364*67e74705SXin Li mutable X x;
1365*67e74705SXin Li struct Y : X { X x; U u; };
1366*67e74705SXin Li mutable Y y;
1367*67e74705SXin Li int n;
1368*67e74705SXin Li };
1369*67e74705SXin Li // This is OK; we don't actually read any mutable state here.
1370*67e74705SXin Li constexpr F f1 = {};
1371*67e74705SXin Li constexpr F f2 = f1;
1372*67e74705SXin Li
1373*67e74705SXin Li struct G {
1374*67e74705SXin Li struct X {};
1375*67e74705SXin Li union U { X a; };
1376*67e74705SXin Li mutable U u; // expected-note {{here}}
1377*67e74705SXin Li };
1378*67e74705SXin Li constexpr G g1 = {};
1379*67e74705SXin Li constexpr G g2 = g1; // expected-error {{constant}} expected-note {{mutable}} expected-note {{in call}}
1380*67e74705SXin Li constexpr G::U gu1 = {};
1381*67e74705SXin Li constexpr G::U gu2 = gu1;
1382*67e74705SXin Li
1383*67e74705SXin Li union H {
1384*67e74705SXin Li mutable G::X gx; // expected-note {{here}}
1385*67e74705SXin Li };
1386*67e74705SXin Li constexpr H h1 = {};
1387*67e74705SXin Li constexpr H h2 = h1; // expected-error {{constant}} expected-note {{mutable}} expected-note {{in call}}
1388*67e74705SXin Li }
1389*67e74705SXin Li
1390*67e74705SXin Li namespace Fold {
1391*67e74705SXin Li
1392*67e74705SXin Li // This macro forces its argument to be constant-folded, even if it's not
1393*67e74705SXin Li // otherwise a constant expression.
1394*67e74705SXin Li #define fold(x) (__builtin_constant_p(x) ? (x) : (x))
1395*67e74705SXin Li
1396*67e74705SXin Li constexpr int n = (int)(char*)123; // expected-error {{constant expression}} expected-note {{reinterpret_cast}}
1397*67e74705SXin Li constexpr int m = fold((int)(char*)123); // ok
1398*67e74705SXin Li static_assert(m == 123, "");
1399*67e74705SXin Li
1400*67e74705SXin Li #undef fold
1401*67e74705SXin Li
1402*67e74705SXin Li }
1403*67e74705SXin Li
1404*67e74705SXin Li namespace DR1454 {
1405*67e74705SXin Li
f(const int & n)1406*67e74705SXin Li constexpr const int &f(const int &n) { return n; }
1407*67e74705SXin Li constexpr int k1 = f(0); // ok
1408*67e74705SXin Li
1409*67e74705SXin Li struct Wrap {
1410*67e74705SXin Li const int &value;
1411*67e74705SXin Li };
g(const Wrap & w)1412*67e74705SXin Li constexpr const Wrap &g(const Wrap &w) { return w; }
1413*67e74705SXin Li constexpr int k2 = g({0}).value; // ok
1414*67e74705SXin Li
1415*67e74705SXin Li // The temporary here has static storage duration, so we can bind a constexpr
1416*67e74705SXin Li // reference to it.
1417*67e74705SXin Li constexpr const int &i = 1;
1418*67e74705SXin Li constexpr const int j = i;
1419*67e74705SXin Li static_assert(j == 1, "");
1420*67e74705SXin Li
1421*67e74705SXin Li // The temporary here is not const, so it can't be read outside the expression
1422*67e74705SXin Li // in which it was created (per the C++14 rules, which we use to avoid a C++11
1423*67e74705SXin Li // defect).
1424*67e74705SXin Li constexpr int &&k = 1; // expected-note {{temporary created here}}
1425*67e74705SXin Li constexpr const int l = k; // expected-error {{constant expression}} expected-note {{read of temporary}}
1426*67e74705SXin Li
f()1427*67e74705SXin Li void f() {
1428*67e74705SXin Li // The temporary here has automatic storage duration, so we can't bind a
1429*67e74705SXin Li // constexpr reference to it.
1430*67e74705SXin Li constexpr const int &i = 1; // expected-error {{constant expression}} expected-note 2{{temporary}}
1431*67e74705SXin Li }
1432*67e74705SXin Li
1433*67e74705SXin Li }
1434*67e74705SXin Li
1435*67e74705SXin Li namespace RecursiveOpaqueExpr {
1436*67e74705SXin Li template<typename Iter>
LastNonzero(Iter p,Iter q)1437*67e74705SXin Li constexpr auto LastNonzero(Iter p, Iter q) -> decltype(+*p) {
1438*67e74705SXin Li return p != q ? (LastNonzero(p+1, q) ?: *p) : 0; // expected-warning {{GNU}}
1439*67e74705SXin Li }
1440*67e74705SXin Li
1441*67e74705SXin Li constexpr int arr1[] = { 1, 0, 0, 3, 0, 2, 0, 4, 0, 0 };
1442*67e74705SXin Li static_assert(LastNonzero(begin(arr1), end(arr1)) == 4, "");
1443*67e74705SXin Li
1444*67e74705SXin Li constexpr int arr2[] = { 1, 0, 0, 3, 0, 2, 0, 4, 0, 5 };
1445*67e74705SXin Li static_assert(LastNonzero(begin(arr2), end(arr2)) == 5, "");
1446*67e74705SXin Li
1447*67e74705SXin Li constexpr int arr3[] = {
1448*67e74705SXin Li 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,
1449*67e74705SXin Li 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,
1450*67e74705SXin Li 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,
1451*67e74705SXin Li 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,
1452*67e74705SXin Li 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,
1453*67e74705SXin Li 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,
1454*67e74705SXin Li 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,
1455*67e74705SXin Li 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 };
1456*67e74705SXin Li static_assert(LastNonzero(begin(arr3), end(arr3)) == 2, "");
1457*67e74705SXin Li }
1458*67e74705SXin Li
1459*67e74705SXin Li namespace VLASizeof {
1460*67e74705SXin Li
f(int k)1461*67e74705SXin Li void f(int k) {
1462*67e74705SXin Li int arr[k]; // expected-warning {{C99}}
1463*67e74705SXin Li constexpr int n = 1 +
1464*67e74705SXin Li sizeof(arr) // expected-error {{constant expression}}
1465*67e74705SXin Li * 3;
1466*67e74705SXin Li }
1467*67e74705SXin Li }
1468*67e74705SXin Li
1469*67e74705SXin Li namespace CompoundLiteral {
1470*67e74705SXin Li // FIXME:
1471*67e74705SXin Li // We don't model the semantics of this correctly: the compound literal is
1472*67e74705SXin Li // represented as a prvalue in the AST, but actually behaves like an lvalue.
1473*67e74705SXin Li // We treat the compound literal as a temporary and refuse to produce a
1474*67e74705SXin Li // pointer to it. This is OK: we're not required to treat this as a constant
1475*67e74705SXin Li // in C++, and in C we model compound literals as lvalues.
1476*67e74705SXin Li constexpr int *p = (int*)(int[1]){0}; // expected-warning {{C99}} expected-error {{constant expression}} expected-note 2{{temporary}}
1477*67e74705SXin Li }
1478*67e74705SXin Li
1479*67e74705SXin Li namespace Vector {
1480*67e74705SXin Li typedef int __attribute__((vector_size(16))) VI4;
f(int n)1481*67e74705SXin Li constexpr VI4 f(int n) {
1482*67e74705SXin Li return VI4 { n * 3, n + 4, n - 5, n / 6 };
1483*67e74705SXin Li }
1484*67e74705SXin Li constexpr auto v1 = f(10);
1485*67e74705SXin Li
1486*67e74705SXin Li typedef double __attribute__((vector_size(32))) VD4;
g(int n)1487*67e74705SXin Li constexpr VD4 g(int n) {
1488*67e74705SXin Li return (VD4) { n / 2.0, n + 1.5, n - 5.4, n * 0.9 }; // expected-warning {{C99}}
1489*67e74705SXin Li }
1490*67e74705SXin Li constexpr auto v2 = g(4);
1491*67e74705SXin Li }
1492*67e74705SXin Li
1493*67e74705SXin Li // PR12626, redux
1494*67e74705SXin Li namespace InvalidClasses {
test0()1495*67e74705SXin Li void test0() {
1496*67e74705SXin Li struct X; // expected-note {{forward declaration}}
1497*67e74705SXin Li struct Y { bool b; X x; }; // expected-error {{field has incomplete type}}
1498*67e74705SXin Li Y y;
1499*67e74705SXin Li auto& b = y.b;
1500*67e74705SXin Li }
1501*67e74705SXin Li }
1502*67e74705SXin Li
1503*67e74705SXin Li namespace NamespaceAlias {
f()1504*67e74705SXin Li constexpr int f() {
1505*67e74705SXin Li namespace NS = NamespaceAlias; // expected-warning {{use of this statement in a constexpr function is a C++14 extension}}
1506*67e74705SXin Li return &NS::f != nullptr;
1507*67e74705SXin Li }
1508*67e74705SXin Li }
1509*67e74705SXin Li
1510*67e74705SXin Li // Constructors can be implicitly constexpr, even for a non-literal type.
1511*67e74705SXin Li namespace ImplicitConstexpr {
1512*67e74705SXin Li struct Q { Q() = default; Q(const Q&) = default; Q(Q&&) = default; ~Q(); }; // expected-note 3{{here}}
1513*67e74705SXin Li struct R { constexpr R() noexcept; constexpr R(const R&) noexcept; constexpr R(R&&) noexcept; ~R() noexcept; };
1514*67e74705SXin Li struct S { R r; }; // expected-note 3{{here}}
1515*67e74705SXin Li struct T { T(const T&) noexcept; T(T &&) noexcept; ~T() noexcept; };
1516*67e74705SXin Li struct U { T t; }; // expected-note 3{{here}}
1517*67e74705SXin Li static_assert(!__is_literal_type(Q), "");
1518*67e74705SXin Li static_assert(!__is_literal_type(R), "");
1519*67e74705SXin Li static_assert(!__is_literal_type(S), "");
1520*67e74705SXin Li static_assert(!__is_literal_type(T), "");
1521*67e74705SXin Li static_assert(!__is_literal_type(U), "");
1522*67e74705SXin Li struct Test {
1523*67e74705SXin Li friend Q::Q() noexcept; // expected-error {{follows constexpr}}
1524*67e74705SXin Li friend Q::Q(Q&&) noexcept; // expected-error {{follows constexpr}}
1525*67e74705SXin Li friend Q::Q(const Q&) noexcept; // expected-error {{follows constexpr}}
1526*67e74705SXin Li friend S::S() noexcept; // expected-error {{follows constexpr}}
1527*67e74705SXin Li friend S::S(S&&) noexcept; // expected-error {{follows constexpr}}
1528*67e74705SXin Li friend S::S(const S&) noexcept; // expected-error {{follows constexpr}}
1529*67e74705SXin Li friend constexpr U::U() noexcept; // expected-error {{follows non-constexpr}}
1530*67e74705SXin Li friend constexpr U::U(U&&) noexcept; // expected-error {{follows non-constexpr}}
1531*67e74705SXin Li friend constexpr U::U(const U&) noexcept; // expected-error {{follows non-constexpr}}
1532*67e74705SXin Li };
1533*67e74705SXin Li }
1534*67e74705SXin Li
1535*67e74705SXin Li // Indirectly test that an implicit lvalue to xvalue conversion performed for
1536*67e74705SXin Li // an NRVO move operation isn't implemented as CK_LValueToRValue.
1537*67e74705SXin Li namespace PR12826 {
1538*67e74705SXin Li struct Foo {};
id(Foo x)1539*67e74705SXin Li constexpr Foo id(Foo x) { return x; }
1540*67e74705SXin Li constexpr Foo res(id(Foo()));
1541*67e74705SXin Li }
1542*67e74705SXin Li
1543*67e74705SXin Li namespace PR13273 {
1544*67e74705SXin Li struct U {
1545*67e74705SXin Li int t;
1546*67e74705SXin Li U() = default;
1547*67e74705SXin Li };
1548*67e74705SXin Li
1549*67e74705SXin Li struct S : U {
1550*67e74705SXin Li S() = default;
1551*67e74705SXin Li };
1552*67e74705SXin Li
1553*67e74705SXin Li // S's default constructor isn't constexpr, because U's default constructor
1554*67e74705SXin Li // doesn't initialize 't', but it's trivial, so value-initialization doesn't
1555*67e74705SXin Li // actually call it.
1556*67e74705SXin Li static_assert(S{}.t == 0, "");
1557*67e74705SXin Li }
1558*67e74705SXin Li
1559*67e74705SXin Li namespace PR12670 {
1560*67e74705SXin Li struct S {
SPR12670::S1561*67e74705SXin Li constexpr S(int a0) : m(a0) {}
SPR12670::S1562*67e74705SXin Li constexpr S() : m(6) {}
1563*67e74705SXin Li int m;
1564*67e74705SXin Li };
1565*67e74705SXin Li constexpr S x[3] = { {4}, 5 };
1566*67e74705SXin Li static_assert(x[0].m == 4, "");
1567*67e74705SXin Li static_assert(x[1].m == 5, "");
1568*67e74705SXin Li static_assert(x[2].m == 6, "");
1569*67e74705SXin Li }
1570*67e74705SXin Li
1571*67e74705SXin Li // Indirectly test that an implicit lvalue-to-rvalue conversion is performed
1572*67e74705SXin Li // when a conditional operator has one argument of type void and where the other
1573*67e74705SXin Li // is a glvalue of class type.
1574*67e74705SXin Li namespace ConditionalLValToRVal {
1575*67e74705SXin Li struct A {
AConditionalLValToRVal::A1576*67e74705SXin Li constexpr A(int a) : v(a) {}
1577*67e74705SXin Li int v;
1578*67e74705SXin Li };
1579*67e74705SXin Li
f(const A & a)1580*67e74705SXin Li constexpr A f(const A &a) {
1581*67e74705SXin Li return a.v == 0 ? throw a : a;
1582*67e74705SXin Li }
1583*67e74705SXin Li
1584*67e74705SXin Li constexpr A a(4);
1585*67e74705SXin Li static_assert(f(a).v == 4, "");
1586*67e74705SXin Li }
1587*67e74705SXin Li
1588*67e74705SXin Li namespace TLS {
1589*67e74705SXin Li __thread int n;
1590*67e74705SXin Li int m;
1591*67e74705SXin Li
1592*67e74705SXin Li constexpr bool b = &n == &n;
1593*67e74705SXin Li
1594*67e74705SXin Li constexpr int *p = &n; // expected-error{{constexpr variable 'p' must be initialized by a constant expression}}
1595*67e74705SXin Li
f()1596*67e74705SXin Li constexpr int *f() { return &n; }
1597*67e74705SXin Li constexpr int *q = f(); // expected-error{{constexpr variable 'q' must be initialized by a constant expression}}
1598*67e74705SXin Li constexpr bool c = f() == f();
1599*67e74705SXin Li
g()1600*67e74705SXin Li constexpr int *g() { return &m; }
1601*67e74705SXin Li constexpr int *r = g();
1602*67e74705SXin Li }
1603*67e74705SXin Li
1604*67e74705SXin Li namespace Void {
f()1605*67e74705SXin Li constexpr void f() { return; } // expected-error{{constexpr function's return type 'void' is not a literal type}}
1606*67e74705SXin Li
1607*67e74705SXin Li void assert_failed(const char *msg, const char *file, int line); // expected-note {{declared here}}
1608*67e74705SXin Li #define ASSERT(expr) ((expr) ? static_cast<void>(0) : assert_failed(#expr, __FILE__, __LINE__))
1609*67e74705SXin Li template<typename T, size_t S>
get(T (& a)[S],size_t k)1610*67e74705SXin Li constexpr T get(T (&a)[S], size_t k) {
1611*67e74705SXin Li return ASSERT(k > 0 && k < S), a[k]; // expected-note{{non-constexpr function 'assert_failed'}}
1612*67e74705SXin Li }
1613*67e74705SXin Li #undef ASSERT
1614*67e74705SXin Li template int get(int (&a)[4], size_t);
1615*67e74705SXin Li constexpr int arr[] = { 4, 1, 2, 3, 4 };
1616*67e74705SXin Li static_assert(get(arr, 1) == 1, "");
1617*67e74705SXin Li static_assert(get(arr, 4) == 4, "");
1618*67e74705SXin Li static_assert(get(arr, 0) == 4, ""); // expected-error{{not an integral constant expression}} \
1619*67e74705SXin Li // expected-note{{in call to 'get(arr, 0)'}}
1620*67e74705SXin Li }
1621*67e74705SXin Li
1622*67e74705SXin Li namespace std { struct type_info; }
1623*67e74705SXin Li
1624*67e74705SXin Li namespace TypeId {
1625*67e74705SXin Li struct A { virtual ~A(); };
1626*67e74705SXin Li A f();
1627*67e74705SXin Li A &g();
1628*67e74705SXin Li constexpr auto &x = typeid(f());
1629*67e74705SXin Li constexpr auto &y = typeid(g()); // expected-error{{constant expression}} \
1630*67e74705SXin Li // expected-note{{typeid applied to expression of polymorphic type 'TypeId::A' is not allowed in a constant expression}} \
1631*67e74705SXin Li // expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}}
1632*67e74705SXin Li }
1633*67e74705SXin Li
1634*67e74705SXin Li namespace PR14203 {
1635*67e74705SXin Li struct duration {
durationPR14203::duration1636*67e74705SXin Li constexpr duration() {}
operator intPR14203::duration1637*67e74705SXin Li constexpr operator int() const { return 0; }
1638*67e74705SXin Li };
f()1639*67e74705SXin Li template<typename T> void f() {
1640*67e74705SXin Li // If we want to evaluate this at the point of the template definition, we
1641*67e74705SXin Li // need to trigger the implicit definition of the move constructor at that
1642*67e74705SXin Li // point.
1643*67e74705SXin Li // FIXME: C++ does not permit us to implicitly define it at the appropriate
1644*67e74705SXin Li // times, since it is only allowed to be implicitly defined when it is
1645*67e74705SXin Li // odr-used.
1646*67e74705SXin Li constexpr duration d = duration();
1647*67e74705SXin Li }
1648*67e74705SXin Li // FIXME: It's unclear whether this is valid. On the one hand, we're not
1649*67e74705SXin Li // allowed to generate a move constructor. On the other hand, if we did,
1650*67e74705SXin Li // this would be a constant expression. For now, we generate a move
1651*67e74705SXin Li // constructor here.
1652*67e74705SXin Li int n = sizeof(short{duration(duration())});
1653*67e74705SXin Li }
1654*67e74705SXin Li
1655*67e74705SXin Li namespace ArrayEltInit {
1656*67e74705SXin Li struct A {
AArrayEltInit::A1657*67e74705SXin Li constexpr A() : p(&p) {}
1658*67e74705SXin Li void *p;
1659*67e74705SXin Li };
1660*67e74705SXin Li constexpr A a[10];
1661*67e74705SXin Li static_assert(a[0].p == &a[0].p, "");
1662*67e74705SXin Li static_assert(a[9].p == &a[9].p, "");
1663*67e74705SXin Li static_assert(a[0].p != &a[9].p, "");
1664*67e74705SXin Li static_assert(a[9].p != &a[0].p, "");
1665*67e74705SXin Li
1666*67e74705SXin Li constexpr A b[10] = {};
1667*67e74705SXin Li static_assert(b[0].p == &b[0].p, "");
1668*67e74705SXin Li static_assert(b[9].p == &b[9].p, "");
1669*67e74705SXin Li static_assert(b[0].p != &b[9].p, "");
1670*67e74705SXin Li static_assert(b[9].p != &b[0].p, "");
1671*67e74705SXin Li }
1672*67e74705SXin Li
1673*67e74705SXin Li namespace PR15884 {
1674*67e74705SXin Li struct S {};
f()1675*67e74705SXin Li constexpr S f() { return {}; }
1676*67e74705SXin Li constexpr S *p = &f();
1677*67e74705SXin Li // expected-error@-1 {{taking the address of a temporary}}
1678*67e74705SXin Li // expected-error@-2 {{constexpr variable 'p' must be initialized by a constant expression}}
1679*67e74705SXin Li // expected-note@-3 {{pointer to temporary is not a constant expression}}
1680*67e74705SXin Li // expected-note@-4 {{temporary created here}}
1681*67e74705SXin Li }
1682*67e74705SXin Li
1683*67e74705SXin Li namespace AfterError {
1684*67e74705SXin Li // FIXME: Suppress the 'no return statements' diagnostic if the body is invalid.
error()1685*67e74705SXin Li constexpr int error() { // expected-error {{no return statement}}
1686*67e74705SXin Li return foobar; // expected-error {{undeclared identifier}}
1687*67e74705SXin Li }
1688*67e74705SXin Li constexpr int k = error(); // expected-error {{must be initialized by a constant expression}}
1689*67e74705SXin Li }
1690*67e74705SXin Li
1691*67e74705SXin Li namespace std {
1692*67e74705SXin Li typedef decltype(sizeof(int)) size_t;
1693*67e74705SXin Li
1694*67e74705SXin Li template <class _E>
1695*67e74705SXin Li class initializer_list
1696*67e74705SXin Li {
1697*67e74705SXin Li const _E* __begin_;
1698*67e74705SXin Li size_t __size_;
1699*67e74705SXin Li
initializer_list(const _E * __b,size_t __s)1700*67e74705SXin Li constexpr initializer_list(const _E* __b, size_t __s)
1701*67e74705SXin Li : __begin_(__b),
1702*67e74705SXin Li __size_(__s)
1703*67e74705SXin Li {}
1704*67e74705SXin Li
1705*67e74705SXin Li public:
1706*67e74705SXin Li typedef _E value_type;
1707*67e74705SXin Li typedef const _E& reference;
1708*67e74705SXin Li typedef const _E& const_reference;
1709*67e74705SXin Li typedef size_t size_type;
1710*67e74705SXin Li
1711*67e74705SXin Li typedef const _E* iterator;
1712*67e74705SXin Li typedef const _E* const_iterator;
1713*67e74705SXin Li
initializer_list()1714*67e74705SXin Li constexpr initializer_list() : __begin_(nullptr), __size_(0) {}
1715*67e74705SXin Li
size() const1716*67e74705SXin Li constexpr size_t size() const {return __size_;}
begin() const1717*67e74705SXin Li constexpr const _E* begin() const {return __begin_;}
end() const1718*67e74705SXin Li constexpr const _E* end() const {return __begin_ + __size_;}
1719*67e74705SXin Li };
1720*67e74705SXin Li }
1721*67e74705SXin Li
1722*67e74705SXin Li namespace InitializerList {
sum(const int * b,const int * e)1723*67e74705SXin Li constexpr int sum(const int *b, const int *e) {
1724*67e74705SXin Li return b != e ? *b + sum(b+1, e) : 0;
1725*67e74705SXin Li }
sum(std::initializer_list<int> ints)1726*67e74705SXin Li constexpr int sum(std::initializer_list<int> ints) {
1727*67e74705SXin Li return sum(ints.begin(), ints.end());
1728*67e74705SXin Li }
1729*67e74705SXin Li static_assert(sum({1, 2, 3, 4, 5}) == 15, "");
1730*67e74705SXin Li
1731*67e74705SXin Li static_assert(*std::initializer_list<int>{1, 2, 3}.begin() == 1, "");
1732*67e74705SXin Li static_assert(std::initializer_list<int>{1, 2, 3}.begin()[2] == 3, "");
1733*67e74705SXin Li }
1734*67e74705SXin Li
1735*67e74705SXin Li namespace StmtExpr {
1736*67e74705SXin Li struct A { int k; };
f()1737*67e74705SXin Li void f() {
1738*67e74705SXin Li static_assert(({ const int x = 5; x * 3; }) == 15, ""); // expected-warning {{extension}}
1739*67e74705SXin Li constexpr auto a = ({ A(); }); // expected-warning {{extension}}
1740*67e74705SXin Li }
g(int k)1741*67e74705SXin Li constexpr int g(int k) {
1742*67e74705SXin Li return ({ // expected-warning {{extension}}
1743*67e74705SXin Li const int x = k;
1744*67e74705SXin Li x * x;
1745*67e74705SXin Li });
1746*67e74705SXin Li }
1747*67e74705SXin Li static_assert(g(123) == 15129, "");
h()1748*67e74705SXin Li constexpr int h() { // expected-error {{never produces a constant}}
1749*67e74705SXin Li return ({ // expected-warning {{extension}}
1750*67e74705SXin Li return 0; // expected-note {{not supported}}
1751*67e74705SXin Li 1;
1752*67e74705SXin Li });
1753*67e74705SXin Li }
1754*67e74705SXin Li }
1755*67e74705SXin Li
1756*67e74705SXin Li namespace VirtualFromBase {
1757*67e74705SXin Li struct S1 {
1758*67e74705SXin Li virtual int f() const;
1759*67e74705SXin Li };
1760*67e74705SXin Li struct S2 {
1761*67e74705SXin Li virtual int f();
1762*67e74705SXin Li };
1763*67e74705SXin Li template <typename T> struct X : T {
XVirtualFromBase::X1764*67e74705SXin Li constexpr X() {}
1765*67e74705SXin Li double d = 0.0;
fVirtualFromBase::X1766*67e74705SXin Li constexpr int f() { return sizeof(T); } // expected-warning {{will not be implicitly 'const' in C++14}}
1767*67e74705SXin Li };
1768*67e74705SXin Li
1769*67e74705SXin Li // Virtual f(), not OK.
1770*67e74705SXin Li constexpr X<X<S1>> xxs1;
1771*67e74705SXin Li constexpr X<S1> *p = const_cast<X<X<S1>>*>(&xxs1);
1772*67e74705SXin Li static_assert(p->f() == sizeof(X<S1>), ""); // expected-error {{constant expression}} expected-note {{virtual function call}}
1773*67e74705SXin Li
1774*67e74705SXin Li // Non-virtual f(), OK.
1775*67e74705SXin Li constexpr X<X<S2>> xxs2;
1776*67e74705SXin Li constexpr X<S2> *q = const_cast<X<X<S2>>*>(&xxs2);
1777*67e74705SXin Li static_assert(q->f() == sizeof(S2), "");
1778*67e74705SXin Li }
1779*67e74705SXin Li
1780*67e74705SXin Li namespace ConstexprConstructorRecovery {
1781*67e74705SXin Li class X {
1782*67e74705SXin Li public:
1783*67e74705SXin Li enum E : short {
1784*67e74705SXin Li headers = 0x1,
1785*67e74705SXin Li middlefile = 0x2,
1786*67e74705SXin Li choices = 0x4
1787*67e74705SXin Li };
X()1788*67e74705SXin Li constexpr X() noexcept {};
1789*67e74705SXin Li protected:
1790*67e74705SXin Li E val{0}; // expected-error {{cannot initialize a member subobject of type 'ConstexprConstructorRecovery::X::E' with an rvalue of type 'int'}}
1791*67e74705SXin Li };
1792*67e74705SXin Li constexpr X x{};
1793*67e74705SXin Li }
1794*67e74705SXin Li
1795*67e74705SXin Li namespace Lifetime {
f()1796*67e74705SXin Li void f() {
1797*67e74705SXin Li constexpr int &n = n; // expected-error {{constant expression}} expected-note {{use of reference outside its lifetime}} expected-warning {{not yet bound to a value}}
1798*67e74705SXin Li constexpr int m = m; // expected-error {{constant expression}} expected-note {{read of object outside its lifetime}}
1799*67e74705SXin Li }
1800*67e74705SXin Li
get(int && n)1801*67e74705SXin Li constexpr int &get(int &&n) { return n; }
1802*67e74705SXin Li struct S {
1803*67e74705SXin Li int &&r; // expected-note 2{{declared here}}
1804*67e74705SXin Li int &s;
1805*67e74705SXin Li int t;
SLifetime::S1806*67e74705SXin Li constexpr S() : r(0), s(get(0)), t(r) {} // expected-warning {{temporary}}
SLifetime::S1807*67e74705SXin Li constexpr S(int) : r(0), s(get(0)), t(s) {} // expected-warning {{temporary}} expected-note {{read of object outside its lifetime}}
1808*67e74705SXin Li };
1809*67e74705SXin Li constexpr int k1 = S().t; // ok, int is lifetime-extended to end of constructor
1810*67e74705SXin Li constexpr int k2 = S(0).t; // expected-error {{constant expression}} expected-note {{in call}}
1811*67e74705SXin Li }
1812*67e74705SXin Li
1813*67e74705SXin Li namespace Bitfields {
1814*67e74705SXin Li struct A {
1815*67e74705SXin Li bool b : 1;
1816*67e74705SXin Li unsigned u : 5;
1817*67e74705SXin Li int n : 5;
1818*67e74705SXin Li bool b2 : 3;
1819*67e74705SXin Li unsigned u2 : 74; // expected-warning {{exceeds the width of its type}}
1820*67e74705SXin Li int n2 : 81; // expected-warning {{exceeds the width of its type}}
1821*67e74705SXin Li };
1822*67e74705SXin Li
1823*67e74705SXin Li constexpr A a = { false, 33, 31, false, 0xffffffff, 0x7fffffff }; // expected-warning 2{{truncation}}
1824*67e74705SXin Li static_assert(a.b == 0 && a.u == 1 && a.n == -1 && a.b2 == 0 &&
1825*67e74705SXin Li a.u2 + 1 == 0 && a.n2 == 0x7fffffff,
1826*67e74705SXin Li "bad truncation of bitfield values");
1827*67e74705SXin Li
1828*67e74705SXin Li struct B {
1829*67e74705SXin Li int n : 3;
BBitfields::B1830*67e74705SXin Li constexpr B(int k) : n(k) {}
1831*67e74705SXin Li };
1832*67e74705SXin Li static_assert(B(3).n == 3, "");
1833*67e74705SXin Li static_assert(B(4).n == -4, "");
1834*67e74705SXin Li static_assert(B(7).n == -1, "");
1835*67e74705SXin Li static_assert(B(8).n == 0, "");
1836*67e74705SXin Li static_assert(B(-1).n == -1, "");
1837*67e74705SXin Li static_assert(B(-8889).n == -1, "");
1838*67e74705SXin Li
1839*67e74705SXin Li namespace PR16755 {
1840*67e74705SXin Li struct X {
1841*67e74705SXin Li int x : 1;
fBitfields::PR16755::X1842*67e74705SXin Li constexpr static int f(int x) {
1843*67e74705SXin Li return X{x}.x;
1844*67e74705SXin Li }
1845*67e74705SXin Li };
1846*67e74705SXin Li static_assert(X::f(3) == -1, "3 should truncate to -1");
1847*67e74705SXin Li }
1848*67e74705SXin Li }
1849*67e74705SXin Li
1850*67e74705SXin Li namespace ZeroSizeTypes {
1851*67e74705SXin Li constexpr int (*p1)[0] = 0, (*p2)[0] = 0;
1852*67e74705SXin Li constexpr int k = p2 - p1;
1853*67e74705SXin Li // expected-error@-1 {{constexpr variable 'k' must be initialized by a constant expression}}
1854*67e74705SXin Li // expected-note@-2 {{subtraction of pointers to type 'int [0]' of zero size}}
1855*67e74705SXin Li
1856*67e74705SXin Li int arr[5][0];
f()1857*67e74705SXin Li constexpr int f() { // expected-error {{never produces a constant expression}}
1858*67e74705SXin Li return &arr[3] - &arr[0]; // expected-note {{subtraction of pointers to type 'int [0]' of zero size}}
1859*67e74705SXin Li }
1860*67e74705SXin Li }
1861*67e74705SXin Li
1862*67e74705SXin Li namespace BadDefaultInit {
1863*67e74705SXin Li template<int N> struct X { static const int n = N; };
1864*67e74705SXin Li
1865*67e74705SXin Li struct A {
1866*67e74705SXin Li int k = // expected-error {{cannot use defaulted default constructor of 'A' within the class outside of member functions because 'k' has an initializer}}
1867*67e74705SXin Li X<A().k>::n; // expected-error {{not a constant expression}} expected-note {{implicit default constructor for 'BadDefaultInit::A' first required here}}
1868*67e74705SXin Li };
1869*67e74705SXin Li
1870*67e74705SXin Li // FIXME: The "constexpr constructor must initialize all members" diagnostic
1871*67e74705SXin Li // here is bogus (we discard the k(k) initializer because the parameter 'k'
1872*67e74705SXin Li // has been marked invalid).
1873*67e74705SXin Li struct B { // expected-note 2{{candidate}}
BBadDefaultInit::B1874*67e74705SXin Li constexpr B( // expected-error {{must initialize all members}} expected-note {{candidate}}
1875*67e74705SXin Li int k = X<B().k>::n) : // expected-error {{no matching constructor}}
1876*67e74705SXin Li k(k) {}
1877*67e74705SXin Li int k; // expected-note {{not initialized}}
1878*67e74705SXin Li };
1879*67e74705SXin Li }
1880*67e74705SXin Li
1881*67e74705SXin Li namespace NeverConstantTwoWays {
1882*67e74705SXin Li // If we see something non-constant but foldable followed by something
1883*67e74705SXin Li // non-constant and not foldable, we want the first diagnostic, not the
1884*67e74705SXin Li // second.
f(int n)1885*67e74705SXin Li constexpr int f(int n) { // expected-error {{never produces a constant expression}}
1886*67e74705SXin Li return (int *)(long)&n == &n ? // expected-note {{reinterpret_cast}}
1887*67e74705SXin Li 1 / 0 : // expected-warning {{division by zero}}
1888*67e74705SXin Li 0;
1889*67e74705SXin Li }
1890*67e74705SXin Li
1891*67e74705SXin Li constexpr int n = // expected-error {{must be initialized by a constant expression}}
1892*67e74705SXin Li (int *)(long)&n == &n ? // expected-note {{reinterpret_cast}}
1893*67e74705SXin Li 1 / 0 : // expected-warning {{division by zero}}
1894*67e74705SXin Li 0;
1895*67e74705SXin Li }
1896*67e74705SXin Li
1897*67e74705SXin Li namespace PR17800 {
1898*67e74705SXin Li struct A {
operator ()PR17800::A1899*67e74705SXin Li constexpr int operator()() const { return 0; }
1900*67e74705SXin Li };
sink(T...)1901*67e74705SXin Li template <typename ...T> constexpr int sink(T ...) {
1902*67e74705SXin Li return 0;
1903*67e74705SXin Li }
run()1904*67e74705SXin Li template <int ...N> constexpr int run() {
1905*67e74705SXin Li return sink(A()() + N ...);
1906*67e74705SXin Li }
1907*67e74705SXin Li constexpr int k = run<1, 2, 3>();
1908*67e74705SXin Li }
1909*67e74705SXin Li
1910*67e74705SXin Li namespace BuiltinStrlen {
1911*67e74705SXin Li constexpr const char *a = "foo\0quux";
1912*67e74705SXin Li constexpr char b[] = "foo\0quux";
f()1913*67e74705SXin Li constexpr int f() { return 'u'; }
1914*67e74705SXin Li constexpr char c[] = { 'f', 'o', 'o', 0, 'q', f(), 'u', 'x', 0 };
1915*67e74705SXin Li
1916*67e74705SXin Li static_assert(__builtin_strlen("foo") == 3, "");
1917*67e74705SXin Li static_assert(__builtin_strlen("foo\0quux") == 3, "");
1918*67e74705SXin Li static_assert(__builtin_strlen("foo\0quux" + 4) == 4, "");
1919*67e74705SXin Li
check(const char * p)1920*67e74705SXin Li constexpr bool check(const char *p) {
1921*67e74705SXin Li return __builtin_strlen(p) == 3 &&
1922*67e74705SXin Li __builtin_strlen(p + 1) == 2 &&
1923*67e74705SXin Li __builtin_strlen(p + 2) == 1 &&
1924*67e74705SXin Li __builtin_strlen(p + 3) == 0 &&
1925*67e74705SXin Li __builtin_strlen(p + 4) == 4 &&
1926*67e74705SXin Li __builtin_strlen(p + 5) == 3 &&
1927*67e74705SXin Li __builtin_strlen(p + 6) == 2 &&
1928*67e74705SXin Li __builtin_strlen(p + 7) == 1 &&
1929*67e74705SXin Li __builtin_strlen(p + 8) == 0;
1930*67e74705SXin Li }
1931*67e74705SXin Li
1932*67e74705SXin Li static_assert(check(a), "");
1933*67e74705SXin Li static_assert(check(b), "");
1934*67e74705SXin Li static_assert(check(c), "");
1935*67e74705SXin Li
1936*67e74705SXin Li constexpr int over1 = __builtin_strlen(a + 9); // expected-error {{constant expression}} expected-note {{one-past-the-end}}
1937*67e74705SXin Li constexpr int over2 = __builtin_strlen(b + 9); // expected-error {{constant expression}} expected-note {{one-past-the-end}}
1938*67e74705SXin Li constexpr int over3 = __builtin_strlen(c + 9); // expected-error {{constant expression}} expected-note {{one-past-the-end}}
1939*67e74705SXin Li
1940*67e74705SXin Li constexpr int under1 = __builtin_strlen(a - 1); // expected-error {{constant expression}} expected-note {{cannot refer to element -1}}
1941*67e74705SXin Li constexpr int under2 = __builtin_strlen(b - 1); // expected-error {{constant expression}} expected-note {{cannot refer to element -1}}
1942*67e74705SXin Li constexpr int under3 = __builtin_strlen(c - 1); // expected-error {{constant expression}} expected-note {{cannot refer to element -1}}
1943*67e74705SXin Li
1944*67e74705SXin Li // FIXME: The diagnostic here could be better.
1945*67e74705SXin Li constexpr char d[] = { 'f', 'o', 'o' }; // no nul terminator.
1946*67e74705SXin Li constexpr int bad = __builtin_strlen(d); // expected-error {{constant expression}} expected-note {{one-past-the-end}}
1947*67e74705SXin Li }
1948*67e74705SXin Li
1949*67e74705SXin Li namespace PR19010 {
1950*67e74705SXin Li struct Empty {};
1951*67e74705SXin Li struct Empty2 : Empty {};
1952*67e74705SXin Li struct Test : Empty2 {
TestPR19010::Test1953*67e74705SXin Li constexpr Test() {}
1954*67e74705SXin Li Empty2 array[2];
1955*67e74705SXin Li };
test()1956*67e74705SXin Li void test() { constexpr Test t; }
1957*67e74705SXin Li }
1958*67e74705SXin Li
PR21327(int a,int b)1959*67e74705SXin Li void PR21327(int a, int b) {
1960*67e74705SXin Li static_assert(&a + 1 != &b, ""); // expected-error {{constant expression}}
1961*67e74705SXin Li }
1962*67e74705SXin Li
1963*67e74705SXin Li namespace EmptyClass {
1964*67e74705SXin Li struct E1 {} e1;
1965*67e74705SXin Li union E2 {} e2; // expected-note {{here}}
1966*67e74705SXin Li struct E3 : E1 {} e3;
1967*67e74705SXin Li
1968*67e74705SXin Li // The defaulted copy constructor for an empty class does not read any
1969*67e74705SXin Li // members. The defaulted copy constructor for an empty union reads the
1970*67e74705SXin Li // object representation.
1971*67e74705SXin Li constexpr E1 e1b(e1);
1972*67e74705SXin Li constexpr E2 e2b(e2); // expected-error {{constant expression}} expected-note{{read of non-const}} expected-note {{in call}}
1973*67e74705SXin Li constexpr E3 e3b(e3);
1974*67e74705SXin Li }
1975*67e74705SXin Li
1976*67e74705SXin Li namespace PR21786 {
1977*67e74705SXin Li extern void (*start[])();
1978*67e74705SXin Li extern void (*end[])();
1979*67e74705SXin Li static_assert(&start != &end, ""); // expected-error {{constant expression}}
1980*67e74705SXin Li static_assert(&start != nullptr, "");
1981*67e74705SXin Li
1982*67e74705SXin Li struct Foo;
1983*67e74705SXin Li struct Bar {
1984*67e74705SXin Li static const Foo x;
1985*67e74705SXin Li static const Foo y;
1986*67e74705SXin Li };
1987*67e74705SXin Li static_assert(&Bar::x != nullptr, "");
1988*67e74705SXin Li static_assert(&Bar::x != &Bar::y, "");
1989*67e74705SXin Li }
1990*67e74705SXin Li
1991*67e74705SXin Li namespace PR21859 {
Fun()1992*67e74705SXin Li constexpr int Fun() { return; } // expected-error {{non-void constexpr function 'Fun' should return a value}}
1993*67e74705SXin Li constexpr int Var = Fun(); // expected-error {{constexpr variable 'Var' must be initialized by a constant expression}}
1994*67e74705SXin Li }
1995*67e74705SXin Li
1996*67e74705SXin Li struct InvalidRedef {
1997*67e74705SXin Li int f; // expected-note{{previous definition is here}}
1998*67e74705SXin Li constexpr int f(void); // expected-error{{redefinition of 'f'}} expected-warning{{will not be implicitly 'const'}}
1999*67e74705SXin Li };
2000*67e74705SXin Li
2001*67e74705SXin Li namespace PR17938 {
f(T const & x)2002*67e74705SXin Li template <typename T> constexpr T const &f(T const &x) { return x; }
2003*67e74705SXin Li
2004*67e74705SXin Li struct X {};
2005*67e74705SXin Li struct Y : X {};
ZPR17938::Z2006*67e74705SXin Li struct Z : Y { constexpr Z() {} };
2007*67e74705SXin Li
2008*67e74705SXin Li static constexpr auto z = f(Z());
2009*67e74705SXin Li }
2010*67e74705SXin Li
2011*67e74705SXin Li namespace PR24597 {
2012*67e74705SXin Li struct A {
2013*67e74705SXin Li int x, *p;
APR24597::A2014*67e74705SXin Li constexpr A() : x(0), p(&x) {}
APR24597::A2015*67e74705SXin Li constexpr A(const A &a) : x(a.x), p(&x) {}
2016*67e74705SXin Li };
f()2017*67e74705SXin Li constexpr A f() { return A(); }
g()2018*67e74705SXin Li constexpr A g() { return f(); }
2019*67e74705SXin Li constexpr int a = *f().p;
2020*67e74705SXin Li constexpr int b = *g().p;
2021*67e74705SXin Li }
2022*67e74705SXin Li
2023*67e74705SXin Li namespace IncompleteClass {
2024*67e74705SXin Li struct XX {
fIncompleteClass::XX2025*67e74705SXin Li static constexpr int f(XX*) { return 1; } // expected-note {{here}}
g(XX *)2026*67e74705SXin Li friend constexpr int g(XX*) { return 2; } // expected-note {{here}}
2027*67e74705SXin Li
2028*67e74705SXin Li static constexpr int i = f(static_cast<XX*>(nullptr)); // expected-error {{constexpr variable 'i' must be initialized by a constant expression}} expected-note {{undefined function 'f' cannot be used in a constant expression}}
2029*67e74705SXin Li static constexpr int j = g(static_cast<XX*>(nullptr)); // expected-error {{constexpr variable 'j' must be initialized by a constant expression}} expected-note {{undefined function 'g' cannot be used in a constant expression}}
2030*67e74705SXin Li };
2031*67e74705SXin Li }
2032*67e74705SXin Li
2033*67e74705SXin Li namespace InheritedCtor {
AInheritedCtor::A2034*67e74705SXin Li struct A { constexpr A(int) {} };
2035*67e74705SXin Li
2036*67e74705SXin Li struct B : A { int n; using A::A; }; // expected-note {{here}}
2037*67e74705SXin Li constexpr B b(0); // expected-error {{constant expression}} expected-note {{derived class}}
2038*67e74705SXin Li
2039*67e74705SXin Li struct C : A { using A::A; struct { union { int n, m = 0; }; union { int a = 0; }; int k = 0; }; struct {}; union {}; }; // expected-warning 4{{extension}}
2040*67e74705SXin Li constexpr C c(0);
2041*67e74705SXin Li
2042*67e74705SXin Li struct D : A {
2043*67e74705SXin Li using A::A; // expected-note {{here}}
2044*67e74705SXin Li struct { // expected-warning {{extension}}
2045*67e74705SXin Li union { // expected-warning {{extension}}
2046*67e74705SXin Li int n;
2047*67e74705SXin Li };
2048*67e74705SXin Li };
2049*67e74705SXin Li };
2050*67e74705SXin Li constexpr D d(0); // expected-error {{constant expression}} expected-note {{derived class}}
2051*67e74705SXin Li
2052*67e74705SXin Li struct E : virtual A { using A::A; }; // expected-note {{here}}
2053*67e74705SXin Li // We wrap a function around this to avoid implicit zero-initialization
2054*67e74705SXin Li // happening first; the zero-initialization step would produce the same
2055*67e74705SXin Li // error and defeat the point of this test.
f()2056*67e74705SXin Li void f() {
2057*67e74705SXin Li constexpr E e(0); // expected-error {{constant expression}} expected-note {{derived class}}
2058*67e74705SXin Li }
2059*67e74705SXin Li // FIXME: This produces a note with no source location.
2060*67e74705SXin Li //constexpr E e(0);
2061*67e74705SXin Li
WInheritedCtor::W2062*67e74705SXin Li struct W { constexpr W(int n) : w(n) {} int w; };
2063*67e74705SXin Li struct X : W { using W::W; int x = 2; };
2064*67e74705SXin Li struct Y : X { using X::X; int y = 3; };
2065*67e74705SXin Li struct Z : Y { using Y::Y; int z = 4; };
2066*67e74705SXin Li constexpr Z z(1);
2067*67e74705SXin Li static_assert(z.w == 1 && z.x == 2 && z.y == 3 && z.z == 4, "");
2068*67e74705SXin Li }
2069