xref: /llvm-project/clang/test/Analysis/invalidated-iterator.cpp (revision 05d8b5e62d7a1cf2f94582346d6fd2d39667a26b)
1 // RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=core,cplusplus,alpha.cplusplus.InvalidatedIterator -analyzer-config aggressive-binary-operation-simplification=true -analyzer-config c++-container-inlining=false %s -verify
2 // RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=core,cplusplus,alpha.cplusplus.InvalidatedIterator -analyzer-config aggressive-binary-operation-simplification=true -analyzer-config c++-container-inlining=true -DINLINE=1 %s -verify
3 
4 #include "Inputs/system-header-simulator-cxx.h"
5 
6 void clang_analyzer_warnIfReached();
7 
normal_dereference(std::vector<int> & V)8 void normal_dereference(std::vector<int> &V) {
9   auto i = V.cbegin();
10   *i; // no-warning
11 }
12 
invalidated_dereference(std::vector<int> & V)13 void invalidated_dereference(std::vector<int> &V) {
14   auto i = V.cbegin();
15   V.erase(i);
16   *i; // expected-warning{{Invalidated iterator accessed}}
17 }
18 
normal_prefix_increment(std::vector<int> & V)19 void normal_prefix_increment(std::vector<int> &V) {
20   auto i = V.cbegin();
21   ++i; // no-warning
22 }
23 
invalidated_prefix_increment(std::vector<int> & V)24 void invalidated_prefix_increment(std::vector<int> &V) {
25   auto i = V.cbegin();
26   V.erase(i);
27   ++i; // expected-warning{{Invalidated iterator accessed}}
28 }
29 
normal_prefix_decrement(std::vector<int> & V)30 void normal_prefix_decrement(std::vector<int> &V) {
31   auto i = ++V.cbegin();
32   --i; // no-warning
33 }
34 
invalidated_prefix_decrement(std::vector<int> & V)35 void invalidated_prefix_decrement(std::vector<int> &V) {
36   auto i = ++V.cbegin();
37   V.erase(i);
38   --i; // expected-warning{{Invalidated iterator accessed}}
39 }
40 
normal_postfix_increment(std::vector<int> & V)41 void normal_postfix_increment(std::vector<int> &V) {
42   auto i = V.cbegin();
43   i++; // no-warning
44 }
45 
invalidated_postfix_increment(std::vector<int> & V)46 void invalidated_postfix_increment(std::vector<int> &V) {
47   auto i = V.cbegin();
48   V.erase(i);
49   i++; // expected-warning{{Invalidated iterator accessed}}
50 }
51 
normal_postfix_decrement(std::vector<int> & V)52 void normal_postfix_decrement(std::vector<int> &V) {
53   auto i = ++V.cbegin();
54   i--; // no-warning
55 }
56 
invalidated_postfix_decrement(std::vector<int> & V)57 void invalidated_postfix_decrement(std::vector<int> &V) {
58   auto i = ++V.cbegin();
59   V.erase(i);
60   i--; // expected-warning{{Invalidated iterator accessed}}
61 }
62 
normal_increment_by_2(std::vector<int> & V)63 void normal_increment_by_2(std::vector<int> &V) {
64   auto i = V.cbegin();
65   i += 2; // no-warning
66 }
67 
invalidated_increment_by_2(std::vector<int> & V)68 void invalidated_increment_by_2(std::vector<int> &V) {
69   auto i = V.cbegin();
70   V.erase(i);
71   i += 2; // expected-warning{{Invalidated iterator accessed}}
72 }
73 
normal_increment_by_2_copy(std::vector<int> & V)74 void normal_increment_by_2_copy(std::vector<int> &V) {
75   auto i = V.cbegin();
76   auto j = i + 2; // no-warning
77 }
78 
invalidated_increment_by_2_copy(std::vector<int> & V)79 void invalidated_increment_by_2_copy(std::vector<int> &V) {
80   auto i = V.cbegin();
81   V.erase(i);
82   auto j = i + 2; // expected-warning{{Invalidated iterator accessed}}
83 }
84 
normal_decrement_by_2(std::vector<int> & V)85 void normal_decrement_by_2(std::vector<int> &V) {
86   auto i = V.cbegin();
87   i -= 2; // no-warning
88 }
89 
invalidated_decrement_by_2(std::vector<int> & V)90 void invalidated_decrement_by_2(std::vector<int> &V) {
91   auto i = V.cbegin();
92   V.erase(i);
93   i -= 2; // expected-warning{{Invalidated iterator accessed}}
94 }
95 
normal_decrement_by_2_copy(std::vector<int> & V)96 void normal_decrement_by_2_copy(std::vector<int> &V) {
97   auto i = V.cbegin();
98   auto j = i - 2; // no-warning
99 }
100 
invalidated_decrement_by_2_copy(std::vector<int> & V)101 void invalidated_decrement_by_2_copy(std::vector<int> &V) {
102   auto i = V.cbegin();
103   V.erase(i);
104   auto j = i - 2; // expected-warning{{Invalidated iterator accessed}}
105 }
106 
normal_subscript(std::vector<int> & V)107 void normal_subscript(std::vector<int> &V) {
108   auto i = V.cbegin();
109   i[1]; // no-warning
110 }
111 
invalidated_subscript(std::vector<int> & V)112 void invalidated_subscript(std::vector<int> &V) {
113   auto i = V.cbegin();
114   V.erase(i);
115   i[1]; // expected-warning{{Invalidated iterator accessed}}
116 }
117 
assignment(std::vector<int> & V)118 void assignment(std::vector<int> &V) {
119   auto i = V.cbegin();
120   V.erase(i);
121   auto j = V.cbegin(); // no-warning
122 }
123 
124 template<typename T>
125 struct cont_with_ptr_iterator {
126   T *begin() const;
127   T *end() const;
128   T &operator[](size_t);
129   void push_back(const T&);
130   T* erase(T*);
131 };
132 
invalidated_access_via_end_iterator_after_push_back()133 void invalidated_access_via_end_iterator_after_push_back() {
134   cont_with_ptr_iterator<int> C;
135   C.push_back(1);
136   auto i = C.end();
137   C.push_back(2);
138   auto j = i[-1]; // expected-warning{{Invalidated iterator accessed}}
139 }
140 
invalidated_dereference_end_ptr_iterator(cont_with_ptr_iterator<int> & C)141 void invalidated_dereference_end_ptr_iterator(cont_with_ptr_iterator<int> &C) {
142   auto i = C.begin();
143   C.erase(i);
144   (void) *i; // expected-warning{{Invalidated iterator accessed}}
145 }
146 
invalidated_prefix_increment_end_ptr_iterator(cont_with_ptr_iterator<int> & C)147 void invalidated_prefix_increment_end_ptr_iterator(
148     cont_with_ptr_iterator<int> &C) {
149   auto i = C.begin();
150   C.erase(i);
151   ++i; // expected-warning{{Invalidated iterator accessed}}
152 }
153 
invalidated_prefix_decrement_end_ptr_iterator(cont_with_ptr_iterator<int> & C)154 void invalidated_prefix_decrement_end_ptr_iterator(
155     cont_with_ptr_iterator<int> &C) {
156   auto i = C.begin() + 1;
157   C.erase(i);
158   --i; // expected-warning{{Invalidated iterator accessed}}
159 }
160 
invalidated_postfix_increment_end_ptr_iterator(cont_with_ptr_iterator<int> & C)161 void invalidated_postfix_increment_end_ptr_iterator(
162     cont_with_ptr_iterator<int> &C) {
163   auto i = C.begin();
164   C.erase(i);
165   i++; // expected-warning{{Invalidated iterator accessed}}
166 }
167 
invalidated_postfix_decrement_end_ptr_iterator(cont_with_ptr_iterator<int> & C)168 void invalidated_postfix_decrement_end_ptr_iterator(
169     cont_with_ptr_iterator<int> &C) {
170   auto i = C.begin() + 1;
171   C.erase(i);
172   i--; // expected-warning{{Invalidated iterator accessed}}
173 }
174 
invalidated_increment_by_2_end_ptr_iterator(cont_with_ptr_iterator<int> & C)175 void invalidated_increment_by_2_end_ptr_iterator(
176     cont_with_ptr_iterator<int> &C) {
177   auto i = C.begin();
178   C.erase(i);
179   i += 2; // expected-warning{{Invalidated iterator accessed}}
180 }
181 
invalidated_increment_by_2_copy_end_ptr_iterator(cont_with_ptr_iterator<int> & C)182 void invalidated_increment_by_2_copy_end_ptr_iterator(
183     cont_with_ptr_iterator<int> &C) {
184   auto i = C.begin();
185   C.erase(i);
186   auto j = i + 2; // expected-warning{{Invalidated iterator accessed}}
187 }
188 
invalidated_decrement_by_2_end_ptr_iterator(cont_with_ptr_iterator<int> & C)189 void invalidated_decrement_by_2_end_ptr_iterator(
190     cont_with_ptr_iterator<int> &C) {
191   auto i = C.begin();
192   C.erase(i);
193   i -= 2; // expected-warning{{Invalidated iterator accessed}}
194 }
195 
invalidated_decrement_by_2_copy_end_ptr_iterator(cont_with_ptr_iterator<int> & C)196 void invalidated_decrement_by_2_copy_end_ptr_iterator(
197     cont_with_ptr_iterator<int> &C) {
198   auto i = C.begin();
199   C.erase(i);
200   auto j = i - 2; // expected-warning{{Invalidated iterator accessed}}
201 }
202 
invalidated_subscript_end_ptr_iterator(cont_with_ptr_iterator<int> & C)203 void invalidated_subscript_end_ptr_iterator(cont_with_ptr_iterator<int> &C) {
204   auto i = C.begin();
205   C.erase(i);
206   (void) i[1]; // expected-warning{{Invalidated iterator accessed}}
207 }