1// RUN: %clang_cc1 -fsyntax-only -verify %s
2
3void abort() __attribute__((noreturn));
4
5class Okay {
6  int a_;
7};
8
9class Virtual {
10  virtual void foo() { abort(); } // expected-note 4 {{because type 'Virtual' has a virtual member function}}
11};
12
13class VirtualBase : virtual Okay { // expected-note 4 {{because type 'VirtualBase' has a virtual base class}}
14};
15
16class Ctor {
17  Ctor() { abort(); } // expected-note 2{{because type 'Ctor' has a user-provided default constructor}} expected-note 2{{here}}
18};
19class Ctor2 {
20  Ctor2(); // expected-note {{because type 'Ctor2' has a user-provided default constructor}} expected-note 2{{here}}
21};
22class CtorTmpl { // expected-note {{because type 'CtorTmpl' has no default constructor}}
23  template<typename T> CtorTmpl(); // expected-note {{implicit default constructor suppressed by user-declared constructor}}
24};
25
26class CopyCtor { // expected-note 2{{because no constructor can be used to copy an object of type 'const CopyCtor'}}
27  CopyCtor(CopyCtor &cc) { abort(); }
28};
29
30class CopyAssign { // expected-note 2 {{because no assignment operator can be used to copy an object of type 'const CopyAssign'}}
31  CopyAssign& operator=(CopyAssign& CA) { abort(); }
32};
33
34class Dtor {
35  ~Dtor() { abort(); } // expected-note 2 {{because type 'Dtor' has a user-provided destructor}} expected-note 2{{here}}
36};
37
38union U1 {
39  Virtual v; // expected-error {{union member 'v' has a non-trivial copy constructor}}
40  VirtualBase vbase; // expected-error {{union member 'vbase' has a non-trivial copy constructor}}
41  Ctor ctor; // expected-error {{union member 'ctor' has a non-trivial constructor}}
42  Ctor2 ctor2; // expected-error {{union member 'ctor2' has a non-trivial constructor}}
43  CtorTmpl ctortmpl; // expected-error {{union member 'ctortmpl' has a non-trivial constructor}}
44  CopyCtor copyctor; // expected-error {{union member 'copyctor' has a non-trivial copy constructor}}
45  CopyAssign copyassign; // expected-error {{union member 'copyassign' has a non-trivial copy assignment operator}}
46  Dtor dtor; // expected-error {{union member 'dtor' has a non-trivial destructor}}
47  Okay okay;
48};
49
50union U2 {
51  struct {
52    Virtual v; // expected-note {{because the function selected to copy field of type 'Virtual' is not trivial}}
53  } m1; // expected-error {{union member 'm1' has a non-trivial copy constructor}}
54  struct {
55    VirtualBase vbase; // expected-note {{because the function selected to copy field of type 'VirtualBase' is not trivial}}
56  } m2; // expected-error {{union member 'm2' has a non-trivial copy constructor}}
57  struct {
58    Ctor ctor; // expected-note {{because field of type 'Ctor' has a user-provided default constructor}}
59  } m3; // expected-error {{union member 'm3' has a non-trivial constructor}}
60  struct {
61    Ctor2 ctor2; // expected-note {{because field of type 'Ctor2' has a user-provided default constructor}}
62  } m3a; // expected-error {{union member 'm3a' has a non-trivial constructor}}
63  struct { // expected-note {{no constructor can be used to copy an object of type 'const}}
64    CopyCtor copyctor;
65  } m4; // expected-error {{union member 'm4' has a non-trivial copy constructor}}
66  struct { // expected-note {{no assignment operator can be used to copy an object of type 'const}}
67    CopyAssign copyassign;
68  } m5; // expected-error {{union member 'm5' has a non-trivial copy assignment operator}}
69  struct {
70    Dtor dtor; // expected-note {{because field of type 'Dtor' has a user-provided destructor}}
71  } m6; // expected-error {{union member 'm6' has a non-trivial destructor}}
72  struct {
73    Okay okay;
74  } m7;
75};
76
77union U3 {
78  struct s1 : Virtual { // expected-note {{because the function selected to copy base class of type 'Virtual' is not trivial}}
79  } m1; // expected-error {{union member 'm1' has a non-trivial copy constructor}}
80  struct s2 : VirtualBase { // expected-note {{because the function selected to copy base class of type 'VirtualBase' is not trivial}}
81  } m2; // expected-error {{union member 'm2' has a non-trivial copy constructor}}
82  struct s3 : Ctor { // expected-note {{because base class of type 'Ctor' has a user-provided default constructor}}
83  } m3; // expected-error {{union member 'm3' has a non-trivial constructor}}
84  struct s3a : Ctor2 { // expected-note {{because base class of type 'Ctor2' has a user-provided default constructor}}
85  } m3a; // expected-error {{union member 'm3a' has a non-trivial constructor}}
86  struct s4 : CopyCtor { // expected-note {{because no constructor can be used to copy an object of type 'const U3::s4'}}
87  } m4; // expected-error {{union member 'm4' has a non-trivial copy constructor}}
88  struct s5 : CopyAssign { // expected-note {{because no assignment operator can be used to copy an object of type 'const U3::s5'}}
89  } m5; // expected-error {{union member 'm5' has a non-trivial copy assignment operator}}
90  struct s6 : Dtor { // expected-note {{because base class of type 'Dtor' has a user-provided destructor}}
91  } m6; // expected-error {{union member 'm6' has a non-trivial destructor}}
92  struct s7 : Okay {
93  } m7;
94  struct s8 {
95    s8(...) = delete; // expected-note {{because it is a variadic function}} expected-warning {{C++11}}
96  } m8; // expected-error {{union member 'm8' has a non-trivial constructor}}
97};
98
99union U4 {
100  static int i1; // expected-warning {{static data member 'i1' in union is a C++11 extension}}
101};
102int U4::i1 = 10;
103
104union U5 {
105  int& i1; // expected-error {{union member 'i1' has reference type 'int &'}}
106};
107
108union U6 {
109  struct S {
110    int &i;
111  } s; // ok
112};
113
114template <class A, class B> struct Either {
115  bool tag;
116  union { // expected-note 6 {{in instantiation of member class}}
117    A a;
118    B b; // expected-error 6 {{non-trivial}}
119  };
120
121  Either(const A& a) : tag(true), a(a) {}
122  Either(const B& b) : tag(false), b(b) {}
123};
124
125void fred() {
126  Either<int,Virtual> virt(0); // expected-note {{in instantiation of template}}
127  Either<int,VirtualBase> vbase(0); // expected-note {{in instantiation of template}}
128  Either<int,Ctor> ctor(0); // expected-note {{in instantiation of template}}
129  Either<int,CopyCtor> copyctor(0); // expected-note {{in instantiation of template}}
130  Either<int,CopyAssign> copyassign(0); // expected-note {{in instantiation of template}}
131  Either<int,Dtor> dtor(0); // expected-note {{in instantiation of template}}
132  Either<int,Okay> okay(0);
133}
134