xref: /aosp_15_r20/external/clang/test/SemaCXX/dcl_init_aggr.cpp (revision 67e74705e28f6214e480b399dd47ea732279e315)
1*67e74705SXin Li // RUN: %clang_cc1 -fsyntax-only -pedantic -verify %s
2*67e74705SXin Li // RUN: %clang_cc1 -fsyntax-only -pedantic -verify -std=c++98 %s
3*67e74705SXin Li // RUN: %clang_cc1 -fsyntax-only -pedantic -verify -std=c++11 %s
4*67e74705SXin Li // C++ [dcl.init.aggr]p2
5*67e74705SXin Li struct A {
6*67e74705SXin Li   int x;
7*67e74705SXin Li   struct B {
8*67e74705SXin Li     int i;
9*67e74705SXin Li     int j;
10*67e74705SXin Li   } b;
11*67e74705SXin Li } a1 = { 1, { 2, 3 } };
12*67e74705SXin Li 
13*67e74705SXin Li struct NonAggregate {
14*67e74705SXin Li #if __cplusplus >= 201103L
15*67e74705SXin Li // expected-note@-2 3 {{candidate constructor (the implicit copy constructor) not viable}}
16*67e74705SXin Li // expected-note@-3 3 {{candidate constructor (the implicit move constructor) not viable}}
17*67e74705SXin Li #endif
18*67e74705SXin Li   NonAggregate();
19*67e74705SXin Li #if __cplusplus >= 201103L
20*67e74705SXin Li // expected-note@-2 3 {{candidate constructor not viable: requires 0 arguments, but 2 were provided}}
21*67e74705SXin Li #endif
22*67e74705SXin Li   int a, b;
23*67e74705SXin Li };
24*67e74705SXin Li NonAggregate non_aggregate_test = { 1, 2 };
25*67e74705SXin Li #if __cplusplus <= 199711L
26*67e74705SXin Li // expected-error@-2 {{non-aggregate type 'NonAggregate' cannot be initialized with an initializer list}}
27*67e74705SXin Li #else
28*67e74705SXin Li // expected-error@-4 {{no matching constructor for initialization of 'NonAggregate'}}
29*67e74705SXin Li #endif
30*67e74705SXin Li 
31*67e74705SXin Li NonAggregate non_aggregate_test2[2] = { { 1, 2 }, { 3, 4 } };
32*67e74705SXin Li #if __cplusplus <= 199711L
33*67e74705SXin Li // expected-error@-2 2 {{non-aggregate type 'NonAggregate' cannot be initialized with an initializer list}}
34*67e74705SXin Li #else
35*67e74705SXin Li // expected-error@-4 2 {{no matching constructor for initialization of 'NonAggregate'}}
36*67e74705SXin Li #endif
37*67e74705SXin Li 
38*67e74705SXin Li // C++ [dcl.init.aggr]p3
39*67e74705SXin Li A a_init = A();
40*67e74705SXin Li 
41*67e74705SXin Li // C++ [dcl.init.aggr]p4
42*67e74705SXin Li int x[] = { 1, 3, 5 };
43*67e74705SXin Li int x_sizecheck[(sizeof(x) / sizeof(int)) == 3? 1 : -1];
44*67e74705SXin Li int x2[] = { }; // expected-warning{{zero size arrays are an extension}}
45*67e74705SXin Li 
46*67e74705SXin Li // C++ [dcl.init.aggr]p5
47*67e74705SXin Li struct StaticMemberTest {
48*67e74705SXin Li   int i;
49*67e74705SXin Li   static int s;
50*67e74705SXin Li   int *j;
51*67e74705SXin Li } smt = { 1, &smt.i };
52*67e74705SXin Li 
53*67e74705SXin Li // C++ [dcl.init.aggr]p6
54*67e74705SXin Li char cv[4] = { 'a', 's', 'd', 'f', 0 }; // expected-error{{excess elements in array initializer}}
55*67e74705SXin Li 
56*67e74705SXin Li // C++ [dcl.init.aggr]p7
57*67e74705SXin Li struct TooFew { int a; char* b; int c; };
58*67e74705SXin Li TooFew too_few = { 1, "asdf" };
59*67e74705SXin Li #if __cplusplus <= 199711L
60*67e74705SXin Li // expected-warning@-2 {{conversion from string literal to 'char *' is deprecated}}
61*67e74705SXin Li #else
62*67e74705SXin Li // expected-warning@-4 {{ISO C++11 does not allow conversion from string literal to 'char *'}}
63*67e74705SXin Li #endif
64*67e74705SXin Li 
65*67e74705SXin Li struct NoDefaultConstructor {
66*67e74705SXin Li #if __cplusplus <= 199711L
67*67e74705SXin Li // expected-note@-2 3 {{candidate constructor (the implicit copy constructor)}}
68*67e74705SXin Li // expected-note@-3 {{declared here}}
69*67e74705SXin Li #else
70*67e74705SXin Li // expected-note@-5 4 {{candidate constructor (the implicit copy constructor)}}
71*67e74705SXin Li // expected-note@-6 4 {{candidate constructor (the implicit move constructor)}}
72*67e74705SXin Li #endif
73*67e74705SXin Li 
74*67e74705SXin Li   NoDefaultConstructor(int);
75*67e74705SXin Li #if __cplusplus <= 199711L
76*67e74705SXin Li   // expected-note@-2 3 {{candidate constructor not viable: requires 1 argument, but 0 were provided}}
77*67e74705SXin Li #else
78*67e74705SXin Li   // expected-note@-4 4 {{candidate constructor not viable: requires 1 argument, but 0 were provided}}
79*67e74705SXin Li #endif
80*67e74705SXin Li 
81*67e74705SXin Li };
82*67e74705SXin Li struct TooFewError {
83*67e74705SXin Li #if __cplusplus <= 199711L
84*67e74705SXin Li // expected-error@-2 {{implicit default constructor for}}
85*67e74705SXin Li #endif
86*67e74705SXin Li 
87*67e74705SXin Li   int a;
88*67e74705SXin Li   NoDefaultConstructor nodef;
89*67e74705SXin Li #if __cplusplus <= 199711L
90*67e74705SXin Li // expected-note@-2 {{member is declared here}}
91*67e74705SXin Li // expected-note@-3 2{{in implicit initialization of field 'nodef' with omitted initializer}}
92*67e74705SXin Li #else
93*67e74705SXin Li // expected-note@-5 3{{in implicit initialization of field 'nodef' with omitted initializer}}
94*67e74705SXin Li #endif
95*67e74705SXin Li };
96*67e74705SXin Li TooFewError too_few_okay = { 1, 1 };
97*67e74705SXin Li TooFewError too_few_error = { 1 }; // expected-error{{no matching constructor}}
98*67e74705SXin Li 
99*67e74705SXin Li TooFewError too_few_okay2[2] = { 1, 1 };
100*67e74705SXin Li #if __cplusplus <= 199711L
101*67e74705SXin Li // expected-note@-2 {{implicit default constructor for 'TooFewError' first required here}}
102*67e74705SXin Li #else
103*67e74705SXin Li // expected-error@-4 {{no matching constructor for initialization of 'NoDefaultConstructor'}}
104*67e74705SXin Li // expected-note@-5 {{in implicit initialization of array element 1 with omitted initializer}}
105*67e74705SXin Li #endif
106*67e74705SXin Li 
107*67e74705SXin Li TooFewError too_few_error2[2] = { 1 }; // expected-error{{no matching constructor}}
108*67e74705SXin Li 
109*67e74705SXin Li NoDefaultConstructor too_few_error3[3] = { }; // expected-error {{no matching constructor}} expected-note {{implicit initialization of array element 0}}
110*67e74705SXin Li 
111*67e74705SXin Li // C++ [dcl.init.aggr]p8
112*67e74705SXin Li struct Empty { };
113*67e74705SXin Li struct EmptyTest {
114*67e74705SXin Li   Empty s;
115*67e74705SXin Li   int i;
116*67e74705SXin Li } empty_test = { { }, 3 };
117*67e74705SXin Li 
118*67e74705SXin Li EmptyTest empty_test2 = { 3 }; // expected-error{{initializer for aggregate with no elements requires explicit braces}}
119*67e74705SXin Li 
120*67e74705SXin Li struct NonEmpty {
121*67e74705SXin Li   int a;
122*67e74705SXin Li   Empty empty;
123*67e74705SXin Li };
124*67e74705SXin Li struct NonEmptyTest {
125*67e74705SXin Li   NonEmpty a, b;
126*67e74705SXin Li } non_empty_test = { { }, { } };
127*67e74705SXin Li 
128*67e74705SXin Li // C++ [dcl.init.aggr]p9
129*67e74705SXin Li struct HasReference {
130*67e74705SXin Li   int i;
131*67e74705SXin Li   int &j; // expected-note{{uninitialized reference member is here}}
132*67e74705SXin Li };
133*67e74705SXin Li int global_int;
134*67e74705SXin Li HasReference r1 = { 1, global_int };
135*67e74705SXin Li HasReference r2 = { 1 } ; // expected-error{{reference member of type 'int &' uninitialized}}
136*67e74705SXin Li 
137*67e74705SXin Li // C++ [dcl.init.aggr]p10
138*67e74705SXin Li // Note: the behavior here is identical to C
139*67e74705SXin Li int xs[2][2] = { 3, 1, 4, 2 };
140*67e74705SXin Li float y[4][3] = { { 1 }, { 2 }, { 3 }, { 4 } };
141*67e74705SXin Li 
142*67e74705SXin Li // C++ [dcl.init.aggr]p11
143*67e74705SXin Li // Note: the behavior here is identical to C
144*67e74705SXin Li float y2[4][3] = { { 1, 3, 5 }, { 2, 4, 6 }, { 3, 5, 7 } };
145*67e74705SXin Li float same_as_y2[4][3] = { 1, 3, 5, 2, 4, 6, 3, 5, 7 };
146*67e74705SXin Li 
147*67e74705SXin Li // C++ [dcl.init.aggr]p12
148*67e74705SXin Li struct A2 {
149*67e74705SXin Li   int i;
150*67e74705SXin Li   operator int *();
151*67e74705SXin Li };
152*67e74705SXin Li struct B2 {
153*67e74705SXin Li   A2 a1, a2;
154*67e74705SXin Li   int *z;
155*67e74705SXin Li };
156*67e74705SXin Li struct C2 {
157*67e74705SXin Li   operator A2();
158*67e74705SXin Li };
159*67e74705SXin Li struct D2 {
160*67e74705SXin Li   operator int();
161*67e74705SXin Li };
162*67e74705SXin Li A2 a2;
163*67e74705SXin Li C2 c2;
164*67e74705SXin Li D2 d2;
165*67e74705SXin Li B2 b2 = { 4, a2, a2 };
166*67e74705SXin Li B2 b2_2 = { 4, d2, 0 };
167*67e74705SXin Li B2 b2_3 = { c2, a2, a2 };
168*67e74705SXin Li 
169*67e74705SXin Li // C++ [dcl.init.aggr]p15:
170*67e74705SXin Li union u { int a; char* b; }; // expected-note{{candidate constructor (the implicit copy constructor)}}
171*67e74705SXin Li #if __cplusplus >= 201103L
172*67e74705SXin Li // expected-note@-2 {{candidate constructor (the implicit move constructor)}}
173*67e74705SXin Li #endif
174*67e74705SXin Li 
175*67e74705SXin Li u u1 = { 1 };
176*67e74705SXin Li u u2 = u1;
177*67e74705SXin Li u u3 = 1; // expected-error{{no viable conversion}}
178*67e74705SXin Li u u4 = { 0, "asdf" };  // expected-error{{excess elements in union initializer}}
179*67e74705SXin Li u u5 = { "asdf" }; // expected-error{{cannot initialize a member subobject of type 'int' with an lvalue of type 'const char [5]'}}
180