1 // RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -analyzer-config unroll-loops=true,cfg-loopexit=true -verify -std=c++11 %s 2 3 void clang_analyzer_numTimesReached(); 4 5 int getNum(); 6 void foo(int &); 7 // Testing for loops. 8 int simple_unroll1() { 9 int a[9]; 10 int k = 42; 11 for (int i = 0; i < 9; i++) { 12 clang_analyzer_numTimesReached(); // expected-warning {{9}} 13 a[i] = 42; 14 } 15 int b = 22 / (k - 42); // expected-warning {{Division by zero}} 16 return 0; 17 } 18 19 int simple_unroll2() { 20 int a[9]; 21 int k = 42; 22 int i; 23 for (i = 0; i < 9; i++) { 24 clang_analyzer_numTimesReached(); // expected-warning {{9}} 25 a[i] = 42; 26 } 27 28 for (int j = 0; j <= 9; ++j) { 29 clang_analyzer_numTimesReached(); // expected-warning {{10}} 30 a[j] = 42; 31 } 32 33 int b = 22 / (k - 42); // expected-warning {{Division by zero}} 34 return 0; 35 } 36 37 int simple_no_unroll1() { 38 int a[9]; 39 int k = 42; 40 for (int i = 0; i < 9; i++) { 41 clang_analyzer_numTimesReached(); // expected-warning {{4}} 42 a[i] = 42; 43 foo(i); 44 } 45 int b = 22 / (k - 42); // expected-warning {{Division by zero}} 46 return 0; 47 } 48 49 int simple_no_unroll2() { 50 int a[9]; 51 int k = 42; 52 int i; 53 for (i = 0; i < 9; i++) { 54 clang_analyzer_numTimesReached(); // expected-warning {{4}} 55 a[i] = 42; 56 i += getNum(); 57 } 58 int b = 22 / (k - 42); // expected-warning {{Division by zero}} 59 return 0; 60 } 61 62 int simple_no_unroll3() { 63 int a[9]; 64 int k = 42; 65 int i; 66 for (i = 0; i < 9; i++) { 67 clang_analyzer_numTimesReached(); // expected-warning {{4}} 68 a[i] = 42; 69 (void)&i; 70 } 71 int b = 22 / (k - 42); // no-warning 72 return 0; 73 } 74 75 int simple_no_unroll4() { 76 int a[9]; 77 int k = 42; 78 int i; 79 for (i = 0; i < 9; i++) { 80 clang_analyzer_numTimesReached(); // expected-warning {{4}} 81 a[i] = 42; 82 int &j = i; 83 } 84 int b = 22 / (k - 42); // no-warning 85 return 0; 86 } 87 88 int simple_no_unroll5() { 89 int a[9]; 90 int k = 42; 91 int i; 92 for (i = 0; i < 9; i++) { 93 clang_analyzer_numTimesReached(); // expected-warning {{4}} 94 a[i] = 42; 95 int &j{i}; 96 } 97 int b = 22 / (k - 42); // no-warning 98 return 0; 99 } 100 101 int escape_before_loop_no_unroll1() { 102 int a[9]; 103 int k = 42; 104 int i; 105 int &j = i; 106 for (i = 0; i < 9; i++) { 107 clang_analyzer_numTimesReached(); // expected-warning {{4}} 108 a[i] = 42; 109 } 110 int b = 22 / (k - 42); // no-warning 111 return 0; 112 } 113 114 int escape_before_loop_no_unroll2() { 115 int a[9]; 116 int k = 42; 117 int i; 118 int *p = &i; 119 for (i = 0; i < 9; i++) { 120 clang_analyzer_numTimesReached(); // expected-warning {{4}} 121 a[i] = 42; 122 } 123 int b = 22 / (k - 42); // no-warning 124 return 0; 125 } 126 127 int escape_before_loop_no_unroll3() { 128 int a[9]; 129 int k = 42; 130 int i; 131 foo(i); 132 for (i = 0; i < 9; i++) { 133 clang_analyzer_numTimesReached(); // expected-warning {{4}} 134 a[i] = 42; 135 } 136 int b = 22 / (k - 42); // no-warning 137 return 0; 138 } 139 140 int nested_outer_unrolled() { 141 int a[9]; 142 int k = 42; 143 int j = 0; 144 for (int i = 0; i < 9; i++) { 145 clang_analyzer_numTimesReached(); // expected-warning {{16}} 146 for (j = 0; j < getNum(); ++j) { 147 clang_analyzer_numTimesReached(); // expected-warning {{15}} 148 a[j] = 22; 149 } 150 a[i] = 42; 151 } 152 int b = 22 / (k - 42); // no-warning 153 return 0; 154 } 155 156 int nested_inner_unrolled() { 157 int a[9]; 158 int k = 42; 159 int j = 0; 160 for (int i = 0; i < getNum(); i++) { 161 clang_analyzer_numTimesReached(); // expected-warning {{4}} 162 for (j = 0; j < 8; ++j) { 163 clang_analyzer_numTimesReached(); // expected-warning {{32}} 164 a[j] = 22; 165 } 166 a[i] = 42; 167 } 168 int b = 22 / (k - 42); // expected-warning {{Division by zero}} 169 return 0; 170 } 171 172 int nested_both_unrolled() { 173 int a[9]; 174 int k = 42; 175 int j = 0; 176 for (int i = 0; i < 7; i++) { 177 clang_analyzer_numTimesReached(); // expected-warning {{7}} 178 for (j = 0; j < 6; ++j) { 179 clang_analyzer_numTimesReached(); // expected-warning {{42}} 180 a[j] = 22; 181 } 182 a[i] = 42; 183 } 184 int b = 22 / (k - 42); // expected-warning {{Division by zero}} 185 return 0; 186 } 187 188 int simple_known_bound_loop() { 189 for (int i = 2; i < 12; i++) { 190 // This function is inlined in nested_inlined_unroll1() 191 clang_analyzer_numTimesReached(); // expected-warning {{90}} 192 } 193 return 0; 194 } 195 196 int simple_unknown_bound_loop() { 197 for (int i = 2; i < getNum(); i++) { 198 clang_analyzer_numTimesReached(); // expected-warning {{10}} 199 } 200 return 0; 201 } 202 203 int nested_inlined_unroll1() { 204 int k; 205 for (int i = 0; i < 9; i++) { 206 clang_analyzer_numTimesReached(); // expected-warning {{9}} 207 k = simple_known_bound_loop(); // no reevaluation without inlining 208 } 209 int a = 22 / k; // expected-warning {{Division by zero}} 210 return 0; 211 } 212 213 int nested_inlined_no_unroll1() { 214 int k; 215 for (int i = 0; i < 9; i++) { 216 clang_analyzer_numTimesReached(); // expected-warning {{26}} 217 k = simple_unknown_bound_loop(); // reevaluation without inlining 218 } 219 int a = 22 / k; // no-warning 220 return 0; 221 } 222 223 224 int recursion_unroll1(bool b) { 225 int k = 2; 226 for (int i = 0; i < 5; i++) { 227 clang_analyzer_numTimesReached(); // expected-warning {{14}} 228 if(i == 0 && b) 229 recursion_unroll1(false); 230 clang_analyzer_numTimesReached(); // expected-warning {{15}} 231 } 232 int a = 22 / k; // no-warning 233 return 0; 234 } 235 236 int recursion_unroll2(bool b) { 237 int k = 0; 238 for (int i = 0; i < 5; i++) { 239 clang_analyzer_numTimesReached(); // expected-warning {{10}} 240 if(i == 0 && b) 241 recursion_unroll2(false); 242 clang_analyzer_numTimesReached(); // expected-warning {{10}} 243 } 244 int a = 22 / k; // expected-warning {{Division by zero}} 245 return 0; 246 } 247 248 int recursion_unroll3(bool b) { 249 int k = 2; 250 for (int i = 0; i < 5; i++) { 251 clang_analyzer_numTimesReached(); // expected-warning {{10}} 252 if(i == 4 && b) { 253 recursion_unroll3(false); 254 break; 255 } 256 clang_analyzer_numTimesReached(); // expected-warning {{10}} 257 } 258 int a = 22 / k; 259 return 0; 260 } 261 262 int recursion_unroll4(bool b) { 263 int k = 2; 264 for (int i = 0; i < 5; i++) { 265 clang_analyzer_numTimesReached(); // expected-warning {{14}} 266 if(i == 0 && b) { 267 recursion_unroll4(false); 268 continue; 269 } 270 clang_analyzer_numTimesReached(); // expected-warning {{14}} 271 } 272 int a = 22 / k; 273 return 0; 274 } 275