[clang-cl] Ignore /Wv and /Wv:17 flags
[llvm-project.git] / clang / test / Analysis / dead-stores.c
blob701e0a58b84ed774ff5eaa722b4b7a93dba72153
1 // RUN: %check_analyzer_fixit %s %t \
2 // RUN: -Wunused-variable -fblocks -Wno-unreachable-code \
3 // RUN: -analyzer-checker=core,deadcode.DeadStores \
4 // RUN: -analyzer-config deadcode.DeadStores:ShowFixIts=true \
5 // RUN: -analyzer-config \
6 // RUN: deadcode.DeadStores:WarnForDeadNestedAssignments=false \
7 // RUN: -verify=non-nested
9 // RUN: %check_analyzer_fixit %s %t \
10 // RUN: -Wunused-variable -fblocks -Wno-unreachable-code \
11 // RUN: -analyzer-checker=core,deadcode.DeadStores \
12 // RUN: -analyzer-config deadcode.DeadStores:ShowFixIts=true \
13 // RUN: -verify=non-nested,nested
15 void f1(void) {
16 int k, y; // non-nested-warning {{unused variable 'k'}}
17 // non-nested-warning@-1 {{unused variable 'y'}}
18 int abc = 1;
19 long idx = abc + 3 * 5; // non-nested-warning {{never read}}
20 // non-nested-warning@-1 {{unused variable 'idx'}}
21 // CHECK-FIXES: int abc = 1;
22 // CHECK-FIXES-NEXT: long idx;
25 void f2(void *b) {
26 char *c = (char *)b; // no-warning
27 char *d = b + 1; // non-nested-warning {{never read}}
28 // non-nested-warning@-1 {{unused variable 'd'}}
29 // CHECK-FIXES: char *c = (char *)b;
30 // CHECK-FIXES-NEXT: char *d;
32 printf("%s", c);
33 // non-nested-warning@-1 {{implicitly declaring library function 'printf' with type 'int (const char *, ...)'}}
34 // non-nested-note@-2 {{include the header <stdio.h> or explicitly provide a declaration for 'printf'}}
37 int f(void);
38 void f3(void) {
39 int r;
40 if ((r = f()) != 0) { // no-warning
41 int y = r; // no-warning
42 printf("the error is: %d\n", y);
46 void f4(int k) {
47 k = 1;
48 if (k)
49 f1();
50 k = 2; // non-nested-warning {{never read}}
53 void f5(void) {
54 int x = 4; // no-warning
55 int *p = &x; // non-nested-warning {{never read}}
56 // non-nested-warning@-1 {{unused variable 'p'}}
57 // CHECK-FIXES: int x = 4;
58 // CHECK-FIXES-NEXT: int *p;
61 int f6(void) {
62 int x = 4;
63 ++x; // no-warning
64 return 1;
67 int f7(int *p) {
68 // This is allowed for defensive programming.
69 p = 0; // no-warning
70 return 1;
73 int f7b(int *p) {
74 // This is allowed for defensive programming.
75 p = (0); // no-warning
76 return 1;
79 int f7c(int *p) {
80 // This is allowed for defensive programming.
81 p = (void *)0; // no-warning
82 return 1;
85 int f7d(int *p) {
86 // This is allowed for defensive programming.
87 p = (void *)(0); // no-warning
88 return 1;
91 // Warn for dead stores in nested expressions.
92 int f8(int *p) {
93 extern int *baz(void);
94 if ((p = baz())) // nested-warning {{Although the value stored}}
95 return 1;
96 return 0;
99 int f9(void) {
100 int x = 4;
101 x = x + 10; // non-nested-warning {{never read}}
102 return 1;
105 int f10(void) {
106 int x = 4;
107 x = 10 + x; // non-nested-warning {{never read}}
108 return 1;
111 int f11(void) {
112 int x = 4;
113 return x++; // non-nested-warning {{never read}}
116 int f11b(void) {
117 int x = 4;
118 return ((((++x)))); // no-warning
121 int f12a(int y) {
122 int x = y; // non-nested-warning {{unused variable 'x'}}
123 return 1;
126 int f12b(int y) {
127 int x __attribute__((unused)) = y; // no-warning
128 return 1;
131 int f12c(int y) {
132 // Allow initialiation of scalar variables by parameters as a form of
133 // defensive programming.
134 int x = y; // no-warning
135 x = 1;
136 return x;
139 // Filed with PR 2630. This code should produce no warnings.
140 int f13(void) {
141 int a = 1;
142 int b, c = b = a + a;
144 if (b > 0)
145 return (0);
146 return (a + b + c);
149 // Filed with PR 2763.
150 int f14(int count) {
151 int index, nextLineIndex;
152 for (index = 0; index < count; index = nextLineIndex + 1) {
153 nextLineIndex = index + 1; // no-warning
154 continue;
156 return index;
159 // Test case for <rdar://problem/6248086>
160 void f15(unsigned x, unsigned y) {
161 int count = x * y; // no-warning
162 int z[count]; // non-nested-warning {{unused variable 'z'}}
165 // Warn for dead stores in nested expressions.
166 int f16(int x) {
167 x = x * 2;
168 x = sizeof(int[x = (x || x + 1) * 2]) ? 5 : 8;
169 // nested-warning@-1 {{Although the value stored}}
170 return x;
173 // Self-assignments should not be flagged as dead stores.
174 void f17(void) {
175 int x = 1;
176 x = x;
179 // <rdar://problem/6506065>
180 // The values of dead stores are only "consumed" in an enclosing expression
181 // what that value is actually used. In other words, don't say "Although the
182 // value stored to 'x' is used...".
183 int f18(void) {
184 int x = 0; // no-warning
185 if (1)
186 x = 10; // non-nested-warning {{Value stored to 'x' is never read}}
187 while (1)
188 x = 10; // non-nested-warning {{Value stored to 'x' is never read}}
189 // unreachable.
191 x = 10; // no-warning
192 while (1);
193 return (x = 10); // no-warning
196 int f18_a(void) {
197 int x = 0; // no-warning
198 return (x = 10); // nested-warning {{Although the value stored}}
201 void f18_b(void) {
202 int x = 0; // no-warning
203 if (1)
204 x = 10; // non-nested-warning {{Value stored to 'x' is never read}}
207 void f18_c(void) {
208 int x = 0;
209 while (1)
210 x = 10; // non-nested-warning {{Value stored to 'x' is never read}}
213 void f18_d(void) {
214 int x = 0; // no-warning
216 x = 10; // non-nested-warning {{Value stored to 'x' is never read}}
217 while (1);
220 // PR 3514: false positive `dead initialization` warning for init to global
221 // http://llvm.org/bugs/show_bug.cgi?id=3514
222 extern const int MyConstant;
223 int f19(void) {
224 int x = MyConstant; // no-warning
225 x = 1;
226 return x;
229 int f19b(void) { // This case is the same as f19.
230 const int MyConstant = 0;
231 int x = MyConstant; // no-warning
232 x = 1;
233 return x;
236 void f20(void) {
237 int x = 1; // no-warning
238 #pragma unused(x)
241 void halt(void) __attribute__((noreturn));
242 int f21(void) {
243 int x = 4;
244 x = x + 1; // non-nested-warning {{never read}}
245 if (1) {
246 halt();
247 (void)x;
249 return 1;
252 int j;
253 void f22(void) {
254 int x = 4;
255 int y1 = 4;
256 int y2 = 4;
257 int y3 = 4;
258 int y4 = 4;
259 int y5 = 4;
260 int y6 = 4;
261 int y7 = 4;
262 int y8 = 4;
263 int y9 = 4;
264 int y10 = 4;
265 int y11 = 4;
266 int y12 = 4;
267 int y13 = 4;
268 int y14 = 4;
269 int y15 = 4;
270 int y16 = 4;
271 int y17 = 4;
272 int y18 = 4;
273 int y19 = 4;
274 int y20 = 4;
276 x = x + 1; // non-nested-warning {{never read}}
277 ++y1;
278 ++y2;
279 ++y3;
280 ++y4;
281 ++y5;
282 ++y6;
283 ++y7;
284 ++y8;
285 ++y9;
286 ++y10;
287 ++y11;
288 ++y12;
289 ++y13;
290 ++y14;
291 ++y15;
292 ++y16;
293 ++y17;
294 ++y18;
295 ++y19;
296 ++y20;
298 switch (j) {
299 case 1:
300 if (0)
301 (void)x;
302 if (1) {
303 (void)y1;
304 return;
306 (void)x;
307 break;
308 case 2:
309 if (0)
310 (void)x;
311 else {
312 (void)y2;
313 return;
315 (void)x;
316 break;
317 case 3:
318 if (1) {
319 (void)y3;
320 return;
321 } else
322 (void)x;
323 (void)x;
324 break;
325 case 4:
326 0 ?: ((void)y4, ({ return; }));
327 (void)x;
328 break;
329 case 5:
330 1 ?: (void)x;
331 0 ? (void)x : ((void)y5, ({ return; }));
332 (void)x;
333 break;
334 case 6:
335 1 ? ((void)y6, ({ return; })) : (void)x;
336 (void)x;
337 break;
338 case 7:
339 (void)(0 && x);
340 (void)y7;
341 (void)(0 || (y8, ({ return; }), 1));
342 // non-nested-warning@-1 {{left operand of comma operator has no effect}}
343 (void)x;
344 break;
345 case 8:
346 (void)(1 && (y9, ({ return; }), 1));
347 // non-nested-warning@-1 {{left operand of comma operator has no effect}}
348 (void)x;
349 break;
350 case 9:
351 (void)(1 || x);
352 (void)y10;
353 break;
354 case 10:
355 while (0) {
356 (void)x;
358 (void)y11;
359 break;
360 case 11:
361 while (1) {
362 (void)y12;
364 (void)x;
365 break;
366 case 12:
367 do {
368 (void)y13;
369 } while (0);
370 (void)y14;
371 break;
372 case 13:
373 do {
374 (void)y15;
375 } while (1);
376 (void)x;
377 break;
378 case 14:
379 for (;;) {
380 (void)y16;
382 (void)x;
383 break;
384 case 15:
385 for (; 1;) {
386 (void)y17;
388 (void)x;
389 break;
390 case 16:
391 for (; 0;) {
392 (void)x;
394 (void)y18;
395 break;
396 case 17:
397 __builtin_choose_expr(0, (void)x, ((void)y19, ({ return; })));
398 (void)x;
399 break;
400 case 19:
401 __builtin_choose_expr(1, ((void)y20, ({ return; })), (void)x);
402 (void)x;
403 break;
407 void f23_aux(const char *s);
408 void f23(int argc, char **argv) {
409 int shouldLog = (argc > 1); // no-warning
411 if (shouldLog)
412 f23_aux("I did too use it!\n");
413 else
414 f23_aux("I shouldn't log. Wait.. d'oh!\n");
415 }();
418 void f23_pos(int argc, char **argv) {
419 int shouldLog = (argc > 1);
420 // non-nested-warning@-1 {{Value stored to 'shouldLog' during its initialization is never read}}
421 // non-nested-warning@-2 {{unused variable 'shouldLog'}}
422 // CHECK-FIXES: void f23_pos(int argc, char **argv) {
423 // CHECK-FIXES-NEXT: int shouldLog;
425 f23_aux("I did too use it!\n");
426 }();
429 void f24_A(int y) {
430 // FIXME: One day this should be reported as dead since 'z = x + y' is dead.
431 int x = (y > 2); // no-warning
433 int z = x + y;
434 // non-nested-warning@-1 {{Value stored to 'z' during its initialization is never read}}
435 // non-nested-warning@-2 {{unused variable 'z'}}
436 // CHECK-FIXES: void f24_A(int y) {
437 // CHECK-FIXES-NEXT: //
438 // CHECK-FIXES-NEXT: int x = (y > 2);
439 // CHECK-FIXES-NEXT: ^{
440 // CHECK-FIXES-NEXT: int z;
441 }();
444 void f24_B(int y) {
445 // FIXME: One day this should be reported as dead since 'x' is just overwritten.
446 __block int x = (y > 2); // no-warning
448 // FIXME: This should eventually be a dead store since it is never read either.
449 x = 5; // no-warning
450 }();
453 int f24_C(int y) {
454 // FIXME: One day this should be reported as dead since 'x' is just overwritten.
455 __block int x = (y > 2); // no-warning
457 x = 5; // no-warning
458 }();
459 return x;
462 int f24_D(int y) {
463 __block int x = (y > 2); // no-warning
465 if (y > 4)
466 x = 5; // no-warning
467 }();
468 return x;
471 // This example shows that writing to a variable captured by a block means that
472 // it might not be dead.
473 int f25(int y) {
474 __block int x = (y > 2);
475 __block int z = 0;
476 void (^foo)(void) = ^{
477 z = x + y;
479 x = 4; // no-warning
480 foo();
481 return z;
484 // This test is mostly the same as 'f25', but shows that the heuristic of
485 // pruning out dead stores for variables that are just marked '__block' is
486 // overly conservative.
487 int f25_b(int y) {
488 // FIXME: we should eventually report a dead store here.
489 __block int x = (y > 2);
490 __block int z = 0;
491 x = 4; // no-warning
492 return z;
495 int f26_nestedblocks(void) {
496 int z;
497 z = 1;
498 __block int y = 0;
500 int k;
501 k = 1; // non-nested-warning {{Value stored to 'k' is never read}}
503 y = z + 1;
504 }();
505 }();
506 return y;
509 // The FOREACH macro in QT uses 'break' statements within statement expressions
510 // placed within the increment code of for loops.
511 void rdar8014335(void) {
512 for (int i = 0 ; i != 10 ; ({ break; })) {
513 for (;; ({ ++i; break; }))
515 // non-nested-warning@-2 {{'break' is bound to current loop, GCC binds it to the enclosing loop}}
516 // Note that the next value stored to 'i' is never executed
517 // because the next statement to be executed is the 'break'
518 // in the increment code of the first loop.
519 i = i * 3; // non-nested-warning {{Value stored to 'i' is never read}}
523 // <rdar://problem/8320674> NullStmts followed by do...while() can lead to disconnected CFG
525 // This previously caused bogus dead-stores warnings because the body of the first do...while was
526 // disconnected from the entry of the function.
527 typedef struct { float r; float i; } s_rdar8320674;
528 typedef struct { s_rdar8320674 x[1]; } s2_rdar8320674;
530 void rdar8320674(s_rdar8320674 *z, unsigned y, s2_rdar8320674 *st, int m)
532 s_rdar8320674 * z2;
533 s_rdar8320674 * tw1 = st->x;
534 s_rdar8320674 t;
535 z2 = z + m;
538 do{ (t).r = (*z2).r*(*tw1).r - (*z2).i*(*tw1).i; (t).i = (*z2).r*(*tw1).i + (*z2).i*(*tw1).r; }while(0);
539 tw1 += y;
540 do { (*z2).r=(*z).r-(t).r; (*z2).i=(*z).i-(t).i; }while(0);
541 do { (*z).r += (t).r; (*z).i += (t).i; }while(0);
542 ++z2;
543 ++z;
544 }while (--m);
547 // Avoid dead stores resulting from an assignment (and use) being unreachable.
548 void rdar8405222_aux(int i);
549 void rdar8405222(void) {
550 const int show = 0;
551 int i = 0;
552 if (show)
553 i = 5; // no-warning
554 if (show)
555 rdar8405222_aux(i);
558 // Look through chains of assignments, e.g.: int x = y = 0, when employing
559 // silencing heuristics.
560 int radar11185138_foo(void) {
561 int x, y;
562 x = y = 0; // non-nested-warning {{never read}}
563 return y;
566 int rdar11185138_bar(void) {
567 int y;
568 int x = y = 0; // nested-warning {{Although the value stored}}
569 x = 2;
570 y = 2;
571 return x + y;
574 int *radar11185138_baz(void) {
575 int *x, *y;
576 x = y = 0; // no-warning
577 return y;
580 int getInt(void);
581 int *getPtr(void);
582 void testBOComma(void) {
583 int x0 = (getInt(), 0); // non-nested-warning {{unused variable 'x0'}}
584 int x1 = (getInt(), getInt());
585 // non-nested-warning@-1 {{Value stored to 'x1' during its initialization is never read}}
586 // non-nested-warning@-2 {{unused variable 'x1'}}
588 int x2 = (getInt(), getInt(), getInt());
589 // non-nested-warning@-1 {{Value stored to 'x2' during its initialization is never read}}
590 // non-nested-warning@-2 {{unused variable 'x2'}}
592 int x3;
593 x3 = (getInt(), getInt(), 0);
594 // non-nested-warning@-1 {{Value stored to 'x3' is never read}}
596 int x4 = (getInt(), (getInt(), 0));
597 // non-nested-warning@-1 {{unused variable 'x4'}}
599 int y;
600 int x5 = (getInt(), (y = 0));
601 // non-nested-warning@-1 {{unused variable 'x5'}}
602 // nested-warning@-2 {{Although the value stored}}
604 int x6 = (getInt(), (y = getInt()));
605 // non-nested-warning@-1 {{Value stored to 'x6' during its initialization is never read}}
606 // non-nested-warning@-2 {{unused variable 'x6'}}
607 // nested-warning@-3 {{Although the value stored}}
609 int x7 = 0, x8 = getInt();
610 // non-nested-warning@-1 {{Value stored to 'x8' during its initialization is never read}}
611 // non-nested-warning@-2 {{unused variable 'x8'}}
612 // non-nested-warning@-3 {{unused variable 'x7'}}
614 int x9 = getInt(), x10 = 0;
615 // non-nested-warning@-1 {{Value stored to 'x9' during its initialization is never read}}
616 // non-nested-warning@-2 {{unused variable 'x9'}}
617 // non-nested-warning@-3 {{unused variable 'x10'}}
619 int m = getInt(), mm, mmm;
620 // non-nested-warning@-1 {{Value stored to 'm' during its initialization is never read}}
621 // non-nested-warning@-2 {{unused variable 'm'}}
622 // non-nested-warning@-3 {{unused variable 'mm'}}
623 // non-nested-warning@-4 {{unused variable 'mmm'}}
625 int n, nn = getInt();
626 // non-nested-warning@-1 {{Value stored to 'nn' during its initialization is never read}}
627 // non-nested-warning@-2 {{unused variable 'n'}}
628 // non-nested-warning@-3 {{unused variable 'nn'}}
630 int *p;
631 p = (getPtr(), (int *)0); // no warning
634 void testVolatile(void) {
635 volatile int v;
636 v = 0; // no warning
639 struct Foo {
640 int x;
641 int y;
644 struct Foo rdar34122265_getFoo(void);
646 int rdar34122265_test(int input) {
647 // This is allowed for defensive programming.
648 struct Foo foo = {0, 0};
649 if (input > 0) {
650 foo = rdar34122265_getFoo();
651 } else {
652 return 0;
654 return foo.x + foo.y;
657 void rdar34122265_test_cast(void) {
658 // This is allowed for defensive programming.
659 struct Foo foo = {0, 0};
660 (void)foo;
663 struct Bar {
664 struct Foo x, y;
667 struct Bar rdar34122265_getBar(void);
669 int rdar34122265_test_nested(int input) {
670 // This is allowed for defensive programming.
671 struct Bar bar = {{0, 0}, {0, 0}};
672 if (input > 0) {
673 bar = rdar34122265_getBar();
674 } else {
675 return 0;
677 return bar.x.x + bar.y.y;