blob: ee45ae529961786180fd9b78be79d1d192789997 [file] [log] [blame]
Richard Trieue7f7ed22017-02-22 01:11:25 +00001// Clear and create directories
2// RUN: rm -rf %t
3// RUN: mkdir %t
4// RUN: mkdir %t/cache
5// RUN: mkdir %t/Inputs
6
7// Build first header file
8// RUN: echo "#define FIRST" >> %t/Inputs/first.h
9// RUN: cat %s >> %t/Inputs/first.h
10
11// Build second header file
12// RUN: echo "#define SECOND" >> %t/Inputs/second.h
13// RUN: cat %s >> %t/Inputs/second.h
14
15// Build module map file
16// RUN: echo "module FirstModule {" >> %t/Inputs/module.map
17// RUN: echo " header \"first.h\"" >> %t/Inputs/module.map
18// RUN: echo "}" >> %t/Inputs/module.map
19// RUN: echo "module SecondModule {" >> %t/Inputs/module.map
20// RUN: echo " header \"second.h\"" >> %t/Inputs/module.map
21// RUN: echo "}" >> %t/Inputs/module.map
22
23// Run test
Richard Trieu639d7b62017-02-22 22:22:42 +000024// RUN: %clang_cc1 -fmodules -fimplicit-module-maps -fmodules-cache-path=%t/cache -x c++ -I%t/Inputs -verify %s -std=c++1z
Richard Trieue7f7ed22017-02-22 01:11:25 +000025
26#if !defined(FIRST) && !defined(SECOND)
27#include "first.h"
28#include "second.h"
29#endif
30
31namespace AccessSpecifiers {
32#if defined(FIRST)
33struct S1 {
34};
35#elif defined(SECOND)
36struct S1 {
37 private:
38};
39#else
40S1 s1;
41// expected-error@second.h:* {{'AccessSpecifiers::S1' has different definitions in different modules; first difference is definition in module 'SecondModule' found private access specifier}}
42// expected-note@first.h:* {{but in 'FirstModule' found end of class}}
43#endif
44
45#if defined(FIRST)
46struct S2 {
47 public:
48};
49#elif defined(SECOND)
50struct S2 {
51 protected:
52};
53#else
54S2 s2;
55// expected-error@second.h:* {{'AccessSpecifiers::S2' has different definitions in different modules; first difference is definition in module 'SecondModule' found protected access specifier}}
56// expected-note@first.h:* {{but in 'FirstModule' found public access specifier}}
57#endif
58} // namespace AccessSpecifiers
59
Richard Trieu639d7b62017-02-22 22:22:42 +000060namespace StaticAssert {
61#if defined(FIRST)
62struct S1 {
63 static_assert(1 == 1, "First");
64};
65#elif defined(SECOND)
66struct S1 {
67 static_assert(1 == 1, "Second");
68};
69#else
70S1 s1;
71// expected-error@second.h:* {{'StaticAssert::S1' has different definitions in different modules; first difference is definition in module 'SecondModule' found static assert with message}}
72// expected-note@first.h:* {{but in 'FirstModule' found static assert with different message}}
73#endif
74
75#if defined(FIRST)
76struct S2 {
77 static_assert(2 == 2, "Message");
78};
79#elif defined(SECOND)
80struct S2 {
81 static_assert(2 == 2);
82};
83#else
84S2 s2;
85// expected-error@second.h:* {{'StaticAssert::S2' has different definitions in different modules; first difference is definition in module 'SecondModule' found static assert with no message}}
86// expected-note@first.h:* {{but in 'FirstModule' found static assert with message}}
87#endif
88
89#if defined(FIRST)
90struct S3 {
91 static_assert(3 == 3, "Message");
92};
93#elif defined(SECOND)
94struct S3 {
95 static_assert(3 != 4, "Message");
96};
97#else
98S3 s3;
99// expected-error@second.h:* {{'StaticAssert::S3' has different definitions in different modules; first difference is definition in module 'SecondModule' found static assert with condition}}
100// expected-note@first.h:* {{but in 'FirstModule' found static assert with different condition}}
101#endif
102
103#if defined(FIRST)
104struct S4 {
105 static_assert(4 == 4, "Message");
106};
107#elif defined(SECOND)
108struct S4 {
109 public:
110};
111#else
112S4 s4;
113// expected-error@second.h:* {{'StaticAssert::S4' has different definitions in different modules; first difference is definition in module 'SecondModule' found public access specifier}}
114// expected-note@first.h:* {{but in 'FirstModule' found static assert}}
115#endif
116}
117
Richard Trieud0786092017-02-23 00:23:01 +0000118namespace Field {
119#if defined(FIRST)
120struct S1 {
121 int x;
122 private:
123 int y;
124};
125#elif defined(SECOND)
126struct S1 {
127 int x;
128 int y;
129};
130#else
131S1 s1;
132// expected-error@second.h:* {{'Field::S1' has different definitions in different modules; first difference is definition in module 'SecondModule' found field}}
133// expected-note@first.h:* {{but in 'FirstModule' found private access specifier}}
134#endif
135
136#if defined(FIRST)
137struct S2 {
138 int x;
139 int y;
140};
141#elif defined(SECOND)
142struct S2 {
143 int y;
144 int x;
145};
146#else
147S2 s2;
148// expected-error@second.h:* {{'Field::S2' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'y'}}
149// expected-note@first.h:* {{but in 'FirstModule' found field 'x'}}
150#endif
Richard Trieubcaaf962017-02-23 03:25:57 +0000151
152#if defined(FIRST)
153struct S3 {
154 double x;
155};
156#elif defined(SECOND)
157struct S3 {
158 int x;
159};
160#else
161S3 s3;
162// expected-error@first.h:* {{'Field::S3::x' from module 'FirstModule' is not present in definition of 'Field::S3' in module 'SecondModule'}}
163// expected-note@second.h:* {{declaration of 'x' does not match}}
164#endif
Richard Trieu8459ddf2017-02-24 02:59:12 +0000165
166#if defined(FIRST)
167typedef int A;
168struct S4 {
169 A x;
170};
171
172struct S5 {
173 A x;
174};
175#elif defined(SECOND)
176typedef int B;
177struct S4 {
178 B x;
179};
180
181struct S5 {
182 int x;
183};
184#else
185S4 s4;
Alex Lorenz76377dc2017-03-10 15:04:58 +0000186// expected-error@second.h:* {{'Field::S4' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with type 'Field::B' (aka 'int')}}
187// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with type 'Field::A' (aka 'int')}}
Richard Trieu8459ddf2017-02-24 02:59:12 +0000188
189S5 s5;
190// expected-error@second.h:* {{'Field::S5' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with type 'int'}}
Alex Lorenz76377dc2017-03-10 15:04:58 +0000191// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with type 'Field::A' (aka 'int')}}
Richard Trieu8459ddf2017-02-24 02:59:12 +0000192#endif
193
Richard Trieu93772fc2017-02-24 20:59:28 +0000194#if defined(FIRST)
195struct S6 {
196 unsigned x;
197};
198#elif defined(SECOND)
199struct S6 {
200 unsigned x : 1;
201};
202#else
203S6 s6;
204// expected-error@second.h:* {{'Field::S6' has different definitions in different modules; first difference is definition in module 'SecondModule' found bitfield 'x'}}
205// expected-note@first.h:* {{but in 'FirstModule' found non-bitfield 'x'}}
206#endif
207
208#if defined(FIRST)
209struct S7 {
210 unsigned x : 2;
211};
212#elif defined(SECOND)
213struct S7 {
214 unsigned x : 1;
215};
216#else
217S7 s7;
218// expected-error@second.h:* {{'Field::S7' has different definitions in different modules; first difference is definition in module 'SecondModule' found bitfield 'x' with one width expression}}
219// expected-note@first.h:* {{but in 'FirstModule' found bitfield 'x' with different width expression}}
220#endif
221
222#if defined(FIRST)
223struct S8 {
224 unsigned x : 2;
225};
226#elif defined(SECOND)
227struct S8 {
228 unsigned x : 1 + 1;
229};
230#else
231S8 s8;
232// expected-error@second.h:* {{'Field::S8' has different definitions in different modules; first difference is definition in module 'SecondModule' found bitfield 'x' with one width expression}}
233// expected-note@first.h:* {{but in 'FirstModule' found bitfield 'x' with different width expression}}
234#endif
Richard Trieu8459ddf2017-02-24 02:59:12 +0000235
Richard Trieu8d543e22017-02-24 23:35:37 +0000236#if defined(FIRST)
237struct S9 {
238 mutable int x;
239};
240#elif defined(SECOND)
241struct S9 {
242 int x;
243};
244#else
245S9 s9;
246// expected-error@second.h:* {{'Field::S9' has different definitions in different modules; first difference is definition in module 'SecondModule' found non-mutable field 'x'}}
247// expected-note@first.h:* {{but in 'FirstModule' found mutable field 'x'}}
248#endif
249
250#if defined(FIRST)
251struct S10 {
252 unsigned x = 5;
253};
254#elif defined(SECOND)
255struct S10 {
256 unsigned x;
257};
258#else
259S10 s10;
260// expected-error@second.h:* {{'Field::S10' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with no initalizer}}
261// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with an initializer}}
262#endif
263
264#if defined(FIRST)
265struct S11 {
266 unsigned x = 5;
267};
268#elif defined(SECOND)
269struct S11 {
270 unsigned x = 7;
271};
272#else
273S11 s11;
274// expected-error@second.h:* {{'Field::S11' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with an initializer}}
275// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with a different initializer}}
276#endif
277
Richard Trieu02552272017-05-02 23:58:52 +0000278#if defined(FIRST)
279struct S12 {
280 unsigned x[5];
281};
282#elif defined(SECOND)
283struct S12 {
284 unsigned x[7];
285};
286#else
287S12 s12;
288// expected-error@first.h:* {{'Field::S12::x' from module 'FirstModule' is not present in definition of 'Field::S12' in module 'SecondModule'}}
289// expected-note@second.h:* {{declaration of 'x' does not match}}
290#endif
291
292#if defined(FIRST)
293struct S13 {
294 unsigned x[7];
295};
296#elif defined(SECOND)
297struct S13 {
298 double x[7];
299};
300#else
301S13 s13;
302// expected-error@first.h:* {{'Field::S13::x' from module 'FirstModule' is not present in definition of 'Field::S13' in module 'SecondModule'}}
303// expected-note@second.h:* {{declaration of 'x' does not match}}
304#endif
Richard Trieud0786092017-02-23 00:23:01 +0000305} // namespace Field
306
Richard Trieu48143742017-02-28 21:24:38 +0000307namespace Method {
308#if defined(FIRST)
309struct S1 {
310 void A() {}
311};
312#elif defined(SECOND)
313struct S1 {
314 private:
315 void A() {}
316};
317#else
318S1 s1;
319// expected-error@second.h:* {{'Method::S1' has different definitions in different modules; first difference is definition in module 'SecondModule' found private access specifier}}
320// expected-note@first.h:* {{but in 'FirstModule' found method}}
321#endif
322
323#if defined(FIRST)
324struct S2 {
325 void A() {}
326 void B() {}
327};
328#elif defined(SECOND)
329struct S2 {
330 void B() {}
331 void A() {}
332};
333#else
334S2 s2;
335// expected-error@second.h:* {{'Method::S2' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'B'}}
336// expected-note@first.h:* {{but in 'FirstModule' found method 'A'}}
337#endif
Richard Trieu583e2c12017-03-04 00:08:58 +0000338
339#if defined(FIRST)
340struct S3 {
341 static void A() {}
Richard Trieuf4b54fe2017-03-04 03:04:15 +0000342 void A(int) {}
Richard Trieu583e2c12017-03-04 00:08:58 +0000343};
344#elif defined(SECOND)
345struct S3 {
Richard Trieuf4b54fe2017-03-04 03:04:15 +0000346 void A(int) {}
347 static void A() {}
Richard Trieu583e2c12017-03-04 00:08:58 +0000348};
349#else
350S3 s3;
351// expected-error@second.h:* {{'Method::S3' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' is not static}}
352// expected-note@first.h:* {{but in 'FirstModule' found method 'A' is static}}
353#endif
354
355#if defined(FIRST)
356struct S4 {
357 virtual void A() {}
358 void B() {}
359};
360#elif defined(SECOND)
361struct S4 {
362 void A() {}
363 virtual void B() {}
364};
365#else
366S4 s4;
367// expected-error@second.h:* {{'Method::S4' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' is not virtual}}
368// expected-note@first.h:* {{but in 'FirstModule' found method 'A' is virtual}}
369#endif
370
371#if defined(FIRST)
372struct S5 {
373 virtual void A() = 0;
374 virtual void B() {};
375};
376#elif defined(SECOND)
377struct S5 {
378 virtual void A() {}
379 virtual void B() = 0;
380};
381#else
382S5 *s5;
383// expected-error@second.h:* {{'Method::S5' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' is virtual}}
384// expected-note@first.h:* {{but in 'FirstModule' found method 'A' is pure virtual}}
385#endif
386
387#if defined(FIRST)
388struct S6 {
389 inline void A() {}
390};
391#elif defined(SECOND)
392struct S6 {
393 void A() {}
394};
395#else
396S6 s6;
397// expected-error@second.h:* {{'Method::S6' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' is not inline}}
398// expected-note@first.h:* {{but in 'FirstModule' found method 'A' is inline}}
399#endif
400
401#if defined(FIRST)
402struct S7 {
403 void A() volatile {}
404 void A() {}
405};
406#elif defined(SECOND)
407struct S7 {
408 void A() {}
409 void A() volatile {}
410};
411#else
412S7 s7;
413// expected-error@second.h:* {{'Method::S7' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' is not volatile}}
414// expected-note@first.h:* {{but in 'FirstModule' found method 'A' is volatile}}
415#endif
416
417#if defined(FIRST)
418struct S8 {
419 void A() const {}
420 void A() {}
421};
422#elif defined(SECOND)
423struct S8 {
424 void A() {}
425 void A() const {}
426};
427#else
428S8 s8;
429// expected-error@second.h:* {{'Method::S8' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' is not const}}
430// expected-note@first.h:* {{but in 'FirstModule' found method 'A' is const}}
431#endif
432
Richard Trieu02552272017-05-02 23:58:52 +0000433#if defined(FIRST)
434struct S9 {
435 void A(int x) {}
436 void A(int x, int y) {}
437};
438#elif defined(SECOND)
439struct S9 {
440 void A(int x, int y) {}
441 void A(int x) {}
442};
443#else
444S9 s9;
445// expected-error@second.h:* {{'Method::S9' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' that has 2 parameters}}
446// expected-note@first.h:* {{but in 'FirstModule' found method 'A' that has 1 parameter}}
447#endif
448
449#if defined(FIRST)
450struct S10 {
451 void A(int x) {}
452 void A(float x) {}
453};
454#elif defined(SECOND)
455struct S10 {
456 void A(float x) {}
457 void A(int x) {}
458};
459#else
460S10 s10;
461// expected-error@second.h:* {{'Method::S10' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' with 1st parameter of type 'float'}}
462// expected-note@first.h:* {{but in 'FirstModule' found method 'A' with 1st parameter of type 'int'}}
463#endif
464
465#if defined(FIRST)
466struct S11 {
467 void A(int x) {}
468};
469#elif defined(SECOND)
470struct S11 {
471 void A(int y) {}
472};
473#else
474S11 s11;
475// expected-error@second.h:* {{'Method::S11' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' with 1st parameter named 'y'}}
476// expected-note@first.h:* {{but in 'FirstModule' found method 'A' with 1st parameter named 'x'}}
477#endif
478
479#if defined(FIRST)
480struct S12 {
481 void A(int x) {}
482};
483#elif defined(SECOND)
484struct S12 {
485 void A(int x = 1) {}
486};
487#else
488S12 s12;
Richard Trieu6e13ff32017-06-16 02:44:29 +0000489// expected-error@second.h:* {{'Method::S12' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' with 1st parameter without a default argument}}
490// expected-note@first.h:* {{but in 'FirstModule' found method 'A' with 1st parameter with a default argument}}
Richard Trieu02552272017-05-02 23:58:52 +0000491#endif
492
493#if defined(FIRST)
494struct S13 {
495 void A(int x = 1 + 0) {}
496};
497#elif defined(SECOND)
498struct S13 {
499 void A(int x = 1) {}
500};
501#else
502S13 s13;
Richard Trieu6e13ff32017-06-16 02:44:29 +0000503// expected-error@second.h:* {{'Method::S13' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' with 1st parameter with a default argument}}
504// expected-note@first.h:* {{but in 'FirstModule' found method 'A' with 1st parameter with a different default argument}}
Richard Trieu02552272017-05-02 23:58:52 +0000505#endif
506
507#if defined(FIRST)
508struct S14 {
509 void A(int x[2]) {}
510};
511#elif defined(SECOND)
512struct S14 {
513 void A(int x[3]) {}
514};
515#else
516S14 s14;
517// expected-error@second.h:* {{'Method::S14' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'A' with 1st parameter of type 'int *' decayed from 'int [3]'}}
518// expected-note@first.h:* {{but in 'FirstModule' found method 'A' with 1st parameter of type 'int *' decayed from 'int [2]'}}
519#endif
Richard Trieu48143742017-02-28 21:24:38 +0000520} // namespace Method
521
Richard Trieue7f7ed22017-02-22 01:11:25 +0000522// Naive parsing of AST can lead to cycles in processing. Ensure
523// self-references don't trigger an endless cycles of AST node processing.
524namespace SelfReference {
525#if defined(FIRST)
526template <template <int> class T> class Wrapper {};
527
528template <int N> class S {
529 S(Wrapper<::SelfReference::S> &Ref) {}
530};
531
532struct Xx {
533 struct Yy {
534 };
535};
536
537Xx::Xx::Xx::Yy yy;
538
539namespace NNS {
540template <typename> struct Foo;
541template <template <class> class T = NNS::Foo>
542struct NestedNamespaceSpecifier {};
543}
544#endif
545} // namespace SelfReference
546
Richard Trieu33562c22017-03-08 00:13:19 +0000547namespace TypeDef {
548#if defined(FIRST)
549struct S1 {
550 typedef int a;
551};
552#elif defined(SECOND)
553struct S1 {
554 typedef double a;
555};
556#else
557S1 s1;
558// expected-error@first.h:* {{'TypeDef::S1::a' from module 'FirstModule' is not present in definition of 'TypeDef::S1' in module 'SecondModule'}}
559// expected-note@second.h:* {{declaration of 'a' does not match}}
560#endif
561
562#if defined(FIRST)
563struct S2 {
564 typedef int a;
565};
566#elif defined(SECOND)
567struct S2 {
568 typedef int b;
569};
570#else
571S2 s2;
572// expected-error@first.h:* {{'TypeDef::S2::a' from module 'FirstModule' is not present in definition of 'TypeDef::S2' in module 'SecondModule'}}
573// expected-note@second.h:* {{definition has no member 'a'}}
574#endif
575
576#if defined(FIRST)
577typedef int T;
578struct S3 {
579 typedef T a;
580};
581#elif defined(SECOND)
582typedef double T;
583struct S3 {
584 typedef T a;
585};
586#else
587S3 s3;
588// expected-error@first.h:* {{'TypeDef::S3::a' from module 'FirstModule' is not present in definition of 'TypeDef::S3' in module 'SecondModule'}}
589// expected-note@second.h:* {{declaration of 'a' does not match}}
590#endif
Richard Trieu11d566a2017-06-12 21:58:22 +0000591
592#if defined(FIRST)
593struct S4 {
594 typedef int a;
595 typedef int b;
596};
597#elif defined(SECOND)
598struct S4 {
599 typedef int b;
600 typedef int a;
601};
602#else
603S4 s4;
604// expected-error@second.h:* {{'TypeDef::S4' has different definitions in different modules; first difference is definition in module 'SecondModule' found typedef name 'b'}}
605// expected-note@first.h:* {{but in 'FirstModule' found typedef name 'a'}}
606#endif
607
608#if defined(FIRST)
609struct S5 {
610 typedef int a;
611 typedef int b;
612 int x;
613};
614#elif defined(SECOND)
615struct S5 {
616 int x;
617 typedef int b;
618 typedef int a;
619};
620#else
621S5 s5;
622// expected-error@second.h:* {{'TypeDef::S5' has different definitions in different modules; first difference is definition in module 'SecondModule' found field}}
623// expected-note@first.h:* {{but in 'FirstModule' found typedef}}
624#endif
625
626#if defined(FIRST)
627typedef float F;
628struct S6 {
629 typedef int a;
630 typedef F b;
631};
632#elif defined(SECOND)
633struct S6 {
634 typedef int a;
635 typedef float b;
636};
637#else
638S6 s6;
639// expected-error@second.h:* {{'TypeDef::S6' has different definitions in different modules; first difference is definition in module 'SecondModule' found typedef 'b' with underlying type 'float'}}
640// expected-note@first.h:* {{but in 'FirstModule' found typedef 'b' with different underlying type 'TypeDef::F' (aka 'float')}}
641#endif
Richard Trieu33562c22017-03-08 00:13:19 +0000642} // namespace TypeDef
643
644namespace Using {
645#if defined(FIRST)
646struct S1 {
647 using a = int;
648};
649#elif defined(SECOND)
650struct S1 {
651 using a = double;
652};
653#else
654S1 s1;
655// expected-error@first.h:* {{'Using::S1::a' from module 'FirstModule' is not present in definition of 'Using::S1' in module 'SecondModule'}}
656// expected-note@second.h:* {{declaration of 'a' does not match}}
657#endif
658
659#if defined(FIRST)
660struct S2 {
661 using a = int;
662};
663#elif defined(SECOND)
664struct S2 {
665 using b = int;
666};
667#else
668S2 s2;
669// expected-error@first.h:* {{'Using::S2::a' from module 'FirstModule' is not present in definition of 'Using::S2' in module 'SecondModule'}}
670// expected-note@second.h:* {{definition has no member 'a'}}
671#endif
672
673#if defined(FIRST)
674typedef int T;
675struct S3 {
676 using a = T;
677};
678#elif defined(SECOND)
679typedef double T;
680struct S3 {
681 using a = T;
682};
683#else
684S3 s3;
685// expected-error@first.h:* {{'Using::S3::a' from module 'FirstModule' is not present in definition of 'Using::S3' in module 'SecondModule'}}
686// expected-note@second.h:* {{declaration of 'a' does not match}}
687#endif
Richard Trieu11d566a2017-06-12 21:58:22 +0000688
689#if defined(FIRST)
690struct S4 {
691 using a = int;
692 using b = int;
693};
694#elif defined(SECOND)
695struct S4 {
696 using b = int;
697 using a = int;
698};
699#else
700S4 s4;
701// expected-error@second.h:* {{'Using::S4' has different definitions in different modules; first difference is definition in module 'SecondModule' found type alias name 'b'}}
702// expected-note@first.h:* {{but in 'FirstModule' found type alias name 'a'}}
703#endif
704
705#if defined(FIRST)
706struct S5 {
707 using a = int;
708 using b = int;
709 int x;
710};
711#elif defined(SECOND)
712struct S5 {
713 int x;
714 using b = int;
715 using a = int;
716};
717#else
718S5 s5;
719// expected-error@second.h:* {{'Using::S5' has different definitions in different modules; first difference is definition in module 'SecondModule' found field}}
720// expected-note@first.h:* {{but in 'FirstModule' found type alias}}
721#endif
722
723#if defined(FIRST)
724typedef float F;
725struct S6 {
726 using a = int;
727 using b = F;
728};
729#elif defined(SECOND)
730struct S6 {
731 using a = int;
732 using b = float;
733};
734#else
735S6 s6;
736// expected-error@second.h:* {{'Using::S6' has different definitions in different modules; first difference is definition in module 'SecondModule' found type alias 'b' with underlying type 'float'}}
737// expected-note@first.h:* {{but in 'FirstModule' found type alias 'b' with different underlying type 'Using::F' (aka 'float')}}
738#endif
Richard Trieu33562c22017-03-08 00:13:19 +0000739} // namespace Using
740
Richard Trieu58bb7bd2017-05-17 02:29:02 +0000741namespace RecordType {
742#if defined(FIRST)
743struct B1 {};
744struct S1 {
745 B1 x;
746};
747#elif defined(SECOND)
748struct A1 {};
749struct S1 {
750 A1 x;
751};
752#else
753S1 s1;
754// expected-error@first.h:* {{'RecordType::S1::x' from module 'FirstModule' is not present in definition of 'RecordType::S1' in module 'SecondModule'}}
755// expected-note@second.h:* {{declaration of 'x' does not match}}
756#endif
757}
758
759namespace DependentType {
760#if defined(FIRST)
761template <class T>
762class S1 {
763 typename T::typeA x;
764};
765#elif defined(SECOND)
766template <class T>
767class S1 {
768 typename T::typeB x;
769};
770#else
771template<class T>
772using U1 = S1<T>;
773// expected-error@first.h:* {{'DependentType::S1::x' from module 'FirstModule' is not present in definition of 'S1<T>' in module 'SecondModule'}}
774// expected-note@second.h:* {{declaration of 'x' does not match}}
775#endif
776}
777
778namespace ElaboratedType {
779#if defined(FIRST)
780namespace N1 { using type = double; }
781struct S1 {
782 N1::type x;
783};
784#elif defined(SECOND)
785namespace N1 { using type = int; }
786struct S1 {
787 N1::type x;
788};
789#else
790S1 s1;
791// expected-error@first.h:* {{'ElaboratedType::S1::x' from module 'FirstModule' is not present in definition of 'ElaboratedType::S1' in module 'SecondModule'}}
792// expected-note@second.h:* {{declaration of 'x' does not match}}
793#endif
794}
795
796namespace Enum {
797#if defined(FIRST)
798enum A1 {};
799struct S1 {
800 A1 x;
801};
802#elif defined(SECOND)
803enum A2 {};
804struct S1 {
805 A2 x;
806};
807#else
808S1 s1;
809// expected-error@first.h:* {{'Enum::S1::x' from module 'FirstModule' is not present in definition of 'Enum::S1' in module 'SecondModule'}}
810// expected-note@second.h:* {{declaration of 'x' does not match}}
811#endif
812}
Hans Wennborg22707762017-04-12 16:40:26 +0000813
Richard Trieuce81b192017-05-17 03:23:35 +0000814namespace NestedNamespaceSpecifier {
815#if defined(FIRST)
816namespace LevelA1 {
817using Type = int;
818}
819
820struct S1 {
821 LevelA1::Type x;
822};
823# elif defined(SECOND)
824namespace LevelB1 {
825namespace LevelC1 {
826using Type = int;
827}
828}
829
830struct S1 {
831 LevelB1::LevelC1::Type x;
832};
833#else
834S1 s1;
835// expected-error@second.h:* {{'NestedNamespaceSpecifier::S1' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with type 'LevelB1::LevelC1::Type' (aka 'int')}}
836// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with type 'LevelA1::Type' (aka 'int')}}
837#endif
838
839#if defined(FIRST)
840namespace LevelA2 { using Type = int; }
841struct S2 {
842 LevelA2::Type x;
843};
844# elif defined(SECOND)
845struct S2 {
846 int x;
847};
848#else
849S2 s2;
850// expected-error@second.h:* {{'NestedNamespaceSpecifier::S2' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with type 'int'}}
851// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with type 'LevelA2::Type' (aka 'int')}}
852#endif
853
854namespace LevelA3 { using Type = int; }
855namespace LevelB3 { using Type = int; }
856#if defined(FIRST)
857struct S3 {
858 LevelA3::Type x;
859};
860# elif defined(SECOND)
861struct S3 {
862 LevelB3::Type x;
863};
864#else
865S3 s3;
866// expected-error@second.h:* {{'NestedNamespaceSpecifier::S3' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with type 'LevelB3::Type' (aka 'int')}}
867// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with type 'LevelA3::Type' (aka 'int')}}
868#endif
869
870#if defined(FIRST)
871struct TA4 { using Type = int; };
872struct S4 {
873 TA4::Type x;
874};
875# elif defined(SECOND)
876struct TB4 { using Type = int; };
877struct S4 {
878 TB4::Type x;
879};
880#else
881S4 s4;
882// expected-error@second.h:* {{'NestedNamespaceSpecifier::S4' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with type 'TB4::Type' (aka 'int')}}
883// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with type 'TA4::Type' (aka 'int')}}
884#endif
885
886#if defined(FIRST)
887struct T5 { using Type = int; };
888struct S5 {
889 T5::Type x;
890};
891# elif defined(SECOND)
892namespace T5 { using Type = int; };
893struct S5 {
894 T5::Type x;
895};
896#else
897S5 s5;
898// expected-error@second.h:* {{'NestedNamespaceSpecifier::S5' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with type 'T5::Type' (aka 'int')}}
899// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with type 'T5::Type' (aka 'int')}}
900#endif
901
902#if defined(FIRST)
903namespace N6 {using I = int;}
904struct S6 {
905 NestedNamespaceSpecifier::N6::I x;
906};
907# elif defined(SECOND)
908using I = int;
909struct S6 {
910 ::NestedNamespaceSpecifier::I x;
911};
912#else
913S6 s6;
914// expected-error@second.h:* {{'NestedNamespaceSpecifier::S6' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with type '::NestedNamespaceSpecifier::I' (aka 'int')}}
915// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with type 'NestedNamespaceSpecifier::N6::I' (aka 'int')}}
916#endif
917
918#if defined(FIRST)
919template <class T, class U>
920class S7 {
921 typename T::type *x = {};
922 int z = x->T::foo();
923};
924#elif defined(SECOND)
925template <class T, class U>
926class S7 {
927 typename T::type *x = {};
928 int z = x->U::foo();
929};
930#else
931template <class T, class U>
932using U7 = S7<T, U>;
933// expected-error@second.h:* {{'NestedNamespaceSpecifier::S7' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'z' with an initializer}}
934// expected-note@first.h:* {{but in 'FirstModule' found field 'z' with a different initializer}}
935#endif
936
937#if defined(FIRST)
938template <class T>
939class S8 {
940 int x = T::template X<int>::value;
941};
942#elif defined(SECOND)
943template <class T>
944class S8 {
945 int x = T::template Y<int>::value;
946};
947#else
948template <class T>
949using U8 = S8<T>;
950// expected-error@second.h:* {{'NestedNamespaceSpecifier::S8' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with an initializer}}
951// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with a different initializer}}
952#endif
953
954#if defined(FIRST)
955namespace N9 { using I = int; }
956namespace O9 = N9;
957struct S9 {
958 O9::I x;
959};
960#elif defined(SECOND)
961namespace N9 { using I = int; }
962namespace P9 = N9;
963struct S9 {
964 P9::I x;
965};
966#else
967S9 s9;
968// expected-error@second.h:* {{'NestedNamespaceSpecifier::S9' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'x' with type 'P9::I' (aka 'int')}}
969// expected-note@first.h:* {{but in 'FirstModule' found field 'x' with type 'O9::I' (aka 'int')}}
970#endif
Richard Trieu96b41642017-07-01 02:00:05 +0000971
972namespace N10 {
973#if defined(FIRST)
974inline namespace A { struct X {}; }
975struct S10 {
976 A::X x;
977};
978#elif defined(SECOND)
979inline namespace B { struct X {}; }
980struct S10 {
981 B::X x;
982};
983#else
984S10 s10;
985// expected-error@second.h:* {{'NestedNamespaceSpecifier::N10::S10::x' from module 'SecondModule' is not present in definition of 'NestedNamespaceSpecifier::N10::S10' in module 'FirstModule'}}
986// expected-note@first.h:* {{declaration of 'x' does not match}}
987#endif
988}
Richard Trieuce81b192017-05-17 03:23:35 +0000989}
990
Richard Trieu96b49622017-05-31 00:31:58 +0000991namespace TemplateSpecializationType {
992#if defined(FIRST)
993template <class T1> struct U1 {};
994struct S1 {
995 U1<int> u;
996};
997#elif defined(SECOND)
998template <class T1, class T2> struct U1 {};
999struct S1 {
1000 U1<int, int> u;
1001};
1002#else
1003S1 s1;
1004// expected-error@first.h:* {{'TemplateSpecializationType::S1::u' from module 'FirstModule' is not present in definition of 'TemplateSpecializationType::S1' in module 'SecondModule'}}
1005// expected-note@second.h:* {{declaration of 'u' does not match}}
1006#endif
1007
1008#if defined(FIRST)
1009template <class T1> struct U2 {};
1010struct S2 {
1011 U2<int> u;
1012};
1013#elif defined(SECOND)
1014template <class T1> struct V1 {};
1015struct S2 {
1016 V1<int> u;
1017};
1018#else
1019S2 s2;
1020// expected-error@first.h:* {{'TemplateSpecializationType::S2::u' from module 'FirstModule' is not present in definition of 'TemplateSpecializationType::S2' in module 'SecondModule'}}
1021// expected-note@second.h:* {{declaration of 'u' does not match}}
1022#endif
1023}
1024
Richard Trieu3b261bb72017-06-13 22:21:18 +00001025namespace TemplateArgument {
1026#if defined(FIRST)
1027template <class> struct U1{};
1028struct S1 {
1029 U1<int> x;
1030};
1031#elif defined(SECOND)
1032template <int> struct U1{};
1033struct S1 {
1034 U1<1> x;
1035};
1036#else
1037S1 s1;
1038// expected-error@first.h:* {{'TemplateArgument::S1::x' from module 'FirstModule' is not present in definition of 'TemplateArgument::S1' in module 'SecondModule'}}
1039// expected-note@second.h:* {{declaration of 'x' does not match}}
1040#endif
Richard Trieu1dcb4052017-06-14 01:28:00 +00001041
1042#if defined(FIRST)
1043template <int> struct U2{};
1044struct S2 {
1045 using T = U2<2>;
1046};
1047#elif defined(SECOND)
1048template <int> struct U2{};
1049struct S2 {
1050 using T = U2<(2)>;
1051};
1052#else
1053S2 s2;
1054// expected-error@second.h:* {{'TemplateArgument::S2' has different definitions in different modules; first difference is definition in module 'SecondModule' found type alias 'T' with underlying type 'U2<(2)>'}}
1055// expected-note@first.h:* {{but in 'FirstModule' found type alias 'T' with different underlying type 'U2<2>'}}
1056#endif
1057
1058#if defined(FIRST)
1059template <int> struct U3{};
1060struct S3 {
1061 using T = U3<2>;
1062};
1063#elif defined(SECOND)
1064template <int> struct U3{};
1065struct S3 {
1066 using T = U3<1 + 1>;
1067};
1068#else
1069S3 s3;
1070// expected-error@second.h:* {{'TemplateArgument::S3' has different definitions in different modules; first difference is definition in module 'SecondModule' found type alias 'T' with underlying type 'U3<1 + 1>'}}
1071// expected-note@first.h:* {{but in 'FirstModule' found type alias 'T' with different underlying type 'U3<2>'}}
1072#endif
1073
Richard Trieuee132d62017-06-14 03:17:26 +00001074#if defined(FIRST)
1075template<class> struct T4a {};
1076template <template <class> class T> struct U4 {};
1077struct S4 {
1078 U4<T4a> x;
1079};
1080#elif defined(SECOND)
1081template<class> struct T4b {};
1082template <template <class> class T> struct U4 {};
1083struct S4 {
1084 U4<T4b> x;
1085};
1086#else
1087S4 s4;
1088// expected-error@first.h:* {{'TemplateArgument::S4::x' from module 'FirstModule' is not present in definition of 'TemplateArgument::S4' in module 'SecondModule'}}
1089// expected-note@second.h:* {{declaration of 'x' does not match}}
1090#endif
Richard Trieu8844c522017-06-30 22:40:33 +00001091
1092#if defined(FIRST)
1093template <class T> struct U5 {};
1094struct S5 {
1095 U5<int> x;
1096};
1097#elif defined(SECOND)
1098template <class T> struct U5 {};
1099struct S5 {
1100 U5<short> x;
1101};
1102#else
1103S5 s5;
1104// expected-error@first.h:* {{'TemplateArgument::S5::x' from module 'FirstModule' is not present in definition of 'TemplateArgument::S5' in module 'SecondModule'}}
1105// expected-note@second.h:* {{declaration of 'x' does not match}}
1106#endif
1107
1108#if defined(FIRST)
1109template <class T> struct U6 {};
1110struct S6 {
1111 U6<int> x;
1112 U6<short> y;
1113};
1114#elif defined(SECOND)
1115template <class T> struct U6 {};
1116struct S6 {
1117 U6<short> y;
1118 U6<int> x;
1119};
1120#else
1121S6 s6;
1122// expected-error@second.h:* {{'TemplateArgument::S6' has different definitions in different modules; first difference is definition in module 'SecondModule' found field 'y'}}
1123// expected-note@first.h:* {{but in 'FirstModule' found field 'x'}}
1124#endif
Richard Trieud9201d02017-06-15 01:35:06 +00001125}
Richard Trieuee132d62017-06-14 03:17:26 +00001126
Richard Trieud9201d02017-06-15 01:35:06 +00001127namespace TemplateTypeParmType {
1128#if defined(FIRST)
1129template <class T1, class T2>
1130struct S1 {
1131 T1 x;
1132};
1133#elif defined(SECOND)
1134template <class T1, class T2>
1135struct S1 {
1136 T2 x;
1137};
1138#else
1139using TemplateTypeParmType::S1;
1140// expected-error@first.h:* {{'TemplateTypeParmType::S1::x' from module 'FirstModule' is not present in definition of 'S1<T1, T2>' in module 'SecondModule'}}
1141// expected-note@second.h:* {{declaration of 'x' does not match}}
1142#endif
1143
1144#if defined(FIRST)
1145template <int ...Ts>
1146struct U2 {};
1147template <int T, int U>
1148class S2 {
1149 typedef U2<U, T> type;
1150 type x;
1151};
1152#elif defined(SECOND)
1153template <int ...Ts>
1154struct U2 {};
1155template <int T, int U>
1156class S2 {
1157 typedef U2<T, U> type;
1158 type x;
1159};
1160#else
1161using TemplateTypeParmType::S2;
1162// expected-error@first.h:* {{'TemplateTypeParmType::S2::x' from module 'FirstModule' is not present in definition of 'S2<T, U>' in module 'SecondModule'}}
1163// expected-note@second.h:* {{declaration of 'x' does not match}}
1164// expected-error@first.h:* {{'TemplateTypeParmType::S2::type' from module 'FirstModule' is not present in definition of 'S2<T, U>' in module 'SecondModule'}}
1165// expected-note@second.h:* {{declaration of 'type' does not match}}
1166#endif
Richard Trieu3b261bb72017-06-13 22:21:18 +00001167}
1168
Richard Trieu6e13ff32017-06-16 02:44:29 +00001169namespace VarDecl {
1170#if defined(FIRST)
1171struct S1 {
1172 static int x;
1173 static int y;
1174};
1175#elif defined(SECOND)
1176struct S1 {
1177 static int y;
1178 static int x;
1179};
1180#else
1181S1 s1;
1182// expected-error@second.h:* {{'VarDecl::S1' has different definitions in different modules; first difference is definition in module 'SecondModule' found data member with name 'y'}}
1183// expected-note@first.h:* {{but in 'FirstModule' found data member with name 'x'}}
1184#endif
1185
1186#if defined(FIRST)
1187struct S2 {
1188 static int x;
1189};
1190#elif defined(SECOND)
1191using I = int;
1192struct S2 {
1193 static I x;
1194};
1195#else
1196S2 s2;
1197// expected-error@second.h:* {{'VarDecl::S2' has different definitions in different modules; first difference is definition in module 'SecondModule' found data member 'x' with type 'VarDecl::I' (aka 'int')}}
1198// expected-note@first.h:* {{but in 'FirstModule' found data member 'x' with different type 'int'}}
1199#endif
1200
1201#if defined(FIRST)
1202struct S3 {
1203 static const int x = 1;
1204};
1205#elif defined(SECOND)
1206struct S3 {
1207 static const int x;
1208};
1209#else
1210S3 s3;
1211// expected-error@second.h:* {{'VarDecl::S3' has different definitions in different modules; first difference is definition in module 'SecondModule' found data member 'x' with an initializer}}
1212// expected-note@first.h:* {{but in 'FirstModule' found data member 'x' without an initializer}}
1213#endif
1214
1215#if defined(FIRST)
1216struct S4 {
1217 static const int x = 1;
1218};
1219#elif defined(SECOND)
1220struct S4 {
1221 static const int x = 2;
1222};
1223#else
1224S4 s4;
1225// expected-error@second.h:* {{'VarDecl::S4' has different definitions in different modules; first difference is definition in module 'SecondModule' found data member 'x' with an initializer}}
1226// expected-note@first.h:* {{but in 'FirstModule' found data member 'x' with a different initializer}}
1227#endif
1228
1229#if defined(FIRST)
1230struct S5 {
1231 static const int x = 1;
1232};
1233#elif defined(SECOND)
1234struct S5 {
1235 static constexpr int x = 1;
1236};
1237#else
1238S5 s5;
1239// expected-error@second.h:* {{'VarDecl::S5' has different definitions in different modules; first difference is definition in module 'SecondModule' found data member 'x' is not constexpr}}
1240// expected-note@first.h:* {{but in 'FirstModule' found data member 'x' is constexpr}}
1241#endif
1242
1243#if defined(FIRST)
1244struct S6 {
1245 static const int x = 1;
1246};
1247#elif defined(SECOND)
1248struct S6 {
1249 static const int y = 1;
1250};
1251#else
1252S6 s6;
1253// expected-error@first.h:* {{'VarDecl::S6::x' from module 'FirstModule' is not present in definition of 'VarDecl::S6' in module 'SecondModule'}}
1254// expected-note@second.h:* {{definition has no member 'x'}}
1255#endif
1256
1257#if defined(FIRST)
1258struct S7 {
1259 static const int x = 1;
1260};
1261#elif defined(SECOND)
1262struct S7 {
1263 static const unsigned x = 1;
1264};
1265#else
1266S7 s7;
1267// expected-error@first.h:* {{'VarDecl::S7::x' from module 'FirstModule' is not present in definition of 'VarDecl::S7' in module 'SecondModule'}}
1268// expected-note@second.h:* {{declaration of 'x' does not match}}
1269#endif
1270
1271#if defined(FIRST)
1272struct S8 {
1273public:
1274 static const int x = 1;
1275};
1276#elif defined(SECOND)
1277struct S8 {
1278 static const int x = 1;
1279public:
1280};
1281#else
1282S8 s8;
1283// expected-error@second.h:* {{'VarDecl::S8' has different definitions in different modules; first difference is definition in module 'SecondModule' found data member}}
1284// expected-note@first.h:* {{but in 'FirstModule' found public access specifier}}
1285#endif
1286
1287#if defined(FIRST)
1288struct S9 {
1289 static const int x = 1;
1290};
1291#elif defined(SECOND)
1292struct S9 {
1293 static int x;
1294};
1295#else
1296S9 s9;
1297// expected-error@first.h:* {{'VarDecl::S9::x' from module 'FirstModule' is not present in definition of 'VarDecl::S9' in module 'SecondModule'}}
1298// expected-note@second.h:* {{declaration of 'x' does not match}}
1299#endif
1300
1301#if defined(FIRST)
1302template <typename T>
1303struct S {
1304 struct R {
1305 void foo(T x = 0) {}
1306 };
1307};
1308#elif defined(SECOND)
1309template <typename T>
1310struct S {
1311 struct R {
1312 void foo(T x = 1) {}
1313 };
1314};
1315#else
1316void run() {
1317 S<int>::R().foo();
1318}
1319// expected-error@second.h:* {{'VarDecl::S::R' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'foo' with 1st parameter with a default argument}}
1320// expected-note@first.h:* {{but in 'FirstModule' found method 'foo' with 1st parameter with a different default argument}}
1321#endif
1322
1323#if defined(FIRST)
1324template <typename alpha> struct Bravo {
1325 void charlie(bool delta = false) {}
1326};
1327typedef Bravo<char> echo;
1328echo foxtrot;
1329#elif defined(SECOND)
1330template <typename alpha> struct Bravo {
1331 void charlie(bool delta = (false)) {}
1332};
1333typedef Bravo<char> echo;
1334echo foxtrot;
1335#else
1336Bravo<char> golf;
1337// expected-error@second.h:* {{'VarDecl::Bravo' has different definitions in different modules; first difference is definition in module 'SecondModule' found method 'charlie' with 1st parameter with a default argument}}
1338// expected-note@first.h:* {{but in 'FirstModule' found method 'charlie' with 1st parameter with a different default argument}}
1339#endif
1340}
1341
Richard Trieuac6a1b62017-07-08 02:04:42 +00001342namespace Friend {
1343#if defined(FIRST)
1344struct T1 {};
1345struct S1 {
1346 friend class T1;
1347};
1348#elif defined(SECOND)
1349struct T1 {};
1350struct S1 {
1351 friend T1;
1352};
1353#else
1354S1 s1;
1355// expected-error@second.h:* {{'Friend::S1' has different definitions in different modules; first difference is definition in module 'SecondModule' found friend 'Friend::T1'}}
1356// expected-note@first.h:* {{but in 'FirstModule' found friend 'class T1'}}
1357#endif
1358
1359#if defined(FIRST)
1360struct T2 {};
1361struct S2 {
1362 friend class T2;
1363};
1364#elif defined(SECOND)
1365struct T2 {};
1366struct S2 {
1367 friend struct T2;
1368};
1369#else
1370S2 s2;
1371// expected-error@second.h:* {{'Friend::S2' has different definitions in different modules; first difference is definition in module 'SecondModule' found friend 'struct T2'}}
1372// expected-note@first.h:* {{but in 'FirstModule' found friend 'class T2'}}
1373#endif
1374
1375#if defined(FIRST)
1376struct T3 {};
1377struct S3 {
1378 friend const T3;
1379};
1380#elif defined(SECOND)
1381struct T3 {};
1382struct S3 {
1383 friend T3;
1384};
1385#else
1386S3 s3;
1387// expected-error@second.h:* {{'Friend::S3' has different definitions in different modules; first difference is definition in module 'SecondModule' found friend 'Friend::T3'}}
1388// expected-note@first.h:* {{but in 'FirstModule' found friend 'const Friend::T3'}}
1389#endif
1390
1391#if defined(FIRST)
1392struct T4 {};
1393struct S4 {
1394 friend T4;
1395};
1396#elif defined(SECOND)
1397struct S4 {
1398 friend void T4();
1399};
1400#else
1401S4 s4;
1402// expected-error@second.h:* {{'Friend::S4' has different definitions in different modules; first difference is definition in module 'SecondModule' found friend function}}
1403// expected-note@first.h:* {{but in 'FirstModule' found friend class}}
1404#endif
1405
1406#if defined(FIRST)
1407struct S5 {
1408 friend void T5a();
1409};
1410#elif defined(SECOND)
1411struct S5 {
1412 friend void T5b();
1413};
1414#else
1415S5 s5;
1416// expected-error@second.h:* {{'Friend::S5' has different definitions in different modules; first difference is definition in module 'SecondModule' found friend function 'T5b'}}
1417// expected-note@first.h:* {{but in 'FirstModule' found friend function 'T5a'}}
1418#endif
1419}
Richard Trieue7f7ed22017-02-22 01:11:25 +00001420// Interesting cases that should not cause errors. struct S should not error
1421// while struct T should error at the access specifier mismatch at the end.
1422namespace AllDecls {
Richard Trieu02552272017-05-02 23:58:52 +00001423#define CREATE_ALL_DECL_STRUCT(NAME, ACCESS) \
1424 typedef int INT; \
1425 struct NAME { \
1426 public: \
1427 private: \
1428 protected: \
1429 static_assert(1 == 1, "Message"); \
1430 static_assert(2 == 2); \
1431 \
1432 int x; \
1433 double y; \
1434 \
1435 INT z; \
1436 \
1437 unsigned a : 1; \
1438 unsigned b : 2 * 2 + 5 / 2; \
1439 \
1440 mutable int c = sizeof(x + y); \
1441 \
1442 void method() {} \
1443 static void static_method() {} \
1444 virtual void virtual_method() {} \
1445 virtual void pure_virtual_method() = 0; \
1446 inline void inline_method() {} \
1447 void volatile_method() volatile {} \
1448 void const_method() const {} \
1449 \
1450 typedef int typedef_int; \
1451 using using_int = int; \
1452 \
1453 void method_one_arg(int x) {} \
1454 void method_one_arg_default_argument(int x = 5 + 5) {} \
1455 void method_decayed_type(int x[5]) {} \
1456 \
1457 int constant_arr[5]; \
1458 \
1459 ACCESS: \
Richard Trieufe564052017-04-20 02:53:53 +00001460 };
1461
Richard Trieue7f7ed22017-02-22 01:11:25 +00001462#if defined(FIRST)
Richard Trieufe564052017-04-20 02:53:53 +00001463CREATE_ALL_DECL_STRUCT(S, public)
Richard Trieue7f7ed22017-02-22 01:11:25 +00001464#elif defined(SECOND)
Richard Trieufe564052017-04-20 02:53:53 +00001465CREATE_ALL_DECL_STRUCT(S, public)
Richard Trieue7f7ed22017-02-22 01:11:25 +00001466#else
Richard Trieu583e2c12017-03-04 00:08:58 +00001467S *s;
Richard Trieue7f7ed22017-02-22 01:11:25 +00001468#endif
1469
1470#if defined(FIRST)
Richard Trieufe564052017-04-20 02:53:53 +00001471CREATE_ALL_DECL_STRUCT(T, private)
Richard Trieue7f7ed22017-02-22 01:11:25 +00001472#elif defined(SECOND)
Richard Trieufe564052017-04-20 02:53:53 +00001473CREATE_ALL_DECL_STRUCT(T, public)
Richard Trieue7f7ed22017-02-22 01:11:25 +00001474#else
Richard Trieu583e2c12017-03-04 00:08:58 +00001475T *t;
Richard Trieue7f7ed22017-02-22 01:11:25 +00001476// expected-error@second.h:* {{'AllDecls::T' has different definitions in different modules; first difference is definition in module 'SecondModule' found public access specifier}}
1477// expected-note@first.h:* {{but in 'FirstModule' found private access specifier}}
1478#endif
1479}
1480
1481namespace FriendFunction {
1482#if defined(FIRST)
1483void F(int = 0);
1484struct S { friend void F(int); };
1485#elif defined(SECOND)
1486void F(int);
1487struct S { friend void F(int); };
1488#else
1489S s;
1490#endif
1491
1492#if defined(FIRST)
1493void G(int = 0);
1494struct T {
1495 friend void G(int);
1496
1497 private:
1498};
1499#elif defined(SECOND)
1500void G(int);
1501struct T {
1502 friend void G(int);
1503
1504 public:
1505};
1506#else
1507T t;
1508// expected-error@second.h:* {{'FriendFunction::T' has different definitions in different modules; first difference is definition in module 'SecondModule' found public access specifier}}
1509// expected-note@first.h:* {{but in 'FirstModule' found private access specifier}}
1510#endif
1511} // namespace FriendFunction
1512
1513namespace ImplicitDecl {
1514#if defined(FIRST)
1515struct S { };
1516void S_Constructors() {
1517 // Trigger creation of implicit contructors
1518 S foo;
1519 S bar = foo;
1520 S baz(bar);
1521}
1522#elif defined(SECOND)
1523struct S { };
1524#else
1525S s;
1526#endif
1527
1528#if defined(FIRST)
1529struct T {
1530 private:
1531};
1532void T_Constructors() {
1533 // Trigger creation of implicit contructors
1534 T foo;
1535 T bar = foo;
1536 T baz(bar);
1537}
1538#elif defined(SECOND)
1539struct T {
1540 public:
1541};
1542#else
1543T t;
1544// expected-error@first.h:* {{'ImplicitDecl::T' has different definitions in different modules; first difference is definition in module 'FirstModule' found private access specifier}}
1545// expected-note@second.h:* {{but in 'SecondModule' found public access specifier}}
1546#endif
1547
1548} // namespace ImplicitDelc
1549
1550namespace TemplatedClass {
1551#if defined(FIRST)
1552template <class>
1553struct S {};
1554#elif defined(SECOND)
1555template <class>
1556struct S {};
1557#else
1558S<int> s;
1559#endif
1560
1561#if defined(FIRST)
1562template <class>
1563struct T {
1564 private:
1565};
1566#elif defined(SECOND)
1567template <class>
1568struct T {
1569 public:
1570};
1571#else
1572T<int> t;
1573// expected-error@second.h:* {{'TemplatedClass::T' has different definitions in different modules; first difference is definition in module 'SecondModule' found public access specifier}}
1574// expected-note@first.h:* {{but in 'FirstModule' found private access specifier}}
1575#endif
1576} // namespace TemplatedClass
1577
1578namespace TemplateClassWithField {
1579#if defined(FIRST)
1580template <class A>
1581struct S {
1582 A a;
1583};
1584#elif defined(SECOND)
1585template <class A>
1586struct S {
1587 A a;
1588};
1589#else
1590S<int> s;
1591#endif
1592
1593#if defined(FIRST)
1594template <class A>
1595struct T {
1596 A a;
1597
1598 private:
1599};
1600#elif defined(SECOND)
1601template <class A>
1602struct T {
1603 A a;
1604
1605 public:
1606};
1607#else
1608T<int> t;
1609// expected-error@second.h:* {{'TemplateClassWithField::T' has different definitions in different modules; first difference is definition in module 'SecondModule' found public access specifier}}
1610// expected-note@first.h:* {{but in 'FirstModule' found private access specifier}}
1611#endif
1612} // namespace TemplateClassWithField
1613
1614namespace TemplateClassWithTemplateField {
1615#if defined(FIRST)
1616template <class A>
1617class WrapperS;
1618template <class A>
1619struct S {
1620 WrapperS<A> a;
1621};
1622#elif defined(SECOND)
1623template <class A>
1624class WrapperS;
1625template <class A>
1626struct S {
1627 WrapperS<A> a;
1628};
1629#else
1630template <class A>
1631class WrapperS{};
1632S<int> s;
1633#endif
1634
1635#if defined(FIRST)
1636template <class A>
1637class WrapperT;
1638template <class A>
1639struct T {
1640 WrapperT<A> a;
1641
1642 public:
1643};
1644#elif defined(SECOND)
1645template <class A>
1646class WrapperT;
1647template <class A>
1648struct T {
1649 WrapperT<A> a;
1650
1651 private:
1652};
1653#else
1654template <class A>
1655class WrapperT{};
1656T<int> t;
1657// expected-error@second.h:* {{'TemplateClassWithTemplateField::T' has different definitions in different modules; first difference is definition in module 'SecondModule' found private access specifier}}
1658// expected-note@first.h:* {{but in 'FirstModule' found public access specifier}}
1659#endif
1660} // namespace TemplateClassWithTemplateField
1661
1662namespace EnumWithForwardDeclaration {
1663#if defined(FIRST)
1664enum E : int;
1665struct S {
1666 void get(E) {}
1667};
1668#elif defined(SECOND)
1669enum E : int { A, B };
1670struct S {
1671 void get(E) {}
1672};
1673#else
1674S s;
1675#endif
1676
1677#if defined(FIRST)
1678struct T {
1679 void get(E) {}
1680 public:
1681};
1682#elif defined(SECOND)
1683struct T {
1684 void get(E) {}
1685 private:
1686};
1687#else
1688T t;
1689// expected-error@second.h:* {{'EnumWithForwardDeclaration::T' has different definitions in different modules; first difference is definition in module 'SecondModule' found private access specifier}}
1690// expected-note@first.h:* {{but in 'FirstModule' found public access specifier}}
1691#endif
1692} // namespace EnumWithForwardDeclaration
1693
1694namespace StructWithForwardDeclaration {
1695#if defined(FIRST)
1696struct P {};
1697struct S {
1698 struct P *ptr;
1699};
1700#elif defined(SECOND)
1701struct S {
1702 struct P *ptr;
1703};
1704#else
1705S s;
1706#endif
1707
1708#if defined(FIRST)
1709struct Q {};
1710struct T {
1711 struct Q *ptr;
1712 public:
1713};
1714#elif defined(SECOND)
1715struct T {
1716 struct Q *ptr;
1717 private:
1718};
1719#else
1720T t;
1721// expected-error@second.h:* {{'StructWithForwardDeclaration::T' has different definitions in different modules; first difference is definition in module 'SecondModule' found private access specifier}}
1722// expected-note@first.h:* {{but in 'FirstModule' found public access specifier}}
1723#endif
1724} // namespace StructWithForwardDeclaration
1725
1726namespace StructWithForwardDeclarationNoDefinition {
1727#if defined(FIRST)
1728struct P;
1729struct S {
1730 struct P *ptr;
1731};
1732#elif defined(SECOND)
1733struct S {
1734 struct P *ptr;
1735};
1736#else
1737S s;
1738#endif
1739
1740#if defined(FIRST)
1741struct Q;
1742struct T {
1743 struct Q *ptr;
1744
1745 public:
1746};
1747#elif defined(SECOND)
1748struct T {
1749 struct Q *ptr;
1750
1751 private:
1752};
1753#else
1754T t;
1755// expected-error@second.h:* {{'StructWithForwardDeclarationNoDefinition::T' has different definitions in different modules; first difference is definition in module 'SecondModule' found private access specifier}}
1756// expected-note@first.h:* {{but in 'FirstModule' found public access specifier}}
1757#endif
1758} // namespace StructWithForwardDeclarationNoDefinition
1759
Richard Trieufe564052017-04-20 02:53:53 +00001760namespace LateParsedDefaultArgument {
1761#if defined(FIRST)
1762template <typename T>
1763struct S {
1764 struct R {
1765 void foo(T x = 0) {}
1766 };
1767};
1768#elif defined(SECOND)
1769#else
1770void run() {
1771 S<int>::R().foo();
1772}
1773#endif
1774}
1775
1776namespace LateParsedDefaultArgument {
1777#if defined(FIRST)
1778template <typename alpha> struct Bravo {
1779 void charlie(bool delta = false) {}
1780};
1781typedef Bravo<char> echo;
1782echo foxtrot;
1783
1784Bravo<char> golf;
1785#elif defined(SECOND)
1786#else
1787#endif
1788}
1789
Richard Trieu157ed942017-04-28 22:03:28 +00001790namespace DifferentParameterNameInTemplate {
1791#if defined(FIRST) || defined(SECOND)
1792template <typename T>
1793struct S {
1794 typedef T Type;
1795
1796 static void Run(const Type *name_one);
1797};
1798
1799template <typename T>
1800void S<T>::Run(const T *name_two) {}
1801
1802template <typename T>
1803struct Foo {
1804 ~Foo() { Handler::Run(nullptr); }
1805 Foo() {}
1806
1807 class Handler : public S<T> {};
1808
1809 void Get(typename Handler::Type *x = nullptr) {}
1810 void Add() { Handler::Run(nullptr); }
1811};
1812#endif
1813
1814#if defined(FIRST)
1815struct Beta;
1816
1817struct Alpha {
1818 Alpha();
1819 void Go() { betas.Get(); }
1820 Foo<Beta> betas;
1821};
1822
1823#elif defined(SECOND)
1824struct Beta {};
1825
1826struct BetaHelper {
1827 void add_Beta() { betas.Add(); }
1828 Foo<Beta> betas;
1829};
1830
1831#else
1832Alpha::Alpha() {}
1833#endif
1834}
1835
Richard Trieu02552272017-05-02 23:58:52 +00001836namespace ParameterTest {
1837#if defined(FIRST)
1838class X {};
1839template <typename G>
1840class S {
1841 public:
1842 typedef G Type;
1843 static inline G *Foo(const G *a, int * = nullptr);
1844};
1845
1846template<typename G>
1847G* S<G>::Foo(const G* aaaa, int*) {}
1848#elif defined(SECOND)
1849template <typename G>
1850class S {
1851 public:
1852 typedef G Type;
1853 static inline G *Foo(const G *a, int * = nullptr);
1854};
1855
1856template<typename G>
1857G* S<G>::Foo(const G* asdf, int*) {}
1858#else
1859S<X> s;
1860#endif
1861}
1862
Richard Trieub35ef2a2017-05-09 03:24:34 +00001863namespace MultipleTypedefs {
1864#if defined(FIRST)
1865typedef int B1;
1866typedef B1 A1;
1867struct S1 {
1868 A1 x;
1869};
1870#elif defined(SECOND)
1871typedef int A1;
1872struct S1 {
1873 A1 x;
1874};
1875#else
1876S1 s1;
1877#endif
1878
1879#if defined(FIRST)
1880struct T2 { int x; };
1881typedef T2 B2;
1882typedef B2 A2;
1883struct S2 {
1884 T2 x;
1885};
1886#elif defined(SECOND)
1887struct T2 { int x; };
1888typedef T2 A2;
1889struct S2 {
1890 T2 x;
1891};
1892#else
1893S2 s2;
1894#endif
Richard Trieu3e03d3e2017-06-29 22:53:04 +00001895
1896#if defined(FIRST)
1897using A3 = const int;
1898using B3 = volatile A3;
1899struct S3 {
1900 B3 x = 1;
1901};
1902#elif defined(SECOND)
1903using A3 = volatile const int;
1904using B3 = A3;
1905struct S3 {
1906 B3 x = 1;
1907};
1908#else
1909S3 s3;
1910#endif
Richard Trieub35ef2a2017-05-09 03:24:34 +00001911}
Richard Trieu02552272017-05-02 23:58:52 +00001912
Richard Trieue7f7ed22017-02-22 01:11:25 +00001913// Keep macros contained to one file.
1914#ifdef FIRST
1915#undef FIRST
1916#endif
1917#ifdef SECOND
1918#undef SECOND
1919#endif