global-region-invalidation.c revision 38f68ef19cb51d5876e9025b5fceb44b33ec9ed7
1// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -analyze -disable-free -analyzer-eagerly-assume -analyzer-checker=core,deadcode,alpha.security.taint,debug.TaintTest,debug.ExprInspection -verify %s 2 3void clang_analyzer_eval(int); 4 5// Note, we do need to include headers here, since the analyzer checks if the function declaration is located in a system header. 6#include "Inputs/system-header-simulator.h" 7 8// Test that system header does not invalidate the internal global. 9int size_rdar9373039 = 1; 10int rdar9373039() { 11 int x; 12 int j = 0; 13 14 for (int i = 0 ; i < size_rdar9373039 ; ++i) 15 x = 1; 16 17 // strlen doesn't invalidate the value of 'size_rdar9373039'. 18 int extra = (2 + strlen ("Clang") + ((4 - ((unsigned int) (2 + strlen ("Clang")) % 4)) % 4)) + (2 + strlen ("1.0") + ((4 - ((unsigned int) (2 + strlen ("1.0")) % 4)) % 4)); 19 20 for (int i = 0 ; i < size_rdar9373039 ; ++i) 21 j += x; // no-warning 22 23 return j; 24} 25 26// Test stdin does not get invalidated by a system call nor by an internal call. 27void foo(); 28int stdinTest() { 29 int i = 0; 30 fscanf(stdin, "%d", &i); 31 foo(); 32 int m = i; // expected-warning + {{tainted}} 33 fscanf(stdin, "%d", &i); 34 int j = i; // expected-warning + {{tainted}} 35 return m + j; // expected-warning + {{tainted}} 36} 37 38// Test errno gets invalidated by a system call. 39int testErrnoSystem() { 40 int i; 41 int *p = 0; 42 fscanf(stdin, "%d", &i); 43 if (errno == 0) { 44 fscanf(stdin, "%d", &i); // errno gets invalidated here. 45 return 5 / errno; // no-warning 46 } 47 return 0; 48} 49 50// Test that errno gets invalidated by internal calls. 51int testErrnoInternal() { 52 int i; 53 int *p = 0; 54 fscanf(stdin, "%d", &i); 55 if (errno == 0) { 56 foo(); // errno gets invalidated here. 57 return 5 / errno; // no-warning 58 } 59 return 0; 60} 61 62// Test that const integer does not get invalidated. 63const int x = 0; 64int constIntGlob() { 65 const int *m = &x; 66 foo(); 67 return 3 / *m; // expected-warning {{Division by zero}} 68} 69 70extern const int y; 71int constIntGlobExtern() { 72 if (y == 0) { 73 foo(); 74 return 5 / y; // expected-warning {{Division by zero}} 75 } 76 return 0; 77} 78 79static void * const ptr = 0; 80void constPtrGlob() { 81 clang_analyzer_eval(ptr == 0); // expected-warning{{TRUE}} 82 foo(); 83 clang_analyzer_eval(ptr == 0); // expected-warning{{TRUE}} 84} 85 86static const int x2 = x; 87void constIntGlob2() { 88 clang_analyzer_eval(x2 == 0); // expected-warning{{TRUE}} 89 foo(); 90 clang_analyzer_eval(x2 == 0); // expected-warning{{TRUE}} 91} 92 93void testAnalyzerEvalIsPure() { 94 extern int someGlobal; 95 if (someGlobal == 0) { 96 clang_analyzer_eval(someGlobal == 0); // expected-warning{{TRUE}} 97 clang_analyzer_eval(someGlobal == 0); // expected-warning{{TRUE}} 98 } 99} 100 101// Test that static variables with initializers do not get reinitialized on 102// recursive calls. 103void Function2(void); 104int *getPtr(); 105void Function1(void) { 106 static unsigned flag; 107 static int *p = 0; 108 if (!flag) { 109 flag = 1; 110 p = getPtr(); 111 } 112 int m = *p; // no-warning: p is never null. 113 m++; 114 Function2(); 115} 116void Function2(void) { 117 Function1(); 118} 119 120void SetToNonZero(void) { 121 static int g = 5; 122 clang_analyzer_eval(g == 5); // expected-warning{{TRUE}} 123} 124 125