1 // RUN: %clang_cc1 -analyze -analyzer-checker=core,unix.Malloc,debug.ExprInspection -analyzer-store region -std=c++11 -verify %s
2
3 void clang_analyzer_eval(bool);
4
5 typedef __typeof__(sizeof(int)) size_t;
6 extern "C" void *malloc(size_t);
7
8 int someGlobal;
testImplicitlyDeclaredGlobalNew()9 void testImplicitlyDeclaredGlobalNew() {
10 if (someGlobal != 0)
11 return;
12
13 // This used to crash because the global operator new is being implicitly
14 // declared and it does not have a valid source location. (PR13090)
15 void *x = ::operator new(0);
16 ::operator delete(x);
17
18 // Check that the new/delete did not invalidate someGlobal;
19 clang_analyzer_eval(someGlobal == 0); // expected-warning{{TRUE}}
20 }
21
22
23 // This is the standard placement new.
operator new(size_t,void * __p)24 inline void* operator new(size_t, void* __p) throw()
25 {
26 return __p;
27 }
28
testPlacementNew()29 void *testPlacementNew() {
30 int *x = (int *)malloc(sizeof(int));
31 *x = 1;
32 clang_analyzer_eval(*x == 1); // expected-warning{{TRUE}};
33
34 void *y = new (x) int;
35 clang_analyzer_eval(x == y); // expected-warning{{TRUE}};
36 clang_analyzer_eval(*x == 1); // expected-warning{{UNKNOWN}};
37
38 return y;
39 }
40
41 void *operator new(size_t, size_t, int *);
testCustomNew()42 void *testCustomNew() {
43 int x[1] = {1};
44 clang_analyzer_eval(*x == 1); // expected-warning{{TRUE}};
45
46 void *y = new (0, x) int;
47 clang_analyzer_eval(*x == 1); // expected-warning{{UNKNOWN}};
48
49 return y; // no-warning
50 }
51
52 void *operator new(size_t, void *, void *);
testCustomNewMalloc()53 void *testCustomNewMalloc() {
54 int *x = (int *)malloc(sizeof(int));
55
56 // Should be no-warning (the custom allocator could have freed x).
57 void *y = new (0, x) int; // no-warning
58
59 return y;
60 }
61
testScalarInitialization()62 void testScalarInitialization() {
63 int *n = new int(3);
64 clang_analyzer_eval(*n == 3); // expected-warning{{TRUE}}
65
66 new (n) int();
67 clang_analyzer_eval(*n == 0); // expected-warning{{TRUE}}
68
69 new (n) int{3};
70 clang_analyzer_eval(*n == 3); // expected-warning{{TRUE}}
71
72 new (n) int{};
73 clang_analyzer_eval(*n == 0); // expected-warning{{TRUE}}
74 }
75
76
77 struct PtrWrapper {
78 int *x;
79
PtrWrapperPtrWrapper80 PtrWrapper(int *input) : x(input) {}
81 };
82
testNewInvalidation()83 PtrWrapper *testNewInvalidation() {
84 // Ensure that we don't consider this a leak.
85 return new PtrWrapper(static_cast<int *>(malloc(4)));
86 }
87
88
89 //--------------------------------
90 // Incorrectly-modelled behavior
91 //--------------------------------
92
testNoInitialization()93 int testNoInitialization() {
94 int *n = new int;
95
96 // Should warn that *n is uninitialized.
97 if (*n) { // no-warning
98 return 0;
99 }
100 return 1;
101 }
102
testNoInitializationPlacement()103 int testNoInitializationPlacement() {
104 int n;
105 new (&n) int;
106
107 // Should warn that n is uninitialized.
108 if (n) { // no-warning
109 return 0;
110 }
111 return 1;
112 }
113