blob: e3fa8ae8d7f2957f62c280c6b6b4c9ab1238e6ae [file] [log] [blame]
Kristof Umannaa9d2622019-05-05 19:42:33 +00001// RUN: %clang_analyze_cc1 -std=c++14 -verify %s \
2// RUN: -analyzer-checker=core \
3// RUN: -analyzer-checker=optin.cplusplus.UninitializedObject \
Kristof Umann85e0ff72019-04-19 23:33:50 +00004// RUN: -analyzer-config optin.cplusplus.UninitializedObject:Pedantic=true -DPEDANTIC \
Kristof Umannaa9d2622019-05-05 19:42:33 +00005// RUN: -analyzer-config \
6// RUN: optin.cplusplus.UninitializedObject:CheckPointeeInitialization=true
Kristof Umann30f08652018-06-18 11:50:17 +00007
Kristof Umannaa9d2622019-05-05 19:42:33 +00008// RUN: %clang_analyze_cc1 -std=c++14 -verify %s \
9// RUN: -analyzer-checker=core \
10// RUN: -analyzer-checker=optin.cplusplus.UninitializedObject \
11// RUN: -analyzer-config \
12// RUN: optin.cplusplus.UninitializedObject:CheckPointeeInitialization=true
Kristof Umann30f08652018-06-18 11:50:17 +000013
14//===----------------------------------------------------------------------===//
15// Default constructor test.
16//===----------------------------------------------------------------------===//
17
18class CompilerGeneratedConstructorTest {
19 int a, b, c, d, e, f, g, h, i, j;
20
21public:
22 CompilerGeneratedConstructorTest() = default;
23};
24
25void fCompilerGeneratedConstructorTest() {
26 CompilerGeneratedConstructorTest();
27}
28
29#ifdef PEDANTIC
30class DefaultConstructorTest {
31 int a; // expected-note{{uninitialized field 'this->a'}}
32
33public:
34 DefaultConstructorTest();
35};
36
37DefaultConstructorTest::DefaultConstructorTest() = default;
38
39void fDefaultConstructorTest() {
40 DefaultConstructorTest(); // expected-warning{{1 uninitialized field}}
41}
42#else
43class DefaultConstructorTest {
44 int a;
45
46public:
47 DefaultConstructorTest();
48};
49
50DefaultConstructorTest::DefaultConstructorTest() = default;
51
52void fDefaultConstructorTest() {
53 DefaultConstructorTest();
54}
55#endif // PEDANTIC
56
57//===----------------------------------------------------------------------===//
58// Initializer list test.
59//===----------------------------------------------------------------------===//
60
61class InitListTest1 {
62 int a;
63 int b;
64
65public:
66 InitListTest1()
67 : a(1),
68 b(2) {
69 // All good!
70 }
71};
72
73void fInitListTest1() {
74 InitListTest1();
75}
76
77class InitListTest2 {
78 int a;
79 int b; // expected-note{{uninitialized field 'this->b'}}
80
81public:
82 InitListTest2()
83 : a(3) {} // expected-warning{{1 uninitialized field}}
84};
85
86void fInitListTest2() {
87 InitListTest2();
88}
89
90class InitListTest3 {
91 int a; // expected-note{{uninitialized field 'this->a'}}
92 int b;
93
94public:
95 InitListTest3()
96 : b(4) {} // expected-warning{{1 uninitialized field}}
97};
98
99void fInitListTest3() {
100 InitListTest3();
101}
102
103//===----------------------------------------------------------------------===//
104// Constructor body test.
105//===----------------------------------------------------------------------===//
106
107class CtorBodyTest1 {
108 int a, b;
109
110public:
111 CtorBodyTest1() {
112 a = 5;
113 b = 6;
114 // All good!
115 }
116};
117
118void fCtorBodyTest1() {
119 CtorBodyTest1();
120}
121
122class CtorBodyTest2 {
123 int a;
124 int b; // expected-note{{uninitialized field 'this->b'}}
125
126public:
127 CtorBodyTest2() {
128 a = 7; // expected-warning{{1 uninitialized field}}
129 }
130};
131
132void fCtorBodyTest2() {
133 CtorBodyTest2();
134}
135
136class CtorBodyTest3 {
137 int a; // expected-note{{uninitialized field 'this->a'}}
138 int b;
139
140public:
141 CtorBodyTest3() {
142 b = 8; // expected-warning{{1 uninitialized field}}
143 }
144};
145
146void fCtorBodyTest3() {
147 CtorBodyTest3();
148}
149
150#ifdef PEDANTIC
151class CtorBodyTest4 {
152 int a; // expected-note{{uninitialized field 'this->a'}}
153 int b; // expected-note{{uninitialized field 'this->b'}}
154
155public:
156 CtorBodyTest4() {}
157};
158
159void fCtorBodyTest4() {
160 CtorBodyTest4(); // expected-warning{{2 uninitialized fields}}
161}
162#else
163class CtorBodyTest4 {
164 int a;
165 int b;
166
167public:
168 CtorBodyTest4() {}
169};
170
171void fCtorBodyTest4() {
172 CtorBodyTest4();
173}
174#endif
175
176//===----------------------------------------------------------------------===//
177// Constructor delegation test.
178//===----------------------------------------------------------------------===//
179
180class CtorDelegationTest1 {
181 int a;
182 int b;
183
184public:
185 CtorDelegationTest1(int)
186 : a(9) {
187 // leaves 'b' unintialized, but we'll never check this function
188 }
189
190 CtorDelegationTest1()
191 : CtorDelegationTest1(int{}) { // Initializing 'a'
192 b = 10;
193 // All good!
194 }
195};
196
197void fCtorDelegationTest1() {
198 CtorDelegationTest1();
199}
200
201class CtorDelegationTest2 {
202 int a; // expected-note{{uninitialized field 'this->a'}}
203 int b;
204
205public:
206 CtorDelegationTest2(int)
207 : b(11) {
208 // leaves 'a' unintialized, but we'll never check this function
209 }
210
211 CtorDelegationTest2()
212 : CtorDelegationTest2(int{}) { // expected-warning{{1 uninitialized field}}
213 }
214};
215
216void fCtorDelegationTest2() {
217 CtorDelegationTest2();
218}
219
220//===----------------------------------------------------------------------===//
221// Tests for classes containing records.
222//===----------------------------------------------------------------------===//
223
224class ContainsRecordTest1 {
225 struct RecordType {
226 int x;
227 int y;
228 } rec;
229 int c, d;
230
231public:
232 ContainsRecordTest1()
233 : rec({12, 13}),
234 c(14),
235 d(15) {
236 // All good!
237 }
238};
239
240void fContainsRecordTest1() {
241 ContainsRecordTest1();
242}
243
244class ContainsRecordTest2 {
245 struct RecordType {
246 int x;
247 int y; // expected-note{{uninitialized field 'this->rec.y'}}
248 } rec;
249 int c, d;
250
251public:
252 ContainsRecordTest2()
253 : c(16),
254 d(17) {
255 rec.x = 18; // expected-warning{{1 uninitialized field}}
256 }
257};
258
259void fContainsRecordTest2() {
260 ContainsRecordTest2();
261}
262
263class ContainsRecordTest3 {
264 struct RecordType {
265 int x; // expected-note{{uninitialized field 'this->rec.x'}}
266 int y; // expected-note{{uninitialized field 'this->rec.y'}}
267 } rec;
268 int c, d;
269
270public:
271 ContainsRecordTest3()
272 : c(19),
273 d(20) { // expected-warning{{2 uninitialized fields}}
274 }
275};
276
277void fContainsRecordTest3() {
278 ContainsRecordTest3();
279}
280
281class ContainsRecordTest4 {
282 struct RecordType {
283 int x; // expected-note{{uninitialized field 'this->rec.x'}}
284 int y; // expected-note{{uninitialized field 'this->rec.y'}}
285 } rec;
286 int c, d; // expected-note{{uninitialized field 'this->d'}}
287
288public:
289 ContainsRecordTest4()
290 : c(19) { // expected-warning{{3 uninitialized fields}}
291 }
292};
293
294void fContainsRecordTest4() {
295 ContainsRecordTest4();
296}
297
298//===----------------------------------------------------------------------===//
299// Tests for template classes.
300//===----------------------------------------------------------------------===//
301
302template <class T>
303class IntTemplateClassTest1 {
304 T t;
305 int b;
306
307public:
308 IntTemplateClassTest1(T i) {
309 b = 21;
310 t = i;
311 // All good!
312 }
313};
314
315void fIntTemplateClassTest1() {
316 IntTemplateClassTest1<int>(22);
317}
318
319template <class T>
320class IntTemplateClassTest2 {
321 T t; // expected-note{{uninitialized field 'this->t'}}
322 int b;
323
324public:
325 IntTemplateClassTest2() {
326 b = 23; // expected-warning{{1 uninitialized field}}
327 }
328};
329
330void fIntTemplateClassTest2() {
331 IntTemplateClassTest2<int>();
332}
333
334struct Record {
335 int x; // expected-note{{uninitialized field 'this->t.x'}}
336 int y; // expected-note{{uninitialized field 'this->t.y'}}
337};
338
339template <class T>
340class RecordTemplateClassTest {
341 T t;
342 int b;
343
344public:
345 RecordTemplateClassTest() {
346 b = 24; // expected-warning{{2 uninitialized fields}}
347 }
348};
349
350void fRecordTemplateClassTest() {
351 RecordTemplateClassTest<Record>();
352}
353
354//===----------------------------------------------------------------------===//
355// Tests involving functions with unknown implementations.
356//===----------------------------------------------------------------------===//
357
358template <class T>
359void mayInitialize(T &);
360
361template <class T>
362void wontInitialize(const T &);
363
364class PassingToUnknownFunctionTest1 {
Artem Dergachev3d90e7e2019-04-03 18:21:16 +0000365 int a, b;
Kristof Umann30f08652018-06-18 11:50:17 +0000366
367public:
368 PassingToUnknownFunctionTest1() {
369 mayInitialize(a);
370 mayInitialize(b);
371 // All good!
372 }
373
374 PassingToUnknownFunctionTest1(int) {
Artem Dergachev3d90e7e2019-04-03 18:21:16 +0000375 mayInitialize(a);
376 // All good!
Kristof Umann30f08652018-06-18 11:50:17 +0000377 }
378
379 PassingToUnknownFunctionTest1(int, int) {
380 mayInitialize(*this);
381 // All good!
382 }
383};
384
385void fPassingToUnknownFunctionTest1() {
386 PassingToUnknownFunctionTest1();
387 PassingToUnknownFunctionTest1(int());
388 PassingToUnknownFunctionTest1(int(), int());
389}
390
391class PassingToUnknownFunctionTest2 {
392 int a; // expected-note{{uninitialized field 'this->a'}}
393 int b;
394
395public:
396 PassingToUnknownFunctionTest2() {
397 wontInitialize(a);
398 b = 4; // expected-warning{{1 uninitialized field}}
399 }
400};
401
402void fPassingToUnknownFunctionTest2() {
403 PassingToUnknownFunctionTest2();
404}
405
406//===----------------------------------------------------------------------===//
407// Tests for classes containing unions.
408//===----------------------------------------------------------------------===//
409
410// FIXME: As of writing this checker, there is no good support for union types
411// in the Static Analyzer. Here is non-exhaustive list of cases.
412// Note that the rules for unions are different in C and C++.
413// http://lists.llvm.org/pipermail/cfe-dev/2017-March/052910.html
414
415class ContainsSimpleUnionTest1 {
416 union SimpleUnion {
417 float uf;
418 int ui;
419 char uc;
420 } u;
421
422public:
423 ContainsSimpleUnionTest1() {
424 u.uf = 3.14;
425 // All good!
426 }
427};
428
429void fContainsSimpleUnionTest1() {
430 ContainsSimpleUnionTest1();
431}
432
433class ContainsSimpleUnionTest2 {
434 union SimpleUnion {
435 float uf;
436 int ui;
437 char uc;
438 // TODO: we'd expect the note: {{uninitialized field 'this->u'}}
439 } u; // no-note
440
441public:
442 ContainsSimpleUnionTest2() {}
443};
444
445void fContainsSimpleUnionTest2() {
446 // TODO: we'd expect the warning: {{1 uninitialized field}}
447 ContainsSimpleUnionTest2(); // no-warning
448}
449
450class UnionPointerTest1 {
451public:
452 union SimpleUnion {
453 float uf;
454 int ui;
455 char uc;
456 };
457
458private:
459 SimpleUnion *uptr;
460
461public:
462 UnionPointerTest1(SimpleUnion *uptr, int) : uptr(uptr) {
463 // All good!
464 }
465};
466
467void fUnionPointerTest1() {
468 UnionPointerTest1::SimpleUnion u;
469 u.uf = 41;
470 UnionPointerTest1(&u, int());
471}
472
473class UnionPointerTest2 {
474public:
475 union SimpleUnion {
476 float uf;
477 int ui;
478 char uc;
479 };
480
481private:
482 // TODO: we'd expect the note: {{uninitialized field 'this->uptr'}}
483 SimpleUnion *uptr; // no-note
484
485public:
486 UnionPointerTest2(SimpleUnion *uptr, char) : uptr(uptr) {}
487};
488
489void fUnionPointerTest2() {
490 UnionPointerTest2::SimpleUnion u;
491 // TODO: we'd expect the warning: {{1 uninitialized field}}
492 UnionPointerTest2(&u, int()); // no-warning
493}
494
495class ContainsUnionWithRecordTest1 {
496 union UnionWithRecord {
497 struct RecordType {
498 int x;
499 int y;
500 } us;
501 double ud;
502 long ul;
503
504 UnionWithRecord(){};
505 } u;
506
507public:
508 ContainsUnionWithRecordTest1() {
509 u.ud = 3.14;
510 // All good!
511 }
512};
513
514void fContainsUnionWithRecordTest1() {
515 ContainsUnionWithRecordTest1();
516}
517
518class ContainsUnionWithRecordTest2 {
519 union UnionWithRecord {
520 struct RecordType {
521 int x;
522 int y;
523 } us;
524 double ud;
525 long ul;
526
527 UnionWithRecord(){};
528 } u;
529
530public:
531 ContainsUnionWithRecordTest2() {
532 u.us = UnionWithRecord::RecordType{42, 43};
533 // All good!
534 }
535};
536
537void fContainsUnionWithRecordTest2() {
538 ContainsUnionWithRecordTest1();
539}
540
541class ContainsUnionWithRecordTest3 {
542 union UnionWithRecord {
543 struct RecordType {
544 int x;
545 int y;
546 } us;
547 double ud;
548 long ul;
549
550 UnionWithRecord(){};
551 // TODO: we'd expect the note: {{uninitialized field 'this->u'}}
552 } u; // no-note
553
554public:
555 ContainsUnionWithRecordTest3() {
556 UnionWithRecord::RecordType rec;
557 rec.x = 44;
558 // TODO: we'd expect the warning: {{1 uninitialized field}}
559 u.us = rec; // no-warning
560 }
561};
562
563void fContainsUnionWithRecordTest3() {
564 ContainsUnionWithRecordTest3();
565}
566
567class ContainsUnionWithSimpleUnionTest1 {
568 union UnionWithSimpleUnion {
569 union SimpleUnion {
570 float uf;
571 int ui;
572 char uc;
573 } usu;
574 long ul;
575 unsigned uu;
576 } u;
577
578public:
579 ContainsUnionWithSimpleUnionTest1() {
580 u.usu.ui = 5;
581 // All good!
582 }
583};
584
585void fContainsUnionWithSimpleUnionTest1() {
586 ContainsUnionWithSimpleUnionTest1();
587}
588
589class ContainsUnionWithSimpleUnionTest2 {
590 union UnionWithSimpleUnion {
591 union SimpleUnion {
592 float uf;
593 int ui;
594 char uc;
595 } usu;
596 long ul;
597 unsigned uu;
598 // TODO: we'd expect the note: {{uninitialized field 'this->u'}}
599 } u; // no-note
600
601public:
602 ContainsUnionWithSimpleUnionTest2() {}
603};
604
605void fContainsUnionWithSimpleUnionTest2() {
606 // TODO: we'd expect the warning: {{1 uninitialized field}}
607 ContainsUnionWithSimpleUnionTest2(); // no-warning
608}
609
610//===----------------------------------------------------------------------===//
611// Zero initialization tests.
612//===----------------------------------------------------------------------===//
613
614struct GlobalVariableTest {
615 int i;
616
617 GlobalVariableTest() {}
618};
619
620GlobalVariableTest gvt; // no-warning
621
622//===----------------------------------------------------------------------===//
623// Copy and move constructor tests.
624//===----------------------------------------------------------------------===//
625
626template <class T>
627void funcToSquelchCompilerWarnings(const T &t);
628
629#ifdef PEDANTIC
630struct CopyConstructorTest {
631 int i; // expected-note{{uninitialized field 'this->i'}}
632
633 CopyConstructorTest() : i(1337) {}
634 CopyConstructorTest(const CopyConstructorTest &other) {}
635};
636
637void fCopyConstructorTest() {
638 CopyConstructorTest cct;
639 CopyConstructorTest copy = cct; // expected-warning{{1 uninitialized field}}
640 funcToSquelchCompilerWarnings(copy);
641}
642#else
643struct CopyConstructorTest {
644 int i;
645
646 CopyConstructorTest() : i(1337) {}
647 CopyConstructorTest(const CopyConstructorTest &other) {}
648};
649
650void fCopyConstructorTest() {
651 CopyConstructorTest cct;
652 CopyConstructorTest copy = cct;
653 funcToSquelchCompilerWarnings(copy);
654}
655#endif // PEDANTIC
656
657struct MoveConstructorTest {
658 // TODO: we'd expect the note: {{uninitialized field 'this->i'}}
659 int i; // no-note
660
661 MoveConstructorTest() : i(1337) {}
662 MoveConstructorTest(const CopyConstructorTest &other) = delete;
663 MoveConstructorTest(const CopyConstructorTest &&other) {}
664};
665
666void fMoveConstructorTest() {
667 MoveConstructorTest cct;
668 // TODO: we'd expect the warning: {{1 uninitialized field}}
669 MoveConstructorTest copy(static_cast<MoveConstructorTest &&>(cct)); // no-warning
670 funcToSquelchCompilerWarnings(copy);
671}
672
673//===----------------------------------------------------------------------===//
674// Array tests.
675//===----------------------------------------------------------------------===//
676
677struct IntArrayTest {
678 int arr[256];
679
680 IntArrayTest() {
681 // All good!
682 }
683};
684
685void fIntArrayTest() {
686 IntArrayTest();
687}
688
689struct RecordTypeArrayTest {
690 struct RecordType {
691 int x, y;
692 } arr[256];
693
694 RecordTypeArrayTest() {
695 // All good!
696 }
697};
698
699void fRecordTypeArrayTest() {
700 RecordTypeArrayTest();
701}
702
703template <class T>
704class CharArrayPointerTest {
705 T *t; // no-crash
706
707public:
708 CharArrayPointerTest(T *t, int) : t(t) {}
709};
710
711void fCharArrayPointerTest() {
712 char str[16] = "012345678912345";
713 CharArrayPointerTest<char[16]>(&str, int());
714}
715
716//===----------------------------------------------------------------------===//
717// Memset tests.
718//===----------------------------------------------------------------------===//
719
720struct MemsetTest1 {
721 int a, b, c;
722
723 MemsetTest1() {
724 __builtin_memset(this, 0, sizeof(decltype(*this)));
725 }
726};
727
728void fMemsetTest1() {
729 MemsetTest1();
730}
731
732struct MemsetTest2 {
733 int a;
734
735 MemsetTest2() {
736 __builtin_memset(&a, 0, sizeof(int));
737 }
738};
739
740void fMemsetTest2() {
741 MemsetTest2();
742}
743
744//===----------------------------------------------------------------------===//
745// Lambda tests.
746//===----------------------------------------------------------------------===//
747
748template <class Callable>
Kristof Umann8c119092018-07-13 12:54:47 +0000749struct LambdaThisTest {
750 Callable functor;
751
752 LambdaThisTest(const Callable &functor, int) : functor(functor) {
753 // All good!
754 }
755};
756
757struct HasCapturableThis {
758 void fLambdaThisTest() {
759 auto isEven = [this](int a) { return a % 2 == 0; }; // no-crash
760 LambdaThisTest<decltype(isEven)>(isEven, int());
761 }
762};
763
764template <class Callable>
Kristof Umann30f08652018-06-18 11:50:17 +0000765struct LambdaTest1 {
766 Callable functor;
767
768 LambdaTest1(const Callable &functor, int) : functor(functor) {
769 // All good!
770 }
771};
772
773void fLambdaTest1() {
774 auto isEven = [](int a) { return a % 2 == 0; };
775 LambdaTest1<decltype(isEven)>(isEven, int());
776}
777
778#ifdef PEDANTIC
779template <class Callable>
780struct LambdaTest2 {
781 Callable functor;
782
783 LambdaTest2(const Callable &functor, int) : functor(functor) {} // expected-warning{{1 uninitialized field}}
784};
785
786void fLambdaTest2() {
787 int b;
Kristof Umannf0dd1012018-09-14 08:58:21 +0000788 auto equals = [&b](int a) { return a == b; }; // expected-note{{uninitialized pointee 'this->functor./*captured variable*/b'}}
Kristof Umann30f08652018-06-18 11:50:17 +0000789 LambdaTest2<decltype(equals)>(equals, int());
790}
791#else
792template <class Callable>
793struct LambdaTest2 {
794 Callable functor;
795
796 LambdaTest2(const Callable &functor, int) : functor(functor) {}
797};
798
799void fLambdaTest2() {
800 int b;
801 auto equals = [&b](int a) { return a == b; };
802 LambdaTest2<decltype(equals)>(equals, int());
803}
804#endif //PEDANTIC
805
806#ifdef PEDANTIC
807namespace LT3Detail {
808
809struct RecordType {
Kristof Umannf0dd1012018-09-14 08:58:21 +0000810 int x; // expected-note{{uninitialized field 'this->functor./*captured variable*/rec1.x'}}
811 int y; // expected-note{{uninitialized field 'this->functor./*captured variable*/rec1.y'}}
Kristof Umann30f08652018-06-18 11:50:17 +0000812};
813
814} // namespace LT3Detail
815template <class Callable>
816struct LambdaTest3 {
817 Callable functor;
818
819 LambdaTest3(const Callable &functor, int) : functor(functor) {} // expected-warning{{2 uninitialized fields}}
820};
821
822void fLambdaTest3() {
823 LT3Detail::RecordType rec1;
824 auto equals = [&rec1](LT3Detail::RecordType rec2) {
825 return rec1.x == rec2.x;
826 };
827 LambdaTest3<decltype(equals)>(equals, int());
828}
829#else
830namespace LT3Detail {
831
832struct RecordType {
833 int x;
834 int y;
835};
836
837} // namespace LT3Detail
838template <class Callable>
839struct LambdaTest3 {
840 Callable functor;
841
842 LambdaTest3(const Callable &functor, int) : functor(functor) {}
843};
844
845void fLambdaTest3() {
846 LT3Detail::RecordType rec1;
847 auto equals = [&rec1](LT3Detail::RecordType rec2) {
848 return rec1.x == rec2.x;
849 };
850 LambdaTest3<decltype(equals)>(equals, int());
851}
852#endif //PEDANTIC
853
Kristof Umann8c119092018-07-13 12:54:47 +0000854template <class Callable>
855struct MultipleLambdaCapturesTest1 {
856 Callable functor;
857 int dontGetFilteredByNonPedanticMode = 0;
858
859 MultipleLambdaCapturesTest1(const Callable &functor, int) : functor(functor) {} // expected-warning{{2 uninitialized field}}
860};
861
862void fMultipleLambdaCapturesTest1() {
863 int b1, b2 = 3, b3;
Kristof Umannf0dd1012018-09-14 08:58:21 +0000864 auto equals = [&b1, &b2, &b3](int a) { return a == b1 == b2 == b3; }; // expected-note{{uninitialized pointee 'this->functor./*captured variable*/b1'}}
865 // expected-note@-1{{uninitialized pointee 'this->functor./*captured variable*/b3'}}
Kristof Umann8c119092018-07-13 12:54:47 +0000866 MultipleLambdaCapturesTest1<decltype(equals)>(equals, int());
867}
868
869template <class Callable>
870struct MultipleLambdaCapturesTest2 {
871 Callable functor;
872 int dontGetFilteredByNonPedanticMode = 0;
873
874 MultipleLambdaCapturesTest2(const Callable &functor, int) : functor(functor) {} // expected-warning{{1 uninitialized field}}
875};
876
877void fMultipleLambdaCapturesTest2() {
878 int b1, b2 = 3, b3;
Kristof Umannf0dd1012018-09-14 08:58:21 +0000879 auto equals = [b1, &b2, &b3](int a) { return a == b1 == b2 == b3; }; // expected-note{{uninitialized pointee 'this->functor./*captured variable*/b3'}}
Kristof Umann8c119092018-07-13 12:54:47 +0000880 MultipleLambdaCapturesTest2<decltype(equals)>(equals, int());
881}
882
Kristof Umannf0dd1012018-09-14 08:58:21 +0000883struct LambdaWrapper {
884 void *func; // no-crash
885 int dontGetFilteredByNonPedanticMode = 0;
886
887 LambdaWrapper(void *ptr) : func(ptr) {} // expected-warning{{1 uninitialized field}}
888};
889
890struct ThisCapturingLambdaFactory {
891 int a; // expected-note{{uninitialized field 'static_cast<decltype(a.ret()) *>(this->func)->/*'this' capture*/->a'}}
892
893 auto ret() {
894 return [this] { (void)this; };
895 }
896};
897
898void fLambdaFieldWithInvalidThisCapture() {
899 void *ptr;
900 {
901 ThisCapturingLambdaFactory a;
902 decltype(a.ret()) lambda = a.ret();
903 ptr = &lambda;
904 }
905 LambdaWrapper t(ptr);
906}
907
Kristof Umann30f08652018-06-18 11:50:17 +0000908//===----------------------------------------------------------------------===//
909// System header tests.
910//===----------------------------------------------------------------------===//
911
912#include "Inputs/system-header-simulator-for-cxx-uninitialized-object.h"
913
914struct SystemHeaderTest1 {
915 RecordInSystemHeader rec; // defined in the system header simulator
916
917 SystemHeaderTest1() {
918 // All good!
919 }
920};
921
922void fSystemHeaderTest1() {
923 SystemHeaderTest1();
924}
925
926#ifdef PEDANTIC
927struct SystemHeaderTest2 {
928 struct RecordType {
929 int x; // expected-note{{uninitialized field 'this->container.t.x}}
930 int y; // expected-note{{uninitialized field 'this->container.t.y}}
931 };
932 ContainerInSystemHeader<RecordType> container;
933
934 SystemHeaderTest2(RecordType &rec, int) : container(rec) {} // expected-warning{{2 uninitialized fields}}
935};
936
937void fSystemHeaderTest2() {
938 SystemHeaderTest2::RecordType rec;
939 SystemHeaderTest2(rec, int());
940}
941#else
942struct SystemHeaderTest2 {
943 struct RecordType {
944 int x;
945 int y;
946 };
947 ContainerInSystemHeader<RecordType> container;
948
949 SystemHeaderTest2(RecordType &rec, int) : container(rec) {}
950};
951
952void fSystemHeaderTest2() {
953 SystemHeaderTest2::RecordType rec;
954 SystemHeaderTest2(rec, int());
955}
956#endif //PEDANTIC
957
958//===----------------------------------------------------------------------===//
959// Incomplete type tests.
960//===----------------------------------------------------------------------===//
961
962struct IncompleteTypeTest1 {
963 struct RecordType;
964 // no-crash
965 RecordType *recptr; // expected-note{{uninitialized pointer 'this->recptr}}
966 int dontGetFilteredByNonPedanticMode = 0;
967
968 IncompleteTypeTest1() {} // expected-warning{{1 uninitialized field}}
969};
970
971void fIncompleteTypeTest1() {
972 IncompleteTypeTest1();
973}
974
975struct IncompleteTypeTest2 {
976 struct RecordType;
977 RecordType *recptr; // no-crash
978 int dontGetFilteredByNonPedanticMode = 0;
979
980 RecordType *recordTypeFactory();
981
982 IncompleteTypeTest2() : recptr(recordTypeFactory()) {}
983};
984
985void fIncompleteTypeTest2() {
986 IncompleteTypeTest2();
987}
988
989struct IncompleteTypeTest3 {
990 struct RecordType;
991 RecordType &recref; // no-crash
992 int dontGetFilteredByNonPedanticMode = 0;
993
994 RecordType &recordTypeFactory();
995
996 IncompleteTypeTest3() : recref(recordTypeFactory()) {}
997};
998
999void fIncompleteTypeTest3() {
1000 IncompleteTypeTest3();
1001}
1002
1003//===----------------------------------------------------------------------===//
1004// Builtin type or enumeration type related tests.
1005//===----------------------------------------------------------------------===//
1006
1007struct IntegralTypeTest {
1008 int a; // expected-note{{uninitialized field 'this->a'}}
1009 int dontGetFilteredByNonPedanticMode = 0;
1010
1011 IntegralTypeTest() {} // expected-warning{{1 uninitialized field}}
1012};
1013
1014void fIntegralTypeTest() {
1015 IntegralTypeTest();
1016}
1017
1018struct FloatingTypeTest {
1019 float a; // expected-note{{uninitialized field 'this->a'}}
1020 int dontGetFilteredByNonPedanticMode = 0;
1021
1022 FloatingTypeTest() {} // expected-warning{{1 uninitialized field}}
1023};
1024
1025void fFloatingTypeTest() {
1026 FloatingTypeTest();
1027}
1028
1029struct NullptrTypeTypeTest {
1030 decltype(nullptr) a; // expected-note{{uninitialized field 'this->a'}}
1031 int dontGetFilteredByNonPedanticMode = 0;
1032
1033 NullptrTypeTypeTest() {} // expected-warning{{1 uninitialized field}}
1034};
1035
1036void fNullptrTypeTypeTest() {
1037 NullptrTypeTypeTest();
1038}
1039
1040struct EnumTest {
1041 enum Enum {
1042 A,
1043 B
1044 } enum1; // expected-note{{uninitialized field 'this->enum1'}}
1045 enum class Enum2 {
1046 A,
1047 B
1048 } enum2; // expected-note{{uninitialized field 'this->enum2'}}
1049 int dontGetFilteredByNonPedanticMode = 0;
1050
1051 EnumTest() {} // expected-warning{{2 uninitialized fields}}
1052};
1053
1054void fEnumTest() {
1055 EnumTest();
1056}
1057
1058//===----------------------------------------------------------------------===//
1059// Tests for constructor calls within another cunstructor, without the two
1060// records being in any relation.
1061//===----------------------------------------------------------------------===//
1062
1063void halt() __attribute__((__noreturn__));
1064void assert(int b) {
1065 if (!b)
1066 halt();
1067}
1068
1069// While a singleton would make more sense as a static variable, that would zero
1070// initialize all of its fields, hence the not too practical implementation.
1071struct Singleton {
Kristof Umann0735cfb2018-08-08 12:23:02 +00001072 int i; // expected-note{{uninitialized field 'this->i'}}
1073 int dontGetFilteredByNonPedanticMode = 0;
Kristof Umann30f08652018-06-18 11:50:17 +00001074
1075 Singleton() {
1076 assert(!isInstantiated);
Kristof Umann0735cfb2018-08-08 12:23:02 +00001077 isInstantiated = true; // expected-warning{{1 uninitialized field}}
Kristof Umann30f08652018-06-18 11:50:17 +00001078 }
1079
1080 ~Singleton() {
1081 isInstantiated = false;
1082 }
1083
1084 static bool isInstantiated;
1085};
1086
1087bool Singleton::isInstantiated = false;
1088
1089struct SingletonTest {
1090 int dontGetFilteredByNonPedanticMode = 0;
1091
1092 SingletonTest() {
1093 Singleton();
1094 }
1095};
1096
1097void fSingletonTest() {
1098 SingletonTest();
1099}
1100
1101//===----------------------------------------------------------------------===//
1102// C++11 member initializer tests.
1103//===----------------------------------------------------------------------===//
1104
1105struct CXX11MemberInitTest1 {
1106 int a = 3;
1107 int b;
1108 CXX11MemberInitTest1() : b(2) {
1109 // All good!
1110 }
1111};
1112
1113void fCXX11MemberInitTest1() {
1114 CXX11MemberInitTest1();
1115}
1116
1117struct CXX11MemberInitTest2 {
1118 struct RecordType {
1119 // TODO: we'd expect the note: {{uninitialized field 'this->rec.a'}}
1120 int a; // no-note
1121 // TODO: we'd expect the note: {{uninitialized field 'this->rec.b'}}
1122 int b; // no-note
1123
1124 RecordType(int) {}
1125 };
1126
1127 RecordType rec = RecordType(int());
1128 int dontGetFilteredByNonPedanticMode = 0;
1129
1130 CXX11MemberInitTest2() {}
1131};
1132
1133void fCXX11MemberInitTest2() {
1134 // TODO: we'd expect the warning: {{2 uninitializeds field}}
1135 CXX11MemberInitTest2(); // no-warning
1136}
Kristof Umannf46c58e2019-04-25 20:00:51 +00001137
1138//===----------------------------------------------------------------------===//
Kristof Umannc21ec002019-04-30 08:47:56 +00001139// "Esoteric" primitive type tests.
Kristof Umannf46c58e2019-04-25 20:00:51 +00001140//===----------------------------------------------------------------------===//
1141
1142struct MyAtomicInt {
1143 _Atomic(int) x; // expected-note{{uninitialized field 'this->x'}}
1144 int dontGetFilteredByNonPedanticMode = 0;
1145
1146 MyAtomicInt() {} // expected-warning{{1 uninitialized field}}
1147};
1148
Kristof Umannc21ec002019-04-30 08:47:56 +00001149void _AtomicTest() {
Kristof Umannf46c58e2019-04-25 20:00:51 +00001150 MyAtomicInt b;
1151}
Kristof Umannc21ec002019-04-30 08:47:56 +00001152
1153struct VectorSizeLong {
1154 VectorSizeLong() {}
1155 __attribute__((__vector_size__(16))) long x;
1156};
1157
1158void __vector_size__LongTest() {
1159 // TODO: Warn for v.x.
1160 VectorSizeLong v;
1161 v.x[0] = 0;
1162}
Kristof Umannaa9d2622019-05-05 19:42:33 +00001163
1164struct ComplexUninitTest {
1165 ComplexUninitTest() {}
1166 __complex__ float x;
1167 __complex__ int y;
1168};
1169
Kristof Umannf40c18b2019-05-18 12:34:08 +00001170struct ComplexInitTest {
1171 ComplexInitTest() {
1172 x = {1.0f, 1.0f};
1173 y = {1, 1};
1174 }
1175 __complex__ float x;
1176 __complex__ int y;
1177};
Kristof Umannaa9d2622019-05-05 19:42:33 +00001178
1179void fComplexTest() {
Kristof Umannf40c18b2019-05-18 12:34:08 +00001180 ComplexInitTest x;
Kristof Umannaa9d2622019-05-05 19:42:33 +00001181
1182 // TODO: we should emit a warning for x2.x and x2.y.
1183 ComplexUninitTest x2;
1184}