Author: Richard Smith Date: 2020-11-24T16:59:06-08:00 New Revision: 23dc04981be29b8398b7a409540646b58af76983
URL: https://github.com/llvm/llvm-project/commit/23dc04981be29b8398b7a409540646b58af76983 DIFF: https://github.com/llvm/llvm-project/commit/23dc04981be29b8398b7a409540646b58af76983.diff LOG: Treat a placeholder type for class template argument deduction as substitutable for the deduced template. As agreed in https://github.com/itanium-cxx-abi/cxx-abi/issues/109. Added: Modified: clang/lib/AST/ItaniumMangle.cpp clang/test/CodeGenCXX/cxx1z-class-deduction.cpp Removed: ################################################################################ diff --git a/clang/lib/AST/ItaniumMangle.cpp b/clang/lib/AST/ItaniumMangle.cpp index 172b94f26018..f5a4f6708c83 100644 --- a/clang/lib/AST/ItaniumMangle.cpp +++ b/clang/lib/AST/ItaniumMangle.cpp @@ -2507,6 +2507,12 @@ static bool isTypeSubstitutable(Qualifiers Quals, const Type *Ty, if (Ctx.getLangOpts().getClangABICompat() > LangOptions::ClangABI::Ver6 && isa<AutoType>(Ty)) return false; + // A placeholder type for class template deduction is substitutable with + // its corresponding template name; this is handled specially when mangling + // the type. + if (auto *DeducedTST = Ty->getAs<DeducedTemplateSpecializationType>()) + if (DeducedTST->getDeducedType().isNull()) + return false; return true; } @@ -3696,16 +3702,16 @@ void CXXNameMangler::mangleType(const AutoType *T) { void CXXNameMangler::mangleType(const DeducedTemplateSpecializationType *T) { QualType Deduced = T->getDeducedType(); if (!Deduced.isNull()) - mangleType(Deduced); - else if (TemplateDecl *TD = T->getTemplateName().getAsTemplateDecl()) - mangleName(GlobalDecl(TD)); - else { - // For an unresolved template-name, mangle it as if it were a template - // specialization but leave off the template arguments. - Out << 'N'; - mangleTemplatePrefix(T->getTemplateName()); - Out << 'E'; - } + return mangleType(Deduced); + + TemplateDecl *TD = T->getTemplateName().getAsTemplateDecl(); + assert(TD && "shouldn't form deduced TST unless we know we have a template"); + + if (mangleSubstitution(TD)) + return; + + mangleName(GlobalDecl(TD)); + addSubstitution(TD); } void CXXNameMangler::mangleType(const AtomicType *T) { diff --git a/clang/test/CodeGenCXX/cxx1z-class-deduction.cpp b/clang/test/CodeGenCXX/cxx1z-class-deduction.cpp index 8edab748338e..bf436e7ec980 100644 --- a/clang/test/CodeGenCXX/cxx1z-class-deduction.cpp +++ b/clang/test/CodeGenCXX/cxx1z-class-deduction.cpp @@ -29,9 +29,9 @@ struct X { template<typename T> struct C { C(T); }; }; -// CHECK: @_Z1gIiEDaT_DTcv1AfL0p_E1AIS0_E( +// CHECK: @_Z1gIiEDaT_DTcv1AfL0p_ES1_IS0_E template<typename T> auto g(T x, decltype(A(x)), A<T>) {} -// CHECK: @_Z1hIiEDaT_DTcvN1N1BEfL0p_ENS1_1BIS0_EE( +// CHECK: @_Z1hIiEDaT_DTcvN1N1BEfL0p_ENS2_IS0_EE template<typename T> auto h(T x, decltype(B(x)), B<T>) {} // CHECK: @_Z1iI1XiEDaT0_DTcvNT_1CEfL0p_ENS2_1CIS1_EE( template<typename U, typename T> auto i(T x, decltype(typename U::C(x)), typename U::template C<T>) {} _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits