https://github.com/shafik created https://github.com/llvm/llvm-project/pull/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 >From ed43ed6c693bcc06ffb637972d3938d8d7f9db25 Mon Sep 17 00:00:00 2001 From: Shafik Yaghmour <sha...@users.noreply.github.com> Date: Wed, 13 Sep 2023 11:09:28 -0700 Subject: [PATCH] [Clang] Fix CXXRewrittenBinaryOperator::getDecomposedForm to handle case when spaceship operator returns comparison category by reference 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 --- clang/lib/AST/ExprCXX.cpp | 2 +- clang/test/SemaCXX/compare-cxx2a.cpp | 23 +++++++++++++++++++++++ 2 files changed, 24 insertions(+), 1 deletion(-) 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