From: Eli Friedman Date: Tue, 8 Dec 2009 05:40:03 +0000 (+0000) Subject: Fix for PR5710: make sure to put function template specializations into the X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=6bc20135a2c46f97da15994095616a305be35c6a;p=clang Fix for PR5710: make sure to put function template specializations into the DeclContext, so they don't completely disappear from the AST. I don't particularly like this fix, but I don't see any obviously better way to deal with it, and I think it's pretty clearly an improvement; comments welcome. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@90835 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/AST/DeclBase.cpp b/lib/AST/DeclBase.cpp index f276faf1be..c557e615e7 100644 --- a/lib/AST/DeclBase.cpp +++ b/lib/AST/DeclBase.cpp @@ -741,6 +741,9 @@ void DeclContext::makeDeclVisibleInContext(NamedDecl *D, bool Recoverable) { // from being visible? if (isa(D)) return; + if (FunctionDecl *FD = dyn_cast(D)) + if (FD->isFunctionTemplateSpecialization()) + return; DeclContext *PrimaryContext = getPrimaryContext(); if (PrimaryContext != this) { diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp index bb3f869425..472dc94bc5 100644 --- a/lib/Sema/SemaDecl.cpp +++ b/lib/Sema/SemaDecl.cpp @@ -379,7 +379,9 @@ void Sema::PushOnScopeChains(NamedDecl *D, Scope *S, bool AddToContext) { // scope. if ((isa(D) && cast(D)->getTemplatedDecl()->isOutOfLine()) || - (isa(D) && cast(D)->isOutOfLine()) || + (isa(D) && + (cast(D)->isFunctionTemplateSpecialization() || + cast(D)->isOutOfLine())) || (isa(D) && cast(D)->isOutOfLine())) return; @@ -2023,9 +2025,7 @@ Sema::HandleDeclarator(Scope *S, Declarator &D, // If this has an identifier and is not an invalid redeclaration or // function template specialization, add it to the scope stack. - if (Name && !(Redeclaration && New->isInvalidDecl()) && - !(isa(New) && - cast(New)->isFunctionTemplateSpecialization())) + if (Name && !(Redeclaration && New->isInvalidDecl())) PushOnScopeChains(New, S); return DeclPtrTy::make(New); diff --git a/test/CodeGenCXX/function-template-explicit-specialization.cpp b/test/CodeGenCXX/function-template-explicit-specialization.cpp new file mode 100644 index 0000000000..046bc325a5 --- /dev/null +++ b/test/CodeGenCXX/function-template-explicit-specialization.cpp @@ -0,0 +1,13 @@ +// RUN: clang-cc -emit-llvm %s -o - | FileCheck %s + +template void a(T); +template<> void a(int) {} + +// CHECK: define void @_Z1aIiEvT_ + +namespace X { +template void b(T); +template<> void b(int) {} +} + +// CHECK: define void @_ZN1X1bIiEEvT_