diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp index 00542bf250064..9b89bac0db394 100644 --- a/clang/lib/Sema/SemaOverload.cpp +++ b/clang/lib/Sema/SemaOverload.cpp @@ -9588,17 +9588,15 @@ bool clang::isBetterOverloadCandidate( if (RC1 && RC2) { bool AtLeastAsConstrained1, AtLeastAsConstrained2; if (S.IsAtLeastAsConstrained(Cand1.Function, {RC1}, Cand2.Function, - {RC2}, AtLeastAsConstrained1)) - return false; - if (!AtLeastAsConstrained1) - return false; - if (S.IsAtLeastAsConstrained(Cand2.Function, {RC2}, Cand1.Function, + {RC2}, AtLeastAsConstrained1) || + S.IsAtLeastAsConstrained(Cand2.Function, {RC2}, Cand1.Function, {RC1}, AtLeastAsConstrained2)) return false; - if (!AtLeastAsConstrained2) - return true; - } else if (RC1 || RC2) + if (AtLeastAsConstrained1 != AtLeastAsConstrained2) + return AtLeastAsConstrained1; + } else if (RC1 || RC2) { return RC1 != nullptr; + } } } diff --git a/clang/test/CXX/over/over.match/over.match.best/p2.cpp b/clang/test/CXX/over/over.match/over.match.best/p2.cpp new file mode 100644 index 0000000000000..3a44436655767 --- /dev/null +++ b/clang/test/CXX/over/over.match/over.match.best/p2.cpp @@ -0,0 +1,16 @@ +// RUN: %clang_cc1 -std=c++2a -verify %s + +namespace PR44761 { + template concept X = (sizeof(T) == sizeof(T)); + + template struct A { + bool operator<(const A&) const & requires X; // #1 + int operator<=>(const A&) const & requires X && X = delete; // #2 + }; + bool k1 = A() < A(); // not ordered by constraints: prefer non-rewritten form + bool k2 = A() < A(); // prefer more-constrained 'operator<=>' + // expected-error@-1 {{deleted}} + // expected-note@#1 {{candidate}} + // expected-note@#2 {{candidate function has been explicitly deleted}} + // expected-note@#2 {{candidate function (with reversed parameter order) has been explicitly deleted}} +}