jtbandes updated this revision to Diff 124033. jtbandes added a comment. @erik.pilkington Updated to use a wrapper function. This is definitely less invasive, but it could defeat some optimizations (any approach that checks the return value will defeat tail recursion, I suppose...)
https://reviews.llvm.org/D40284 Files: lib/Sema/SemaTemplateDeduction.cpp test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/basic.cpp Index: test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/basic.cpp =================================================================== --- test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/basic.cpp +++ test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/basic.cpp @@ -45,3 +45,11 @@ func(foo<int>()); // expected-error {{no matching function}} } } + +namespace test4 { + // expected-note@+1 {{candidate template ignored: could not match 'int [N]' against 'int []'}} + template<int N> void f1(int (&arr)[N]); + template<int N> void f2(int (&arr)[]) { + f1(arr); // expected-error {{no matching function}} + } +} Index: lib/Sema/SemaTemplateDeduction.cpp =================================================================== --- lib/Sema/SemaTemplateDeduction.cpp +++ lib/Sema/SemaTemplateDeduction.cpp @@ -1056,6 +1056,12 @@ return false; } +static Sema::TemplateDeductionResult DeduceTemplateArgumentsByTypeMatchInner( + Sema &S, TemplateParameterList *TemplateParams, QualType ParamIn, + QualType ArgIn, TemplateDeductionInfo &Info, + SmallVectorImpl<DeducedTemplateArgument> &Deduced, unsigned TDF, + bool PartialOrdering, bool DeducedFromArrayBound); + /// \brief Deduce the template arguments by comparing the parameter type and /// the argument type (C++ [temp.deduct.type]). /// @@ -1080,15 +1086,34 @@ /// \returns the result of template argument deduction so far. Note that a /// "success" result means that template argument deduction has not yet failed, /// but it may still fail, later, for other reasons. -static Sema::TemplateDeductionResult -DeduceTemplateArgumentsByTypeMatch(Sema &S, - TemplateParameterList *TemplateParams, - QualType ParamIn, QualType ArgIn, - TemplateDeductionInfo &Info, - SmallVectorImpl<DeducedTemplateArgument> &Deduced, - unsigned TDF, - bool PartialOrdering, - bool DeducedFromArrayBound) { +static Sema::TemplateDeductionResult DeduceTemplateArgumentsByTypeMatch( + Sema &S, TemplateParameterList *TemplateParams, QualType ParamIn, + QualType ArgIn, TemplateDeductionInfo &Info, + SmallVectorImpl<DeducedTemplateArgument> &Deduced, unsigned TDF, + bool PartialOrdering, bool DeducedFromArrayBound) { + // Because DeduceTemplateArgumentsByTypeMatchInner is recursive, and tends to + // modify Info.FirstArg and SecondArg even when deduction succeeds, save the + // original values and restore them if no error occurred. + const auto OriginalFirstArg = Info.FirstArg; + const auto OriginalSecondArg = Info.SecondArg; + + const auto Result = DeduceTemplateArgumentsByTypeMatchInner( + S, TemplateParams, ParamIn, ArgIn, Info, Deduced, TDF, PartialOrdering, + DeducedFromArrayBound); + + if (Result == Sema::TDK_Success) { + Info.FirstArg = OriginalFirstArg; + Info.SecondArg = OriginalSecondArg; + } + return Result; +} + +/// \see DeduceTemplateArgumentsByTypeMatch() +static Sema::TemplateDeductionResult DeduceTemplateArgumentsByTypeMatchInner( + Sema &S, TemplateParameterList *TemplateParams, QualType ParamIn, + QualType ArgIn, TemplateDeductionInfo &Info, + SmallVectorImpl<DeducedTemplateArgument> &Deduced, unsigned TDF, + bool PartialOrdering, bool DeducedFromArrayBound) { // We only want to look at the canonical types, since typedefs and // sugar are not part of template argument deduction. QualType Param = S.Context.getCanonicalType(ParamIn);
Index: test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/basic.cpp =================================================================== --- test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/basic.cpp +++ test/CXX/temp/temp.fct.spec/temp.deduct/temp.deduct.call/basic.cpp @@ -45,3 +45,11 @@ func(foo<int>()); // expected-error {{no matching function}} } } + +namespace test4 { + // expected-note@+1 {{candidate template ignored: could not match 'int [N]' against 'int []'}} + template<int N> void f1(int (&arr)[N]); + template<int N> void f2(int (&arr)[]) { + f1(arr); // expected-error {{no matching function}} + } +} Index: lib/Sema/SemaTemplateDeduction.cpp =================================================================== --- lib/Sema/SemaTemplateDeduction.cpp +++ lib/Sema/SemaTemplateDeduction.cpp @@ -1056,6 +1056,12 @@ return false; } +static Sema::TemplateDeductionResult DeduceTemplateArgumentsByTypeMatchInner( + Sema &S, TemplateParameterList *TemplateParams, QualType ParamIn, + QualType ArgIn, TemplateDeductionInfo &Info, + SmallVectorImpl<DeducedTemplateArgument> &Deduced, unsigned TDF, + bool PartialOrdering, bool DeducedFromArrayBound); + /// \brief Deduce the template arguments by comparing the parameter type and /// the argument type (C++ [temp.deduct.type]). /// @@ -1080,15 +1086,34 @@ /// \returns the result of template argument deduction so far. Note that a /// "success" result means that template argument deduction has not yet failed, /// but it may still fail, later, for other reasons. -static Sema::TemplateDeductionResult -DeduceTemplateArgumentsByTypeMatch(Sema &S, - TemplateParameterList *TemplateParams, - QualType ParamIn, QualType ArgIn, - TemplateDeductionInfo &Info, - SmallVectorImpl<DeducedTemplateArgument> &Deduced, - unsigned TDF, - bool PartialOrdering, - bool DeducedFromArrayBound) { +static Sema::TemplateDeductionResult DeduceTemplateArgumentsByTypeMatch( + Sema &S, TemplateParameterList *TemplateParams, QualType ParamIn, + QualType ArgIn, TemplateDeductionInfo &Info, + SmallVectorImpl<DeducedTemplateArgument> &Deduced, unsigned TDF, + bool PartialOrdering, bool DeducedFromArrayBound) { + // Because DeduceTemplateArgumentsByTypeMatchInner is recursive, and tends to + // modify Info.FirstArg and SecondArg even when deduction succeeds, save the + // original values and restore them if no error occurred. + const auto OriginalFirstArg = Info.FirstArg; + const auto OriginalSecondArg = Info.SecondArg; + + const auto Result = DeduceTemplateArgumentsByTypeMatchInner( + S, TemplateParams, ParamIn, ArgIn, Info, Deduced, TDF, PartialOrdering, + DeducedFromArrayBound); + + if (Result == Sema::TDK_Success) { + Info.FirstArg = OriginalFirstArg; + Info.SecondArg = OriginalSecondArg; + } + return Result; +} + +/// \see DeduceTemplateArgumentsByTypeMatch() +static Sema::TemplateDeductionResult DeduceTemplateArgumentsByTypeMatchInner( + Sema &S, TemplateParameterList *TemplateParams, QualType ParamIn, + QualType ArgIn, TemplateDeductionInfo &Info, + SmallVectorImpl<DeducedTemplateArgument> &Deduced, unsigned TDF, + bool PartialOrdering, bool DeducedFromArrayBound) { // We only want to look at the canonical types, since typedefs and // sugar are not part of template argument deduction. QualType Param = S.Context.getCanonicalType(ParamIn);
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits