[PATCH] D66164: [LifetimeAnalysis] Support std::stack::top() and std::optional::value()
This revision was automatically updated to reflect the committed changes. Closed by commit rL368929: [LifetimeAnalysis] Support std::stack::top() and std::optional::value() (authored by mgehre, committed by ). Herald added a project: LLVM. Herald added a subscriber: llvm-commits. Changed prior to commit: https://reviews.llvm.org/D66164?vs=214954=215259#toc Repository: rL LLVM CHANGES SINCE LAST ACTION https://reviews.llvm.org/D66164/new/ https://reviews.llvm.org/D66164 Files: cfe/trunk/lib/Sema/SemaInit.cpp cfe/trunk/test/Sema/warn-lifetime-analysis-nocfg.cpp Index: cfe/trunk/lib/Sema/SemaInit.cpp === --- cfe/trunk/lib/Sema/SemaInit.cpp +++ cfe/trunk/lib/Sema/SemaInit.cpp @@ -6610,7 +6610,7 @@ OO == OverloadedOperatorKind::OO_Star; } return llvm::StringSwitch(Callee->getName()) -.Cases("front", "back", "at", true) +.Cases("front", "back", "at", "top", "value", true) .Default(false); } return false; Index: cfe/trunk/test/Sema/warn-lifetime-analysis-nocfg.cpp === --- cfe/trunk/test/Sema/warn-lifetime-analysis-nocfg.cpp +++ cfe/trunk/test/Sema/warn-lifetime-analysis-nocfg.cpp @@ -170,7 +170,15 @@ struct optional { optional(); optional(const T&); - T *(); + T *() &; + T &*() &&; + T () &; + T &() &&; +}; + +template +struct stack { + T (); }; } @@ -188,6 +196,16 @@ return s.c_str(); // expected-warning {{address of stack memory associated with local variable 's' returned}} } +int () { + std::optional o; + return o.value(); // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + +int () { + std::optional o; + return *o; // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + const char *danglingRawPtrFromTemp() { return std::basic_string().c_str(); // expected-warning {{returning address of local temporary object}} } @@ -203,9 +221,10 @@ } void danglingReferenceFromTempOwner() { - int = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = *std::optional(5); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int & = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int & = *std::optional(5);// expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int & = std::optional(5).value(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} } std::vector getTempVec(); Index: cfe/trunk/lib/Sema/SemaInit.cpp === --- cfe/trunk/lib/Sema/SemaInit.cpp +++ cfe/trunk/lib/Sema/SemaInit.cpp @@ -6610,7 +6610,7 @@ OO == OverloadedOperatorKind::OO_Star; } return llvm::StringSwitch(Callee->getName()) -.Cases("front", "back", "at", true) +.Cases("front", "back", "at", "top", "value", true) .Default(false); } return false; Index: cfe/trunk/test/Sema/warn-lifetime-analysis-nocfg.cpp === --- cfe/trunk/test/Sema/warn-lifetime-analysis-nocfg.cpp +++ cfe/trunk/test/Sema/warn-lifetime-analysis-nocfg.cpp @@ -170,7 +170,15 @@ struct optional { optional(); optional(const T&); - T *(); + T *() &; + T &*() &&; + T () &; + T &() &&; +}; + +template +struct stack { + T (); }; } @@ -188,6 +196,16 @@ return s.c_str(); // expected-warning {{address of stack memory associated with local variable 's' returned}} } +int () { + std::optional o; + return o.value(); // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + +int () { + std::optional o; + return *o; // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + const char *danglingRawPtrFromTemp() { return std::basic_string().c_str(); // expected-warning {{returning address of local temporary object}} } @@ -203,9 +221,10 @@ } void danglingReferenceFromTempOwner() { - int = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = *std::optional(5); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = std::vector().at(3); // expected-warning {{object
[PATCH] D66164: [LifetimeAnalysis] Support std::stack::top() and std::optional::value()
mgehre updated this revision to Diff 214954. mgehre marked an inline comment as done. mgehre added a comment. Add tests for rvalue-ref overloads Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D66164/new/ https://reviews.llvm.org/D66164 Files: clang/lib/Sema/SemaInit.cpp clang/test/Sema/warn-lifetime-analysis-nocfg.cpp Index: clang/test/Sema/warn-lifetime-analysis-nocfg.cpp === --- clang/test/Sema/warn-lifetime-analysis-nocfg.cpp +++ clang/test/Sema/warn-lifetime-analysis-nocfg.cpp @@ -168,7 +168,15 @@ struct optional { optional(); optional(const T&); - T *(); + T *() &; + T &*() &&; + T () &; + T &() &&; +}; + +template +struct stack { + T (); }; } @@ -186,6 +194,16 @@ return s.c_str(); // expected-warning {{address of stack memory associated with local variable 's' returned}} } +int () { + std::optional o; + return o.value(); // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + +int () { + std::optional o; + return *o; // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + const char *danglingRawPtrFromTemp() { return std::basic_string().c_str(); // expected-warning {{returning address of local temporary object}} } @@ -201,9 +219,10 @@ } void danglingReferenceFromTempOwner() { - int = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = *std::optional(5); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int & = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int & = *std::optional(5);// expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int & = std::optional(5).value(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} } std::vector getTempVec(); Index: clang/lib/Sema/SemaInit.cpp === --- clang/lib/Sema/SemaInit.cpp +++ clang/lib/Sema/SemaInit.cpp @@ -6591,7 +6591,7 @@ OO == OverloadedOperatorKind::OO_Star; } return llvm::StringSwitch(Callee->getName()) -.Cases("front", "back", "at", true) +.Cases("front", "back", "at", "top", "value", true) .Default(false); } return false; Index: clang/test/Sema/warn-lifetime-analysis-nocfg.cpp === --- clang/test/Sema/warn-lifetime-analysis-nocfg.cpp +++ clang/test/Sema/warn-lifetime-analysis-nocfg.cpp @@ -168,7 +168,15 @@ struct optional { optional(); optional(const T&); - T *(); + T *() &; + T &*() &&; + T () &; + T &() &&; +}; + +template +struct stack { + T (); }; } @@ -186,6 +194,16 @@ return s.c_str(); // expected-warning {{address of stack memory associated with local variable 's' returned}} } +int () { + std::optional o; + return o.value(); // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + +int () { + std::optional o; + return *o; // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + const char *danglingRawPtrFromTemp() { return std::basic_string().c_str(); // expected-warning {{returning address of local temporary object}} } @@ -201,9 +219,10 @@ } void danglingReferenceFromTempOwner() { - int = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = *std::optional(5); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int & = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int & = *std::optional(5);// expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int & = std::optional(5).value(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} } std::vector getTempVec(); Index: clang/lib/Sema/SemaInit.cpp
[PATCH] D66164: [LifetimeAnalysis] Support std::stack::top() and std::optional::value()
mgehre marked 3 inline comments as done. mgehre added inline comments. Comment at: clang/lib/Sema/SemaInit.cpp:6583 .Cases("end", "rend", "cend", "crend", true) -.Cases("c_str", "data", "get", true) +.Cases("c_str", "data", "get", "value", true) // Map and set types. xazax.hun wrote: > Oh, this one needs to be updated, as `value` returns a reference not a > pointer. Yes, I noticed the same. Comment at: clang/test/Sema/warn-lifetime-analysis-nocfg.cpp:172 T *(); + T (); +}; xazax.hun wrote: > mgehre wrote: > > xazax.hun wrote: > > > I actually was a bit lazy when I added these tests. Both `value` and > > > `operator*` is overloaded on `&&`. But if you do not feel like adjusting > > > the tests this is fine, I can do it myself later :) > > I'll change it to use the `&` variant in the test - the `&&` cannot dangle > > as far as I understand. > It can! > > Consider the following code: > > ``` > int & = *std::optional(5); > // r dangles here. > ``` Oh, sure! Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D66164/new/ https://reviews.llvm.org/D66164 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D66164: [LifetimeAnalysis] Support std::stack::top() and std::optional::value()
mgehre updated this revision to Diff 214950. mgehre marked 2 inline comments as done. mgehre added a comment. Fix commit Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D66164/new/ https://reviews.llvm.org/D66164 Files: clang/lib/Sema/SemaInit.cpp clang/test/Sema/warn-lifetime-analysis-nocfg.cpp Index: clang/test/Sema/warn-lifetime-analysis-nocfg.cpp === --- clang/test/Sema/warn-lifetime-analysis-nocfg.cpp +++ clang/test/Sema/warn-lifetime-analysis-nocfg.cpp @@ -168,7 +168,14 @@ struct optional { optional(); optional(const T&); - T *(); + T *() &; + T &*() &&; + T () &; +}; + +template +struct stack { + T (); }; } @@ -186,6 +193,16 @@ return s.c_str(); // expected-warning {{address of stack memory associated with local variable 's' returned}} } +int () { + std::optional o; + return o.value(); // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + +int () { + std::optional o; + return *o; // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + const char *danglingRawPtrFromTemp() { return std::basic_string().c_str(); // expected-warning {{returning address of local temporary object}} } @@ -201,9 +218,8 @@ } void danglingReferenceFromTempOwner() { - int = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = *std::optional(5); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::stack().top(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} } std::vector getTempVec(); Index: clang/lib/Sema/SemaInit.cpp === --- clang/lib/Sema/SemaInit.cpp +++ clang/lib/Sema/SemaInit.cpp @@ -6591,7 +6591,7 @@ OO == OverloadedOperatorKind::OO_Star; } return llvm::StringSwitch(Callee->getName()) -.Cases("front", "back", "at", true) +.Cases("front", "back", "at", "top", "value", true) .Default(false); } return false; Index: clang/test/Sema/warn-lifetime-analysis-nocfg.cpp === --- clang/test/Sema/warn-lifetime-analysis-nocfg.cpp +++ clang/test/Sema/warn-lifetime-analysis-nocfg.cpp @@ -168,7 +168,14 @@ struct optional { optional(); optional(const T&); - T *(); + T *() &; + T &*() &&; + T () &; +}; + +template +struct stack { + T (); }; } @@ -186,6 +193,16 @@ return s.c_str(); // expected-warning {{address of stack memory associated with local variable 's' returned}} } +int () { + std::optional o; + return o.value(); // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + +int () { + std::optional o; + return *o; // expected-warning {{reference to stack memory associated with local variable 'o' returned}} +} + const char *danglingRawPtrFromTemp() { return std::basic_string().c_str(); // expected-warning {{returning address of local temporary object}} } @@ -201,9 +218,8 @@ } void danglingReferenceFromTempOwner() { - int = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = *std::optional(5); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} - int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::stack().top(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} } std::vector getTempVec(); Index: clang/lib/Sema/SemaInit.cpp === --- clang/lib/Sema/SemaInit.cpp +++ clang/lib/Sema/SemaInit.cpp @@ -6591,7 +6591,7 @@ OO == OverloadedOperatorKind::OO_Star; } return llvm::StringSwitch(Callee->getName()) -.Cases("front", "back", "at", true) +.Cases("front", "back", "at", "top", "value", true) .Default(false); } return false; ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D66164: [LifetimeAnalysis] Support std::stack::top() and std::optional::value()
xazax.hun added inline comments. Comment at: clang/test/Sema/warn-lifetime-analysis-nocfg.cpp:172 T *(); + T (); +}; mgehre wrote: > xazax.hun wrote: > > I actually was a bit lazy when I added these tests. Both `value` and > > `operator*` is overloaded on `&&`. But if you do not feel like adjusting > > the tests this is fine, I can do it myself later :) > I'll change it to use the `&` variant in the test - the `&&` cannot dangle as > far as I understand. It can! Consider the following code: ``` int & = *std::optional(5); // r dangles here. ``` Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D66164/new/ https://reviews.llvm.org/D66164 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D66164: [LifetimeAnalysis] Support std::stack::top() and std::optional::value()
mgehre marked an inline comment as done. mgehre added inline comments. Comment at: clang/test/Sema/warn-lifetime-analysis-nocfg.cpp:172 T *(); + T (); +}; xazax.hun wrote: > I actually was a bit lazy when I added these tests. Both `value` and > `operator*` is overloaded on `&&`. But if you do not feel like adjusting the > tests this is fine, I can do it myself later :) I'll change it to use the `&` variant in the test - the `&&` cannot dangle as far as I understand. Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D66164/new/ https://reviews.llvm.org/D66164 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D66164: [LifetimeAnalysis] Support std::stack::top() and std::optional::value()
xazax.hun added inline comments. Comment at: clang/lib/Sema/SemaInit.cpp:6583 .Cases("end", "rend", "cend", "crend", true) -.Cases("c_str", "data", "get", true) +.Cases("c_str", "data", "get", "value", true) // Map and set types. Oh, this one needs to be updated, as `value` returns a reference not a pointer. Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D66164/new/ https://reviews.llvm.org/D66164 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D66164: [LifetimeAnalysis] Support std::stack::top() and std::optional::value()
xazax.hun accepted this revision. xazax.hun added a comment. This revision is now accepted and ready to land. Herald added a subscriber: rnkovacs. LG! But let's wait for Dmitri :) Comment at: clang/test/Sema/warn-lifetime-analysis-nocfg.cpp:172 T *(); + T (); +}; I actually was a bit lazy when I added these tests. Both `value` and `operator*` is overloaded on `&&`. But if you do not feel like adjusting the tests this is fine, I can do it myself later :) Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D66164/new/ https://reviews.llvm.org/D66164 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[PATCH] D66164: [LifetimeAnalysis] Support std::stack::top() and std::optional::value()
mgehre created this revision. mgehre added a reviewer: gribozavr. Herald added a project: clang. Diagnose dangling pointers that come from std::stack::top() and std::optional::value(). Repository: rG LLVM Github Monorepo https://reviews.llvm.org/D66164 Files: clang/lib/Sema/SemaInit.cpp clang/test/Sema/warn-lifetime-analysis-nocfg.cpp Index: clang/test/Sema/warn-lifetime-analysis-nocfg.cpp === --- clang/test/Sema/warn-lifetime-analysis-nocfg.cpp +++ clang/test/Sema/warn-lifetime-analysis-nocfg.cpp @@ -169,6 +169,12 @@ optional(); optional(const T&); T *(); + T (); +}; + +template +struct stack { + T (); }; } @@ -204,6 +210,8 @@ int = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} int = *std::optional(5); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::optional(5).value(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::stack().top(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} } std::vector getTempVec(); Index: clang/lib/Sema/SemaInit.cpp === --- clang/lib/Sema/SemaInit.cpp +++ clang/lib/Sema/SemaInit.cpp @@ -6580,7 +6580,7 @@ return llvm::StringSwitch(Callee->getName()) .Cases("begin", "rbegin", "cbegin", "crbegin", true) .Cases("end", "rend", "cend", "crend", true) -.Cases("c_str", "data", "get", true) +.Cases("c_str", "data", "get", "value", true) // Map and set types. .Cases("find", "equal_range", "lower_bound", "upper_bound", true) .Default(false); @@ -6591,7 +6591,7 @@ OO == OverloadedOperatorKind::OO_Star; } return llvm::StringSwitch(Callee->getName()) -.Cases("front", "back", "at", true) +.Cases("front", "back", "at", "top", true) .Default(false); } return false; Index: clang/test/Sema/warn-lifetime-analysis-nocfg.cpp === --- clang/test/Sema/warn-lifetime-analysis-nocfg.cpp +++ clang/test/Sema/warn-lifetime-analysis-nocfg.cpp @@ -169,6 +169,12 @@ optional(); optional(const T&); T *(); + T (); +}; + +template +struct stack { + T (); }; } @@ -204,6 +210,8 @@ int = *std::optional(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} int = *std::optional(5); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} int = std::vector().at(3); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::optional(5).value(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} + int = std::stack().top(); // expected-warning {{object backing the pointer will be destroyed at the end of the full-expression}} } std::vector getTempVec(); Index: clang/lib/Sema/SemaInit.cpp === --- clang/lib/Sema/SemaInit.cpp +++ clang/lib/Sema/SemaInit.cpp @@ -6580,7 +6580,7 @@ return llvm::StringSwitch(Callee->getName()) .Cases("begin", "rbegin", "cbegin", "crbegin", true) .Cases("end", "rend", "cend", "crend", true) -.Cases("c_str", "data", "get", true) +.Cases("c_str", "data", "get", "value", true) // Map and set types. .Cases("find", "equal_range", "lower_bound", "upper_bound", true) .Default(false); @@ -6591,7 +6591,7 @@ OO == OverloadedOperatorKind::OO_Star; } return llvm::StringSwitch(Callee->getName()) -.Cases("front", "back", "at", true) +.Cases("front", "back", "at", "top", true) .Default(false); } return false; ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits