Author: Shafik Yaghmour Date: 2023-09-25T13:08:10-07:00 New Revision: bb764eccf8053244d64270df29c2e0bd3606f6c0
URL: https://github.com/llvm/llvm-project/commit/bb764eccf8053244d64270df29c2e0bd3606f6c0 DIFF: https://github.com/llvm/llvm-project/commit/bb764eccf8053244d64270df29c2e0bd3606f6c0.diff LOG: [Clang] Fix CXXRewrittenBinaryOperator::getDecomposedForm to handle case when spaceship operator returns comparison category by reference (#66270) Currently CXXRewrittenBinaryOperator::getDecomposedForm(...) may crash if the spaceship operator returns a comparison category by reference. This because IgnoreImplicitAsWritten() does not look through CXXConstructExpr. The fix is to use IgnoreUnlessSpelledInSource() which will look though CXXConstructExpr. This fixes: https://github.com/llvm/llvm-project/issues/64162 Added: Modified: clang/docs/ReleaseNotes.rst clang/lib/AST/ExprCXX.cpp clang/test/SemaCXX/compare-cxx2a.cpp Removed: ################################################################################ diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index 294b77a3e260908..688454d6b562ec3 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -353,6 +353,10 @@ Bug Fixes to C++ Support NTTP types are compared with the ' diff ' method. (`#66744 https://github.com/llvm/llvm-project/issues/66744`) +- Fix crash caused by a spaceship operator returning a comparision category by + reference. Fixes: + (`#64162 <https://github.com/llvm/llvm-project/issues/64162>`_) + Bug Fixes to AST Handling ^^^^^^^^^^^^^^^^^^^^^^^^^ - Fixed an import failure of recursive friend class template. diff --git a/clang/lib/AST/ExprCXX.cpp b/clang/lib/AST/ExprCXX.cpp index efb64842fb6d96d..06163255f9b5e54 100644 --- a/clang/lib/AST/ExprCXX.cpp +++ b/clang/lib/AST/ExprCXX.cpp @@ -111,7 +111,7 @@ CXXRewrittenBinaryOperator::getDecomposedForm() const { return Result; // Otherwise, we expect a <=> to now be on the LHS. - E = Result.LHS->IgnoreImplicitAsWritten(); + E = Result.LHS->IgnoreUnlessSpelledInSource(); if (auto *BO = dyn_cast<BinaryOperator>(E)) { assert(BO->getOpcode() == BO_Cmp); Result.LHS = BO->getLHS(); diff --git a/clang/test/SemaCXX/compare-cxx2a.cpp b/clang/test/SemaCXX/compare-cxx2a.cpp index 619e16aa7458179..15a0baccfca17a2 100644 --- a/clang/test/SemaCXX/compare-cxx2a.cpp +++ b/clang/test/SemaCXX/compare-cxx2a.cpp @@ -479,3 +479,26 @@ void DoSomething() { // expected-note {{undefined function 'operator++' cannot be used in a constant expression}} } } + +namespace GH64162 { +struct S { + const std::strong_ordering& operator<=>(const S&) const = default; +}; +bool test(S s) { + return s < s; // We expect this not to crash anymore +} + +// Following example never crashed but worth adding in because it is related +struct A {}; +bool operator<(A, int); + +struct B { + operator A(); +}; + +struct C { + B operator<=>(C); +}; + +bool f(C c) { return c < c; } +} _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits