1*f4a2713aSLionel Sambuc // RUN: %clang_cc1 -fsyntax-only -Wuninitialized -fsyntax-only -fcxx-exceptions %s -verify 2*f4a2713aSLionel Sambuc 3*f4a2713aSLionel Sambuc // Stub out types for 'typeid' to work. 4*f4a2713aSLionel Sambuc namespace std { class type_info {}; } 5*f4a2713aSLionel Sambuc 6*f4a2713aSLionel Sambuc int test1_aux(int &x); 7*f4a2713aSLionel Sambuc int test1() { 8*f4a2713aSLionel Sambuc int x; 9*f4a2713aSLionel Sambuc test1_aux(x); 10*f4a2713aSLionel Sambuc return x; // no-warning 11*f4a2713aSLionel Sambuc } 12*f4a2713aSLionel Sambuc 13*f4a2713aSLionel Sambuc int test2_aux() { 14*f4a2713aSLionel Sambuc int x; 15*f4a2713aSLionel Sambuc int &y = x; 16*f4a2713aSLionel Sambuc return x; // no-warning 17*f4a2713aSLionel Sambuc } 18*f4a2713aSLionel Sambuc 19*f4a2713aSLionel Sambuc // Don't warn on unevaluated contexts. 20*f4a2713aSLionel Sambuc void unevaluated_tests() { 21*f4a2713aSLionel Sambuc int x; 22*f4a2713aSLionel Sambuc (void)sizeof(x); 23*f4a2713aSLionel Sambuc (void)typeid(x); 24*f4a2713aSLionel Sambuc } 25*f4a2713aSLionel Sambuc 26*f4a2713aSLionel Sambuc // Warn for glvalue arguments to typeid whose type is polymorphic. 27*f4a2713aSLionel Sambuc struct A { virtual ~A() {} }; 28*f4a2713aSLionel Sambuc void polymorphic_test() { 29*f4a2713aSLionel Sambuc A *a; // expected-note{{initialize the variable 'a' to silence this warning}} 30*f4a2713aSLionel Sambuc (void)typeid(*a); // expected-warning{{variable 'a' is uninitialized when used here}} 31*f4a2713aSLionel Sambuc } 32*f4a2713aSLionel Sambuc 33*f4a2713aSLionel Sambuc // Handle cases where the CFG may constant fold some branches, thus 34*f4a2713aSLionel Sambuc // mitigating the need for some path-sensitivity in the analysis. 35*f4a2713aSLionel Sambuc unsigned test3_aux(); 36*f4a2713aSLionel Sambuc unsigned test3() { 37*f4a2713aSLionel Sambuc unsigned x = 0; 38*f4a2713aSLionel Sambuc const bool flag = true; 39*f4a2713aSLionel Sambuc if (flag && (x = test3_aux()) == 0) { 40*f4a2713aSLionel Sambuc return x; 41*f4a2713aSLionel Sambuc } 42*f4a2713aSLionel Sambuc return x; 43*f4a2713aSLionel Sambuc } 44*f4a2713aSLionel Sambuc unsigned test3_b() { 45*f4a2713aSLionel Sambuc unsigned x ; 46*f4a2713aSLionel Sambuc const bool flag = true; 47*f4a2713aSLionel Sambuc if (flag && (x = test3_aux()) == 0) { 48*f4a2713aSLionel Sambuc x = 1; 49*f4a2713aSLionel Sambuc } 50*f4a2713aSLionel Sambuc return x; // no-warning 51*f4a2713aSLionel Sambuc } 52*f4a2713aSLionel Sambuc unsigned test3_c() { 53*f4a2713aSLionel Sambuc unsigned x; // expected-note{{initialize the variable 'x' to silence this warning}} 54*f4a2713aSLionel Sambuc const bool flag = false; 55*f4a2713aSLionel Sambuc if (flag && (x = test3_aux()) == 0) { 56*f4a2713aSLionel Sambuc x = 1; 57*f4a2713aSLionel Sambuc } 58*f4a2713aSLionel Sambuc return x; // expected-warning{{variable 'x' is uninitialized when used here}} 59*f4a2713aSLionel Sambuc } 60*f4a2713aSLionel Sambuc 61*f4a2713aSLionel Sambuc enum test4_A { 62*f4a2713aSLionel Sambuc test4_A_a, test_4_A_b 63*f4a2713aSLionel Sambuc }; 64*f4a2713aSLionel Sambuc test4_A test4() { 65*f4a2713aSLionel Sambuc test4_A a; // expected-note{{variable 'a' is declared here}} 66*f4a2713aSLionel Sambuc return a; // expected-warning{{variable 'a' is uninitialized when used here}} 67*f4a2713aSLionel Sambuc } 68*f4a2713aSLionel Sambuc 69*f4a2713aSLionel Sambuc // Test variables getting invalidated by function calls with reference arguments 70*f4a2713aSLionel Sambuc // *AND* there are multiple invalidated arguments. 71*f4a2713aSLionel Sambuc void test5_aux(int &, int &); 72*f4a2713aSLionel Sambuc 73*f4a2713aSLionel Sambuc int test5() { 74*f4a2713aSLionel Sambuc int x, y; 75*f4a2713aSLionel Sambuc test5_aux(x, y); 76*f4a2713aSLionel Sambuc return x + y; // no-warning 77*f4a2713aSLionel Sambuc } 78*f4a2713aSLionel Sambuc 79*f4a2713aSLionel Sambuc // This test previously crashed Sema. 80*f4a2713aSLionel Sambuc class Rdar9188004A { 81*f4a2713aSLionel Sambuc public: 82*f4a2713aSLionel Sambuc virtual ~Rdar9188004A(); 83*f4a2713aSLionel Sambuc }; 84*f4a2713aSLionel Sambuc 85*f4a2713aSLionel Sambuc template< typename T > class Rdar9188004B : public Rdar9188004A { 86*f4a2713aSLionel Sambuc virtual double *foo(Rdar9188004B *next) const { 87*f4a2713aSLionel Sambuc double *values = next->foo(0); 88*f4a2713aSLionel Sambuc try { 89*f4a2713aSLionel Sambuc } 90*f4a2713aSLionel Sambuc catch(double e) { 91*f4a2713aSLionel Sambuc values[0] = e; 92*f4a2713aSLionel Sambuc } 93*f4a2713aSLionel Sambuc return 0; 94*f4a2713aSLionel Sambuc } 95*f4a2713aSLionel Sambuc }; 96*f4a2713aSLionel Sambuc class Rdar9188004C : public Rdar9188004B<Rdar9188004A> { 97*f4a2713aSLionel Sambuc virtual void bar(void) const; 98*f4a2713aSLionel Sambuc }; 99*f4a2713aSLionel Sambuc void Rdar9188004C::bar(void) const {} 100*f4a2713aSLionel Sambuc 101*f4a2713aSLionel Sambuc // Don't warn about uninitialized variables in unreachable code. 102*f4a2713aSLionel Sambuc void PR9625() { 103*f4a2713aSLionel Sambuc if (false) { 104*f4a2713aSLionel Sambuc int x; 105*f4a2713aSLionel Sambuc (void)static_cast<float>(x); // no-warning 106*f4a2713aSLionel Sambuc } 107*f4a2713aSLionel Sambuc } 108*f4a2713aSLionel Sambuc 109*f4a2713aSLionel Sambuc // Don't warn about variables declared in "catch" 110*f4a2713aSLionel Sambuc void RDar9251392_bar(const char *msg); 111*f4a2713aSLionel Sambuc 112*f4a2713aSLionel Sambuc void RDar9251392() { 113*f4a2713aSLionel Sambuc try { 114*f4a2713aSLionel Sambuc throw "hi"; 115*f4a2713aSLionel Sambuc } 116*f4a2713aSLionel Sambuc catch (const char* msg) { 117*f4a2713aSLionel Sambuc RDar9251392_bar(msg); // no-warning 118*f4a2713aSLionel Sambuc } 119*f4a2713aSLionel Sambuc } 120*f4a2713aSLionel Sambuc 121*f4a2713aSLionel Sambuc // Test handling of "no-op" casts. 122*f4a2713aSLionel Sambuc void test_noop_cast() 123*f4a2713aSLionel Sambuc { 124*f4a2713aSLionel Sambuc int x = 1; 125*f4a2713aSLionel Sambuc int y = (int&)x; // no-warning 126*f4a2713aSLionel Sambuc } 127*f4a2713aSLionel Sambuc 128*f4a2713aSLionel Sambuc void test_noop_cast2() { 129*f4a2713aSLionel Sambuc int x; // expected-note {{initialize the variable 'x' to silence this warning}} 130*f4a2713aSLionel Sambuc int y = (int&)x; // expected-warning {{uninitialized when used here}} 131*f4a2713aSLionel Sambuc } 132*f4a2713aSLionel Sambuc 133*f4a2713aSLionel Sambuc // Test handling of bit casts. 134*f4a2713aSLionel Sambuc void test_bitcasts() { 135*f4a2713aSLionel Sambuc int x = 1; 136*f4a2713aSLionel Sambuc int y = (float &)x; // no-warning 137*f4a2713aSLionel Sambuc } 138*f4a2713aSLionel Sambuc 139*f4a2713aSLionel Sambuc void test_bitcasts_2() { 140*f4a2713aSLionel Sambuc int x; // expected-note {{initialize the variable 'x' to silence this warning}} 141*f4a2713aSLionel Sambuc int y = (float &)x; // expected-warning {{uninitialized when used here}} 142*f4a2713aSLionel Sambuc } 143*f4a2713aSLionel Sambuc 144*f4a2713aSLionel Sambuc void consume_const_ref(const int &n); 145*f4a2713aSLionel Sambuc int test_const_ref() { 146*f4a2713aSLionel Sambuc int n; // expected-note {{variable}} 147*f4a2713aSLionel Sambuc consume_const_ref(n); 148*f4a2713aSLionel Sambuc return n; // expected-warning {{uninitialized when used here}} 149*f4a2713aSLionel Sambuc } 150