1// RUN: %clang_cc1 -analyze -analyzer-checker=core -analyzer-store=region -verify %s -Wno-undefined-bool-conversion 2 3typedef __INTPTR_TYPE__ intptr_t; 4 5const int& g() { 6 int s; 7 return s; // expected-warning{{Address of stack memory associated with local variable 's' returned}} expected-warning{{reference to stack memory associated with local variable 's' returned}} 8} 9 10const int& g2() { 11 int s1; 12 int &s2 = s1; // expected-note {{binding reference variable 's2' here}} 13 return s2; // expected-warning{{Address of stack memory associated with local variable 's1' returned}} expected-warning {{reference to stack memory associated with local variable 's1' returned}} 14} 15 16const int& g3() { 17 int s1; 18 int &s2 = s1; // expected-note {{binding reference variable 's2' here}} 19 int &s3 = s2; // expected-note {{binding reference variable 's3' here}} 20 return s3; // expected-warning{{Address of stack memory associated with local variable 's1' returned}} expected-warning {{reference to stack memory associated with local variable 's1' returned}} 21} 22 23void g4() { 24 static const int &x = 3; // no warning 25} 26 27int get_value(); 28 29const int &get_reference1() { return get_value(); } // expected-warning{{Address of stack memory associated with temporary object of type 'int' returned}} expected-warning {{returning reference to local temporary}} 30 31const int &get_reference2() { 32 const int &x = get_value(); // expected-note {{binding reference variable 'x' here}} 33 return x; // expected-warning{{Address of stack memory associated with temporary object of type 'int' returned}} expected-warning {{returning reference to local temporary}} 34} 35 36const int &get_reference3() { 37 const int &x1 = get_value(); // expected-note {{binding reference variable 'x1' here}} 38 const int &x2 = x1; // expected-note {{binding reference variable 'x2' here}} 39 return x2; // expected-warning{{Address of stack memory associated with temporary object of type 'int' returned}} expected-warning {{returning reference to local temporary}} 40} 41 42int global_var; 43int *f1() { 44 int &y = global_var; 45 return &y; 46} 47 48int *f2() { 49 int x1; 50 int &x2 = x1; // expected-note {{binding reference variable 'x2' here}} 51 return &x2; // expected-warning{{Address of stack memory associated with local variable 'x1' returned}} expected-warning {{address of stack memory associated with local variable 'x1' returned}} 52} 53 54int *f3() { 55 int x1; 56 int *const &x2 = &x1; // expected-note {{binding reference variable 'x2' here}} 57 return x2; // expected-warning {{address of stack memory associated with local variable 'x1' returned}} expected-warning {{Address of stack memory associated with local variable 'x1' returned to caller}} 58} 59 60const int *f4() { 61 const int &x1 = get_value(); // expected-note {{binding reference variable 'x1' here}} 62 const int &x2 = x1; // expected-note {{binding reference variable 'x2' here}} 63 return &x2; // expected-warning{{Address of stack memory associated with temporary object of type 'int' returned}} expected-warning {{returning address of local temporary}} 64} 65 66struct S { 67 int x; 68}; 69 70int *mf() { 71 S s1; 72 S &s2 = s1; // expected-note {{binding reference variable 's2' here}} 73 int &x = s2.x; // expected-note {{binding reference variable 'x' here}} 74 return &x; // expected-warning{{Address of stack memory associated with local variable 's1' returned}} expected-warning {{address of stack memory associated with local variable 's1' returned}} 75} 76 77void *lf() { 78 label: 79 void *const &x = &&label; // expected-note {{binding reference variable 'x' here}} 80 return x; // expected-warning {{returning address of label, which is local}} 81} 82 83template <typename T> 84struct TS { 85 int *get(); 86 int *m() { 87 int *&x = get(); 88 return x; 89 } 90}; 91 92// rdar://11345441 93int* f5() { 94 int& i = i; // expected-warning {{Assigned value is garbage or undefined}} expected-note {{binding reference variable 'i' here}} expected-warning{{reference 'i' is not yet bound to a value when used within its own initialization}} 95 return &i; // expected-warning {{address of stack memory associated with local variable 'i' returned}} 96} 97 98void *radar13226577() { 99 void *p = &p; 100 return p; // expected-warning {{stack memory associated with local variable 'p' returned to caller}} 101} 102 103namespace rdar13296133 { 104 class ConvertsToBool { 105 public: 106 operator bool() const { return this; } 107 }; 108 109 class ConvertsToIntptr { 110 public: 111 operator intptr_t() const { return reinterpret_cast<intptr_t>(this); } 112 }; 113 114 class ConvertsToPointer { 115 public: 116 operator const void *() const { return this; } 117 }; 118 119 intptr_t returnAsNonLoc() { 120 ConvertsToIntptr obj; 121 return obj; // expected-warning{{Address of stack memory associated with local variable 'obj' returned to caller}} 122 } 123 124 bool returnAsBool() { 125 ConvertsToBool obj; 126 return obj; // no-warning 127 } 128 129 intptr_t returnAsNonLocViaPointer() { 130 ConvertsToPointer obj; 131 return reinterpret_cast<intptr_t>(static_cast<const void *>(obj)); // expected-warning{{Address of stack memory associated with local variable 'obj' returned to caller}} 132 } 133 134 bool returnAsBoolViaPointer() { 135 ConvertsToPointer obj; 136 return obj; // no-warning 137 } 138} 139 140