Skip to content

Commit 77a9f8f

Browse files
committed
[clang][Sema] Bugfix for choosing the more specialized overload (llvm#83279)
There was a bug in Clang where it couldn't choose which overload candidate was more specialized if it was comparing a member-function to a non-member function. Previously, this was detected as an ambiguity, now Clang chooses correctly. This patch fixes the bug by fully implementing CWG2445 and moving the template transformation described in `[temp.func.order]` paragraph 3 from `isAtLeastAsSpecializedAs()` to `Sema::getMoreSpecializedTemplate()` so we have the transformed parameter list during the whole comparison. Also, to be able to add the correct type for the implicit object parameter `Sema::getMoreSpecializedTemplate()` has new parameters for the object type. Fixes llvm#74494, fixes llvm#82509
1 parent c624dc9 commit 77a9f8f

File tree

8 files changed

+291
-163
lines changed

8 files changed

+291
-163
lines changed

clang/docs/ReleaseNotes.rst

+41-2
Original file line numberDiff line numberDiff line change
@@ -219,8 +219,47 @@ Bug Fixes to C++ Support
219219
an empty template parameter lists.
220220
- Clang now classifies aggregate initialization in C++17 and newer as constant
221221
or non-constant more accurately. Previously, only a subset of the initializer
222-
elements were considered, misclassifying some initializers as constant. Fixes
223-
some of (`#80510 <https://github.com/llvm/llvm-project/issues/80510>`).
222+
elements were considered, misclassifying some initializers as constant. Partially fixes
223+
#GH80510.
224+
- Clang now ignores top-level cv-qualifiers on function parameters in template partial orderings. (#GH75404)
225+
- No longer reject valid use of the ``_Alignas`` specifier when declaring a
226+
local variable, which is supported as a C11 extension in C++. Previously, it
227+
was only accepted at namespace scope but not at local function scope.
228+
- Clang no longer tries to call consteval constructors at runtime when they appear in a member initializer. (#GH82154)
229+
- Fix crash when using an immediate-escalated function at global scope. (#GH82258)
230+
- Correctly immediate-escalate lambda conversion functions. (#GH82258)
231+
- Fixed an issue where template parameters of a nested abbreviated generic lambda within
232+
a requires-clause lie at the same depth as those of the surrounding lambda. This,
233+
in turn, results in the wrong template argument substitution during constraint checking.
234+
(#GH78524)
235+
- Clang no longer instantiates the exception specification of discarded candidate function
236+
templates when determining the primary template of an explicit specialization.
237+
- Fixed a crash in Microsoft compatibility mode where unqualified dependent base class
238+
lookup searches the bases of an incomplete class.
239+
- Fix a crash when an unresolved overload set is encountered on the RHS of a ``.*`` operator.
240+
(#GH53815)
241+
- In ``__restrict``-qualified member functions, attach ``__restrict`` to the pointer type of
242+
``this`` rather than the pointee type.
243+
Fixes (#GH82941), (#GH42411) and (#GH18121).
244+
- Clang now properly reports supported C++11 attributes when using
245+
``__has_cpp_attribute`` and parses attributes with arguments in C++03 (#GH82995)
246+
- Clang now properly diagnoses missing 'default' template arguments on a variety
247+
of templates. Previously we were diagnosing on any non-function template
248+
instead of only on class, alias, and variable templates, as last updated by
249+
CWG2032. Fixes (#GH83461)
250+
- Fixed an issue where an attribute on a declarator would cause the attribute to
251+
be destructed prematurely. This fixes a pair of Chromium that were brought to
252+
our attention by an attempt to fix in (#GH77703). Fixes (#GH83385).
253+
- Fix evaluation of some immediate calls in default arguments.
254+
Fixes (#GH80630)
255+
- Fix a crash when an explicit template argument list is used with a name for which lookup
256+
finds a non-template function and a dependent using declarator.
257+
- Fix a bug where overload resolution falsely reported an ambiguity when it was comparing
258+
a member-function against a non member function or a member-function with an
259+
explicit object parameter against a member function with no explicit object parameter
260+
when one of the function had more specialized templates.
261+
Fixes (`#82509 <https://github.com/llvm/llvm-project/issues/82509>`_)
262+
and (`#74494 <https://github.com/llvm/llvm-project/issues/74494>`_)
224263

225264
Bug Fixes to AST Handling
226265
^^^^^^^^^^^^^^^^^^^^^^^^^

clang/include/clang/Sema/Sema.h

+7-2
Original file line numberDiff line numberDiff line change
@@ -9458,8 +9458,8 @@ class Sema final {
94589458
FunctionTemplateDecl *getMoreSpecializedTemplate(
94599459
FunctionTemplateDecl *FT1, FunctionTemplateDecl *FT2, SourceLocation Loc,
94609460
TemplatePartialOrderingContext TPOC, unsigned NumCallArguments1,
9461-
unsigned NumCallArguments2, QualType ObjType1={},
9462-
QualType ObjType2={}, bool Reversed = false);
9461+
QualType RawObj1Ty = {}, QualType RawObj2Ty = {}, bool Reversed = false);
9462+
94639463
UnresolvedSetIterator
94649464
getMostSpecialized(UnresolvedSetIterator SBegin, UnresolvedSetIterator SEnd,
94659465
TemplateSpecCandidateSet &FailedCandidates,
@@ -9506,6 +9506,11 @@ class Sema final {
95069506

95079507
//===--------------------------------------------------------------------===//
95089508
// C++ Template Instantiation
9509+
///@}
9510+
//
9511+
//
9512+
// -------------------------------------------------------------------------
9513+
//
95099514
//
95109515

95119516
MultiLevelTemplateArgumentList getTemplateInstantiationArgs(

clang/lib/Sema/SemaOverload.cpp

+11-8
Original file line numberDiff line numberDiff line change
@@ -10516,23 +10516,26 @@ bool clang::isBetterOverloadCandidate(
1051610516
// according to the partial ordering rules described in 14.5.5.2, or,
1051710517
// if not that,
1051810518
if (Cand1IsSpecialization && Cand2IsSpecialization) {
10519-
auto* ObjContext1=dyn_cast<CXXRecordDecl>(Cand1.FoundDecl->getDeclContext());
10520-
auto* ObjContext2=dyn_cast<CXXRecordDecl>(Cand2.FoundDecl->getDeclContext());
10519+
const auto *Obj1Context =
10520+
dyn_cast<CXXRecordDecl>(Cand1.FoundDecl->getDeclContext());
10521+
const auto *Obj2Context =
10522+
dyn_cast<CXXRecordDecl>(Cand2.FoundDecl->getDeclContext());
1052110523
if (FunctionTemplateDecl *BetterTemplate = S.getMoreSpecializedTemplate(
1052210524
Cand1.Function->getPrimaryTemplate(),
1052310525
Cand2.Function->getPrimaryTemplate(), Loc,
1052410526
isa<CXXConversionDecl>(Cand1.Function) ? TPOC_Conversion
1052510527
: TPOC_Call,
10526-
Cand1.ExplicitCallArguments, Cand2.ExplicitCallArguments,
10527-
ObjContext1?QualType(ObjContext1->getTypeForDecl(),0):QualType{},
10528-
ObjContext2?QualType(ObjContext2->getTypeForDecl(),0):QualType{},
10529-
Cand1.isReversed() ^ Cand2.isReversed())){
10528+
Cand1.ExplicitCallArguments,
10529+
Obj1Context ? QualType(Obj1Context->getTypeForDecl(), 0)
10530+
: QualType{},
10531+
Obj2Context ? QualType(Obj2Context->getTypeForDecl(), 0)
10532+
: QualType{},
10533+
Cand1.isReversed() ^ Cand2.isReversed())) {
1053010534
if (LLVM_UNLIKELY(!S.OverloadInspectionCallbacks.empty()))
1053110535
atCompareOverloadEnd(S.OverloadInspectionCallbacks,S,Loc,Cand1,Cand2,
1053210536
BetterTemplate==Cand1.Function->getPrimaryTemplate(),moreSpecialized);
10533-
return BetterTemplate==Cand1.Function->getPrimaryTemplate();
10537+
return BetterTemplate == Cand1.Function->getPrimaryTemplate();
1053410538
}
10535-
1053610539
}
1053710540

1053810541
// -— F1 and F2 are non-template functions with the same

0 commit comments

Comments
 (0)