diff options
Diffstat (limited to 'lib/Sema/SemaTemplateInstantiateDecl.cpp')
-rw-r--r-- | lib/Sema/SemaTemplateInstantiateDecl.cpp | 43 |
1 files changed, 14 insertions, 29 deletions
diff --git a/lib/Sema/SemaTemplateInstantiateDecl.cpp b/lib/Sema/SemaTemplateInstantiateDecl.cpp index d929b5a370..cbd9086dfb 100644 --- a/lib/Sema/SemaTemplateInstantiateDecl.cpp +++ b/lib/Sema/SemaTemplateInstantiateDecl.cpp @@ -904,15 +904,8 @@ Decl *TemplateDeclInstantiator::VisitFunctionDecl(FunctionDecl *D, // Check whether there is already a function template specialization for // this declaration. FunctionTemplateDecl *FunctionTemplate = D->getDescribedFunctionTemplate(); - - bool isFriend; - if (FunctionTemplate) - isFriend = (FunctionTemplate->getFriendObjectKind() != Decl::FOK_None); - else - isFriend = (D->getFriendObjectKind() != Decl::FOK_None); - void *InsertPos = 0; - if (!isFriend && FunctionTemplate && !TemplateParams) { + if (FunctionTemplate && !TemplateParams) { llvm::FoldingSetNodeID ID; FunctionTemplateSpecializationInfo::Profile(ID, TemplateArgs.getInnermost().getFlatArgumentList(), @@ -940,29 +933,14 @@ Decl *TemplateDeclInstantiator::VisitFunctionDecl(FunctionDecl *D, return 0; QualType T = TInfo->getType(); - NestedNameSpecifier *Qualifier = D->getQualifier(); - if (Qualifier) { - Qualifier = SemaRef.SubstNestedNameSpecifier(Qualifier, - D->getQualifierRange(), - TemplateArgs); - if (!Qualifier) return 0; - } - // If we're instantiating a local function declaration, put the result // in the owner; otherwise we need to find the instantiated context. DeclContext *DC; if (D->getDeclContext()->isFunctionOrMethod()) DC = Owner; - else if (isFriend && Qualifier) { - CXXScopeSpec SS; - SS.setScopeRep(Qualifier); - SS.setRange(D->getQualifierRange()); - DC = SemaRef.computeDeclContext(SS); - if (!DC) return 0; - } else { + else DC = SemaRef.FindInstantiatedContext(D->getLocation(), D->getDeclContext(), TemplateArgs); - } FunctionDecl *Function = FunctionDecl::Create(SemaRef.Context, DC, D->getLocation(), @@ -970,8 +948,9 @@ Decl *TemplateDeclInstantiator::VisitFunctionDecl(FunctionDecl *D, D->getStorageClass(), D->isInlineSpecified(), D->hasWrittenPrototype()); - if (Qualifier) - Function->setQualifierInfo(Qualifier, D->getQualifierRange()); + // Substitute the nested name specifier, if any. + if (SubstQualifier(D, Function)) + return 0; Function->setLexicalDeclContext(Owner); @@ -995,7 +974,7 @@ Decl *TemplateDeclInstantiator::VisitFunctionDecl(FunctionDecl *D, // which means substituting int for T, but leaving "f" as a friend function // template. // Build the function template itself. - FunctionTemplate = FunctionTemplateDecl::Create(SemaRef.Context, DC, + FunctionTemplate = FunctionTemplateDecl::Create(SemaRef.Context, Owner, Function->getLocation(), Function->getDeclName(), TemplateParams, Function); @@ -1037,7 +1016,9 @@ Decl *TemplateDeclInstantiator::VisitFunctionDecl(FunctionDecl *D, // If the original function was part of a friend declaration, // inherit its namespace state and add it to the owner. - if (isFriend) { + NamedDecl *FromFriendD + = TemplateParams? cast<NamedDecl>(D->getDescribedFunctionTemplate()) : D; + if (FromFriendD->getFriendObjectKind()) { NamedDecl *ToFriendD = 0; NamedDecl *PrevDecl; if (TemplateParams) { @@ -1048,7 +1029,11 @@ Decl *TemplateDeclInstantiator::VisitFunctionDecl(FunctionDecl *D, PrevDecl = Function->getPreviousDeclaration(); } ToFriendD->setObjectOfFriendDecl(PrevDecl != NULL); - DC->makeDeclVisibleInContext(ToFriendD, /*Recoverable=*/ false); + if (!Owner->isDependentContext() && !PrevDecl) + DC->makeDeclVisibleInContext(ToFriendD, /* Recoverable = */ false); + + if (!TemplateParams) + Function->setInstantiationOfMemberFunction(D, TSK_ImplicitInstantiation); } return Function; |