forked from OSchip/llvm-project
Implement C++ [over.ics.user]p3, which restricts the final conversion
from a conversion function template specialization to one of exact match rank. We only know how to test this in C++0x with default function template arguments, but it's also in the C++03 spec. Fixes PR6285. llvm-svn: 101089
This commit is contained in:
parent
5c0066f1cf
commit
2c326bce38
|
@ -2819,6 +2819,17 @@ Sema::AddConversionCandidate(CXXConversionDecl *Conversion,
|
|||
switch (ICS.getKind()) {
|
||||
case ImplicitConversionSequence::StandardConversion:
|
||||
Candidate.FinalConversion = ICS.Standard;
|
||||
|
||||
// C++ [over.ics.user]p3:
|
||||
// If the user-defined conversion is specified by a specialization of a
|
||||
// conversion function template, the second standard conversion sequence
|
||||
// shall have exact match rank.
|
||||
if (Conversion->getPrimaryTemplate() &&
|
||||
GetConversionRank(ICS.Standard.Second) != ICR_Exact_Match) {
|
||||
Candidate.Viable = false;
|
||||
Candidate.FailureKind = ovl_fail_final_conversion_not_exact;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case ImplicitConversionSequence::BadConversion:
|
||||
|
@ -4628,6 +4639,7 @@ void NoteFunctionCandidate(Sema &S, OverloadCandidate *Cand,
|
|||
|
||||
case ovl_fail_trivial_conversion:
|
||||
case ovl_fail_bad_final_conversion:
|
||||
case ovl_fail_final_conversion_not_exact:
|
||||
return S.NoteOverloadCandidate(Fn);
|
||||
|
||||
case ovl_fail_bad_conversion: {
|
||||
|
|
|
@ -440,7 +440,11 @@ namespace clang {
|
|||
|
||||
/// This conversion candidate is not viable because its result
|
||||
/// type is not implicitly convertible to the desired type.
|
||||
ovl_fail_bad_final_conversion
|
||||
ovl_fail_bad_final_conversion,
|
||||
|
||||
/// This conversion function template specialization candidate is not
|
||||
/// viable because the final conversion was not an exact match.
|
||||
ovl_fail_final_conversion_not_exact
|
||||
};
|
||||
|
||||
/// OverloadCandidate - A single candidate in an overload set (C++ 13.3).
|
||||
|
|
|
@ -0,0 +1,14 @@
|
|||
// RUN: %clang_cc1 -fsyntax-only -std=c++0x -verify %s
|
||||
|
||||
namespace PR6285 {
|
||||
template<typename T> struct identity
|
||||
{ typedef T type; };
|
||||
|
||||
struct D {
|
||||
template<typename T = short>
|
||||
operator typename identity<T>::type(); // expected-note{{candidate}}
|
||||
};
|
||||
|
||||
int f() { return D(); } // expected-error{{no viable conversion}}
|
||||
}
|
||||
|
Loading…
Reference in New Issue