• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // RUN: %clang_cc1 -std=c++11 -verify %s
2 
3 namespace UseBeforeDefinition {
4   struct A {
getUseBeforeDefinition::A5     template<typename T> static constexpr T get() { return T(); }
6     // ok, not a constant expression.
7     int n = get<int>();
8   };
9 
10   // ok, constant expression.
11   constexpr int j = A::get<int>();
12 
13   template<typename T> constexpr int consume(T);
14   // ok, not a constant expression.
15   const int k = consume(0); // expected-note {{here}}
16 
consume(T)17   template<typename T> constexpr int consume(T) { return 0; }
18   // ok, constant expression.
19   constexpr int l = consume(0);
20 
21   constexpr int m = k; // expected-error {{constant expression}} expected-note {{initializer of 'k'}}
22 }
23 
24 namespace IntegralConst {
f(T n)25   template<typename T> constexpr T f(T n) { return n; }
26   enum E {
27     v = f(0), w = f(1) // ok
28   };
29   static_assert(w == 1, "");
30 
31   char arr[f('x')]; // ok
32   static_assert(sizeof(arr) == 'x', "");
33 }
34 
35 namespace ConvertedConst {
f(T n)36   template<typename T> constexpr T f(T n) { return n; }
f()37   int f() {
38     switch (f()) {
39       case f(4): return 0;
40     }
41     return 1;
42   }
43 }
44 
45 namespace OverloadResolution {
f(T t)46   template<typename T> constexpr T f(T t) { return t; }
47 
48   template<int n> struct S { };
49 
50   template<typename T> auto g(T t) -> S<f(sizeof(T))> &;
51   char &f(...);
52 
h(T t[f (sizeof (T))])53   template<typename T> auto h(T t[f(sizeof(T))]) -> decltype(&*t) {
54     return t;
55   }
56 
57   S<4> &k = g(0);
58   int *p, *q = h(p);
59 }
60 
61 namespace DataMember {
62   template<typename T> struct S { static const int k; };
63   const int n = S<int>::k; // expected-note {{here}}
64   template<typename T> const int S<T>::k = 0;
65   constexpr int m = S<int>::k; // ok
66   constexpr int o = n; // expected-error {{constant expression}} expected-note {{initializer of 'n'}}
67 }
68 
69 namespace Reference {
70   const int k = 5;
71   template<typename T> struct S {
72     static volatile int &r;
73   };
74   template<typename T> volatile int &S<T>::r = const_cast<volatile int&>(k);
75   constexpr int n = const_cast<int&>(S<int>::r);
76   static_assert(n == 5, "");
77 }
78