ChuanqiXu updated this revision to Diff 417479. ChuanqiXu added a comment. Address comments.
CHANGES SINCE LAST ACTION https://reviews.llvm.org/D120397/new/ https://reviews.llvm.org/D120397 Files: clang/lib/AST/Decl.cpp clang/unittests/AST/DeclTest.cpp Index: clang/unittests/AST/DeclTest.cpp =================================================================== --- clang/unittests/AST/DeclTest.cpp +++ clang/unittests/AST/DeclTest.cpp @@ -171,3 +171,26 @@ selectFirst<FunctionDecl>("f", match(functionDecl().bind("f"), Ctx)); EXPECT_TRUE(f->isInExportDeclContext()); } + +TEST(Decl, InConsistLinkageForTemplates) { + llvm::Annotations Code(R"( + export module m; + export template <class T> + void f() {} + + template <> + void f<int>() {})"); + + auto AST = + tooling::buildASTFromCodeWithArgs(Code.code(), /*Args=*/{"-std=c++20"}); + ASTContext &Ctx = AST->getASTContext(); + + llvm::SmallVector<ast_matchers::BoundNodes, 2> Funcs = + match(functionDecl().bind("f"), Ctx); + + EXPECT_EQ(Funcs.size(), 2); + const FunctionDecl *TemplateF = Funcs[0].getNodeAs<FunctionDecl>("f"); + const FunctionDecl *SpecializedF = Funcs[1].getNodeAs<FunctionDecl>("f"); + EXPECT_EQ(TemplateF->getLinkageInternal(), + SpecializedF->getLinkageInternal()); +} Index: clang/lib/AST/Decl.cpp =================================================================== --- clang/lib/AST/Decl.cpp +++ clang/lib/AST/Decl.cpp @@ -391,11 +391,18 @@ bool considerVisibility = shouldConsiderTemplateVisibility(fn, specInfo); - // Merge information from the template parameters. FunctionTemplateDecl *temp = specInfo->getTemplate(); - LinkageInfo tempLV = - getLVForTemplateParameterList(temp->getTemplateParameters(), computation); - LV.mergeMaybeWithVisibility(tempLV, considerVisibility); + + // Merge information from the template declaration. + LinkageInfo tempLV = getLVForDecl(temp, computation); + // The linkage of the specialization should be consistent with the + // template declaration. + LV.setLinkage(tempLV.getLinkage()); + + // Merge information from the template parameters. + LinkageInfo paramsLV = + getLVForTemplateParameterList(temp->getTemplateParameters(), computation); + LV.mergeMaybeWithVisibility(paramsLV, considerVisibility); // Merge information from the template arguments. const TemplateArgumentList &templateArgs = *specInfo->TemplateArguments;
Index: clang/unittests/AST/DeclTest.cpp =================================================================== --- clang/unittests/AST/DeclTest.cpp +++ clang/unittests/AST/DeclTest.cpp @@ -171,3 +171,26 @@ selectFirst<FunctionDecl>("f", match(functionDecl().bind("f"), Ctx)); EXPECT_TRUE(f->isInExportDeclContext()); } + +TEST(Decl, InConsistLinkageForTemplates) { + llvm::Annotations Code(R"( + export module m; + export template <class T> + void f() {} + + template <> + void f<int>() {})"); + + auto AST = + tooling::buildASTFromCodeWithArgs(Code.code(), /*Args=*/{"-std=c++20"}); + ASTContext &Ctx = AST->getASTContext(); + + llvm::SmallVector<ast_matchers::BoundNodes, 2> Funcs = + match(functionDecl().bind("f"), Ctx); + + EXPECT_EQ(Funcs.size(), 2); + const FunctionDecl *TemplateF = Funcs[0].getNodeAs<FunctionDecl>("f"); + const FunctionDecl *SpecializedF = Funcs[1].getNodeAs<FunctionDecl>("f"); + EXPECT_EQ(TemplateF->getLinkageInternal(), + SpecializedF->getLinkageInternal()); +} Index: clang/lib/AST/Decl.cpp =================================================================== --- clang/lib/AST/Decl.cpp +++ clang/lib/AST/Decl.cpp @@ -391,11 +391,18 @@ bool considerVisibility = shouldConsiderTemplateVisibility(fn, specInfo); - // Merge information from the template parameters. FunctionTemplateDecl *temp = specInfo->getTemplate(); - LinkageInfo tempLV = - getLVForTemplateParameterList(temp->getTemplateParameters(), computation); - LV.mergeMaybeWithVisibility(tempLV, considerVisibility); + + // Merge information from the template declaration. + LinkageInfo tempLV = getLVForDecl(temp, computation); + // The linkage of the specialization should be consistent with the + // template declaration. + LV.setLinkage(tempLV.getLinkage()); + + // Merge information from the template parameters. + LinkageInfo paramsLV = + getLVForTemplateParameterList(temp->getTemplateParameters(), computation); + LV.mergeMaybeWithVisibility(paramsLV, considerVisibility); // Merge information from the template arguments. const TemplateArgumentList &templateArgs = *specInfo->TemplateArguments;
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits