1*67e74705SXin Li // RUN: %clang_cc1 -fsyntax-only -verify -std=c++11 %s 2*67e74705SXin Li 3*67e74705SXin Li int f() __attribute__((warn_unused_result)); 4*67e74705SXin Li 5*67e74705SXin Li struct S { 6*67e74705SXin Li void t() const; 7*67e74705SXin Li }; 8*67e74705SXin Li S g1() __attribute__((warn_unused_result)); 9*67e74705SXin Li S *g2() __attribute__((warn_unused_result)); 10*67e74705SXin Li S &g3() __attribute__((warn_unused_result)); 11*67e74705SXin Li test()12*67e74705SXin Livoid test() { 13*67e74705SXin Li f(); // expected-warning {{ignoring return value}} 14*67e74705SXin Li g1(); // expected-warning {{ignoring return value}} 15*67e74705SXin Li g2(); // expected-warning {{ignoring return value}} 16*67e74705SXin Li g3(); // expected-warning {{ignoring return value}} 17*67e74705SXin Li 18*67e74705SXin Li (void)f(); 19*67e74705SXin Li (void)g1(); 20*67e74705SXin Li (void)g2(); 21*67e74705SXin Li (void)g3(); 22*67e74705SXin Li 23*67e74705SXin Li if (f() == 0) return; 24*67e74705SXin Li 25*67e74705SXin Li g1().t(); 26*67e74705SXin Li g2()->t(); 27*67e74705SXin Li g3().t(); 28*67e74705SXin Li 29*67e74705SXin Li int i = f(); 30*67e74705SXin Li S s1 = g1(); 31*67e74705SXin Li S *s2 = g2(); 32*67e74705SXin Li S &s3 = g3(); 33*67e74705SXin Li const S &s4 = g1(); 34*67e74705SXin Li } 35*67e74705SXin Li 36*67e74705SXin Li struct X { 37*67e74705SXin Li int foo() __attribute__((warn_unused_result)); 38*67e74705SXin Li }; 39*67e74705SXin Li bah()40*67e74705SXin Livoid bah() { 41*67e74705SXin Li X x, *x2; 42*67e74705SXin Li x.foo(); // expected-warning {{ignoring return value}} 43*67e74705SXin Li x2->foo(); // expected-warning {{ignoring return value}} 44*67e74705SXin Li } 45*67e74705SXin Li 46*67e74705SXin Li namespace warn_unused_CXX11 { 47*67e74705SXin Li class Status; 48*67e74705SXin Li class Foo { 49*67e74705SXin Li public: 50*67e74705SXin Li Status doStuff(); 51*67e74705SXin Li }; 52*67e74705SXin Li 53*67e74705SXin Li struct [[clang::warn_unused_result]] Status { 54*67e74705SXin Li bool ok() const; 55*67e74705SXin Li Status& operator=(const Status& x); Updatewarn_unused_CXX11::Status56*67e74705SXin Li inline void Update(const Status& new_status) { 57*67e74705SXin Li if (ok()) { 58*67e74705SXin Li *this = new_status; //no-warning 59*67e74705SXin Li } 60*67e74705SXin Li } 61*67e74705SXin Li }; 62*67e74705SXin Li Status DoSomething(); 63*67e74705SXin Li Status& DoSomethingElse(); 64*67e74705SXin Li Status* DoAnotherThing(); 65*67e74705SXin Li Status** DoYetAnotherThing(); lazy()66*67e74705SXin Livoid lazy() { 67*67e74705SXin Li Status s = DoSomething(); 68*67e74705SXin Li if (!s.ok()) return; 69*67e74705SXin Li Status &rs = DoSomethingElse(); 70*67e74705SXin Li if (!rs.ok()) return; 71*67e74705SXin Li Status *ps = DoAnotherThing(); 72*67e74705SXin Li if (!ps->ok()) return; 73*67e74705SXin Li Status **pps = DoYetAnotherThing(); 74*67e74705SXin Li if (!(*pps)->ok()) return; 75*67e74705SXin Li 76*67e74705SXin Li (void)DoSomething(); 77*67e74705SXin Li (void)DoSomethingElse(); 78*67e74705SXin Li (void)DoAnotherThing(); 79*67e74705SXin Li (void)DoYetAnotherThing(); 80*67e74705SXin Li 81*67e74705SXin Li DoSomething(); // expected-warning {{ignoring return value}} 82*67e74705SXin Li DoSomethingElse(); 83*67e74705SXin Li DoAnotherThing(); 84*67e74705SXin Li DoYetAnotherThing(); 85*67e74705SXin Li } 86*67e74705SXin Li 87*67e74705SXin Li template <typename T> 88*67e74705SXin Li class [[clang::warn_unused_result]] StatusOr { 89*67e74705SXin Li }; 90*67e74705SXin Li StatusOr<int> doit(); test()91*67e74705SXin Livoid test() { 92*67e74705SXin Li Foo f; 93*67e74705SXin Li f.doStuff(); // expected-warning {{ignoring return value}} 94*67e74705SXin Li doit(); // expected-warning {{ignoring return value}} 95*67e74705SXin Li 96*67e74705SXin Li auto func = []() { return Status(); }; 97*67e74705SXin Li func(); // expected-warning {{ignoring return value}} 98*67e74705SXin Li } 99*67e74705SXin Li } 100*67e74705SXin Li 101*67e74705SXin Li namespace PR17587 { 102*67e74705SXin Li struct [[clang::warn_unused_result]] Status; 103*67e74705SXin Li 104*67e74705SXin Li struct Foo { 105*67e74705SXin Li Status Bar(); 106*67e74705SXin Li }; 107*67e74705SXin Li 108*67e74705SXin Li struct Status {}; 109*67e74705SXin Li Bar()110*67e74705SXin Livoid Bar() { 111*67e74705SXin Li Foo f; 112*67e74705SXin Li f.Bar(); // expected-warning {{ignoring return value}} 113*67e74705SXin Li }; 114*67e74705SXin Li 115*67e74705SXin Li } 116*67e74705SXin Li 117*67e74705SXin Li namespace PR18571 { 118*67e74705SXin Li // Unevaluated contexts should not trigger unused result warnings. 119*67e74705SXin Li template <typename T> foo(T)120*67e74705SXin Liauto foo(T) -> decltype(f(), bool()) { // Should not warn. 121*67e74705SXin Li return true; 122*67e74705SXin Li } 123*67e74705SXin Li g()124*67e74705SXin Livoid g() { 125*67e74705SXin Li foo(1); 126*67e74705SXin Li } 127*67e74705SXin Li } 128*67e74705SXin Li 129*67e74705SXin Li namespace std { 130*67e74705SXin Li class type_info { }; 131*67e74705SXin Li } 132*67e74705SXin Li 133*67e74705SXin Li namespace { 134*67e74705SXin Li // The typeid expression operand is evaluated only when the expression type is 135*67e74705SXin Li // a glvalue of polymorphic class type. 136*67e74705SXin Li 137*67e74705SXin Li struct B { f__anon838ee1c80211::B138*67e74705SXin Li virtual void f() {} 139*67e74705SXin Li }; 140*67e74705SXin Li 141*67e74705SXin Li struct D : B { f__anon838ee1c80211::D142*67e74705SXin Li void f() override {} 143*67e74705SXin Li }; 144*67e74705SXin Li 145*67e74705SXin Li struct C {}; 146*67e74705SXin Li g()147*67e74705SXin Livoid g() { 148*67e74705SXin Li // The typeid expression operand is evaluated only when the expression type is 149*67e74705SXin Li // a glvalue of polymorphic class type; otherwise the expression operand is not 150*67e74705SXin Li // evaluated and should not trigger a diagnostic. 151*67e74705SXin Li D d; 152*67e74705SXin Li C c; 153*67e74705SXin Li (void)typeid(f(), c); // Should not warn. 154*67e74705SXin Li (void)typeid(f(), d); // expected-warning {{ignoring return value}} expected-warning {{expression with side effects will be evaluated despite being used as an operand to 'typeid'}} 155*67e74705SXin Li 156*67e74705SXin Li // The sizeof expression operand is never evaluated. 157*67e74705SXin Li (void)sizeof(f(), c); // Should not warn. 158*67e74705SXin Li 159*67e74705SXin Li // The noexcept expression operand is never evaluated. 160*67e74705SXin Li (void)noexcept(f(), false); // Should not warn. 161*67e74705SXin Li } 162*67e74705SXin Li } 163