@@ -3686,6 +3686,54 @@ static void inheritDefaultTemplateArguments(ASTContext &Context,
3686
3686
}
3687
3687
}
3688
3688
3689
+ // [basic.link]/p10:
3690
+ // If two declarations of an entity are attached to different modules,
3691
+ // the program is ill-formed;
3692
+ static void checkMultipleDefinitionInNamedModules (ASTReader &Reader, Decl *D,
3693
+ Decl *Previous) {
3694
+ Module *M = Previous->getOwningModule ();
3695
+
3696
+ // We only care about the case in named modules.
3697
+ if (!M || !M->isNamedModule ())
3698
+ return ;
3699
+
3700
+ // If it is previous implcitly introduced, it is not meaningful to
3701
+ // diagnose it.
3702
+ if (Previous->isImplicit ())
3703
+ return ;
3704
+
3705
+ // FIXME: Get rid of the enumeration of decl types once we have an appropriate
3706
+ // abstract for decls of an entity. e.g., the namespace decl and using decl
3707
+ // doesn't introduce an entity.
3708
+ if (!isa<VarDecl, FunctionDecl, TagDecl, RedeclarableTemplateDecl>(Previous))
3709
+ return ;
3710
+
3711
+ // Skip implicit instantiations since it may give false positive diagnostic
3712
+ // messages.
3713
+ // FIXME: Maybe this shows the implicit instantiations may have incorrect
3714
+ // module owner ships. But given we've finished the compilation of a module,
3715
+ // how can we add new entities to that module?
3716
+ if (auto *VTSD = dyn_cast<VarTemplateSpecializationDecl>(Previous);
3717
+ VTSD && !VTSD->isExplicitSpecialization ())
3718
+ return ;
3719
+ if (auto *CTSD = dyn_cast<ClassTemplateSpecializationDecl>(Previous);
3720
+ CTSD && !CTSD->isExplicitSpecialization ())
3721
+ return ;
3722
+ if (auto *Func = dyn_cast<FunctionDecl>(Previous))
3723
+ if (auto *FTSI = Func->getTemplateSpecializationInfo ();
3724
+ FTSI && !FTSI->isExplicitSpecialization ())
3725
+ return ;
3726
+
3727
+ // It is fine if they are in the same module.
3728
+ if (Reader.getContext ().isInSameModule (M, D->getOwningModule ()))
3729
+ return ;
3730
+
3731
+ Reader.Diag (Previous->getLocation (),
3732
+ diag::err_multiple_decl_in_different_modules)
3733
+ << cast<NamedDecl>(Previous) << M->Name ;
3734
+ Reader.Diag (D->getLocation (), diag::note_also_found);
3735
+ }
3736
+
3689
3737
void ASTDeclReader::attachPreviousDecl (ASTReader &Reader, Decl *D,
3690
3738
Decl *Previous, Decl *Canon) {
3691
3739
assert (D && Previous);
@@ -3699,22 +3747,7 @@ void ASTDeclReader::attachPreviousDecl(ASTReader &Reader, Decl *D,
3699
3747
#include " clang/AST/DeclNodes.inc"
3700
3748
}
3701
3749
3702
- // [basic.link]/p10:
3703
- // If two declarations of an entity are attached to different modules,
3704
- // the program is ill-formed;
3705
- //
3706
- // FIXME: Get rid of the enumeration of decl types once we have an appropriate
3707
- // abstract for decls of an entity. e.g., the namespace decl and using decl
3708
- // doesn't introduce an entity.
3709
- if (Module *M = Previous->getOwningModule ();
3710
- M && M->isNamedModule () &&
3711
- isa<VarDecl, FunctionDecl, TagDecl, RedeclarableTemplateDecl>(Previous) &&
3712
- !Reader.getContext ().isInSameModule (M, D->getOwningModule ())) {
3713
- Reader.Diag (Previous->getLocation (),
3714
- diag::err_multiple_decl_in_different_modules)
3715
- << cast<NamedDecl>(Previous) << M->Name ;
3716
- Reader.Diag (D->getLocation (), diag::note_also_found);
3717
- }
3750
+ checkMultipleDefinitionInNamedModules (Reader, D, Previous);
3718
3751
3719
3752
// If the declaration was visible in one module, a redeclaration of it in
3720
3753
// another module remains visible even if it wouldn't be visible by itself.
0 commit comments