aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/Sema/Sema.h16
-rw-r--r--lib/Sema/SemaDeclCXX.cpp8
-rw-r--r--lib/Sema/SemaExprCXX.cpp6
-rw-r--r--lib/Sema/SemaInit.cpp15
-rw-r--r--lib/Sema/SemaOverload.cpp116
-rw-r--r--test/Sema/overloadable.c6
-rw-r--r--test/SemaCXX/attr-unavailable.cpp4
-rw-r--r--test/SemaCXX/rval-references.cpp2
8 files changed, 114 insertions, 59 deletions
diff --git a/lib/Sema/Sema.h b/lib/Sema/Sema.h
index 0b6d16c9ad..54dd060fce 100644
--- a/lib/Sema/Sema.h
+++ b/lib/Sema/Sema.h
@@ -1028,10 +1028,20 @@ public:
OverloadingResult BestViableFunction(OverloadCandidateSet& CandidateSet,
SourceLocation Loc,
OverloadCandidateSet::iterator& Best);
+
+ enum OverloadCandidateDisplayKind {
+ /// Requests that all candidates be shown. Viable candidates will
+ /// be printed first.
+ OCD_AllCandidates,
+
+ /// Requests that only viable candidates be shown.
+ OCD_ViableCandidates
+ };
void PrintOverloadCandidates(OverloadCandidateSet& CandidateSet,
- bool OnlyViable,
- const char *Opc=0,
- SourceLocation Loc=SourceLocation());
+ OverloadCandidateDisplayKind OCD,
+ const char *Opc = 0,
+ SourceLocation Loc = SourceLocation());
+
void NoteOverloadCandidate(FunctionDecl *Fn);
FunctionDecl *ResolveAddressOfOverloadedFunction(Expr *From, QualType ToType,
diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp
index d3c8de326c..8965199c2f 100644
--- a/lib/Sema/SemaDeclCXX.cpp
+++ b/lib/Sema/SemaDeclCXX.cpp
@@ -4193,7 +4193,7 @@ Sema::PerformInitializationByConstructor(QualType ClassType,
else
Diag(Loc, diag::err_ovl_no_viable_function_in_init)
<< ClassType << Range;
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
return 0;
case OR_Ambiguous:
@@ -4201,7 +4201,7 @@ Sema::PerformInitializationByConstructor(QualType ClassType,
Diag(Loc, diag::err_ovl_ambiguous_init) << InitEntity << Range;
else
Diag(Loc, diag::err_ovl_ambiguous_init) << ClassType << Range;
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_ViableCandidates);
return 0;
case OR_Deleted:
@@ -4216,7 +4216,7 @@ Sema::PerformInitializationByConstructor(QualType ClassType,
<< Best->Function->isDeleted()
<< RD->getDeclName() << Range;
}
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
return 0;
}
@@ -4540,7 +4540,7 @@ Sema::CheckReferenceInit(Expr *&Init, QualType DeclType,
}
Diag(DeclLoc, diag::err_ref_init_ambiguous) << DeclType << Init->getType()
<< Init->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_ViableCandidates);
return true;
case OR_No_Viable_Function:
diff --git a/lib/Sema/SemaExprCXX.cpp b/lib/Sema/SemaExprCXX.cpp
index fa1a62b14a..6407441aa1 100644
--- a/lib/Sema/SemaExprCXX.cpp
+++ b/lib/Sema/SemaExprCXX.cpp
@@ -673,20 +673,20 @@ bool Sema::FindAllocationOverload(SourceLocation StartLoc, SourceRange Range,
case OR_No_Viable_Function:
Diag(StartLoc, diag::err_ovl_no_viable_function_in_call)
<< Name << Range;
- PrintOverloadCandidates(Candidates, /*OnlyViable=*/false);
+ PrintOverloadCandidates(Candidates, OCD_AllCandidates);
return true;
case OR_Ambiguous:
Diag(StartLoc, diag::err_ovl_ambiguous_call)
<< Name << Range;
- PrintOverloadCandidates(Candidates, /*OnlyViable=*/true);
+ PrintOverloadCandidates(Candidates, OCD_ViableCandidates);
return true;
case OR_Deleted:
Diag(StartLoc, diag::err_ovl_deleted_call)
<< Best->Function->isDeleted()
<< Name << Range;
- PrintOverloadCandidates(Candidates, /*OnlyViable=*/true);
+ PrintOverloadCandidates(Candidates, OCD_AllCandidates);
return true;
}
assert(false && "Unreachable, bad result from BestViableFunction");
diff --git a/lib/Sema/SemaInit.cpp b/lib/Sema/SemaInit.cpp
index c2a62cbc52..8c45edb21f 100644
--- a/lib/Sema/SemaInit.cpp
+++ b/lib/Sema/SemaInit.cpp
@@ -88,7 +88,7 @@ static bool CheckSingleInitializer(Expr *&Init, QualType DeclType,
S.Diag(Init->getSourceRange().getBegin(),
diag::err_typecheck_convert_ambiguous)
<< DeclType << Init->getType() << Init->getSourceRange();
- S.PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+ S.PrintOverloadCandidates(CandidateSet, Sema::OCD_AllCandidates);
return true;
}
return false;
@@ -3010,14 +3010,14 @@ static Sema::OwningExprResult CopyIfRequiredForEntity(Sema &S,
S.Diag(Loc, diag::err_temp_copy_no_viable)
<< (int)Entity.getKind() << CurInitExpr->getType()
<< CurInitExpr->getSourceRange();
- S.PrintOverloadCandidates(CandidateSet, false);
+ S.PrintOverloadCandidates(CandidateSet, Sema::OCD_AllCandidates);
return S.ExprError();
case OR_Ambiguous:
S.Diag(Loc, diag::err_temp_copy_ambiguous)
<< (int)Entity.getKind() << CurInitExpr->getType()
<< CurInitExpr->getSourceRange();
- S.PrintOverloadCandidates(CandidateSet, true);
+ S.PrintOverloadCandidates(CandidateSet, Sema::OCD_ViableCandidates);
return S.ExprError();
case OR_Deleted:
@@ -3432,14 +3432,14 @@ bool InitializationSequence::Diagnose(Sema &S,
<< DestType << Args[0]->getType()
<< Args[0]->getSourceRange();
- S.PrintOverloadCandidates(FailedCandidateSet, true);
+ S.PrintOverloadCandidates(FailedCandidateSet, Sema::OCD_ViableCandidates);
break;
case OR_No_Viable_Function:
S.Diag(Kind.getLocation(), diag::err_typecheck_nonviable_condition)
<< Args[0]->getType() << DestType.getNonReferenceType()
<< Args[0]->getSourceRange();
- S.PrintOverloadCandidates(FailedCandidateSet, false);
+ S.PrintOverloadCandidates(FailedCandidateSet, Sema::OCD_AllCandidates);
break;
case OR_Deleted: {
@@ -3541,13 +3541,14 @@ bool InitializationSequence::Diagnose(Sema &S,
case OR_Ambiguous:
S.Diag(Kind.getLocation(), diag::err_ovl_ambiguous_init)
<< DestType << ArgsRange;
- S.PrintOverloadCandidates(FailedCandidateSet, true);
+ S.PrintOverloadCandidates(FailedCandidateSet,
+ Sema::OCD_ViableCandidates);
break;
case OR_No_Viable_Function:
S.Diag(Kind.getLocation(), diag::err_ovl_no_viable_function_in_init)
<< DestType << ArgsRange;
- S.PrintOverloadCandidates(FailedCandidateSet, false);
+ S.PrintOverloadCandidates(FailedCandidateSet, Sema::OCD_AllCandidates);
break;
case OR_Deleted: {
diff --git a/lib/Sema/SemaOverload.cpp b/lib/Sema/SemaOverload.cpp
index dc590ceab4..825dabfbc7 100644
--- a/lib/Sema/SemaOverload.cpp
+++ b/lib/Sema/SemaOverload.cpp
@@ -1617,7 +1617,7 @@ Sema::DiagnoseMultipleUserDefinedConversion(Expr *From, QualType ToType) {
<< From->getType() << ToType << From->getSourceRange();
else
return false;
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
return true;
}
@@ -4314,14 +4314,20 @@ void Sema::NoteOverloadCandidate(FunctionDecl *Fn) {
namespace {
+void NoteDeletedCandidate(Sema &S, OverloadCandidate *Cand) {
+}
+
void NoteFunctionCandidate(Sema &S, OverloadCandidate *Cand) {
- if (Cand->Function->isDeleted() ||
- Cand->Function->getAttr<UnavailableAttr>()) {
- // Deleted or "unavailable" function.
+ // Note deleted candidates, but only if they're viable.
+ if (Cand->Viable &&
+ (Cand->Function->isDeleted() ||
+ Cand->Function->hasAttr<UnavailableAttr>())) {
S.Diag(Cand->Function->getLocation(), diag::note_ovl_candidate_deleted)
<< Cand->Function->isDeleted();
return;
- } else if (FunctionTemplateDecl *FunTmpl
+ }
+
+ if (FunctionTemplateDecl *FunTmpl
= Cand->Function->getPrimaryTemplate()) {
// Function template specialization
// FIXME: Give a better reason!
@@ -4431,23 +4437,61 @@ void NoteAmbiguousUserConversions(Sema &S, SourceLocation OpLoc,
}
}
+struct CompareOverloadCandidates {
+ SourceManager &SM;
+ CompareOverloadCandidates(SourceManager &SM) : SM(SM) {}
+
+ bool operator()(const OverloadCandidate *L,
+ const OverloadCandidate *R) {
+ // Order first by viability.
+ if (L->Viable != R->Viable)
+ return L->Viable;
+
+ // Put declared functions first.
+ if (L->Function) {
+ if (!R->Function) return true;
+ return SM.isBeforeInTranslationUnit(L->Function->getLocation(),
+ R->Function->getLocation());
+ } else if (R->Function) return false;
+
+ // Then surrogates.
+ if (L->IsSurrogate) {
+ if (!R->IsSurrogate) return true;
+ return SM.isBeforeInTranslationUnit(L->Surrogate->getLocation(),
+ R->Surrogate->getLocation());
+ } else if (R->IsSurrogate) return false;
+
+ // And builtins just come in a jumble.
+ return false;
+ }
+};
+
} // end anonymous namespace
/// PrintOverloadCandidates - When overload resolution fails, prints
/// diagnostic messages containing the candidates in the candidate
-/// set. If OnlyViable is true, only viable candidates will be printed.
+/// set.
void
Sema::PrintOverloadCandidates(OverloadCandidateSet& CandidateSet,
- bool OnlyViable,
+ OverloadCandidateDisplayKind OCD,
const char *Opc,
SourceLocation OpLoc) {
+ // Sort the candidates by viability and position. Sorting directly would
+ // be prohibitive, so we make a set of pointers and sort those.
+ llvm::SmallVector<OverloadCandidate*, 32> Cands;
+ if (OCD == OCD_AllCandidates) Cands.reserve(CandidateSet.size());
+ for (OverloadCandidateSet::iterator Cand = CandidateSet.begin(),
+ LastCand = CandidateSet.end();
+ Cand != LastCand; ++Cand)
+ if (Cand->Viable || OCD == OCD_AllCandidates)
+ Cands.push_back(Cand);
+ std::sort(Cands.begin(), Cands.end(), CompareOverloadCandidates(SourceMgr));
+
bool ReportedNonViableOperator = false;
- OverloadCandidateSet::iterator Cand = CandidateSet.begin(),
- LastCand = CandidateSet.end();
- for (; Cand != LastCand; ++Cand) {
- if (OnlyViable && !Cand->Viable)
- continue;
+ llvm::SmallVectorImpl<OverloadCandidate*>::iterator I, E;
+ for (I = Cands.begin(), E = Cands.end(); I != E; ++I) {
+ OverloadCandidate *Cand = *I;
if (Cand->Function)
NoteFunctionCandidate(*this, Cand);
@@ -4457,14 +4501,13 @@ Sema::PrintOverloadCandidates(OverloadCandidateSet& CandidateSet,
// This a builtin candidate. We do not, in general, want to list
// every possible builtin candidate.
- // If 'OnlyViable' is true, there were viable candidates.
- // This must be one of them because of the header condition. List it.
- else if (OnlyViable)
+ // If this is a viable builtin, print it.
+ else if (Cand->Viable)
NoteBuiltinOperatorCandidate(*this, Opc, OpLoc, Cand);
// Otherwise, non-viability might be due to ambiguous user-defined
// conversions. Report them exactly once.
- else if (!Cand->Viable && !ReportedNonViableOperator) {
+ else if (!ReportedNonViableOperator) {
NoteAmbiguousUserConversions(*this, OpLoc, Cand);
ReportedNonViableOperator = true;
}
@@ -4975,13 +5018,13 @@ Sema::BuildOverloadedCallExpr(Expr *Fn, UnresolvedLookupExpr *ULE,
Diag(Fn->getSourceRange().getBegin(),
diag::err_ovl_no_viable_function_in_call)
<< ULE->getName() << Fn->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
break;
case OR_Ambiguous:
Diag(Fn->getSourceRange().getBegin(), diag::err_ovl_ambiguous_call)
<< ULE->getName() << Fn->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_ViableCandidates);
break;
case OR_Deleted:
@@ -4989,7 +5032,7 @@ Sema::BuildOverloadedCallExpr(Expr *Fn, UnresolvedLookupExpr *ULE,
<< Best->Function->isDeleted()
<< ULE->getName()
<< Fn->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
break;
}
@@ -5144,7 +5187,7 @@ Sema::OwningExprResult Sema::CreateOverloadedUnaryOp(SourceLocation OpLoc,
Diag(OpLoc, diag::err_ovl_ambiguous_oper)
<< UnaryOperator::getOpcodeStr(Opc)
<< Input->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true,
+ PrintOverloadCandidates(CandidateSet, OCD_ViableCandidates,
UnaryOperator::getOpcodeStr(Opc), OpLoc);
return ExprError();
@@ -5153,7 +5196,7 @@ Sema::OwningExprResult Sema::CreateOverloadedUnaryOp(SourceLocation OpLoc,
<< Best->Function->isDeleted()
<< UnaryOperator::getOpcodeStr(Opc)
<< Input->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
return ExprError();
}
@@ -5360,7 +5403,7 @@ Sema::CreateOverloadedBinOp(SourceLocation OpLoc,
assert(Result.isInvalid() &&
"C++ binary operator overloading is missing candidates!");
if (Result.isInvalid())
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false,
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates,
BinaryOperator::getOpcodeStr(Opc), OpLoc);
return move(Result);
}
@@ -5369,7 +5412,7 @@ Sema::CreateOverloadedBinOp(SourceLocation OpLoc,
Diag(OpLoc, diag::err_ovl_ambiguous_oper)
<< BinaryOperator::getOpcodeStr(Opc)
<< Args[0]->getSourceRange() << Args[1]->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true,
+ PrintOverloadCandidates(CandidateSet, OCD_ViableCandidates,
BinaryOperator::getOpcodeStr(Opc), OpLoc);
return ExprError();
@@ -5378,7 +5421,7 @@ Sema::CreateOverloadedBinOp(SourceLocation OpLoc,
<< Best->Function->isDeleted()
<< BinaryOperator::getOpcodeStr(Opc)
<< Args[0]->getSourceRange() << Args[1]->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
return ExprError();
}
@@ -5488,7 +5531,7 @@ Sema::CreateOverloadedArraySubscriptExpr(SourceLocation LLoc,
Diag(LLoc, diag::err_ovl_no_viable_subscript)
<< Args[0]->getType()
<< Args[0]->getSourceRange() << Args[1]->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false,
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates,
"[]", LLoc);
return ExprError();
}
@@ -5496,7 +5539,7 @@ Sema::CreateOverloadedArraySubscriptExpr(SourceLocation LLoc,
case OR_Ambiguous:
Diag(LLoc, diag::err_ovl_ambiguous_oper)
<< "[]" << Args[0]->getSourceRange() << Args[1]->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true,
+ PrintOverloadCandidates(CandidateSet, OCD_ViableCandidates,
"[]", LLoc);
return ExprError();
@@ -5504,7 +5547,8 @@ Sema::CreateOverloadedArraySubscriptExpr(SourceLocation LLoc,
Diag(LLoc, diag::err_ovl_deleted_oper)
<< Best->Function->isDeleted() << "[]"
<< Args[0]->getSourceRange() << Args[1]->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates,
+ "[]", LLoc);
return ExprError();
}
@@ -5588,14 +5632,14 @@ Sema::BuildCallToMemberFunction(Scope *S, Expr *MemExprE,
Diag(UnresExpr->getMemberLoc(),
diag::err_ovl_no_viable_member_function_in_call)
<< DeclName << MemExprE->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
// FIXME: Leaking incoming expressions!
return ExprError();
case OR_Ambiguous:
Diag(UnresExpr->getMemberLoc(), diag::err_ovl_ambiguous_member_call)
<< DeclName << MemExprE->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
// FIXME: Leaking incoming expressions!
return ExprError();
@@ -5603,7 +5647,7 @@ Sema::BuildCallToMemberFunction(Scope *S, Expr *MemExprE,
Diag(UnresExpr->getMemberLoc(), diag::err_ovl_deleted_member_call)
<< Best->Function->isDeleted()
<< DeclName << MemExprE->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
// FIXME: Leaking incoming expressions!
return ExprError();
}
@@ -5752,14 +5796,14 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object,
Diag(Object->getSourceRange().getBegin(),
diag::err_ovl_no_viable_object_call)
<< Object->getType() << Object->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
break;
case OR_Ambiguous:
Diag(Object->getSourceRange().getBegin(),
diag::err_ovl_ambiguous_object_call)
<< Object->getType() << Object->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_ViableCandidates);
break;
case OR_Deleted:
@@ -5767,7 +5811,7 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object,
diag::err_ovl_deleted_object_call)
<< Best->Function->isDeleted()
<< Object->getType() << Object->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
break;
}
@@ -5948,20 +5992,20 @@ Sema::BuildOverloadedArrowExpr(Scope *S, ExprArg BaseIn, SourceLocation OpLoc) {
else
Diag(OpLoc, diag::err_ovl_no_viable_oper)
<< "operator->" << Base->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/false);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
return ExprError();
case OR_Ambiguous:
Diag(OpLoc, diag::err_ovl_ambiguous_oper)
<< "->" << Base->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_ViableCandidates);
return ExprError();
case OR_Deleted:
Diag(OpLoc, diag::err_ovl_deleted_oper)
<< Best->Function->isDeleted()
<< "->" << Base->getSourceRange();
- PrintOverloadCandidates(CandidateSet, /*OnlyViable=*/true);
+ PrintOverloadCandidates(CandidateSet, OCD_AllCandidates);
return ExprError();
}
diff --git a/test/Sema/overloadable.c b/test/Sema/overloadable.c
index 72d3673c82..ff631ed9c8 100644
--- a/test/Sema/overloadable.c
+++ b/test/Sema/overloadable.c
@@ -37,9 +37,9 @@ void test_struct(struct X x, struct Y y) {
double *f(int) __attribute__((overloadable)); // expected-error{{conflicting types for 'f'}}
-double promote(float) __attribute__((__overloadable__));
-double promote(double) __attribute__((__overloadable__));
-long double promote(long double) __attribute__((__overloadable__));
+double promote(float) __attribute__((__overloadable__)); // expected-note {{candidate}}
+double promote(double) __attribute__((__overloadable__)); // expected-note {{candidate}}
+long double promote(long double) __attribute__((__overloadable__)); // expected-note {{candidate}}
void promote() __attribute__((__overloadable__)); // expected-error{{'overloadable' function 'promote' must have a prototype}}
void promote(...) __attribute__((__overloadable__, __unavailable__)); // \
diff --git a/test/SemaCXX/attr-unavailable.cpp b/test/SemaCXX/attr-unavailable.cpp
index bebd4cb18e..8b381dfe4b 100644
--- a/test/SemaCXX/attr-unavailable.cpp
+++ b/test/SemaCXX/attr-unavailable.cpp
@@ -1,7 +1,7 @@
// RUN: %clang_cc1 -fsyntax-only -verify %s
-int &foo(int);
-double &foo(double);
+int &foo(int); // expected-note {{candidate}}
+double &foo(double); // expected-note {{candidate}}
void foo(...) __attribute__((__unavailable__)); // expected-note {{candidate function}} \
// expected-note{{function has been explicitly marked unavailable here}}
diff --git a/test/SemaCXX/rval-references.cpp b/test/SemaCXX/rval-references.cpp
index 1cde26352a..2a7fb25c62 100644
--- a/test/SemaCXX/rval-references.cpp
+++ b/test/SemaCXX/rval-references.cpp
@@ -65,7 +65,7 @@ int&& should_not_warn(int&& i) { // But GCC 4.4 does
// Test the return dance. This also tests IsReturnCopyElidable.
struct MoveOnly {
MoveOnly();
- MoveOnly(const MoveOnly&) = delete; // expected-note {{candidate function}} \
+ MoveOnly(const MoveOnly&) = delete; // expected-note {{candidate constructor}} \
// expected-note 3{{explicitly marked deleted here}}
MoveOnly(MoveOnly&&); // expected-note {{candidate constructor}}
MoveOnly(int&&); // expected-note {{candidate constructor}}