When re-entering a template scope, we may be entering a class template
partial specialization rather than a subclass of TemplateDecl. Fixes a
crash in libstdc++ 4.2's <map>.


git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@81407 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp
index 8fd3a70..b3cef85 100644
--- a/lib/Sema/SemaDeclCXX.cpp
+++ b/lib/Sema/SemaDeclCXX.cpp
@@ -1858,11 +1858,19 @@
 }
 
 void Sema::ActOnReenterTemplateScope(Scope *S, DeclPtrTy TemplateD) {
-  TemplateDecl *Template = TemplateD.getAs<TemplateDecl>();
-  if (!Template)
+  Decl *D = TemplateD.getAs<Decl>();
+  if (!D)
+    return;
+  
+  TemplateParameterList *Params = 0;
+  if (TemplateDecl *Template = dyn_cast<TemplateDecl>(D))
+    Params = Template->getTemplateParameters();
+  else if (ClassTemplatePartialSpecializationDecl *PartialSpec
+           = dyn_cast<ClassTemplatePartialSpecializationDecl>(D))
+    Params = PartialSpec->getTemplateParameters();
+  else
     return;
 
-  TemplateParameterList *Params = Template->getTemplateParameters();
   for (TemplateParameterList::iterator Param = Params->begin(),
                                     ParamEnd = Params->end();
        Param != ParamEnd; ++Param) {
diff --git a/test/SemaTemplate/nested-template.cpp b/test/SemaTemplate/nested-template.cpp
index 896eb72..5ee2c99 100644
--- a/test/SemaTemplate/nested-template.cpp
+++ b/test/SemaTemplate/nested-template.cpp
@@ -91,3 +91,13 @@
 template<typename X>
 template<typename Y>
 Y Outer<X>::Inner1<Y*>::ReallyInner::value4; // expected-error{{Outer<X>::Inner1<Y *>::ReallyInner::}}
+
+
+template<typename T>
+struct X0 { };
+
+template<typename T>
+struct X0<T*> {
+  template<typename U>
+  void f(U u = T()) { }
+};