]> granicus.if.org Git - clang/commitdiff
RP18408: If a member template is used as a template template argument, it does
authorRichard Smith <richard-llvm@metafoo.co.uk>
Wed, 8 Jan 2014 01:51:59 +0000 (01:51 +0000)
committerRichard Smith <richard-llvm@metafoo.co.uk>
Wed, 8 Jan 2014 01:51:59 +0000 (01:51 +0000)
not cause the template specialization to have no linkage.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@198726 91177308-0d34-0410-b5e6-96231b3b80d8

lib/AST/Decl.cpp
test/CodeGenCXX/linkage.cpp

index 29443960c47d8ee50efbab6f93676da8ceebc12d..4e69a9063690ecf66b964c7ee6483a4c3fa88df5 100644 (file)
@@ -782,11 +782,18 @@ static LinkageInfo getLVForClassMember(const NamedDecl *D,
   // really have linkage, but it's convenient to say they do for the
   // purposes of calculating linkage of pointer-to-data-member
   // template arguments.
+  //
+  // Templates also don't officially have linkage, but since we ignore
+  // the C++ standard and look at template arguments when determining
+  // linkage and visibility of a template specialization, we might hit
+  // a template template argument that way. If we do, we need to
+  // consider its linkage.
   if (!(isa<CXXMethodDecl>(D) ||
         isa<VarDecl>(D) ||
         isa<FieldDecl>(D) ||
         isa<IndirectFieldDecl>(D) ||
-        isa<TagDecl>(D)))
+        isa<TagDecl>(D) ||
+        isa<TemplateDecl>(D)))
     return LinkageInfo::none();
 
   LinkageInfo LV;
index 19f1b20773c002f0eddef744465d60b424f5d201..b858ecbfe473be3b1b361c562e650031a5d00e78 100644 (file)
@@ -220,3 +220,11 @@ namespace test17 {
   }
   template int *foo<42>();
 }
+
+// PR18408
+namespace test18 {
+  template<template<typename> class> struct A {};
+  struct B { template<typename> struct C; };
+  void f(A<B::C>) {}
+  // CHECK-DAG: define void @_ZN6test181fENS_1AINS_1B1CEEE(
+}