diff options
Diffstat (limited to 'clang/lib/Sema')
-rw-r--r-- | clang/lib/Sema/SemaDeclCXX.cpp | 18 | ||||
-rw-r--r-- | clang/lib/Sema/SemaModule.cpp | 33 |
2 files changed, 42 insertions, 9 deletions
diff --git a/clang/lib/Sema/SemaDeclCXX.cpp b/clang/lib/Sema/SemaDeclCXX.cpp index 2658e96..558ee3f 100644 --- a/clang/lib/Sema/SemaDeclCXX.cpp +++ b/clang/lib/Sema/SemaDeclCXX.cpp @@ -16146,6 +16146,20 @@ Decl *Sema::ActOnStartLinkageSpecification(Scope *S, SourceLocation ExternLoc, LinkageSpecDecl *D = LinkageSpecDecl::Create(Context, CurContext, ExternLoc, LangStr->getExprLoc(), Language, LBraceLoc.isValid()); + + /// C++ [module.unit]p7.2.3 + /// - Otherwise, if the declaration + /// - ... + /// - ... + /// - appears within a linkage-specification, + /// it is attached to the global module. + if (getLangOpts().CPlusPlusModules) { + Module *GlobalModule = + PushGlobalModuleFragment(ExternLoc, /*IsImplicit=*/true); + D->setModuleOwnershipKind(Decl::ModuleOwnershipKind::ModulePrivate); + D->setLocalOwningModule(GlobalModule); + } + CurContext->addDecl(D); PushDeclContext(S, D); return D; @@ -16162,6 +16176,10 @@ Decl *Sema::ActOnFinishLinkageSpecification(Scope *S, LinkageSpecDecl* LSDecl = cast<LinkageSpecDecl>(LinkageSpec); LSDecl->setRBraceLoc(RBraceLoc); } + + if (getLangOpts().CPlusPlusModules) + PopGlobalModuleFragment(); + PopDeclContext(); return LinkageSpec; } diff --git a/clang/lib/Sema/SemaModule.cpp b/clang/lib/Sema/SemaModule.cpp index af95b1a..34a6c6e 100644 --- a/clang/lib/Sema/SemaModule.cpp +++ b/clang/lib/Sema/SemaModule.cpp @@ -68,15 +68,8 @@ Sema::ActOnGlobalModuleFragmentDecl(SourceLocation ModuleLoc) { // We start in the global module; all those declarations are implicitly // module-private (though they do not have module linkage). - auto &Map = PP.getHeaderSearchInfo().getModuleMap(); - auto *GlobalModule = Map.createGlobalModuleFragmentForModuleUnit(ModuleLoc); - assert(GlobalModule && "module creation should not fail"); - - // Enter the scope of the global module. - ModuleScopes.push_back({}); - ModuleScopes.back().BeginLoc = ModuleLoc; - ModuleScopes.back().Module = GlobalModule; - VisibleModules.setVisible(GlobalModule, ModuleLoc); + Module *GlobalModule = + PushGlobalModuleFragment(ModuleLoc, /*IsImplicit=*/false); // All declarations created from now on are owned by the global module. auto *TU = Context.getTranslationUnitDecl(); @@ -708,3 +701,25 @@ Decl *Sema::ActOnFinishExportDecl(Scope *S, Decl *D, SourceLocation RBraceLoc) { return D; } + +Module *Sema::PushGlobalModuleFragment(SourceLocation BeginLoc, + bool IsImplicit) { + ModuleMap &Map = PP.getHeaderSearchInfo().getModuleMap(); + Module *GlobalModule = + Map.createGlobalModuleFragmentForModuleUnit(BeginLoc, getCurrentModule()); + assert(GlobalModule && "module creation should not fail"); + + // Enter the scope of the global module. + ModuleScopes.push_back({BeginLoc, GlobalModule, + /*ModuleInterface=*/false, + /*ImplicitGlobalModuleFragment=*/IsImplicit}); + VisibleModules.setVisible(GlobalModule, BeginLoc); + + return GlobalModule; +} + +void Sema::PopGlobalModuleFragment() { + assert(!ModuleScopes.empty() && getCurrentModule()->isGlobalModule() && + "left the wrong module scope, which is not global module fragment"); + ModuleScopes.pop_back(); +} |