1// RUN: %clang_cc1 -fcxx-exceptions -fexceptions -fsyntax-only -verify -std=c++11 -fms-extensions -Wno-delete-incomplete %s
2// expected-no-diagnostics
3
4#define P(e) static_assert(noexcept(e), "expected nothrow")
5#define N(e) static_assert(!noexcept(e), "expected throw")
6#define B(b, e) static_assert(b == noexcept(e), "expectation failed")
7
8void simple() {
9  P(0);
10  P(0 + 0);
11  int i;
12  P(i);
13  P(sizeof(0));
14  P(static_cast<int>(0));
15  N(throw 0);
16  N((throw 0, 0));
17}
18
19void nospec();
20void allspec() throw(...);
21void intspec() throw(int);
22void emptyspec() throw();
23void nothrowattr() __attribute__((nothrow));
24void noexcept_true() noexcept;
25void noexcept_false() noexcept(false);
26
27void call() {
28  N(nospec());
29  N(allspec());
30  N(intspec());
31  P(emptyspec());
32  P(nothrowattr());
33  P(noexcept_true());
34  N(noexcept_false());
35}
36
37void (*pnospec)();
38void (*pallspec)() throw(...);
39void (*pintspec)() throw(int);
40void (*pemptyspec)() throw();
41
42typedef void (*funcptr)();
43funcptr returnsptr() throw();
44
45void callptr() {
46  N(pnospec());
47  N((*pnospec)());
48  N(pallspec());
49  N((*pallspec)());
50  N(pintspec());
51  N((*pintspec)());
52  P(pemptyspec());
53  P((*pemptyspec)());
54  N(returnsptr()());
55}
56
57struct S1 {
58  void nospec();
59  void allspec() throw(...);
60  void intspec() throw(int);
61  void emptyspec() throw();
62};
63
64void callmem() {
65  S1 s;
66  N(s.nospec());
67  N(s.allspec());
68  N(s.intspec());
69  P(s.emptyspec());
70}
71
72void (S1::*mpnospec)();
73void (S1::*mpallspec)() throw(...);
74void (S1::*mpintspec)() throw(int);
75void (S1::*mpemptyspec)() throw();
76
77void callmemptr() {
78  S1 s;
79  N((s.*mpnospec)());
80  N((s.*mpallspec)());
81  N((s.*mpintspec)());
82  P((s.*mpemptyspec)());
83}
84
85struct S2 {
86  S2();
87  S2(int, int) throw();
88  void operator +();
89  void operator -() throw();
90  void operator +(int);
91  void operator -(int) throw();
92  operator int();
93  operator float() throw();
94};
95
96void *operator new(__typeof__(sizeof(int)) sz, int) throw();
97
98struct IncompleteStruct;
99
100struct Bad1 {
101  ~Bad1() throw(int);
102};
103struct Bad2 {
104  void operator delete(void*) throw(int);
105};
106
107typedef int X;
108
109void implicits() {
110  N(new int);
111  P(new (0) int);
112  P(delete (int*)0);
113  P(delete (IncompleteStruct*)0);
114  N(delete (Bad1*)0);
115  N(delete (Bad2*)0);
116  N(S2());
117  P(S2(0, 0));
118  S2 s;
119  N(+s);
120  P(-s);
121  N(s + 0);
122  P(s - 0);
123  N(static_cast<int>(s));
124  P(static_cast<float>(s));
125  N(Bad1());
126  P(X().~X());
127}
128
129struct V {
130  virtual ~V() throw();
131};
132struct D : V {};
133
134void dyncast() {
135  V *pv = 0;
136  D *pd = 0;
137  P(dynamic_cast<V&>(*pd));
138  P(dynamic_cast<V*>(pd));
139  N(dynamic_cast<D&>(*pv));
140  P(dynamic_cast<D*>(pv));
141}
142
143namespace std {
144  struct type_info {};
145}
146
147void idtype() {
148  P(typeid(V));
149  P(typeid((V*)0));
150  P(typeid(*(S1*)0));
151  N(typeid(*(V*)0));
152}
153
154void uneval() {
155  P(sizeof(typeid(*(V*)0)));
156  P(typeid(typeid(*(V*)0)));
157}
158
159struct G1 {};
160struct G2 { int i; };
161struct G3 { S2 s; };
162
163void gencon() {
164  P(G1());
165  P(G2());
166  N(G3());
167}
168
169template <class T> void f(T&&) noexcept;
170template <typename T, bool b>
171void late() {
172  B(b, typeid(*(T*)0));
173  B(b, T(1));
174  B(b, static_cast<T>(S2(0, 0)));
175  B(b, S1() + T());
176  P(f(T()));
177  P(new (0) T);
178  P(delete (T*)0);
179}
180struct S3 {
181  virtual ~S3() throw();
182  S3() throw();
183  explicit S3(int);
184  S3(const S2&);
185};
186template <class T> T&& f2() noexcept;
187template <typename T>
188void late2() {
189  P(dynamic_cast<S3&>(f2<T&>()));
190}
191void operator +(const S1&, float) throw();
192void operator +(const S1&, const S3&);
193void tlate() {
194  late<float, true>();
195  late<S3, false>();
196  late2<S3>();
197}
198