diff --git a/clang/lib/Sema/SemaTemplate.cpp b/clang/lib/Sema/SemaTemplate.cpp index 7ad313162701..88b24a1702c3 100644 --- a/clang/lib/Sema/SemaTemplate.cpp +++ b/clang/lib/Sema/SemaTemplate.cpp @@ -6341,14 +6341,22 @@ Sema::ActOnExplicitInstantiation(Scope *S, AttributeList *Attr) { // Find the class template we're specializing TemplateName Name = TemplateD.getAsVal(); - ClassTemplateDecl *ClassTemplate - = cast(Name.getAsTemplateDecl()); - + TemplateDecl *TD = Name.getAsTemplateDecl(); // Check that the specialization uses the same tag kind as the // original template. TagTypeKind Kind = TypeWithKeyword::getTagTypeKindForTypeSpec(TagSpec); assert(Kind != TTK_Enum && "Invalid enum tag in class template explicit instantiation!"); + + if (isa(TD)) { + Diag(KWLoc, diag::err_tag_reference_non_tag) << Kind; + Diag(TD->getTemplatedDecl()->getLocation(), + diag::note_previous_use); + return true; + } + + ClassTemplateDecl *ClassTemplate = cast(TD); + if (!isAcceptableTagRedeclaration(ClassTemplate->getTemplatedDecl(), Kind, /*isDefinition*/false, KWLoc, *ClassTemplate->getIdentifier())) { diff --git a/clang/test/SemaCXX/using-decl-templates.cpp b/clang/test/SemaCXX/using-decl-templates.cpp index 2fc679564255..8314688bcbc7 100644 --- a/clang/test/SemaCXX/using-decl-templates.cpp +++ b/clang/test/SemaCXX/using-decl-templates.cpp @@ -1,4 +1,4 @@ -// RUN: %clang_cc1 -fsyntax-only -verify %s +// RUN: %clang_cc1 -fsyntax-only -std=c++11 -verify %s template struct A { void f() { } @@ -85,3 +85,10 @@ template class UsingTypenameNNS { using typename T::X; typename X::X x; }; + +namespace aliastemplateinst { + template struct A { }; + template using APtr = A; // expected-note{{previous use is here}} + + template struct APtr; // expected-error{{elaborated type refers to a non-tag type}} +}