@@ -1125,6 +1125,15 @@ void OverloadCandidateSet::clear(CandidateSetKind CSK) {
11251125 Kind = CSK;
11261126}
11271127
1128+ void OverloadCandidateSet::eliminateDuplicatesWithUnusedDefaultArgs() {
1129+ llvm::SmallPtrSet<Decl *, 16> UniqueEntities;
1130+ llvm::erase_if(Candidates, [&](const OverloadCandidate &Candidate) {
1131+ auto [It, New] =
1132+ UniqueEntities.insert(Candidate.Function->getCanonicalDecl());
1133+ return !(New || Candidate.ViableByDefaultArgument);
1134+ });
1135+ }
1136+
11281137namespace {
11291138 class UnbridgedCastsSet {
11301139 struct Entry {
@@ -6986,6 +6995,7 @@ void Sema::AddOverloadCandidate(
69866995 Candidate.FoundDecl = FoundDecl;
69876996 Candidate.Function = Function;
69886997 Candidate.Viable = true;
6998+ Candidate.ViableByDefaultArgument = false;
69896999 Candidate.RewriteKind =
69907000 CandidateSet.getRewriteInfo().getRewriteKind(Function, PO);
69917001 Candidate.IsADLCandidate = llvm::to_underlying(IsADLCandidate);
@@ -7113,6 +7123,10 @@ void Sema::AddOverloadCandidate(
71137123 return;
71147124 }
71157125
7126+ if (Args.size() < Function->getNumParams()) {
7127+ Candidate.ViableByDefaultArgument = true;
7128+ }
7129+
71167130 // (CUDA B.1): Check for invalid calls between targets.
71177131 if (getLangOpts().CUDA) {
71187132 const FunctionDecl *Caller = getCurFunctionDecl(/*AllowLambda=*/true);
@@ -13726,6 +13740,8 @@ void Sema::AddOverloadedCallCandidates(UnresolvedLookupExpr *ULE,
1372613740 CandidateSet, PartialOverloading,
1372713741 /*KnownValid*/ true);
1372813742
13743+ CandidateSet.eliminateDuplicatesWithUnusedDefaultArgs();
13744+
1372913745 if (ULE->requiresADL())
1373013746 AddArgumentDependentLookupCandidates(ULE->getName(), ULE->getExprLoc(),
1373113747 Args, ExplicitTemplateArgs,
@@ -14179,13 +14195,54 @@ static ExprResult FinishOverloadedCallExpr(Sema &SemaRef, Scope *S, Expr *Fn,
1417914195 break;
1418014196 }
1418114197
14182- case OR_Ambiguous:
14198+ case OR_Ambiguous: {
14199+ auto handleAmbiguousDefaultArgs = [&] {
14200+ unsigned FirstDefaultArgIndex = Args.size();
14201+ llvm::SmallVector<PartialDiagnosticAt, 4> Notes;
14202+ for (const OverloadCandidate &Cand : *CandidateSet) {
14203+ if (!Cand.Best)
14204+ continue;
14205+ if (isa<CXXMethodDecl>(Cand.Function) ||
14206+ Cand.Function->isFunctionTemplateSpecialization()) {
14207+ return false;
14208+ }
14209+ if (!Cand.ViableByDefaultArgument) {
14210+ // We found a candidate marked best which wasn't made viable by
14211+ // default argument, which means this is not an "ambiguous by
14212+ // default argument" situation.
14213+ return false;
14214+ }
14215+ const ParmVarDecl *Parameter =
14216+ Cand.Function->getParamDecl(FirstDefaultArgIndex);
14217+ Notes.emplace_back(
14218+ Parameter->getDefaultArg()->getExprLoc(),
14219+ SemaRef.PDiag(diag::note_default_argument_declared_here)
14220+ << Parameter->getDefaultArgRange());
14221+ }
14222+ if (Notes.empty())
14223+ return false;
14224+
14225+ assert(Notes.size() >= 2 &&
14226+ "Overloaded call is considered ambiguous by default arguments,"
14227+ " but we found less than two candidates");
14228+ SemaRef.Diag(Fn->getBeginLoc(), diag::err_ovl_ambiguous_default_arg)
14229+ << Fn->getSourceRange();
14230+ llvm::sort(Notes);
14231+ for (const PartialDiagnosticAt &PDiag : Notes) {
14232+ SemaRef.Diag(PDiag.first, PDiag.second);
14233+ }
14234+ return true;
14235+ };
14236+ if (handleAmbiguousDefaultArgs())
14237+ break;
14238+
1418314239 CandidateSet->NoteCandidates(
1418414240 PartialDiagnosticAt(Fn->getBeginLoc(),
1418514241 SemaRef.PDiag(diag::err_ovl_ambiguous_call)
1418614242 << ULE->getName() << Fn->getSourceRange()),
1418714243 SemaRef, OCD_AmbiguousCandidates, Args);
1418814244 break;
14245+ }
1418914246
1419014247 case OR_Deleted: {
1419114248 FunctionDecl *FDecl = (*Best)->Function;
0 commit comments