13a02247dSChandler Carruth //===--- Module.cpp - Describe a module -----------------------------------===//
2de3ef502SDouglas Gregor //
3de3ef502SDouglas Gregor //                     The LLVM Compiler Infrastructure
4de3ef502SDouglas Gregor //
5de3ef502SDouglas Gregor // This file is distributed under the University of Illinois Open Source
6de3ef502SDouglas Gregor // License. See LICENSE.TXT for details.
7de3ef502SDouglas Gregor //
8de3ef502SDouglas Gregor //===----------------------------------------------------------------------===//
9de3ef502SDouglas Gregor //
10de3ef502SDouglas Gregor // This file defines the Module class, which describes a module in the source
11de3ef502SDouglas Gregor // code.
12de3ef502SDouglas Gregor //
13de3ef502SDouglas Gregor //===----------------------------------------------------------------------===//
14a3feee2aSRichard Smith 
15de3ef502SDouglas Gregor #include "clang/Basic/Module.h"
16de3ef502SDouglas Gregor #include "clang/Basic/FileManager.h"
171fb5c3a6SDouglas Gregor #include "clang/Basic/LangOptions.h"
180070c0bfSDouglas Gregor #include "clang/Basic/TargetInfo.h"
193c5305c1SArgyrios Kyrtzidis #include "llvm/ADT/ArrayRef.h"
201fb5c3a6SDouglas Gregor #include "llvm/ADT/SmallVector.h"
211fb5c3a6SDouglas Gregor #include "llvm/ADT/StringSwitch.h"
223a02247dSChandler Carruth #include "llvm/Support/ErrorHandling.h"
233a02247dSChandler Carruth #include "llvm/Support/raw_ostream.h"
24a3feee2aSRichard Smith 
25de3ef502SDouglas Gregor using namespace clang;
26de3ef502SDouglas Gregor 
27eb90e830SDouglas Gregor Module::Module(StringRef Name, SourceLocation DefinitionLoc, Module *Parent,
28a7e2cc68SRichard Smith                bool IsFramework, bool IsExplicit, unsigned VisibilityID)
293c1a41adSRichard Smith     : Name(Name), DefinitionLoc(DefinitionLoc), Parent(Parent), Directory(),
3015bcf70cSAdrian Prantl       Umbrella(), Signature(0), ASTFile(nullptr), VisibilityID(VisibilityID),
318a308ec2SRichard Smith       IsMissingRequirement(false), HasIncompatibleModuleFile(false),
328a308ec2SRichard Smith       IsAvailable(true), IsFromModuleFile(false), IsFramework(IsFramework),
338a308ec2SRichard Smith       IsExplicit(IsExplicit), IsSystem(false), IsExternC(false),
348a308ec2SRichard Smith       IsInferred(false), InferSubmodules(false), InferExplicitSubmodules(false),
358a308ec2SRichard Smith       InferExportWildcard(false), ConfigMacrosExhaustive(false),
36*ed84df00SBruno Cardoso Lopes       NoUndeclaredIncludes(false), NameVisibility(Hidden) {
37eb90e830SDouglas Gregor   if (Parent) {
38eb90e830SDouglas Gregor     if (!Parent->isAvailable())
39eb90e830SDouglas Gregor       IsAvailable = false;
403ec6663bSDouglas Gregor     if (Parent->IsSystem)
413ec6663bSDouglas Gregor       IsSystem = true;
429bca298fSRichard Smith     if (Parent->IsExternC)
439bca298fSRichard Smith       IsExternC = true;
44*ed84df00SBruno Cardoso Lopes     if (Parent->NoUndeclaredIncludes)
45*ed84df00SBruno Cardoso Lopes       NoUndeclaredIncludes = true;
46993055f8SBen Langmuir     IsMissingRequirement = Parent->IsMissingRequirement;
47eb90e830SDouglas Gregor 
48eb90e830SDouglas Gregor     Parent->SubModuleIndex[Name] = Parent->SubModules.size();
49eb90e830SDouglas Gregor     Parent->SubModules.push_back(this);
50eb90e830SDouglas Gregor   }
51eb90e830SDouglas Gregor }
52eb90e830SDouglas Gregor 
53de3ef502SDouglas Gregor Module::~Module() {
54eb90e830SDouglas Gregor   for (submodule_iterator I = submodule_begin(), IEnd = submodule_end();
55de3ef502SDouglas Gregor        I != IEnd; ++I) {
56eb90e830SDouglas Gregor     delete *I;
57de3ef502SDouglas Gregor   }
58de3ef502SDouglas Gregor }
59de3ef502SDouglas Gregor 
601fb5c3a6SDouglas Gregor /// \brief Determine whether a translation unit built using the current
611fb5c3a6SDouglas Gregor /// language options has the given feature.
6289929282SDouglas Gregor static bool hasFeature(StringRef Feature, const LangOptions &LangOpts,
6389929282SDouglas Gregor                        const TargetInfo &Target) {
64532d2104SBen Langmuir   bool HasFeature = llvm::StringSwitch<bool>(Feature)
650070c0bfSDouglas Gregor                         .Case("altivec", LangOpts.AltiVec)
661fb5c3a6SDouglas Gregor                         .Case("blocks", LangOpts.Blocks)
671fb5c3a6SDouglas Gregor                         .Case("cplusplus", LangOpts.CPlusPlus)
682bf7fdb7SRichard Smith                         .Case("cplusplus11", LangOpts.CPlusPlus11)
69fb6358d2SElad Cohen                         .Case("freestanding", LangOpts.Freestanding)
706736e199SBruno Cardoso Lopes                         .Case("gnuinlineasm", LangOpts.GNUAsm)
711fb5c3a6SDouglas Gregor                         .Case("objc", LangOpts.ObjC1)
721fb5c3a6SDouglas Gregor                         .Case("objc_arc", LangOpts.ObjCAutoRefCount)
730070c0bfSDouglas Gregor                         .Case("opencl", LangOpts.OpenCL)
740070c0bfSDouglas Gregor                         .Case("tls", Target.isTLSSupported())
753c5038a5SUlrich Weigand                         .Case("zvector", LangOpts.ZVector)
760070c0bfSDouglas Gregor                         .Default(Target.hasFeature(Feature));
77532d2104SBen Langmuir   if (!HasFeature)
78532d2104SBen Langmuir     HasFeature = std::find(LangOpts.ModuleFeatures.begin(),
79532d2104SBen Langmuir                            LangOpts.ModuleFeatures.end(),
80532d2104SBen Langmuir                            Feature) != LangOpts.ModuleFeatures.end();
81532d2104SBen Langmuir   return HasFeature;
821fb5c3a6SDouglas Gregor }
831fb5c3a6SDouglas Gregor 
843c1a41adSRichard Smith bool Module::isAvailable(const LangOptions &LangOpts, const TargetInfo &Target,
853c1a41adSRichard Smith                          Requirement &Req,
863c1a41adSRichard Smith                          UnresolvedHeaderDirective &MissingHeader) const {
871fb5c3a6SDouglas Gregor   if (IsAvailable)
881fb5c3a6SDouglas Gregor     return true;
891fb5c3a6SDouglas Gregor 
901fb5c3a6SDouglas Gregor   for (const Module *Current = this; Current; Current = Current->Parent) {
91a3feee2aSRichard Smith     for (unsigned I = 0, N = Current->Requirements.size(); I != N; ++I) {
92a3feee2aSRichard Smith       if (hasFeature(Current->Requirements[I].first, LangOpts, Target) !=
93a3feee2aSRichard Smith               Current->Requirements[I].second) {
94a3feee2aSRichard Smith         Req = Current->Requirements[I];
951fb5c3a6SDouglas Gregor         return false;
961fb5c3a6SDouglas Gregor       }
971fb5c3a6SDouglas Gregor     }
9875a7e435SBen Langmuir     if (!Current->MissingHeaders.empty()) {
9975a7e435SBen Langmuir       MissingHeader = Current->MissingHeaders.front();
10075a7e435SBen Langmuir       return false;
10175a7e435SBen Langmuir     }
1021fb5c3a6SDouglas Gregor   }
1031fb5c3a6SDouglas Gregor 
1041fb5c3a6SDouglas Gregor   llvm_unreachable("could not find a reason why module is unavailable");
1051fb5c3a6SDouglas Gregor }
1061fb5c3a6SDouglas Gregor 
10762bcd925SDmitri Gribenko bool Module::isSubModuleOf(const Module *Other) const {
108f5eedd05SDouglas Gregor   const Module *This = this;
109f5eedd05SDouglas Gregor   do {
110f5eedd05SDouglas Gregor     if (This == Other)
111f5eedd05SDouglas Gregor       return true;
112f5eedd05SDouglas Gregor 
113f5eedd05SDouglas Gregor     This = This->Parent;
114f5eedd05SDouglas Gregor   } while (This);
115f5eedd05SDouglas Gregor 
116f5eedd05SDouglas Gregor   return false;
117f5eedd05SDouglas Gregor }
118f5eedd05SDouglas Gregor 
11973441091SDouglas Gregor const Module *Module::getTopLevelModule() const {
12073441091SDouglas Gregor   const Module *Result = this;
12173441091SDouglas Gregor   while (Result->Parent)
12273441091SDouglas Gregor     Result = Result->Parent;
12373441091SDouglas Gregor 
12473441091SDouglas Gregor   return Result;
12573441091SDouglas Gregor }
12673441091SDouglas Gregor 
127de3ef502SDouglas Gregor std::string Module::getFullModuleName() const {
128f857950dSDmitri Gribenko   SmallVector<StringRef, 2> Names;
129de3ef502SDouglas Gregor 
130de3ef502SDouglas Gregor   // Build up the set of module names (from innermost to outermost).
131de3ef502SDouglas Gregor   for (const Module *M = this; M; M = M->Parent)
132de3ef502SDouglas Gregor     Names.push_back(M->Name);
133de3ef502SDouglas Gregor 
134de3ef502SDouglas Gregor   std::string Result;
13561ac906bSCraig Topper   for (SmallVectorImpl<StringRef>::reverse_iterator I = Names.rbegin(),
136de3ef502SDouglas Gregor                                                  IEnd = Names.rend();
137de3ef502SDouglas Gregor        I != IEnd; ++I) {
138de3ef502SDouglas Gregor     if (!Result.empty())
139de3ef502SDouglas Gregor       Result += '.';
140de3ef502SDouglas Gregor 
141de3ef502SDouglas Gregor     Result += *I;
142de3ef502SDouglas Gregor   }
143de3ef502SDouglas Gregor 
144de3ef502SDouglas Gregor   return Result;
145de3ef502SDouglas Gregor }
146de3ef502SDouglas Gregor 
1477ff29148SBen Langmuir bool Module::fullModuleNameIs(ArrayRef<StringRef> nameParts) const {
1487ff29148SBen Langmuir   for (const Module *M = this; M; M = M->Parent) {
1497ff29148SBen Langmuir     if (nameParts.empty() || M->Name != nameParts.back())
1507ff29148SBen Langmuir       return false;
1517ff29148SBen Langmuir     nameParts = nameParts.drop_back();
1527ff29148SBen Langmuir   }
1537ff29148SBen Langmuir   return nameParts.empty();
1547ff29148SBen Langmuir }
1557ff29148SBen Langmuir 
1562b63d15fSRichard Smith Module::DirectoryName Module::getUmbrellaDir() const {
1572b63d15fSRichard Smith   if (Header U = getUmbrellaHeader())
1582b63d15fSRichard Smith     return {"", U.Entry->getDir()};
15973141fa9SDouglas Gregor 
1602b63d15fSRichard Smith   return {UmbrellaAsWritten, Umbrella.dyn_cast<const DirectoryEntry *>()};
16173141fa9SDouglas Gregor }
16273141fa9SDouglas Gregor 
1633c5305c1SArgyrios Kyrtzidis ArrayRef<const FileEntry *> Module::getTopHeaders(FileManager &FileMgr) {
1643c5305c1SArgyrios Kyrtzidis   if (!TopHeaderNames.empty()) {
1653c5305c1SArgyrios Kyrtzidis     for (std::vector<std::string>::iterator
1663c5305c1SArgyrios Kyrtzidis            I = TopHeaderNames.begin(), E = TopHeaderNames.end(); I != E; ++I) {
1673c5305c1SArgyrios Kyrtzidis       if (const FileEntry *FE = FileMgr.getFile(*I))
1683c5305c1SArgyrios Kyrtzidis         TopHeaders.insert(FE);
1693c5305c1SArgyrios Kyrtzidis     }
1703c5305c1SArgyrios Kyrtzidis     TopHeaderNames.clear();
1713c5305c1SArgyrios Kyrtzidis   }
1723c5305c1SArgyrios Kyrtzidis 
1733c5305c1SArgyrios Kyrtzidis   return llvm::makeArrayRef(TopHeaders.begin(), TopHeaders.end());
1743c5305c1SArgyrios Kyrtzidis }
1753c5305c1SArgyrios Kyrtzidis 
1768f4d3ff1SRichard Smith bool Module::directlyUses(const Module *Requested) const {
1778f4d3ff1SRichard Smith   auto *Top = getTopLevelModule();
1788f4d3ff1SRichard Smith 
1798f4d3ff1SRichard Smith   // A top-level module implicitly uses itself.
1808f4d3ff1SRichard Smith   if (Requested->isSubModuleOf(Top))
1818f4d3ff1SRichard Smith     return true;
1828f4d3ff1SRichard Smith 
1838f4d3ff1SRichard Smith   for (auto *Use : Top->DirectUses)
1848f4d3ff1SRichard Smith     if (Requested->isSubModuleOf(Use))
1858f4d3ff1SRichard Smith       return true;
186*ed84df00SBruno Cardoso Lopes 
187*ed84df00SBruno Cardoso Lopes   // Anyone is allowed to use our builtin stddef.h and its accompanying module.
188*ed84df00SBruno Cardoso Lopes   if (!Requested->Parent && Requested->Name == "_Builtin_stddef_max_align_t")
189*ed84df00SBruno Cardoso Lopes     return true;
190*ed84df00SBruno Cardoso Lopes 
1918f4d3ff1SRichard Smith   return false;
1928f4d3ff1SRichard Smith }
1938f4d3ff1SRichard Smith 
194a3feee2aSRichard Smith void Module::addRequirement(StringRef Feature, bool RequiredState,
195a3feee2aSRichard Smith                             const LangOptions &LangOpts,
19689929282SDouglas Gregor                             const TargetInfo &Target) {
197a3feee2aSRichard Smith   Requirements.push_back(Requirement(Feature, RequiredState));
1981fb5c3a6SDouglas Gregor 
1991fb5c3a6SDouglas Gregor   // If this feature is currently available, we're done.
200a3feee2aSRichard Smith   if (hasFeature(Feature, LangOpts, Target) == RequiredState)
2011fb5c3a6SDouglas Gregor     return;
2021fb5c3a6SDouglas Gregor 
203993055f8SBen Langmuir   markUnavailable(/*MissingRequirement*/true);
204ec8c9752SBen Langmuir }
205ec8c9752SBen Langmuir 
206993055f8SBen Langmuir void Module::markUnavailable(bool MissingRequirement) {
20775a7e435SBen Langmuir   auto needUpdate = [MissingRequirement](Module *M) {
20875a7e435SBen Langmuir     return M->IsAvailable || (!M->IsMissingRequirement && MissingRequirement);
20975a7e435SBen Langmuir   };
21075a7e435SBen Langmuir 
21175a7e435SBen Langmuir   if (!needUpdate(this))
2121fb5c3a6SDouglas Gregor     return;
2131fb5c3a6SDouglas Gregor 
214f857950dSDmitri Gribenko   SmallVector<Module *, 2> Stack;
2151fb5c3a6SDouglas Gregor   Stack.push_back(this);
2161fb5c3a6SDouglas Gregor   while (!Stack.empty()) {
2171fb5c3a6SDouglas Gregor     Module *Current = Stack.back();
2181fb5c3a6SDouglas Gregor     Stack.pop_back();
2191fb5c3a6SDouglas Gregor 
22075a7e435SBen Langmuir     if (!needUpdate(Current))
2211fb5c3a6SDouglas Gregor       continue;
2221fb5c3a6SDouglas Gregor 
2231fb5c3a6SDouglas Gregor     Current->IsAvailable = false;
224993055f8SBen Langmuir     Current->IsMissingRequirement |= MissingRequirement;
225eb90e830SDouglas Gregor     for (submodule_iterator Sub = Current->submodule_begin(),
226eb90e830SDouglas Gregor                          SubEnd = Current->submodule_end();
2271fb5c3a6SDouglas Gregor          Sub != SubEnd; ++Sub) {
22875a7e435SBen Langmuir       if (needUpdate(*Sub))
229eb90e830SDouglas Gregor         Stack.push_back(*Sub);
2301fb5c3a6SDouglas Gregor     }
2311fb5c3a6SDouglas Gregor   }
2321fb5c3a6SDouglas Gregor }
2331fb5c3a6SDouglas Gregor 
234eb90e830SDouglas Gregor Module *Module::findSubmodule(StringRef Name) const {
235eb90e830SDouglas Gregor   llvm::StringMap<unsigned>::const_iterator Pos = SubModuleIndex.find(Name);
236eb90e830SDouglas Gregor   if (Pos == SubModuleIndex.end())
237f1186c5aSCraig Topper     return nullptr;
238eb90e830SDouglas Gregor 
239eb90e830SDouglas Gregor   return SubModules[Pos->getValue()];
240eb90e830SDouglas Gregor }
241eb90e830SDouglas Gregor 
242f857950dSDmitri Gribenko static void printModuleId(raw_ostream &OS, const ModuleId &Id) {
24324bb923aSDouglas Gregor   for (unsigned I = 0, N = Id.size(); I != N; ++I) {
24424bb923aSDouglas Gregor     if (I)
24524bb923aSDouglas Gregor       OS << ".";
24624bb923aSDouglas Gregor     OS << Id[I].first;
24724bb923aSDouglas Gregor   }
24824bb923aSDouglas Gregor }
24924bb923aSDouglas Gregor 
2508739f7b7SArgyrios Kyrtzidis void Module::getExportedModules(SmallVectorImpl<Module *> &Exported) const {
251e9bcf5b7SDmitri Gribenko   // All non-explicit submodules are exported.
252e9bcf5b7SDmitri Gribenko   for (std::vector<Module *>::const_iterator I = SubModules.begin(),
253e9bcf5b7SDmitri Gribenko                                              E = SubModules.end();
254e9bcf5b7SDmitri Gribenko        I != E; ++I) {
255e9bcf5b7SDmitri Gribenko     Module *Mod = *I;
256e9bcf5b7SDmitri Gribenko     if (!Mod->IsExplicit)
257e9bcf5b7SDmitri Gribenko       Exported.push_back(Mod);
258e9bcf5b7SDmitri Gribenko   }
259e9bcf5b7SDmitri Gribenko 
260e9bcf5b7SDmitri Gribenko   // Find re-exported modules by filtering the list of imported modules.
2618739f7b7SArgyrios Kyrtzidis   bool AnyWildcard = false;
2628739f7b7SArgyrios Kyrtzidis   bool UnrestrictedWildcard = false;
2638739f7b7SArgyrios Kyrtzidis   SmallVector<Module *, 4> WildcardRestrictions;
2648739f7b7SArgyrios Kyrtzidis   for (unsigned I = 0, N = Exports.size(); I != N; ++I) {
2658739f7b7SArgyrios Kyrtzidis     Module *Mod = Exports[I].getPointer();
2668739f7b7SArgyrios Kyrtzidis     if (!Exports[I].getInt()) {
2678739f7b7SArgyrios Kyrtzidis       // Export a named module directly; no wildcards involved.
2688739f7b7SArgyrios Kyrtzidis       Exported.push_back(Mod);
2698739f7b7SArgyrios Kyrtzidis 
2708739f7b7SArgyrios Kyrtzidis       continue;
2718739f7b7SArgyrios Kyrtzidis     }
2728739f7b7SArgyrios Kyrtzidis 
2738739f7b7SArgyrios Kyrtzidis     // Wildcard export: export all of the imported modules that match
2748739f7b7SArgyrios Kyrtzidis     // the given pattern.
2758739f7b7SArgyrios Kyrtzidis     AnyWildcard = true;
2768739f7b7SArgyrios Kyrtzidis     if (UnrestrictedWildcard)
2778739f7b7SArgyrios Kyrtzidis       continue;
2788739f7b7SArgyrios Kyrtzidis 
2798739f7b7SArgyrios Kyrtzidis     if (Module *Restriction = Exports[I].getPointer())
2808739f7b7SArgyrios Kyrtzidis       WildcardRestrictions.push_back(Restriction);
2818739f7b7SArgyrios Kyrtzidis     else {
2828739f7b7SArgyrios Kyrtzidis       WildcardRestrictions.clear();
2838739f7b7SArgyrios Kyrtzidis       UnrestrictedWildcard = true;
2848739f7b7SArgyrios Kyrtzidis     }
2858739f7b7SArgyrios Kyrtzidis   }
2868739f7b7SArgyrios Kyrtzidis 
2878739f7b7SArgyrios Kyrtzidis   // If there were any wildcards, push any imported modules that were
2888739f7b7SArgyrios Kyrtzidis   // re-exported by the wildcard restriction.
2898739f7b7SArgyrios Kyrtzidis   if (!AnyWildcard)
2908739f7b7SArgyrios Kyrtzidis     return;
2918739f7b7SArgyrios Kyrtzidis 
2928739f7b7SArgyrios Kyrtzidis   for (unsigned I = 0, N = Imports.size(); I != N; ++I) {
2938739f7b7SArgyrios Kyrtzidis     Module *Mod = Imports[I];
2948739f7b7SArgyrios Kyrtzidis     bool Acceptable = UnrestrictedWildcard;
2958739f7b7SArgyrios Kyrtzidis     if (!Acceptable) {
2968739f7b7SArgyrios Kyrtzidis       // Check whether this module meets one of the restrictions.
2978739f7b7SArgyrios Kyrtzidis       for (unsigned R = 0, NR = WildcardRestrictions.size(); R != NR; ++R) {
2988739f7b7SArgyrios Kyrtzidis         Module *Restriction = WildcardRestrictions[R];
2998739f7b7SArgyrios Kyrtzidis         if (Mod == Restriction || Mod->isSubModuleOf(Restriction)) {
3008739f7b7SArgyrios Kyrtzidis           Acceptable = true;
3018739f7b7SArgyrios Kyrtzidis           break;
3028739f7b7SArgyrios Kyrtzidis         }
3038739f7b7SArgyrios Kyrtzidis       }
3048739f7b7SArgyrios Kyrtzidis     }
3058739f7b7SArgyrios Kyrtzidis 
3068739f7b7SArgyrios Kyrtzidis     if (!Acceptable)
3078739f7b7SArgyrios Kyrtzidis       continue;
3088739f7b7SArgyrios Kyrtzidis 
3098739f7b7SArgyrios Kyrtzidis     Exported.push_back(Mod);
3108739f7b7SArgyrios Kyrtzidis   }
3118739f7b7SArgyrios Kyrtzidis }
3128739f7b7SArgyrios Kyrtzidis 
3130e5d7b8cSRichard Smith void Module::buildVisibleModulesCache() const {
3140e5d7b8cSRichard Smith   assert(VisibleModulesCache.empty() && "cache does not need building");
3150e5d7b8cSRichard Smith 
3160e5d7b8cSRichard Smith   // This module is visible to itself.
3170e5d7b8cSRichard Smith   VisibleModulesCache.insert(this);
3180e5d7b8cSRichard Smith 
3190e5d7b8cSRichard Smith   // Every imported module is visible.
320dde17e74SRichard Smith   SmallVector<Module *, 16> Stack(Imports.begin(), Imports.end());
321dc360d57SDmitri Gribenko   while (!Stack.empty()) {
322dc360d57SDmitri Gribenko     Module *CurrModule = Stack.pop_back_val();
323dc360d57SDmitri Gribenko 
324dde17e74SRichard Smith     // Every module transitively exported by an imported module is visible.
325dde17e74SRichard Smith     if (VisibleModulesCache.insert(CurrModule).second)
326dde17e74SRichard Smith       CurrModule->getExportedModules(Stack);
3270e5d7b8cSRichard Smith   }
3280e5d7b8cSRichard Smith }
3290e5d7b8cSRichard Smith 
330f857950dSDmitri Gribenko void Module::print(raw_ostream &OS, unsigned Indent) const {
331de3ef502SDouglas Gregor   OS.indent(Indent);
332de3ef502SDouglas Gregor   if (IsFramework)
333de3ef502SDouglas Gregor     OS << "framework ";
334de3ef502SDouglas Gregor   if (IsExplicit)
335de3ef502SDouglas Gregor     OS << "explicit ";
336a686e1b0SDouglas Gregor   OS << "module " << Name;
337a686e1b0SDouglas Gregor 
3387615f00eSBen Langmuir   if (IsSystem || IsExternC) {
339a686e1b0SDouglas Gregor     OS.indent(Indent + 2);
3407615f00eSBen Langmuir     if (IsSystem)
341a686e1b0SDouglas Gregor       OS << " [system]";
3427615f00eSBen Langmuir     if (IsExternC)
3437615f00eSBen Langmuir       OS << " [extern_c]";
344a686e1b0SDouglas Gregor   }
345a686e1b0SDouglas Gregor 
346a686e1b0SDouglas Gregor   OS << " {\n";
347de3ef502SDouglas Gregor 
348a3feee2aSRichard Smith   if (!Requirements.empty()) {
3491fb5c3a6SDouglas Gregor     OS.indent(Indent + 2);
3501fb5c3a6SDouglas Gregor     OS << "requires ";
351a3feee2aSRichard Smith     for (unsigned I = 0, N = Requirements.size(); I != N; ++I) {
3521fb5c3a6SDouglas Gregor       if (I)
3531fb5c3a6SDouglas Gregor         OS << ", ";
354a3feee2aSRichard Smith       if (!Requirements[I].second)
355a3feee2aSRichard Smith         OS << "!";
356a3feee2aSRichard Smith       OS << Requirements[I].first;
3571fb5c3a6SDouglas Gregor     }
3581fb5c3a6SDouglas Gregor     OS << "\n";
3591fb5c3a6SDouglas Gregor   }
3601fb5c3a6SDouglas Gregor 
3612b63d15fSRichard Smith   if (Header H = getUmbrellaHeader()) {
362de3ef502SDouglas Gregor     OS.indent(Indent + 2);
363322f633cSDouglas Gregor     OS << "umbrella header \"";
3642b63d15fSRichard Smith     OS.write_escaped(H.NameAsWritten);
365de3ef502SDouglas Gregor     OS << "\"\n";
3662b63d15fSRichard Smith   } else if (DirectoryName D = getUmbrellaDir()) {
367322f633cSDouglas Gregor     OS.indent(Indent + 2);
368322f633cSDouglas Gregor     OS << "umbrella \"";
3692b63d15fSRichard Smith     OS.write_escaped(D.NameAsWritten);
370322f633cSDouglas Gregor     OS << "\"\n";
371de3ef502SDouglas Gregor   }
372de3ef502SDouglas Gregor 
37335b13eceSDouglas Gregor   if (!ConfigMacros.empty() || ConfigMacrosExhaustive) {
37435b13eceSDouglas Gregor     OS.indent(Indent + 2);
37535b13eceSDouglas Gregor     OS << "config_macros ";
37635b13eceSDouglas Gregor     if (ConfigMacrosExhaustive)
3778d932427SDouglas Gregor       OS << "[exhaustive]";
37835b13eceSDouglas Gregor     for (unsigned I = 0, N = ConfigMacros.size(); I != N; ++I) {
37935b13eceSDouglas Gregor       if (I)
38035b13eceSDouglas Gregor         OS << ", ";
38135b13eceSDouglas Gregor       OS << ConfigMacros[I];
38235b13eceSDouglas Gregor     }
3838d932427SDouglas Gregor     OS << "\n";
38435b13eceSDouglas Gregor   }
38535b13eceSDouglas Gregor 
3863c1a41adSRichard Smith   struct {
387306d8920SRichard Smith     StringRef Prefix;
3883c1a41adSRichard Smith     HeaderKind Kind;
3893c1a41adSRichard Smith   } Kinds[] = {{"", HK_Normal},
3903c1a41adSRichard Smith                {"textual ", HK_Textual},
3913c1a41adSRichard Smith                {"private ", HK_Private},
3923c1a41adSRichard Smith                {"private textual ", HK_PrivateTextual},
3933c1a41adSRichard Smith                {"exclude ", HK_Excluded}};
394306d8920SRichard Smith 
395306d8920SRichard Smith   for (auto &K : Kinds) {
3963c1a41adSRichard Smith     for (auto &H : Headers[K.Kind]) {
397de3ef502SDouglas Gregor       OS.indent(Indent + 2);
398306d8920SRichard Smith       OS << K.Prefix << "header \"";
3993c1a41adSRichard Smith       OS.write_escaped(H.NameAsWritten);
400de3ef502SDouglas Gregor       OS << "\"\n";
401de3ef502SDouglas Gregor     }
402b53e5483SLawrence Crowl   }
403b53e5483SLawrence Crowl 
404eb90e830SDouglas Gregor   for (submodule_const_iterator MI = submodule_begin(), MIEnd = submodule_end();
405de3ef502SDouglas Gregor        MI != MIEnd; ++MI)
4069d6448b1SBen Langmuir     // Print inferred subframework modules so that we don't need to re-infer
4079d6448b1SBen Langmuir     // them (requires expensive directory iteration + stat calls) when we build
4089d6448b1SBen Langmuir     // the module. Regular inferred submodules are OK, as we need to look at all
4099d6448b1SBen Langmuir     // those header files anyway.
4109d6448b1SBen Langmuir     if (!(*MI)->IsInferred || (*MI)->IsFramework)
411eb90e830SDouglas Gregor       (*MI)->print(OS, Indent + 2);
412de3ef502SDouglas Gregor 
41324bb923aSDouglas Gregor   for (unsigned I = 0, N = Exports.size(); I != N; ++I) {
41424bb923aSDouglas Gregor     OS.indent(Indent + 2);
4158c7c8352SDouglas Gregor     OS << "export ";
4168c7c8352SDouglas Gregor     if (Module *Restriction = Exports[I].getPointer()) {
4178c7c8352SDouglas Gregor       OS << Restriction->getFullModuleName();
41824bb923aSDouglas Gregor       if (Exports[I].getInt())
41924bb923aSDouglas Gregor         OS << ".*";
4208c7c8352SDouglas Gregor     } else {
4218c7c8352SDouglas Gregor       OS << "*";
4228c7c8352SDouglas Gregor     }
42324bb923aSDouglas Gregor     OS << "\n";
42424bb923aSDouglas Gregor   }
42524bb923aSDouglas Gregor 
42624bb923aSDouglas Gregor   for (unsigned I = 0, N = UnresolvedExports.size(); I != N; ++I) {
42724bb923aSDouglas Gregor     OS.indent(Indent + 2);
42824bb923aSDouglas Gregor     OS << "export ";
42924bb923aSDouglas Gregor     printModuleId(OS, UnresolvedExports[I].Id);
4307f96b391SDavide Italiano     if (UnresolvedExports[I].Wildcard)
4317f96b391SDavide Italiano       OS << (UnresolvedExports[I].Id.empty() ? "*" : ".*");
43224bb923aSDouglas Gregor     OS << "\n";
43324bb923aSDouglas Gregor   }
43424bb923aSDouglas Gregor 
435ba7f2f71SDaniel Jasper   for (unsigned I = 0, N = DirectUses.size(); I != N; ++I) {
436ba7f2f71SDaniel Jasper     OS.indent(Indent + 2);
437ba7f2f71SDaniel Jasper     OS << "use ";
438ba7f2f71SDaniel Jasper     OS << DirectUses[I]->getFullModuleName();
439ba7f2f71SDaniel Jasper     OS << "\n";
440ba7f2f71SDaniel Jasper   }
441ba7f2f71SDaniel Jasper 
442ba7f2f71SDaniel Jasper   for (unsigned I = 0, N = UnresolvedDirectUses.size(); I != N; ++I) {
443ba7f2f71SDaniel Jasper     OS.indent(Indent + 2);
444ba7f2f71SDaniel Jasper     OS << "use ";
445ba7f2f71SDaniel Jasper     printModuleId(OS, UnresolvedDirectUses[I]);
446ba7f2f71SDaniel Jasper     OS << "\n";
447ba7f2f71SDaniel Jasper   }
448ba7f2f71SDaniel Jasper 
4496ddfca91SDouglas Gregor   for (unsigned I = 0, N = LinkLibraries.size(); I != N; ++I) {
4506ddfca91SDouglas Gregor     OS.indent(Indent + 2);
4516ddfca91SDouglas Gregor     OS << "link ";
4526ddfca91SDouglas Gregor     if (LinkLibraries[I].IsFramework)
4536ddfca91SDouglas Gregor       OS << "framework ";
4546ddfca91SDouglas Gregor     OS << "\"";
4556ddfca91SDouglas Gregor     OS.write_escaped(LinkLibraries[I].Library);
4566ddfca91SDouglas Gregor     OS << "\"";
4576ddfca91SDouglas Gregor   }
4586ddfca91SDouglas Gregor 
459fb912657SDouglas Gregor   for (unsigned I = 0, N = UnresolvedConflicts.size(); I != N; ++I) {
460fb912657SDouglas Gregor     OS.indent(Indent + 2);
461fb912657SDouglas Gregor     OS << "conflict ";
462fb912657SDouglas Gregor     printModuleId(OS, UnresolvedConflicts[I].Id);
463fb912657SDouglas Gregor     OS << ", \"";
464fb912657SDouglas Gregor     OS.write_escaped(UnresolvedConflicts[I].Message);
465fb912657SDouglas Gregor     OS << "\"\n";
466fb912657SDouglas Gregor   }
467fb912657SDouglas Gregor 
468fb912657SDouglas Gregor   for (unsigned I = 0, N = Conflicts.size(); I != N; ++I) {
469fb912657SDouglas Gregor     OS.indent(Indent + 2);
470fb912657SDouglas Gregor     OS << "conflict ";
471fb912657SDouglas Gregor     OS << Conflicts[I].Other->getFullModuleName();
472fb912657SDouglas Gregor     OS << ", \"";
473fb912657SDouglas Gregor     OS.write_escaped(Conflicts[I].Message);
474fb912657SDouglas Gregor     OS << "\"\n";
475fb912657SDouglas Gregor   }
476fb912657SDouglas Gregor 
47773441091SDouglas Gregor   if (InferSubmodules) {
47873441091SDouglas Gregor     OS.indent(Indent + 2);
47973441091SDouglas Gregor     if (InferExplicitSubmodules)
48073441091SDouglas Gregor       OS << "explicit ";
48173441091SDouglas Gregor     OS << "module * {\n";
48273441091SDouglas Gregor     if (InferExportWildcard) {
48373441091SDouglas Gregor       OS.indent(Indent + 4);
48473441091SDouglas Gregor       OS << "export *\n";
48573441091SDouglas Gregor     }
48673441091SDouglas Gregor     OS.indent(Indent + 2);
48773441091SDouglas Gregor     OS << "}\n";
48873441091SDouglas Gregor   }
48973441091SDouglas Gregor 
490de3ef502SDouglas Gregor   OS.indent(Indent);
491de3ef502SDouglas Gregor   OS << "}\n";
492de3ef502SDouglas Gregor }
493de3ef502SDouglas Gregor 
494cdae941eSYaron Keren LLVM_DUMP_METHOD void Module::dump() const {
495de3ef502SDouglas Gregor   print(llvm::errs());
496de3ef502SDouglas Gregor }
497de3ef502SDouglas Gregor 
498a7e2cc68SRichard Smith void VisibleModuleSet::setVisible(Module *M, SourceLocation Loc,
499a7e2cc68SRichard Smith                                   VisibleCallback Vis, ConflictCallback Cb) {
5006d25fdc4SBen Langmuir   assert(Loc.isValid() && "setVisible expects a valid import location");
501a7e2cc68SRichard Smith   if (isVisible(M))
502a7e2cc68SRichard Smith     return;
503de3ef502SDouglas Gregor 
504a7e2cc68SRichard Smith   ++Generation;
505a7e2cc68SRichard Smith 
506a7e2cc68SRichard Smith   struct Visiting {
507a7e2cc68SRichard Smith     Module *M;
508a7e2cc68SRichard Smith     Visiting *ExportedBy;
509a7e2cc68SRichard Smith   };
510a7e2cc68SRichard Smith 
511a7e2cc68SRichard Smith   std::function<void(Visiting)> VisitModule = [&](Visiting V) {
512a7e2cc68SRichard Smith     // Modules that aren't available cannot be made visible.
513a7e2cc68SRichard Smith     if (!V.M->isAvailable())
514a7e2cc68SRichard Smith       return;
515a7e2cc68SRichard Smith 
516a7e2cc68SRichard Smith     // Nothing to do for a module that's already visible.
517a7e2cc68SRichard Smith     unsigned ID = V.M->getVisibilityID();
518a7e2cc68SRichard Smith     if (ImportLocs.size() <= ID)
519a7e2cc68SRichard Smith       ImportLocs.resize(ID + 1);
520a7e2cc68SRichard Smith     else if (ImportLocs[ID].isValid())
521a7e2cc68SRichard Smith       return;
522a7e2cc68SRichard Smith 
523a7e2cc68SRichard Smith     ImportLocs[ID] = Loc;
524a7e2cc68SRichard Smith     Vis(M);
525a7e2cc68SRichard Smith 
526a7e2cc68SRichard Smith     // Make any exported modules visible.
527a7e2cc68SRichard Smith     SmallVector<Module *, 16> Exports;
528a7e2cc68SRichard Smith     V.M->getExportedModules(Exports);
529a7e2cc68SRichard Smith     for (Module *E : Exports)
530a7e2cc68SRichard Smith       VisitModule({E, &V});
531a7e2cc68SRichard Smith 
532a7e2cc68SRichard Smith     for (auto &C : V.M->Conflicts) {
533a7e2cc68SRichard Smith       if (isVisible(C.Other)) {
534a7e2cc68SRichard Smith         llvm::SmallVector<Module*, 8> Path;
535a7e2cc68SRichard Smith         for (Visiting *I = &V; I; I = I->ExportedBy)
536a7e2cc68SRichard Smith           Path.push_back(I->M);
537a7e2cc68SRichard Smith         Cb(Path, C.Other, C.Message);
538a7e2cc68SRichard Smith       }
539a7e2cc68SRichard Smith     }
540a7e2cc68SRichard Smith   };
541a7e2cc68SRichard Smith   VisitModule({M, nullptr});
542a7e2cc68SRichard Smith }
543