1 //===--- ModuleMap.cpp - Describe the layout of modules ---------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This file defines the ModuleMap implementation, which describes the layout 11 // of a module as it relates to headers. 12 // 13 //===----------------------------------------------------------------------===// 14 #include "clang/Lex/ModuleMap.h" 15 #include "clang/Basic/CharInfo.h" 16 #include "clang/Basic/Diagnostic.h" 17 #include "clang/Basic/DiagnosticOptions.h" 18 #include "clang/Basic/FileManager.h" 19 #include "clang/Basic/TargetInfo.h" 20 #include "clang/Basic/TargetOptions.h" 21 #include "clang/Lex/HeaderSearch.h" 22 #include "clang/Lex/HeaderSearchOptions.h" 23 #include "clang/Lex/LexDiagnostic.h" 24 #include "clang/Lex/Lexer.h" 25 #include "clang/Lex/LiteralSupport.h" 26 #include "llvm/ADT/StringRef.h" 27 #include "llvm/ADT/StringSwitch.h" 28 #include "llvm/Support/Allocator.h" 29 #include "llvm/Support/FileSystem.h" 30 #include "llvm/Support/Host.h" 31 #include "llvm/Support/Path.h" 32 #include "llvm/Support/raw_ostream.h" 33 #include <stdlib.h> 34 #if defined(LLVM_ON_UNIX) 35 #include <limits.h> 36 #endif 37 using namespace clang; 38 39 Module::ExportDecl 40 ModuleMap::resolveExport(Module *Mod, 41 const Module::UnresolvedExportDecl &Unresolved, 42 bool Complain) const { 43 // We may have just a wildcard. 44 if (Unresolved.Id.empty()) { 45 assert(Unresolved.Wildcard && "Invalid unresolved export"); 46 return Module::ExportDecl(nullptr, true); 47 } 48 49 // Resolve the module-id. 50 Module *Context = resolveModuleId(Unresolved.Id, Mod, Complain); 51 if (!Context) 52 return Module::ExportDecl(); 53 54 return Module::ExportDecl(Context, Unresolved.Wildcard); 55 } 56 57 Module *ModuleMap::resolveModuleId(const ModuleId &Id, Module *Mod, 58 bool Complain) const { 59 // Find the starting module. 60 Module *Context = lookupModuleUnqualified(Id[0].first, Mod); 61 if (!Context) { 62 if (Complain) 63 Diags.Report(Id[0].second, diag::err_mmap_missing_module_unqualified) 64 << Id[0].first << Mod->getFullModuleName(); 65 66 return nullptr; 67 } 68 69 // Dig into the module path. 70 for (unsigned I = 1, N = Id.size(); I != N; ++I) { 71 Module *Sub = lookupModuleQualified(Id[I].first, Context); 72 if (!Sub) { 73 if (Complain) 74 Diags.Report(Id[I].second, diag::err_mmap_missing_module_qualified) 75 << Id[I].first << Context->getFullModuleName() 76 << SourceRange(Id[0].second, Id[I-1].second); 77 78 return nullptr; 79 } 80 81 Context = Sub; 82 } 83 84 return Context; 85 } 86 87 ModuleMap::ModuleMap(SourceManager &SourceMgr, DiagnosticsEngine &Diags, 88 const LangOptions &LangOpts, const TargetInfo *Target, 89 HeaderSearch &HeaderInfo) 90 : SourceMgr(SourceMgr), Diags(Diags), LangOpts(LangOpts), Target(Target), 91 HeaderInfo(HeaderInfo), BuiltinIncludeDir(nullptr), 92 SourceModule(nullptr), NumCreatedModules(0) { 93 MMapLangOpts.LineComment = true; 94 } 95 96 ModuleMap::~ModuleMap() { 97 for (auto &M : Modules) 98 delete M.getValue(); 99 } 100 101 void ModuleMap::setTarget(const TargetInfo &Target) { 102 assert((!this->Target || this->Target == &Target) && 103 "Improper target override"); 104 this->Target = &Target; 105 } 106 107 /// \brief "Sanitize" a filename so that it can be used as an identifier. 108 static StringRef sanitizeFilenameAsIdentifier(StringRef Name, 109 SmallVectorImpl<char> &Buffer) { 110 if (Name.empty()) 111 return Name; 112 113 if (!isValidIdentifier(Name)) { 114 // If we don't already have something with the form of an identifier, 115 // create a buffer with the sanitized name. 116 Buffer.clear(); 117 if (isDigit(Name[0])) 118 Buffer.push_back('_'); 119 Buffer.reserve(Buffer.size() + Name.size()); 120 for (unsigned I = 0, N = Name.size(); I != N; ++I) { 121 if (isIdentifierBody(Name[I])) 122 Buffer.push_back(Name[I]); 123 else 124 Buffer.push_back('_'); 125 } 126 127 Name = StringRef(Buffer.data(), Buffer.size()); 128 } 129 130 while (llvm::StringSwitch<bool>(Name) 131 #define KEYWORD(Keyword,Conditions) .Case(#Keyword, true) 132 #define ALIAS(Keyword, AliasOf, Conditions) .Case(Keyword, true) 133 #include "clang/Basic/TokenKinds.def" 134 .Default(false)) { 135 if (Name.data() != Buffer.data()) 136 Buffer.append(Name.begin(), Name.end()); 137 Buffer.push_back('_'); 138 Name = StringRef(Buffer.data(), Buffer.size()); 139 } 140 141 return Name; 142 } 143 144 /// \brief Determine whether the given file name is the name of a builtin 145 /// header, supplied by Clang to replace, override, or augment existing system 146 /// headers. 147 static bool isBuiltinHeader(StringRef FileName) { 148 return llvm::StringSwitch<bool>(FileName) 149 .Case("float.h", true) 150 .Case("iso646.h", true) 151 .Case("limits.h", true) 152 .Case("stdalign.h", true) 153 .Case("stdarg.h", true) 154 .Case("stdatomic.h", true) 155 .Case("stdbool.h", true) 156 .Case("stddef.h", true) 157 .Case("stdint.h", true) 158 .Case("tgmath.h", true) 159 .Case("unwind.h", true) 160 .Default(false); 161 } 162 163 ModuleMap::HeadersMap::iterator 164 ModuleMap::findKnownHeader(const FileEntry *File) { 165 HeadersMap::iterator Known = Headers.find(File); 166 if (HeaderInfo.getHeaderSearchOpts().ImplicitModuleMaps && 167 Known == Headers.end() && File->getDir() == BuiltinIncludeDir && 168 isBuiltinHeader(llvm::sys::path::filename(File->getName()))) { 169 HeaderInfo.loadTopLevelSystemModules(); 170 return Headers.find(File); 171 } 172 return Known; 173 } 174 175 ModuleMap::KnownHeader 176 ModuleMap::findHeaderInUmbrellaDirs(const FileEntry *File, 177 SmallVectorImpl<const DirectoryEntry *> &IntermediateDirs) { 178 if (UmbrellaDirs.empty()) 179 return KnownHeader(); 180 181 const DirectoryEntry *Dir = File->getDir(); 182 assert(Dir && "file in no directory"); 183 184 // Note: as an egregious but useful hack we use the real path here, because 185 // frameworks moving from top-level frameworks to embedded frameworks tend 186 // to be symlinked from the top-level location to the embedded location, 187 // and we need to resolve lookups as if we had found the embedded location. 188 StringRef DirName = SourceMgr.getFileManager().getCanonicalName(Dir); 189 190 // Keep walking up the directory hierarchy, looking for a directory with 191 // an umbrella header. 192 do { 193 auto KnownDir = UmbrellaDirs.find(Dir); 194 if (KnownDir != UmbrellaDirs.end()) 195 return KnownHeader(KnownDir->second, NormalHeader); 196 197 IntermediateDirs.push_back(Dir); 198 199 // Retrieve our parent path. 200 DirName = llvm::sys::path::parent_path(DirName); 201 if (DirName.empty()) 202 break; 203 204 // Resolve the parent path to a directory entry. 205 Dir = SourceMgr.getFileManager().getDirectory(DirName); 206 } while (Dir); 207 return KnownHeader(); 208 } 209 210 static bool violatesPrivateInclude(Module *RequestingModule, 211 const FileEntry *IncFileEnt, 212 ModuleMap::KnownHeader Header) { 213 #ifndef NDEBUG 214 if (Header.getRole() & ModuleMap::PrivateHeader) { 215 // Check for consistency between the module header role 216 // as obtained from the lookup and as obtained from the module. 217 // This check is not cheap, so enable it only for debugging. 218 bool IsPrivate = false; 219 SmallVectorImpl<Module::Header> *HeaderList[] = { 220 &Header.getModule()->Headers[Module::HK_Private], 221 &Header.getModule()->Headers[Module::HK_PrivateTextual]}; 222 for (auto *Hs : HeaderList) 223 IsPrivate |= 224 std::find_if(Hs->begin(), Hs->end(), [&](const Module::Header &H) { 225 return H.Entry == IncFileEnt; 226 }) != Hs->end(); 227 assert(IsPrivate && "inconsistent headers and roles"); 228 } 229 #endif 230 return !Header.isAccessibleFrom(RequestingModule); 231 } 232 233 static Module *getTopLevelOrNull(Module *M) { 234 return M ? M->getTopLevelModule() : nullptr; 235 } 236 237 void ModuleMap::diagnoseHeaderInclusion(Module *RequestingModule, 238 bool RequestingModuleIsModuleInterface, 239 SourceLocation FilenameLoc, 240 StringRef Filename, 241 const FileEntry *File) { 242 // No errors for indirect modules. This may be a bit of a problem for modules 243 // with no source files. 244 if (getTopLevelOrNull(RequestingModule) != getTopLevelOrNull(SourceModule)) 245 return; 246 247 if (RequestingModule) 248 resolveUses(RequestingModule, /*Complain=*/false); 249 250 bool Excluded = false; 251 Module *Private = nullptr; 252 Module *NotUsed = nullptr; 253 254 HeadersMap::iterator Known = findKnownHeader(File); 255 if (Known != Headers.end()) { 256 for (const KnownHeader &Header : Known->second) { 257 // Remember private headers for later printing of a diagnostic. 258 if (violatesPrivateInclude(RequestingModule, File, Header)) { 259 Private = Header.getModule(); 260 continue; 261 } 262 263 // If uses need to be specified explicitly, we are only allowed to return 264 // modules that are explicitly used by the requesting module. 265 if (RequestingModule && LangOpts.ModulesDeclUse && 266 !RequestingModule->directlyUses(Header.getModule())) { 267 NotUsed = Header.getModule(); 268 continue; 269 } 270 271 // We have found a module that we can happily use. 272 return; 273 } 274 275 Excluded = true; 276 } 277 278 // We have found a header, but it is private. 279 if (Private) { 280 Diags.Report(FilenameLoc, diag::warn_use_of_private_header_outside_module) 281 << Filename; 282 return; 283 } 284 285 // We have found a module, but we don't use it. 286 if (NotUsed) { 287 Diags.Report(FilenameLoc, diag::err_undeclared_use_of_module) 288 << RequestingModule->getFullModuleName() << Filename; 289 return; 290 } 291 292 if (Excluded || isHeaderInUmbrellaDirs(File)) 293 return; 294 295 // At this point, only non-modular includes remain. 296 297 if (LangOpts.ModulesStrictDeclUse) { 298 Diags.Report(FilenameLoc, diag::err_undeclared_use_of_module) 299 << RequestingModule->getFullModuleName() << Filename; 300 } else if (RequestingModule && RequestingModuleIsModuleInterface) { 301 diag::kind DiagID = RequestingModule->getTopLevelModule()->IsFramework ? 302 diag::warn_non_modular_include_in_framework_module : 303 diag::warn_non_modular_include_in_module; 304 Diags.Report(FilenameLoc, DiagID) << RequestingModule->getFullModuleName(); 305 } 306 } 307 308 static bool isBetterKnownHeader(const ModuleMap::KnownHeader &New, 309 const ModuleMap::KnownHeader &Old) { 310 // Prefer available modules. 311 if (New.getModule()->isAvailable() && !Old.getModule()->isAvailable()) 312 return true; 313 314 // Prefer a public header over a private header. 315 if ((New.getRole() & ModuleMap::PrivateHeader) != 316 (Old.getRole() & ModuleMap::PrivateHeader)) 317 return !(New.getRole() & ModuleMap::PrivateHeader); 318 319 // Prefer a non-textual header over a textual header. 320 if ((New.getRole() & ModuleMap::TextualHeader) != 321 (Old.getRole() & ModuleMap::TextualHeader)) 322 return !(New.getRole() & ModuleMap::TextualHeader); 323 324 // Don't have a reason to choose between these. Just keep the first one. 325 return false; 326 } 327 328 ModuleMap::KnownHeader ModuleMap::findModuleForHeader(const FileEntry *File) { 329 auto MakeResult = [&](ModuleMap::KnownHeader R) -> ModuleMap::KnownHeader { 330 if (R.getRole() & ModuleMap::TextualHeader) 331 return ModuleMap::KnownHeader(); 332 return R; 333 }; 334 335 HeadersMap::iterator Known = findKnownHeader(File); 336 if (Known != Headers.end()) { 337 ModuleMap::KnownHeader Result; 338 // Iterate over all modules that 'File' is part of to find the best fit. 339 for (KnownHeader &H : Known->second) { 340 // Prefer a header from the source module over all others. 341 if (H.getModule()->getTopLevelModule() == SourceModule) 342 return MakeResult(H); 343 if (!Result || isBetterKnownHeader(H, Result)) 344 Result = H; 345 } 346 return MakeResult(Result); 347 } 348 349 return MakeResult(findOrCreateModuleForHeaderInUmbrellaDir(File)); 350 } 351 352 ModuleMap::KnownHeader 353 ModuleMap::findOrCreateModuleForHeaderInUmbrellaDir(const FileEntry *File) { 354 assert(!Headers.count(File) && "already have a module for this header"); 355 356 SmallVector<const DirectoryEntry *, 2> SkippedDirs; 357 KnownHeader H = findHeaderInUmbrellaDirs(File, SkippedDirs); 358 if (H) { 359 Module *Result = H.getModule(); 360 361 // Search up the module stack until we find a module with an umbrella 362 // directory. 363 Module *UmbrellaModule = Result; 364 while (!UmbrellaModule->getUmbrellaDir() && UmbrellaModule->Parent) 365 UmbrellaModule = UmbrellaModule->Parent; 366 367 if (UmbrellaModule->InferSubmodules) { 368 const FileEntry *UmbrellaModuleMap = 369 getModuleMapFileForUniquing(UmbrellaModule); 370 371 // Infer submodules for each of the directories we found between 372 // the directory of the umbrella header and the directory where 373 // the actual header is located. 374 bool Explicit = UmbrellaModule->InferExplicitSubmodules; 375 376 for (unsigned I = SkippedDirs.size(); I != 0; --I) { 377 // Find or create the module that corresponds to this directory name. 378 SmallString<32> NameBuf; 379 StringRef Name = sanitizeFilenameAsIdentifier( 380 llvm::sys::path::stem(SkippedDirs[I-1]->getName()), NameBuf); 381 Result = findOrCreateModule(Name, Result, /*IsFramework=*/false, 382 Explicit).first; 383 InferredModuleAllowedBy[Result] = UmbrellaModuleMap; 384 Result->IsInferred = true; 385 386 // Associate the module and the directory. 387 UmbrellaDirs[SkippedDirs[I-1]] = Result; 388 389 // If inferred submodules export everything they import, add a 390 // wildcard to the set of exports. 391 if (UmbrellaModule->InferExportWildcard && Result->Exports.empty()) 392 Result->Exports.push_back(Module::ExportDecl(nullptr, true)); 393 } 394 395 // Infer a submodule with the same name as this header file. 396 SmallString<32> NameBuf; 397 StringRef Name = sanitizeFilenameAsIdentifier( 398 llvm::sys::path::stem(File->getName()), NameBuf); 399 Result = findOrCreateModule(Name, Result, /*IsFramework=*/false, 400 Explicit).first; 401 InferredModuleAllowedBy[Result] = UmbrellaModuleMap; 402 Result->IsInferred = true; 403 Result->addTopHeader(File); 404 405 // If inferred submodules export everything they import, add a 406 // wildcard to the set of exports. 407 if (UmbrellaModule->InferExportWildcard && Result->Exports.empty()) 408 Result->Exports.push_back(Module::ExportDecl(nullptr, true)); 409 } else { 410 // Record each of the directories we stepped through as being part of 411 // the module we found, since the umbrella header covers them all. 412 for (unsigned I = 0, N = SkippedDirs.size(); I != N; ++I) 413 UmbrellaDirs[SkippedDirs[I]] = Result; 414 } 415 416 KnownHeader Header(Result, NormalHeader); 417 Headers[File].push_back(Header); 418 return Header; 419 } 420 421 return KnownHeader(); 422 } 423 424 ArrayRef<ModuleMap::KnownHeader> 425 ModuleMap::findAllModulesForHeader(const FileEntry *File) const { 426 auto It = Headers.find(File); 427 if (It == Headers.end()) 428 return None; 429 return It->second; 430 } 431 432 bool ModuleMap::isHeaderInUnavailableModule(const FileEntry *Header) const { 433 return isHeaderUnavailableInModule(Header, nullptr); 434 } 435 436 bool 437 ModuleMap::isHeaderUnavailableInModule(const FileEntry *Header, 438 const Module *RequestingModule) const { 439 HeadersMap::const_iterator Known = Headers.find(Header); 440 if (Known != Headers.end()) { 441 for (SmallVectorImpl<KnownHeader>::const_iterator 442 I = Known->second.begin(), 443 E = Known->second.end(); 444 I != E; ++I) { 445 if (I->isAvailable() && (!RequestingModule || 446 I->getModule()->isSubModuleOf(RequestingModule))) 447 return false; 448 } 449 return true; 450 } 451 452 const DirectoryEntry *Dir = Header->getDir(); 453 SmallVector<const DirectoryEntry *, 2> SkippedDirs; 454 StringRef DirName = Dir->getName(); 455 456 auto IsUnavailable = [&](const Module *M) { 457 return !M->isAvailable() && (!RequestingModule || 458 M->isSubModuleOf(RequestingModule)); 459 }; 460 461 // Keep walking up the directory hierarchy, looking for a directory with 462 // an umbrella header. 463 do { 464 llvm::DenseMap<const DirectoryEntry *, Module *>::const_iterator KnownDir 465 = UmbrellaDirs.find(Dir); 466 if (KnownDir != UmbrellaDirs.end()) { 467 Module *Found = KnownDir->second; 468 if (IsUnavailable(Found)) 469 return true; 470 471 // Search up the module stack until we find a module with an umbrella 472 // directory. 473 Module *UmbrellaModule = Found; 474 while (!UmbrellaModule->getUmbrellaDir() && UmbrellaModule->Parent) 475 UmbrellaModule = UmbrellaModule->Parent; 476 477 if (UmbrellaModule->InferSubmodules) { 478 for (unsigned I = SkippedDirs.size(); I != 0; --I) { 479 // Find or create the module that corresponds to this directory name. 480 SmallString<32> NameBuf; 481 StringRef Name = sanitizeFilenameAsIdentifier( 482 llvm::sys::path::stem(SkippedDirs[I-1]->getName()), 483 NameBuf); 484 Found = lookupModuleQualified(Name, Found); 485 if (!Found) 486 return false; 487 if (IsUnavailable(Found)) 488 return true; 489 } 490 491 // Infer a submodule with the same name as this header file. 492 SmallString<32> NameBuf; 493 StringRef Name = sanitizeFilenameAsIdentifier( 494 llvm::sys::path::stem(Header->getName()), 495 NameBuf); 496 Found = lookupModuleQualified(Name, Found); 497 if (!Found) 498 return false; 499 } 500 501 return IsUnavailable(Found); 502 } 503 504 SkippedDirs.push_back(Dir); 505 506 // Retrieve our parent path. 507 DirName = llvm::sys::path::parent_path(DirName); 508 if (DirName.empty()) 509 break; 510 511 // Resolve the parent path to a directory entry. 512 Dir = SourceMgr.getFileManager().getDirectory(DirName); 513 } while (Dir); 514 515 return false; 516 } 517 518 Module *ModuleMap::findModule(StringRef Name) const { 519 llvm::StringMap<Module *>::const_iterator Known = Modules.find(Name); 520 if (Known != Modules.end()) 521 return Known->getValue(); 522 523 return nullptr; 524 } 525 526 Module *ModuleMap::lookupModuleUnqualified(StringRef Name, 527 Module *Context) const { 528 for(; Context; Context = Context->Parent) { 529 if (Module *Sub = lookupModuleQualified(Name, Context)) 530 return Sub; 531 } 532 533 return findModule(Name); 534 } 535 536 Module *ModuleMap::lookupModuleQualified(StringRef Name, Module *Context) const{ 537 if (!Context) 538 return findModule(Name); 539 540 return Context->findSubmodule(Name); 541 } 542 543 std::pair<Module *, bool> 544 ModuleMap::findOrCreateModule(StringRef Name, Module *Parent, bool IsFramework, 545 bool IsExplicit) { 546 // Try to find an existing module with this name. 547 if (Module *Sub = lookupModuleQualified(Name, Parent)) 548 return std::make_pair(Sub, false); 549 550 // Create a new module with this name. 551 Module *Result = new Module(Name, SourceLocation(), Parent, 552 IsFramework, IsExplicit, NumCreatedModules++); 553 if (!Parent) { 554 if (LangOpts.CurrentModule == Name) 555 SourceModule = Result; 556 Modules[Name] = Result; 557 } 558 return std::make_pair(Result, true); 559 } 560 561 /// \brief For a framework module, infer the framework against which we 562 /// should link. 563 static void inferFrameworkLink(Module *Mod, const DirectoryEntry *FrameworkDir, 564 FileManager &FileMgr) { 565 assert(Mod->IsFramework && "Can only infer linking for framework modules"); 566 assert(!Mod->isSubFramework() && 567 "Can only infer linking for top-level frameworks"); 568 569 SmallString<128> LibName; 570 LibName += FrameworkDir->getName(); 571 llvm::sys::path::append(LibName, Mod->Name); 572 573 // The library name of a framework has more than one possible extension since 574 // the introduction of the text-based dynamic library format. We need to check 575 // for both before we give up. 576 static const char *frameworkExtensions[] = {"", ".tbd"}; 577 for (const auto *extension : frameworkExtensions) { 578 llvm::sys::path::replace_extension(LibName, extension); 579 if (FileMgr.getFile(LibName)) { 580 Mod->LinkLibraries.push_back(Module::LinkLibrary(Mod->Name, 581 /*IsFramework=*/true)); 582 return; 583 } 584 } 585 } 586 587 Module *ModuleMap::inferFrameworkModule(const DirectoryEntry *FrameworkDir, 588 bool IsSystem, Module *Parent) { 589 Attributes Attrs; 590 Attrs.IsSystem = IsSystem; 591 return inferFrameworkModule(FrameworkDir, Attrs, Parent); 592 } 593 594 Module *ModuleMap::inferFrameworkModule(const DirectoryEntry *FrameworkDir, 595 Attributes Attrs, Module *Parent) { 596 // Note: as an egregious but useful hack we use the real path here, because 597 // we might be looking at an embedded framework that symlinks out to a 598 // top-level framework, and we need to infer as if we were naming the 599 // top-level framework. 600 StringRef FrameworkDirName = 601 SourceMgr.getFileManager().getCanonicalName(FrameworkDir); 602 603 // In case this is a case-insensitive filesystem, use the canonical 604 // directory name as the ModuleName, since modules are case-sensitive. 605 // FIXME: we should be able to give a fix-it hint for the correct spelling. 606 SmallString<32> ModuleNameStorage; 607 StringRef ModuleName = sanitizeFilenameAsIdentifier( 608 llvm::sys::path::stem(FrameworkDirName), ModuleNameStorage); 609 610 // Check whether we've already found this module. 611 if (Module *Mod = lookupModuleQualified(ModuleName, Parent)) 612 return Mod; 613 614 FileManager &FileMgr = SourceMgr.getFileManager(); 615 616 // If the framework has a parent path from which we're allowed to infer 617 // a framework module, do so. 618 const FileEntry *ModuleMapFile = nullptr; 619 if (!Parent) { 620 // Determine whether we're allowed to infer a module map. 621 bool canInfer = false; 622 if (llvm::sys::path::has_parent_path(FrameworkDirName)) { 623 // Figure out the parent path. 624 StringRef Parent = llvm::sys::path::parent_path(FrameworkDirName); 625 if (const DirectoryEntry *ParentDir = FileMgr.getDirectory(Parent)) { 626 // Check whether we have already looked into the parent directory 627 // for a module map. 628 llvm::DenseMap<const DirectoryEntry *, InferredDirectory>::const_iterator 629 inferred = InferredDirectories.find(ParentDir); 630 if (inferred == InferredDirectories.end()) { 631 // We haven't looked here before. Load a module map, if there is 632 // one. 633 bool IsFrameworkDir = Parent.endswith(".framework"); 634 if (const FileEntry *ModMapFile = 635 HeaderInfo.lookupModuleMapFile(ParentDir, IsFrameworkDir)) { 636 parseModuleMapFile(ModMapFile, Attrs.IsSystem, ParentDir); 637 inferred = InferredDirectories.find(ParentDir); 638 } 639 640 if (inferred == InferredDirectories.end()) 641 inferred = InferredDirectories.insert( 642 std::make_pair(ParentDir, InferredDirectory())).first; 643 } 644 645 if (inferred->second.InferModules) { 646 // We're allowed to infer for this directory, but make sure it's okay 647 // to infer this particular module. 648 StringRef Name = llvm::sys::path::stem(FrameworkDirName); 649 canInfer = std::find(inferred->second.ExcludedModules.begin(), 650 inferred->second.ExcludedModules.end(), 651 Name) == inferred->second.ExcludedModules.end(); 652 653 Attrs.IsSystem |= inferred->second.Attrs.IsSystem; 654 Attrs.IsExternC |= inferred->second.Attrs.IsExternC; 655 Attrs.IsExhaustive |= inferred->second.Attrs.IsExhaustive; 656 ModuleMapFile = inferred->second.ModuleMapFile; 657 } 658 } 659 } 660 661 // If we're not allowed to infer a framework module, don't. 662 if (!canInfer) 663 return nullptr; 664 } else 665 ModuleMapFile = getModuleMapFileForUniquing(Parent); 666 667 668 // Look for an umbrella header. 669 SmallString<128> UmbrellaName = StringRef(FrameworkDir->getName()); 670 llvm::sys::path::append(UmbrellaName, "Headers", ModuleName + ".h"); 671 const FileEntry *UmbrellaHeader = FileMgr.getFile(UmbrellaName); 672 673 // FIXME: If there's no umbrella header, we could probably scan the 674 // framework to load *everything*. But, it's not clear that this is a good 675 // idea. 676 if (!UmbrellaHeader) 677 return nullptr; 678 679 Module *Result = new Module(ModuleName, SourceLocation(), Parent, 680 /*IsFramework=*/true, /*IsExplicit=*/false, 681 NumCreatedModules++); 682 InferredModuleAllowedBy[Result] = ModuleMapFile; 683 Result->IsInferred = true; 684 if (!Parent) { 685 if (LangOpts.CurrentModule == ModuleName) 686 SourceModule = Result; 687 Modules[ModuleName] = Result; 688 } 689 690 Result->IsSystem |= Attrs.IsSystem; 691 Result->IsExternC |= Attrs.IsExternC; 692 Result->ConfigMacrosExhaustive |= Attrs.IsExhaustive; 693 Result->Directory = FrameworkDir; 694 695 // umbrella header "umbrella-header-name" 696 // 697 // The "Headers/" component of the name is implied because this is 698 // a framework module. 699 setUmbrellaHeader(Result, UmbrellaHeader, ModuleName + ".h"); 700 701 // export * 702 Result->Exports.push_back(Module::ExportDecl(nullptr, true)); 703 704 // module * { export * } 705 Result->InferSubmodules = true; 706 Result->InferExportWildcard = true; 707 708 // Look for subframeworks. 709 std::error_code EC; 710 SmallString<128> SubframeworksDirName 711 = StringRef(FrameworkDir->getName()); 712 llvm::sys::path::append(SubframeworksDirName, "Frameworks"); 713 llvm::sys::path::native(SubframeworksDirName); 714 for (llvm::sys::fs::directory_iterator Dir(SubframeworksDirName, EC), DirEnd; 715 Dir != DirEnd && !EC; Dir.increment(EC)) { 716 if (!StringRef(Dir->path()).endswith(".framework")) 717 continue; 718 719 if (const DirectoryEntry *SubframeworkDir 720 = FileMgr.getDirectory(Dir->path())) { 721 // Note: as an egregious but useful hack, we use the real path here and 722 // check whether it is actually a subdirectory of the parent directory. 723 // This will not be the case if the 'subframework' is actually a symlink 724 // out to a top-level framework. 725 StringRef SubframeworkDirName = FileMgr.getCanonicalName(SubframeworkDir); 726 bool FoundParent = false; 727 do { 728 // Get the parent directory name. 729 SubframeworkDirName 730 = llvm::sys::path::parent_path(SubframeworkDirName); 731 if (SubframeworkDirName.empty()) 732 break; 733 734 if (FileMgr.getDirectory(SubframeworkDirName) == FrameworkDir) { 735 FoundParent = true; 736 break; 737 } 738 } while (true); 739 740 if (!FoundParent) 741 continue; 742 743 // FIXME: Do we want to warn about subframeworks without umbrella headers? 744 inferFrameworkModule(SubframeworkDir, Attrs, Result); 745 } 746 } 747 748 // If the module is a top-level framework, automatically link against the 749 // framework. 750 if (!Result->isSubFramework()) { 751 inferFrameworkLink(Result, FrameworkDir, FileMgr); 752 } 753 754 return Result; 755 } 756 757 void ModuleMap::setUmbrellaHeader(Module *Mod, const FileEntry *UmbrellaHeader, 758 Twine NameAsWritten) { 759 Headers[UmbrellaHeader].push_back(KnownHeader(Mod, NormalHeader)); 760 Mod->Umbrella = UmbrellaHeader; 761 Mod->UmbrellaAsWritten = NameAsWritten.str(); 762 UmbrellaDirs[UmbrellaHeader->getDir()] = Mod; 763 } 764 765 void ModuleMap::setUmbrellaDir(Module *Mod, const DirectoryEntry *UmbrellaDir, 766 Twine NameAsWritten) { 767 Mod->Umbrella = UmbrellaDir; 768 Mod->UmbrellaAsWritten = NameAsWritten.str(); 769 UmbrellaDirs[UmbrellaDir] = Mod; 770 } 771 772 static Module::HeaderKind headerRoleToKind(ModuleMap::ModuleHeaderRole Role) { 773 switch ((int)Role) { 774 default: llvm_unreachable("unknown header role"); 775 case ModuleMap::NormalHeader: 776 return Module::HK_Normal; 777 case ModuleMap::PrivateHeader: 778 return Module::HK_Private; 779 case ModuleMap::TextualHeader: 780 return Module::HK_Textual; 781 case ModuleMap::PrivateHeader | ModuleMap::TextualHeader: 782 return Module::HK_PrivateTextual; 783 } 784 } 785 786 void ModuleMap::addHeader(Module *Mod, Module::Header Header, 787 ModuleHeaderRole Role, bool Imported) { 788 KnownHeader KH(Mod, Role); 789 790 // Only add each header to the headers list once. 791 // FIXME: Should we diagnose if a header is listed twice in the 792 // same module definition? 793 auto &HeaderList = Headers[Header.Entry]; 794 for (auto H : HeaderList) 795 if (H == KH) 796 return; 797 798 HeaderList.push_back(KH); 799 Mod->Headers[headerRoleToKind(Role)].push_back(std::move(Header)); 800 801 bool isCompilingModuleHeader = 802 LangOpts.CompilingModule && Mod->getTopLevelModule() == SourceModule; 803 if (!Imported || isCompilingModuleHeader) { 804 // When we import HeaderFileInfo, the external source is expected to 805 // set the isModuleHeader flag itself. 806 HeaderInfo.MarkFileModuleHeader(Header.Entry, Role, 807 isCompilingModuleHeader); 808 } 809 810 // Notify callbacks that we just added a new header. 811 for (const auto &Cb : Callbacks) 812 Cb->moduleMapAddHeader(Header.Entry->getName()); 813 } 814 815 void ModuleMap::excludeHeader(Module *Mod, Module::Header Header) { 816 // Add this as a known header so we won't implicitly add it to any 817 // umbrella directory module. 818 // FIXME: Should we only exclude it from umbrella modules within the 819 // specified module? 820 (void) Headers[Header.Entry]; 821 822 Mod->Headers[Module::HK_Excluded].push_back(std::move(Header)); 823 } 824 825 const FileEntry * 826 ModuleMap::getContainingModuleMapFile(const Module *Module) const { 827 if (Module->DefinitionLoc.isInvalid()) 828 return nullptr; 829 830 return SourceMgr.getFileEntryForID( 831 SourceMgr.getFileID(Module->DefinitionLoc)); 832 } 833 834 const FileEntry *ModuleMap::getModuleMapFileForUniquing(const Module *M) const { 835 if (M->IsInferred) { 836 assert(InferredModuleAllowedBy.count(M) && "missing inferred module map"); 837 return InferredModuleAllowedBy.find(M)->second; 838 } 839 return getContainingModuleMapFile(M); 840 } 841 842 void ModuleMap::setInferredModuleAllowedBy(Module *M, const FileEntry *ModMap) { 843 assert(M->IsInferred && "module not inferred"); 844 InferredModuleAllowedBy[M] = ModMap; 845 } 846 847 LLVM_DUMP_METHOD void ModuleMap::dump() { 848 llvm::errs() << "Modules:"; 849 for (llvm::StringMap<Module *>::iterator M = Modules.begin(), 850 MEnd = Modules.end(); 851 M != MEnd; ++M) 852 M->getValue()->print(llvm::errs(), 2); 853 854 llvm::errs() << "Headers:"; 855 for (HeadersMap::iterator H = Headers.begin(), HEnd = Headers.end(); 856 H != HEnd; ++H) { 857 llvm::errs() << " \"" << H->first->getName() << "\" -> "; 858 for (SmallVectorImpl<KnownHeader>::const_iterator I = H->second.begin(), 859 E = H->second.end(); 860 I != E; ++I) { 861 if (I != H->second.begin()) 862 llvm::errs() << ","; 863 llvm::errs() << I->getModule()->getFullModuleName(); 864 } 865 llvm::errs() << "\n"; 866 } 867 } 868 869 bool ModuleMap::resolveExports(Module *Mod, bool Complain) { 870 auto Unresolved = std::move(Mod->UnresolvedExports); 871 Mod->UnresolvedExports.clear(); 872 for (auto &UE : Unresolved) { 873 Module::ExportDecl Export = resolveExport(Mod, UE, Complain); 874 if (Export.getPointer() || Export.getInt()) 875 Mod->Exports.push_back(Export); 876 else 877 Mod->UnresolvedExports.push_back(UE); 878 } 879 return !Mod->UnresolvedExports.empty(); 880 } 881 882 bool ModuleMap::resolveUses(Module *Mod, bool Complain) { 883 auto Unresolved = std::move(Mod->UnresolvedDirectUses); 884 Mod->UnresolvedDirectUses.clear(); 885 for (auto &UDU : Unresolved) { 886 Module *DirectUse = resolveModuleId(UDU, Mod, Complain); 887 if (DirectUse) 888 Mod->DirectUses.push_back(DirectUse); 889 else 890 Mod->UnresolvedDirectUses.push_back(UDU); 891 } 892 return !Mod->UnresolvedDirectUses.empty(); 893 } 894 895 bool ModuleMap::resolveConflicts(Module *Mod, bool Complain) { 896 auto Unresolved = std::move(Mod->UnresolvedConflicts); 897 Mod->UnresolvedConflicts.clear(); 898 for (auto &UC : Unresolved) { 899 if (Module *OtherMod = resolveModuleId(UC.Id, Mod, Complain)) { 900 Module::Conflict Conflict; 901 Conflict.Other = OtherMod; 902 Conflict.Message = UC.Message; 903 Mod->Conflicts.push_back(Conflict); 904 } else 905 Mod->UnresolvedConflicts.push_back(UC); 906 } 907 return !Mod->UnresolvedConflicts.empty(); 908 } 909 910 Module *ModuleMap::inferModuleFromLocation(FullSourceLoc Loc) { 911 if (Loc.isInvalid()) 912 return nullptr; 913 914 // Use the expansion location to determine which module we're in. 915 FullSourceLoc ExpansionLoc = Loc.getExpansionLoc(); 916 if (!ExpansionLoc.isFileID()) 917 return nullptr; 918 919 const SourceManager &SrcMgr = Loc.getManager(); 920 FileID ExpansionFileID = ExpansionLoc.getFileID(); 921 922 while (const FileEntry *ExpansionFile 923 = SrcMgr.getFileEntryForID(ExpansionFileID)) { 924 // Find the module that owns this header (if any). 925 if (Module *Mod = findModuleForHeader(ExpansionFile).getModule()) 926 return Mod; 927 928 // No module owns this header, so look up the inclusion chain to see if 929 // any included header has an associated module. 930 SourceLocation IncludeLoc = SrcMgr.getIncludeLoc(ExpansionFileID); 931 if (IncludeLoc.isInvalid()) 932 return nullptr; 933 934 ExpansionFileID = SrcMgr.getFileID(IncludeLoc); 935 } 936 937 return nullptr; 938 } 939 940 //----------------------------------------------------------------------------// 941 // Module map file parser 942 //----------------------------------------------------------------------------// 943 944 namespace clang { 945 /// \brief A token in a module map file. 946 struct MMToken { 947 enum TokenKind { 948 Comma, 949 ConfigMacros, 950 Conflict, 951 EndOfFile, 952 HeaderKeyword, 953 Identifier, 954 Exclaim, 955 ExcludeKeyword, 956 ExplicitKeyword, 957 ExportKeyword, 958 ExternKeyword, 959 FrameworkKeyword, 960 LinkKeyword, 961 ModuleKeyword, 962 Period, 963 PrivateKeyword, 964 UmbrellaKeyword, 965 UseKeyword, 966 RequiresKeyword, 967 Star, 968 StringLiteral, 969 TextualKeyword, 970 LBrace, 971 RBrace, 972 LSquare, 973 RSquare 974 } Kind; 975 976 unsigned Location; 977 unsigned StringLength; 978 const char *StringData; 979 980 void clear() { 981 Kind = EndOfFile; 982 Location = 0; 983 StringLength = 0; 984 StringData = nullptr; 985 } 986 987 bool is(TokenKind K) const { return Kind == K; } 988 989 SourceLocation getLocation() const { 990 return SourceLocation::getFromRawEncoding(Location); 991 } 992 993 StringRef getString() const { 994 return StringRef(StringData, StringLength); 995 } 996 }; 997 998 class ModuleMapParser { 999 Lexer &L; 1000 SourceManager &SourceMgr; 1001 1002 /// \brief Default target information, used only for string literal 1003 /// parsing. 1004 const TargetInfo *Target; 1005 1006 DiagnosticsEngine &Diags; 1007 ModuleMap ⤅ 1008 1009 /// \brief The current module map file. 1010 const FileEntry *ModuleMapFile; 1011 1012 /// \brief The directory that file names in this module map file should 1013 /// be resolved relative to. 1014 const DirectoryEntry *Directory; 1015 1016 /// \brief The directory containing Clang-supplied headers. 1017 const DirectoryEntry *BuiltinIncludeDir; 1018 1019 /// \brief Whether this module map is in a system header directory. 1020 bool IsSystem; 1021 1022 /// \brief Whether an error occurred. 1023 bool HadError; 1024 1025 /// \brief Stores string data for the various string literals referenced 1026 /// during parsing. 1027 llvm::BumpPtrAllocator StringData; 1028 1029 /// \brief The current token. 1030 MMToken Tok; 1031 1032 /// \brief The active module. 1033 Module *ActiveModule; 1034 1035 /// \brief Whether a module uses the 'requires excluded' hack to mark its 1036 /// contents as 'textual'. 1037 /// 1038 /// On older Darwin SDK versions, 'requires excluded' is used to mark the 1039 /// contents of the Darwin.C.excluded (assert.h) and Tcl.Private modules as 1040 /// non-modular headers. For backwards compatibility, we continue to 1041 /// support this idiom for just these modules, and map the headers to 1042 /// 'textual' to match the original intent. 1043 llvm::SmallPtrSet<Module *, 2> UsesRequiresExcludedHack; 1044 1045 /// \brief Consume the current token and return its location. 1046 SourceLocation consumeToken(); 1047 1048 /// \brief Skip tokens until we reach the a token with the given kind 1049 /// (or the end of the file). 1050 void skipUntil(MMToken::TokenKind K); 1051 1052 typedef SmallVector<std::pair<std::string, SourceLocation>, 2> ModuleId; 1053 bool parseModuleId(ModuleId &Id); 1054 void parseModuleDecl(); 1055 void parseExternModuleDecl(); 1056 void parseRequiresDecl(); 1057 void parseHeaderDecl(clang::MMToken::TokenKind, 1058 SourceLocation LeadingLoc); 1059 void parseUmbrellaDirDecl(SourceLocation UmbrellaLoc); 1060 void parseExportDecl(); 1061 void parseUseDecl(); 1062 void parseLinkDecl(); 1063 void parseConfigMacros(); 1064 void parseConflict(); 1065 void parseInferredModuleDecl(bool Framework, bool Explicit); 1066 1067 typedef ModuleMap::Attributes Attributes; 1068 bool parseOptionalAttributes(Attributes &Attrs); 1069 1070 public: 1071 explicit ModuleMapParser(Lexer &L, SourceManager &SourceMgr, 1072 const TargetInfo *Target, 1073 DiagnosticsEngine &Diags, 1074 ModuleMap &Map, 1075 const FileEntry *ModuleMapFile, 1076 const DirectoryEntry *Directory, 1077 const DirectoryEntry *BuiltinIncludeDir, 1078 bool IsSystem) 1079 : L(L), SourceMgr(SourceMgr), Target(Target), Diags(Diags), Map(Map), 1080 ModuleMapFile(ModuleMapFile), Directory(Directory), 1081 BuiltinIncludeDir(BuiltinIncludeDir), IsSystem(IsSystem), 1082 HadError(false), ActiveModule(nullptr) 1083 { 1084 Tok.clear(); 1085 consumeToken(); 1086 } 1087 1088 bool parseModuleMapFile(); 1089 }; 1090 } 1091 1092 SourceLocation ModuleMapParser::consumeToken() { 1093 retry: 1094 SourceLocation Result = Tok.getLocation(); 1095 Tok.clear(); 1096 1097 Token LToken; 1098 L.LexFromRawLexer(LToken); 1099 Tok.Location = LToken.getLocation().getRawEncoding(); 1100 switch (LToken.getKind()) { 1101 case tok::raw_identifier: { 1102 StringRef RI = LToken.getRawIdentifier(); 1103 Tok.StringData = RI.data(); 1104 Tok.StringLength = RI.size(); 1105 Tok.Kind = llvm::StringSwitch<MMToken::TokenKind>(RI) 1106 .Case("config_macros", MMToken::ConfigMacros) 1107 .Case("conflict", MMToken::Conflict) 1108 .Case("exclude", MMToken::ExcludeKeyword) 1109 .Case("explicit", MMToken::ExplicitKeyword) 1110 .Case("export", MMToken::ExportKeyword) 1111 .Case("extern", MMToken::ExternKeyword) 1112 .Case("framework", MMToken::FrameworkKeyword) 1113 .Case("header", MMToken::HeaderKeyword) 1114 .Case("link", MMToken::LinkKeyword) 1115 .Case("module", MMToken::ModuleKeyword) 1116 .Case("private", MMToken::PrivateKeyword) 1117 .Case("requires", MMToken::RequiresKeyword) 1118 .Case("textual", MMToken::TextualKeyword) 1119 .Case("umbrella", MMToken::UmbrellaKeyword) 1120 .Case("use", MMToken::UseKeyword) 1121 .Default(MMToken::Identifier); 1122 break; 1123 } 1124 1125 case tok::comma: 1126 Tok.Kind = MMToken::Comma; 1127 break; 1128 1129 case tok::eof: 1130 Tok.Kind = MMToken::EndOfFile; 1131 break; 1132 1133 case tok::l_brace: 1134 Tok.Kind = MMToken::LBrace; 1135 break; 1136 1137 case tok::l_square: 1138 Tok.Kind = MMToken::LSquare; 1139 break; 1140 1141 case tok::period: 1142 Tok.Kind = MMToken::Period; 1143 break; 1144 1145 case tok::r_brace: 1146 Tok.Kind = MMToken::RBrace; 1147 break; 1148 1149 case tok::r_square: 1150 Tok.Kind = MMToken::RSquare; 1151 break; 1152 1153 case tok::star: 1154 Tok.Kind = MMToken::Star; 1155 break; 1156 1157 case tok::exclaim: 1158 Tok.Kind = MMToken::Exclaim; 1159 break; 1160 1161 case tok::string_literal: { 1162 if (LToken.hasUDSuffix()) { 1163 Diags.Report(LToken.getLocation(), diag::err_invalid_string_udl); 1164 HadError = true; 1165 goto retry; 1166 } 1167 1168 // Parse the string literal. 1169 LangOptions LangOpts; 1170 StringLiteralParser StringLiteral(LToken, SourceMgr, LangOpts, *Target); 1171 if (StringLiteral.hadError) 1172 goto retry; 1173 1174 // Copy the string literal into our string data allocator. 1175 unsigned Length = StringLiteral.GetStringLength(); 1176 char *Saved = StringData.Allocate<char>(Length + 1); 1177 memcpy(Saved, StringLiteral.GetString().data(), Length); 1178 Saved[Length] = 0; 1179 1180 // Form the token. 1181 Tok.Kind = MMToken::StringLiteral; 1182 Tok.StringData = Saved; 1183 Tok.StringLength = Length; 1184 break; 1185 } 1186 1187 case tok::comment: 1188 goto retry; 1189 1190 default: 1191 Diags.Report(LToken.getLocation(), diag::err_mmap_unknown_token); 1192 HadError = true; 1193 goto retry; 1194 } 1195 1196 return Result; 1197 } 1198 1199 void ModuleMapParser::skipUntil(MMToken::TokenKind K) { 1200 unsigned braceDepth = 0; 1201 unsigned squareDepth = 0; 1202 do { 1203 switch (Tok.Kind) { 1204 case MMToken::EndOfFile: 1205 return; 1206 1207 case MMToken::LBrace: 1208 if (Tok.is(K) && braceDepth == 0 && squareDepth == 0) 1209 return; 1210 1211 ++braceDepth; 1212 break; 1213 1214 case MMToken::LSquare: 1215 if (Tok.is(K) && braceDepth == 0 && squareDepth == 0) 1216 return; 1217 1218 ++squareDepth; 1219 break; 1220 1221 case MMToken::RBrace: 1222 if (braceDepth > 0) 1223 --braceDepth; 1224 else if (Tok.is(K)) 1225 return; 1226 break; 1227 1228 case MMToken::RSquare: 1229 if (squareDepth > 0) 1230 --squareDepth; 1231 else if (Tok.is(K)) 1232 return; 1233 break; 1234 1235 default: 1236 if (braceDepth == 0 && squareDepth == 0 && Tok.is(K)) 1237 return; 1238 break; 1239 } 1240 1241 consumeToken(); 1242 } while (true); 1243 } 1244 1245 /// \brief Parse a module-id. 1246 /// 1247 /// module-id: 1248 /// identifier 1249 /// identifier '.' module-id 1250 /// 1251 /// \returns true if an error occurred, false otherwise. 1252 bool ModuleMapParser::parseModuleId(ModuleId &Id) { 1253 Id.clear(); 1254 do { 1255 if (Tok.is(MMToken::Identifier) || Tok.is(MMToken::StringLiteral)) { 1256 Id.push_back(std::make_pair(Tok.getString(), Tok.getLocation())); 1257 consumeToken(); 1258 } else { 1259 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_module_name); 1260 return true; 1261 } 1262 1263 if (!Tok.is(MMToken::Period)) 1264 break; 1265 1266 consumeToken(); 1267 } while (true); 1268 1269 return false; 1270 } 1271 1272 namespace { 1273 /// \brief Enumerates the known attributes. 1274 enum AttributeKind { 1275 /// \brief An unknown attribute. 1276 AT_unknown, 1277 /// \brief The 'system' attribute. 1278 AT_system, 1279 /// \brief The 'extern_c' attribute. 1280 AT_extern_c, 1281 /// \brief The 'exhaustive' attribute. 1282 AT_exhaustive 1283 }; 1284 } 1285 1286 /// \brief Parse a module declaration. 1287 /// 1288 /// module-declaration: 1289 /// 'extern' 'module' module-id string-literal 1290 /// 'explicit'[opt] 'framework'[opt] 'module' module-id attributes[opt] 1291 /// { module-member* } 1292 /// 1293 /// module-member: 1294 /// requires-declaration 1295 /// header-declaration 1296 /// submodule-declaration 1297 /// export-declaration 1298 /// link-declaration 1299 /// 1300 /// submodule-declaration: 1301 /// module-declaration 1302 /// inferred-submodule-declaration 1303 void ModuleMapParser::parseModuleDecl() { 1304 assert(Tok.is(MMToken::ExplicitKeyword) || Tok.is(MMToken::ModuleKeyword) || 1305 Tok.is(MMToken::FrameworkKeyword) || Tok.is(MMToken::ExternKeyword)); 1306 if (Tok.is(MMToken::ExternKeyword)) { 1307 parseExternModuleDecl(); 1308 return; 1309 } 1310 1311 // Parse 'explicit' or 'framework' keyword, if present. 1312 SourceLocation ExplicitLoc; 1313 bool Explicit = false; 1314 bool Framework = false; 1315 1316 // Parse 'explicit' keyword, if present. 1317 if (Tok.is(MMToken::ExplicitKeyword)) { 1318 ExplicitLoc = consumeToken(); 1319 Explicit = true; 1320 } 1321 1322 // Parse 'framework' keyword, if present. 1323 if (Tok.is(MMToken::FrameworkKeyword)) { 1324 consumeToken(); 1325 Framework = true; 1326 } 1327 1328 // Parse 'module' keyword. 1329 if (!Tok.is(MMToken::ModuleKeyword)) { 1330 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_module); 1331 consumeToken(); 1332 HadError = true; 1333 return; 1334 } 1335 consumeToken(); // 'module' keyword 1336 1337 // If we have a wildcard for the module name, this is an inferred submodule. 1338 // Parse it. 1339 if (Tok.is(MMToken::Star)) 1340 return parseInferredModuleDecl(Framework, Explicit); 1341 1342 // Parse the module name. 1343 ModuleId Id; 1344 if (parseModuleId(Id)) { 1345 HadError = true; 1346 return; 1347 } 1348 1349 if (ActiveModule) { 1350 if (Id.size() > 1) { 1351 Diags.Report(Id.front().second, diag::err_mmap_nested_submodule_id) 1352 << SourceRange(Id.front().second, Id.back().second); 1353 1354 HadError = true; 1355 return; 1356 } 1357 } else if (Id.size() == 1 && Explicit) { 1358 // Top-level modules can't be explicit. 1359 Diags.Report(ExplicitLoc, diag::err_mmap_explicit_top_level); 1360 Explicit = false; 1361 ExplicitLoc = SourceLocation(); 1362 HadError = true; 1363 } 1364 1365 Module *PreviousActiveModule = ActiveModule; 1366 if (Id.size() > 1) { 1367 // This module map defines a submodule. Go find the module of which it 1368 // is a submodule. 1369 ActiveModule = nullptr; 1370 const Module *TopLevelModule = nullptr; 1371 for (unsigned I = 0, N = Id.size() - 1; I != N; ++I) { 1372 if (Module *Next = Map.lookupModuleQualified(Id[I].first, ActiveModule)) { 1373 if (I == 0) 1374 TopLevelModule = Next; 1375 ActiveModule = Next; 1376 continue; 1377 } 1378 1379 if (ActiveModule) { 1380 Diags.Report(Id[I].second, diag::err_mmap_missing_module_qualified) 1381 << Id[I].first 1382 << ActiveModule->getTopLevelModule()->getFullModuleName(); 1383 } else { 1384 Diags.Report(Id[I].second, diag::err_mmap_expected_module_name); 1385 } 1386 HadError = true; 1387 return; 1388 } 1389 1390 if (ModuleMapFile != Map.getContainingModuleMapFile(TopLevelModule)) { 1391 assert(ModuleMapFile != Map.getModuleMapFileForUniquing(TopLevelModule) && 1392 "submodule defined in same file as 'module *' that allowed its " 1393 "top-level module"); 1394 Map.addAdditionalModuleMapFile(TopLevelModule, ModuleMapFile); 1395 } 1396 } 1397 1398 StringRef ModuleName = Id.back().first; 1399 SourceLocation ModuleNameLoc = Id.back().second; 1400 1401 // Parse the optional attribute list. 1402 Attributes Attrs; 1403 if (parseOptionalAttributes(Attrs)) 1404 return; 1405 1406 1407 // Parse the opening brace. 1408 if (!Tok.is(MMToken::LBrace)) { 1409 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_lbrace) 1410 << ModuleName; 1411 HadError = true; 1412 return; 1413 } 1414 SourceLocation LBraceLoc = consumeToken(); 1415 1416 // Determine whether this (sub)module has already been defined. 1417 if (Module *Existing = Map.lookupModuleQualified(ModuleName, ActiveModule)) { 1418 if (Existing->DefinitionLoc.isInvalid() && !ActiveModule) { 1419 // Skip the module definition. 1420 skipUntil(MMToken::RBrace); 1421 if (Tok.is(MMToken::RBrace)) 1422 consumeToken(); 1423 else { 1424 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_rbrace); 1425 Diags.Report(LBraceLoc, diag::note_mmap_lbrace_match); 1426 HadError = true; 1427 } 1428 return; 1429 } 1430 1431 Diags.Report(ModuleNameLoc, diag::err_mmap_module_redefinition) 1432 << ModuleName; 1433 Diags.Report(Existing->DefinitionLoc, diag::note_mmap_prev_definition); 1434 1435 // Skip the module definition. 1436 skipUntil(MMToken::RBrace); 1437 if (Tok.is(MMToken::RBrace)) 1438 consumeToken(); 1439 1440 HadError = true; 1441 return; 1442 } 1443 1444 // Start defining this module. 1445 ActiveModule = Map.findOrCreateModule(ModuleName, ActiveModule, Framework, 1446 Explicit).first; 1447 ActiveModule->DefinitionLoc = ModuleNameLoc; 1448 if (Attrs.IsSystem || IsSystem) 1449 ActiveModule->IsSystem = true; 1450 if (Attrs.IsExternC) 1451 ActiveModule->IsExternC = true; 1452 ActiveModule->Directory = Directory; 1453 1454 bool Done = false; 1455 do { 1456 switch (Tok.Kind) { 1457 case MMToken::EndOfFile: 1458 case MMToken::RBrace: 1459 Done = true; 1460 break; 1461 1462 case MMToken::ConfigMacros: 1463 parseConfigMacros(); 1464 break; 1465 1466 case MMToken::Conflict: 1467 parseConflict(); 1468 break; 1469 1470 case MMToken::ExplicitKeyword: 1471 case MMToken::ExternKeyword: 1472 case MMToken::FrameworkKeyword: 1473 case MMToken::ModuleKeyword: 1474 parseModuleDecl(); 1475 break; 1476 1477 case MMToken::ExportKeyword: 1478 parseExportDecl(); 1479 break; 1480 1481 case MMToken::UseKeyword: 1482 parseUseDecl(); 1483 break; 1484 1485 case MMToken::RequiresKeyword: 1486 parseRequiresDecl(); 1487 break; 1488 1489 case MMToken::TextualKeyword: 1490 parseHeaderDecl(MMToken::TextualKeyword, consumeToken()); 1491 break; 1492 1493 case MMToken::UmbrellaKeyword: { 1494 SourceLocation UmbrellaLoc = consumeToken(); 1495 if (Tok.is(MMToken::HeaderKeyword)) 1496 parseHeaderDecl(MMToken::UmbrellaKeyword, UmbrellaLoc); 1497 else 1498 parseUmbrellaDirDecl(UmbrellaLoc); 1499 break; 1500 } 1501 1502 case MMToken::ExcludeKeyword: 1503 parseHeaderDecl(MMToken::ExcludeKeyword, consumeToken()); 1504 break; 1505 1506 case MMToken::PrivateKeyword: 1507 parseHeaderDecl(MMToken::PrivateKeyword, consumeToken()); 1508 break; 1509 1510 case MMToken::HeaderKeyword: 1511 parseHeaderDecl(MMToken::HeaderKeyword, consumeToken()); 1512 break; 1513 1514 case MMToken::LinkKeyword: 1515 parseLinkDecl(); 1516 break; 1517 1518 default: 1519 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_member); 1520 consumeToken(); 1521 break; 1522 } 1523 } while (!Done); 1524 1525 if (Tok.is(MMToken::RBrace)) 1526 consumeToken(); 1527 else { 1528 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_rbrace); 1529 Diags.Report(LBraceLoc, diag::note_mmap_lbrace_match); 1530 HadError = true; 1531 } 1532 1533 // If the active module is a top-level framework, and there are no link 1534 // libraries, automatically link against the framework. 1535 if (ActiveModule->IsFramework && !ActiveModule->isSubFramework() && 1536 ActiveModule->LinkLibraries.empty()) { 1537 inferFrameworkLink(ActiveModule, Directory, SourceMgr.getFileManager()); 1538 } 1539 1540 // If the module meets all requirements but is still unavailable, mark the 1541 // whole tree as unavailable to prevent it from building. 1542 if (!ActiveModule->IsAvailable && !ActiveModule->IsMissingRequirement && 1543 ActiveModule->Parent) { 1544 ActiveModule->getTopLevelModule()->markUnavailable(); 1545 ActiveModule->getTopLevelModule()->MissingHeaders.append( 1546 ActiveModule->MissingHeaders.begin(), ActiveModule->MissingHeaders.end()); 1547 } 1548 1549 // We're done parsing this module. Pop back to the previous module. 1550 ActiveModule = PreviousActiveModule; 1551 } 1552 1553 /// \brief Parse an extern module declaration. 1554 /// 1555 /// extern module-declaration: 1556 /// 'extern' 'module' module-id string-literal 1557 void ModuleMapParser::parseExternModuleDecl() { 1558 assert(Tok.is(MMToken::ExternKeyword)); 1559 SourceLocation ExternLoc = consumeToken(); // 'extern' keyword 1560 1561 // Parse 'module' keyword. 1562 if (!Tok.is(MMToken::ModuleKeyword)) { 1563 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_module); 1564 consumeToken(); 1565 HadError = true; 1566 return; 1567 } 1568 consumeToken(); // 'module' keyword 1569 1570 // Parse the module name. 1571 ModuleId Id; 1572 if (parseModuleId(Id)) { 1573 HadError = true; 1574 return; 1575 } 1576 1577 // Parse the referenced module map file name. 1578 if (!Tok.is(MMToken::StringLiteral)) { 1579 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_mmap_file); 1580 HadError = true; 1581 return; 1582 } 1583 std::string FileName = Tok.getString(); 1584 consumeToken(); // filename 1585 1586 StringRef FileNameRef = FileName; 1587 SmallString<128> ModuleMapFileName; 1588 if (llvm::sys::path::is_relative(FileNameRef)) { 1589 ModuleMapFileName += Directory->getName(); 1590 llvm::sys::path::append(ModuleMapFileName, FileName); 1591 FileNameRef = ModuleMapFileName; 1592 } 1593 if (const FileEntry *File = SourceMgr.getFileManager().getFile(FileNameRef)) 1594 Map.parseModuleMapFile( 1595 File, /*IsSystem=*/false, 1596 Map.HeaderInfo.getHeaderSearchOpts().ModuleMapFileHomeIsCwd 1597 ? Directory 1598 : File->getDir(), ExternLoc); 1599 } 1600 1601 /// Whether to add the requirement \p Feature to the module \p M. 1602 /// 1603 /// This preserves backwards compatibility for two hacks in the Darwin system 1604 /// module map files: 1605 /// 1606 /// 1. The use of 'requires excluded' to make headers non-modular, which 1607 /// should really be mapped to 'textual' now that we have this feature. We 1608 /// drop the 'excluded' requirement, and set \p IsRequiresExcludedHack to 1609 /// true. Later, this bit will be used to map all the headers inside this 1610 /// module to 'textual'. 1611 /// 1612 /// This affects Darwin.C.excluded (for assert.h) and Tcl.Private. 1613 /// 1614 /// 2. Removes a bogus cplusplus requirement from IOKit.avc. This requirement 1615 /// was never correct and causes issues now that we check it, so drop it. 1616 static bool shouldAddRequirement(Module *M, StringRef Feature, 1617 bool &IsRequiresExcludedHack) { 1618 static const StringRef DarwinCExcluded[] = {"Darwin", "C", "excluded"}; 1619 static const StringRef TclPrivate[] = {"Tcl", "Private"}; 1620 static const StringRef IOKitAVC[] = {"IOKit", "avc"}; 1621 1622 if (Feature == "excluded" && (M->fullModuleNameIs(DarwinCExcluded) || 1623 M->fullModuleNameIs(TclPrivate))) { 1624 IsRequiresExcludedHack = true; 1625 return false; 1626 } else if (Feature == "cplusplus" && M->fullModuleNameIs(IOKitAVC)) { 1627 return false; 1628 } 1629 1630 return true; 1631 } 1632 1633 /// \brief Parse a requires declaration. 1634 /// 1635 /// requires-declaration: 1636 /// 'requires' feature-list 1637 /// 1638 /// feature-list: 1639 /// feature ',' feature-list 1640 /// feature 1641 /// 1642 /// feature: 1643 /// '!'[opt] identifier 1644 void ModuleMapParser::parseRequiresDecl() { 1645 assert(Tok.is(MMToken::RequiresKeyword)); 1646 1647 // Parse 'requires' keyword. 1648 consumeToken(); 1649 1650 // Parse the feature-list. 1651 do { 1652 bool RequiredState = true; 1653 if (Tok.is(MMToken::Exclaim)) { 1654 RequiredState = false; 1655 consumeToken(); 1656 } 1657 1658 if (!Tok.is(MMToken::Identifier)) { 1659 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_feature); 1660 HadError = true; 1661 return; 1662 } 1663 1664 // Consume the feature name. 1665 std::string Feature = Tok.getString(); 1666 consumeToken(); 1667 1668 bool IsRequiresExcludedHack = false; 1669 bool ShouldAddRequirement = 1670 shouldAddRequirement(ActiveModule, Feature, IsRequiresExcludedHack); 1671 1672 if (IsRequiresExcludedHack) 1673 UsesRequiresExcludedHack.insert(ActiveModule); 1674 1675 if (ShouldAddRequirement) { 1676 // Add this feature. 1677 ActiveModule->addRequirement(Feature, RequiredState, Map.LangOpts, 1678 *Map.Target); 1679 } 1680 1681 if (!Tok.is(MMToken::Comma)) 1682 break; 1683 1684 // Consume the comma. 1685 consumeToken(); 1686 } while (true); 1687 } 1688 1689 /// \brief Append to \p Paths the set of paths needed to get to the 1690 /// subframework in which the given module lives. 1691 static void appendSubframeworkPaths(Module *Mod, 1692 SmallVectorImpl<char> &Path) { 1693 // Collect the framework names from the given module to the top-level module. 1694 SmallVector<StringRef, 2> Paths; 1695 for (; Mod; Mod = Mod->Parent) { 1696 if (Mod->IsFramework) 1697 Paths.push_back(Mod->Name); 1698 } 1699 1700 if (Paths.empty()) 1701 return; 1702 1703 // Add Frameworks/Name.framework for each subframework. 1704 for (unsigned I = Paths.size() - 1; I != 0; --I) 1705 llvm::sys::path::append(Path, "Frameworks", Paths[I-1] + ".framework"); 1706 } 1707 1708 /// \brief Parse a header declaration. 1709 /// 1710 /// header-declaration: 1711 /// 'textual'[opt] 'header' string-literal 1712 /// 'private' 'textual'[opt] 'header' string-literal 1713 /// 'exclude' 'header' string-literal 1714 /// 'umbrella' 'header' string-literal 1715 /// 1716 /// FIXME: Support 'private textual header'. 1717 void ModuleMapParser::parseHeaderDecl(MMToken::TokenKind LeadingToken, 1718 SourceLocation LeadingLoc) { 1719 // We've already consumed the first token. 1720 ModuleMap::ModuleHeaderRole Role = ModuleMap::NormalHeader; 1721 if (LeadingToken == MMToken::PrivateKeyword) { 1722 Role = ModuleMap::PrivateHeader; 1723 // 'private' may optionally be followed by 'textual'. 1724 if (Tok.is(MMToken::TextualKeyword)) { 1725 LeadingToken = Tok.Kind; 1726 consumeToken(); 1727 } 1728 } 1729 1730 if (LeadingToken == MMToken::TextualKeyword) 1731 Role = ModuleMap::ModuleHeaderRole(Role | ModuleMap::TextualHeader); 1732 1733 if (UsesRequiresExcludedHack.count(ActiveModule)) { 1734 // Mark this header 'textual' (see doc comment for 1735 // Module::UsesRequiresExcludedHack). 1736 Role = ModuleMap::ModuleHeaderRole(Role | ModuleMap::TextualHeader); 1737 } 1738 1739 if (LeadingToken != MMToken::HeaderKeyword) { 1740 if (!Tok.is(MMToken::HeaderKeyword)) { 1741 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_header) 1742 << (LeadingToken == MMToken::PrivateKeyword ? "private" : 1743 LeadingToken == MMToken::ExcludeKeyword ? "exclude" : 1744 LeadingToken == MMToken::TextualKeyword ? "textual" : "umbrella"); 1745 return; 1746 } 1747 consumeToken(); 1748 } 1749 1750 // Parse the header name. 1751 if (!Tok.is(MMToken::StringLiteral)) { 1752 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_header) 1753 << "header"; 1754 HadError = true; 1755 return; 1756 } 1757 Module::UnresolvedHeaderDirective Header; 1758 Header.FileName = Tok.getString(); 1759 Header.FileNameLoc = consumeToken(); 1760 1761 // Check whether we already have an umbrella. 1762 if (LeadingToken == MMToken::UmbrellaKeyword && ActiveModule->Umbrella) { 1763 Diags.Report(Header.FileNameLoc, diag::err_mmap_umbrella_clash) 1764 << ActiveModule->getFullModuleName(); 1765 HadError = true; 1766 return; 1767 } 1768 1769 // Look for this file. 1770 const FileEntry *File = nullptr; 1771 const FileEntry *BuiltinFile = nullptr; 1772 SmallString<128> RelativePathName; 1773 if (llvm::sys::path::is_absolute(Header.FileName)) { 1774 RelativePathName = Header.FileName; 1775 File = SourceMgr.getFileManager().getFile(RelativePathName); 1776 } else { 1777 // Search for the header file within the search directory. 1778 SmallString<128> FullPathName(Directory->getName()); 1779 unsigned FullPathLength = FullPathName.size(); 1780 1781 if (ActiveModule->isPartOfFramework()) { 1782 appendSubframeworkPaths(ActiveModule, RelativePathName); 1783 1784 // Check whether this file is in the public headers. 1785 llvm::sys::path::append(RelativePathName, "Headers", Header.FileName); 1786 llvm::sys::path::append(FullPathName, RelativePathName); 1787 File = SourceMgr.getFileManager().getFile(FullPathName); 1788 1789 if (!File) { 1790 // Check whether this file is in the private headers. 1791 // FIXME: Should we retain the subframework paths here? 1792 RelativePathName.clear(); 1793 FullPathName.resize(FullPathLength); 1794 llvm::sys::path::append(RelativePathName, "PrivateHeaders", 1795 Header.FileName); 1796 llvm::sys::path::append(FullPathName, RelativePathName); 1797 File = SourceMgr.getFileManager().getFile(FullPathName); 1798 } 1799 } else { 1800 // Lookup for normal headers. 1801 llvm::sys::path::append(RelativePathName, Header.FileName); 1802 llvm::sys::path::append(FullPathName, RelativePathName); 1803 File = SourceMgr.getFileManager().getFile(FullPathName); 1804 1805 // If this is a system module with a top-level header, this header 1806 // may have a counterpart (or replacement) in the set of headers 1807 // supplied by Clang. Find that builtin header. 1808 if (ActiveModule->IsSystem && LeadingToken != MMToken::UmbrellaKeyword && 1809 BuiltinIncludeDir && BuiltinIncludeDir != Directory && 1810 isBuiltinHeader(Header.FileName)) { 1811 SmallString<128> BuiltinPathName(BuiltinIncludeDir->getName()); 1812 llvm::sys::path::append(BuiltinPathName, Header.FileName); 1813 BuiltinFile = SourceMgr.getFileManager().getFile(BuiltinPathName); 1814 1815 // If Clang supplies this header but the underlying system does not, 1816 // just silently swap in our builtin version. Otherwise, we'll end 1817 // up adding both (later). 1818 // 1819 // For local visibility, entirely replace the system file with our 1820 // one and textually include the system one. We need to pass macros 1821 // from our header to the system one if we #include_next it. 1822 // 1823 // FIXME: Can we do this in all cases? 1824 if (BuiltinFile && (!File || Map.LangOpts.ModulesLocalVisibility)) { 1825 File = BuiltinFile; 1826 RelativePathName = BuiltinPathName; 1827 BuiltinFile = nullptr; 1828 } 1829 } 1830 } 1831 } 1832 1833 // FIXME: We shouldn't be eagerly stat'ing every file named in a module map. 1834 // Come up with a lazy way to do this. 1835 if (File) { 1836 if (LeadingToken == MMToken::UmbrellaKeyword) { 1837 const DirectoryEntry *UmbrellaDir = File->getDir(); 1838 if (Module *UmbrellaModule = Map.UmbrellaDirs[UmbrellaDir]) { 1839 Diags.Report(LeadingLoc, diag::err_mmap_umbrella_clash) 1840 << UmbrellaModule->getFullModuleName(); 1841 HadError = true; 1842 } else { 1843 // Record this umbrella header. 1844 Map.setUmbrellaHeader(ActiveModule, File, RelativePathName.str()); 1845 } 1846 } else if (LeadingToken == MMToken::ExcludeKeyword) { 1847 Module::Header H = {RelativePathName.str(), File}; 1848 Map.excludeHeader(ActiveModule, H); 1849 } else { 1850 // If there is a builtin counterpart to this file, add it now, before 1851 // the "real" header, so we build the built-in one first when building 1852 // the module. 1853 if (BuiltinFile) { 1854 // FIXME: Taking the name from the FileEntry is unstable and can give 1855 // different results depending on how we've previously named that file 1856 // in this build. 1857 Module::Header H = { BuiltinFile->getName(), BuiltinFile }; 1858 Map.addHeader(ActiveModule, H, Role); 1859 } 1860 1861 // Record this header. 1862 Module::Header H = { RelativePathName.str(), File }; 1863 Map.addHeader(ActiveModule, H, Role); 1864 } 1865 } else if (LeadingToken != MMToken::ExcludeKeyword) { 1866 // Ignore excluded header files. They're optional anyway. 1867 1868 // If we find a module that has a missing header, we mark this module as 1869 // unavailable and store the header directive for displaying diagnostics. 1870 Header.IsUmbrella = LeadingToken == MMToken::UmbrellaKeyword; 1871 ActiveModule->markUnavailable(); 1872 ActiveModule->MissingHeaders.push_back(Header); 1873 } 1874 } 1875 1876 static int compareModuleHeaders(const Module::Header *A, 1877 const Module::Header *B) { 1878 return A->NameAsWritten.compare(B->NameAsWritten); 1879 } 1880 1881 /// \brief Parse an umbrella directory declaration. 1882 /// 1883 /// umbrella-dir-declaration: 1884 /// umbrella string-literal 1885 void ModuleMapParser::parseUmbrellaDirDecl(SourceLocation UmbrellaLoc) { 1886 // Parse the directory name. 1887 if (!Tok.is(MMToken::StringLiteral)) { 1888 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_header) 1889 << "umbrella"; 1890 HadError = true; 1891 return; 1892 } 1893 1894 std::string DirName = Tok.getString(); 1895 SourceLocation DirNameLoc = consumeToken(); 1896 1897 // Check whether we already have an umbrella. 1898 if (ActiveModule->Umbrella) { 1899 Diags.Report(DirNameLoc, diag::err_mmap_umbrella_clash) 1900 << ActiveModule->getFullModuleName(); 1901 HadError = true; 1902 return; 1903 } 1904 1905 // Look for this file. 1906 const DirectoryEntry *Dir = nullptr; 1907 if (llvm::sys::path::is_absolute(DirName)) 1908 Dir = SourceMgr.getFileManager().getDirectory(DirName); 1909 else { 1910 SmallString<128> PathName; 1911 PathName = Directory->getName(); 1912 llvm::sys::path::append(PathName, DirName); 1913 Dir = SourceMgr.getFileManager().getDirectory(PathName); 1914 } 1915 1916 if (!Dir) { 1917 Diags.Report(DirNameLoc, diag::err_mmap_umbrella_dir_not_found) 1918 << DirName; 1919 HadError = true; 1920 return; 1921 } 1922 1923 if (UsesRequiresExcludedHack.count(ActiveModule)) { 1924 // Mark this header 'textual' (see doc comment for 1925 // ModuleMapParser::UsesRequiresExcludedHack). Although iterating over the 1926 // directory is relatively expensive, in practice this only applies to the 1927 // uncommonly used Tcl module on Darwin platforms. 1928 std::error_code EC; 1929 SmallVector<Module::Header, 6> Headers; 1930 for (llvm::sys::fs::recursive_directory_iterator I(Dir->getName(), EC), E; 1931 I != E && !EC; I.increment(EC)) { 1932 if (const FileEntry *FE = SourceMgr.getFileManager().getFile(I->path())) { 1933 1934 Module::Header Header = {I->path(), FE}; 1935 Headers.push_back(std::move(Header)); 1936 } 1937 } 1938 1939 // Sort header paths so that the pcm doesn't depend on iteration order. 1940 llvm::array_pod_sort(Headers.begin(), Headers.end(), compareModuleHeaders); 1941 1942 for (auto &Header : Headers) 1943 Map.addHeader(ActiveModule, std::move(Header), ModuleMap::TextualHeader); 1944 return; 1945 } 1946 1947 if (Module *OwningModule = Map.UmbrellaDirs[Dir]) { 1948 Diags.Report(UmbrellaLoc, diag::err_mmap_umbrella_clash) 1949 << OwningModule->getFullModuleName(); 1950 HadError = true; 1951 return; 1952 } 1953 1954 // Record this umbrella directory. 1955 Map.setUmbrellaDir(ActiveModule, Dir, DirName); 1956 } 1957 1958 /// \brief Parse a module export declaration. 1959 /// 1960 /// export-declaration: 1961 /// 'export' wildcard-module-id 1962 /// 1963 /// wildcard-module-id: 1964 /// identifier 1965 /// '*' 1966 /// identifier '.' wildcard-module-id 1967 void ModuleMapParser::parseExportDecl() { 1968 assert(Tok.is(MMToken::ExportKeyword)); 1969 SourceLocation ExportLoc = consumeToken(); 1970 1971 // Parse the module-id with an optional wildcard at the end. 1972 ModuleId ParsedModuleId; 1973 bool Wildcard = false; 1974 do { 1975 // FIXME: Support string-literal module names here. 1976 if (Tok.is(MMToken::Identifier)) { 1977 ParsedModuleId.push_back(std::make_pair(Tok.getString(), 1978 Tok.getLocation())); 1979 consumeToken(); 1980 1981 if (Tok.is(MMToken::Period)) { 1982 consumeToken(); 1983 continue; 1984 } 1985 1986 break; 1987 } 1988 1989 if(Tok.is(MMToken::Star)) { 1990 Wildcard = true; 1991 consumeToken(); 1992 break; 1993 } 1994 1995 Diags.Report(Tok.getLocation(), diag::err_mmap_module_id); 1996 HadError = true; 1997 return; 1998 } while (true); 1999 2000 Module::UnresolvedExportDecl Unresolved = { 2001 ExportLoc, ParsedModuleId, Wildcard 2002 }; 2003 ActiveModule->UnresolvedExports.push_back(Unresolved); 2004 } 2005 2006 /// \brief Parse a module use declaration. 2007 /// 2008 /// use-declaration: 2009 /// 'use' wildcard-module-id 2010 void ModuleMapParser::parseUseDecl() { 2011 assert(Tok.is(MMToken::UseKeyword)); 2012 auto KWLoc = consumeToken(); 2013 // Parse the module-id. 2014 ModuleId ParsedModuleId; 2015 parseModuleId(ParsedModuleId); 2016 2017 if (ActiveModule->Parent) 2018 Diags.Report(KWLoc, diag::err_mmap_use_decl_submodule); 2019 else 2020 ActiveModule->UnresolvedDirectUses.push_back(ParsedModuleId); 2021 } 2022 2023 /// \brief Parse a link declaration. 2024 /// 2025 /// module-declaration: 2026 /// 'link' 'framework'[opt] string-literal 2027 void ModuleMapParser::parseLinkDecl() { 2028 assert(Tok.is(MMToken::LinkKeyword)); 2029 SourceLocation LinkLoc = consumeToken(); 2030 2031 // Parse the optional 'framework' keyword. 2032 bool IsFramework = false; 2033 if (Tok.is(MMToken::FrameworkKeyword)) { 2034 consumeToken(); 2035 IsFramework = true; 2036 } 2037 2038 // Parse the library name 2039 if (!Tok.is(MMToken::StringLiteral)) { 2040 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_library_name) 2041 << IsFramework << SourceRange(LinkLoc); 2042 HadError = true; 2043 return; 2044 } 2045 2046 std::string LibraryName = Tok.getString(); 2047 consumeToken(); 2048 ActiveModule->LinkLibraries.push_back(Module::LinkLibrary(LibraryName, 2049 IsFramework)); 2050 } 2051 2052 /// \brief Parse a configuration macro declaration. 2053 /// 2054 /// module-declaration: 2055 /// 'config_macros' attributes[opt] config-macro-list? 2056 /// 2057 /// config-macro-list: 2058 /// identifier (',' identifier)? 2059 void ModuleMapParser::parseConfigMacros() { 2060 assert(Tok.is(MMToken::ConfigMacros)); 2061 SourceLocation ConfigMacrosLoc = consumeToken(); 2062 2063 // Only top-level modules can have configuration macros. 2064 if (ActiveModule->Parent) { 2065 Diags.Report(ConfigMacrosLoc, diag::err_mmap_config_macro_submodule); 2066 } 2067 2068 // Parse the optional attributes. 2069 Attributes Attrs; 2070 if (parseOptionalAttributes(Attrs)) 2071 return; 2072 2073 if (Attrs.IsExhaustive && !ActiveModule->Parent) { 2074 ActiveModule->ConfigMacrosExhaustive = true; 2075 } 2076 2077 // If we don't have an identifier, we're done. 2078 // FIXME: Support macros with the same name as a keyword here. 2079 if (!Tok.is(MMToken::Identifier)) 2080 return; 2081 2082 // Consume the first identifier. 2083 if (!ActiveModule->Parent) { 2084 ActiveModule->ConfigMacros.push_back(Tok.getString().str()); 2085 } 2086 consumeToken(); 2087 2088 do { 2089 // If there's a comma, consume it. 2090 if (!Tok.is(MMToken::Comma)) 2091 break; 2092 consumeToken(); 2093 2094 // We expect to see a macro name here. 2095 // FIXME: Support macros with the same name as a keyword here. 2096 if (!Tok.is(MMToken::Identifier)) { 2097 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_config_macro); 2098 break; 2099 } 2100 2101 // Consume the macro name. 2102 if (!ActiveModule->Parent) { 2103 ActiveModule->ConfigMacros.push_back(Tok.getString().str()); 2104 } 2105 consumeToken(); 2106 } while (true); 2107 } 2108 2109 /// \brief Format a module-id into a string. 2110 static std::string formatModuleId(const ModuleId &Id) { 2111 std::string result; 2112 { 2113 llvm::raw_string_ostream OS(result); 2114 2115 for (unsigned I = 0, N = Id.size(); I != N; ++I) { 2116 if (I) 2117 OS << "."; 2118 OS << Id[I].first; 2119 } 2120 } 2121 2122 return result; 2123 } 2124 2125 /// \brief Parse a conflict declaration. 2126 /// 2127 /// module-declaration: 2128 /// 'conflict' module-id ',' string-literal 2129 void ModuleMapParser::parseConflict() { 2130 assert(Tok.is(MMToken::Conflict)); 2131 SourceLocation ConflictLoc = consumeToken(); 2132 Module::UnresolvedConflict Conflict; 2133 2134 // Parse the module-id. 2135 if (parseModuleId(Conflict.Id)) 2136 return; 2137 2138 // Parse the ','. 2139 if (!Tok.is(MMToken::Comma)) { 2140 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_conflicts_comma) 2141 << SourceRange(ConflictLoc); 2142 return; 2143 } 2144 consumeToken(); 2145 2146 // Parse the message. 2147 if (!Tok.is(MMToken::StringLiteral)) { 2148 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_conflicts_message) 2149 << formatModuleId(Conflict.Id); 2150 return; 2151 } 2152 Conflict.Message = Tok.getString().str(); 2153 consumeToken(); 2154 2155 // Add this unresolved conflict. 2156 ActiveModule->UnresolvedConflicts.push_back(Conflict); 2157 } 2158 2159 /// \brief Parse an inferred module declaration (wildcard modules). 2160 /// 2161 /// module-declaration: 2162 /// 'explicit'[opt] 'framework'[opt] 'module' * attributes[opt] 2163 /// { inferred-module-member* } 2164 /// 2165 /// inferred-module-member: 2166 /// 'export' '*' 2167 /// 'exclude' identifier 2168 void ModuleMapParser::parseInferredModuleDecl(bool Framework, bool Explicit) { 2169 assert(Tok.is(MMToken::Star)); 2170 SourceLocation StarLoc = consumeToken(); 2171 bool Failed = false; 2172 2173 // Inferred modules must be submodules. 2174 if (!ActiveModule && !Framework) { 2175 Diags.Report(StarLoc, diag::err_mmap_top_level_inferred_submodule); 2176 Failed = true; 2177 } 2178 2179 if (ActiveModule) { 2180 // Inferred modules must have umbrella directories. 2181 if (!Failed && ActiveModule->IsAvailable && 2182 !ActiveModule->getUmbrellaDir()) { 2183 Diags.Report(StarLoc, diag::err_mmap_inferred_no_umbrella); 2184 Failed = true; 2185 } 2186 2187 // Check for redefinition of an inferred module. 2188 if (!Failed && ActiveModule->InferSubmodules) { 2189 Diags.Report(StarLoc, diag::err_mmap_inferred_redef); 2190 if (ActiveModule->InferredSubmoduleLoc.isValid()) 2191 Diags.Report(ActiveModule->InferredSubmoduleLoc, 2192 diag::note_mmap_prev_definition); 2193 Failed = true; 2194 } 2195 2196 // Check for the 'framework' keyword, which is not permitted here. 2197 if (Framework) { 2198 Diags.Report(StarLoc, diag::err_mmap_inferred_framework_submodule); 2199 Framework = false; 2200 } 2201 } else if (Explicit) { 2202 Diags.Report(StarLoc, diag::err_mmap_explicit_inferred_framework); 2203 Explicit = false; 2204 } 2205 2206 // If there were any problems with this inferred submodule, skip its body. 2207 if (Failed) { 2208 if (Tok.is(MMToken::LBrace)) { 2209 consumeToken(); 2210 skipUntil(MMToken::RBrace); 2211 if (Tok.is(MMToken::RBrace)) 2212 consumeToken(); 2213 } 2214 HadError = true; 2215 return; 2216 } 2217 2218 // Parse optional attributes. 2219 Attributes Attrs; 2220 if (parseOptionalAttributes(Attrs)) 2221 return; 2222 2223 if (ActiveModule) { 2224 // Note that we have an inferred submodule. 2225 ActiveModule->InferSubmodules = true; 2226 ActiveModule->InferredSubmoduleLoc = StarLoc; 2227 ActiveModule->InferExplicitSubmodules = Explicit; 2228 } else { 2229 // We'll be inferring framework modules for this directory. 2230 Map.InferredDirectories[Directory].InferModules = true; 2231 Map.InferredDirectories[Directory].Attrs = Attrs; 2232 Map.InferredDirectories[Directory].ModuleMapFile = ModuleMapFile; 2233 // FIXME: Handle the 'framework' keyword. 2234 } 2235 2236 // Parse the opening brace. 2237 if (!Tok.is(MMToken::LBrace)) { 2238 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_lbrace_wildcard); 2239 HadError = true; 2240 return; 2241 } 2242 SourceLocation LBraceLoc = consumeToken(); 2243 2244 // Parse the body of the inferred submodule. 2245 bool Done = false; 2246 do { 2247 switch (Tok.Kind) { 2248 case MMToken::EndOfFile: 2249 case MMToken::RBrace: 2250 Done = true; 2251 break; 2252 2253 case MMToken::ExcludeKeyword: { 2254 if (ActiveModule) { 2255 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_inferred_member) 2256 << (ActiveModule != nullptr); 2257 consumeToken(); 2258 break; 2259 } 2260 2261 consumeToken(); 2262 // FIXME: Support string-literal module names here. 2263 if (!Tok.is(MMToken::Identifier)) { 2264 Diags.Report(Tok.getLocation(), diag::err_mmap_missing_exclude_name); 2265 break; 2266 } 2267 2268 Map.InferredDirectories[Directory].ExcludedModules 2269 .push_back(Tok.getString()); 2270 consumeToken(); 2271 break; 2272 } 2273 2274 case MMToken::ExportKeyword: 2275 if (!ActiveModule) { 2276 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_inferred_member) 2277 << (ActiveModule != nullptr); 2278 consumeToken(); 2279 break; 2280 } 2281 2282 consumeToken(); 2283 if (Tok.is(MMToken::Star)) 2284 ActiveModule->InferExportWildcard = true; 2285 else 2286 Diags.Report(Tok.getLocation(), 2287 diag::err_mmap_expected_export_wildcard); 2288 consumeToken(); 2289 break; 2290 2291 case MMToken::ExplicitKeyword: 2292 case MMToken::ModuleKeyword: 2293 case MMToken::HeaderKeyword: 2294 case MMToken::PrivateKeyword: 2295 case MMToken::UmbrellaKeyword: 2296 default: 2297 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_inferred_member) 2298 << (ActiveModule != nullptr); 2299 consumeToken(); 2300 break; 2301 } 2302 } while (!Done); 2303 2304 if (Tok.is(MMToken::RBrace)) 2305 consumeToken(); 2306 else { 2307 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_rbrace); 2308 Diags.Report(LBraceLoc, diag::note_mmap_lbrace_match); 2309 HadError = true; 2310 } 2311 } 2312 2313 /// \brief Parse optional attributes. 2314 /// 2315 /// attributes: 2316 /// attribute attributes 2317 /// attribute 2318 /// 2319 /// attribute: 2320 /// [ identifier ] 2321 /// 2322 /// \param Attrs Will be filled in with the parsed attributes. 2323 /// 2324 /// \returns true if an error occurred, false otherwise. 2325 bool ModuleMapParser::parseOptionalAttributes(Attributes &Attrs) { 2326 bool HadError = false; 2327 2328 while (Tok.is(MMToken::LSquare)) { 2329 // Consume the '['. 2330 SourceLocation LSquareLoc = consumeToken(); 2331 2332 // Check whether we have an attribute name here. 2333 if (!Tok.is(MMToken::Identifier)) { 2334 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_attribute); 2335 skipUntil(MMToken::RSquare); 2336 if (Tok.is(MMToken::RSquare)) 2337 consumeToken(); 2338 HadError = true; 2339 } 2340 2341 // Decode the attribute name. 2342 AttributeKind Attribute 2343 = llvm::StringSwitch<AttributeKind>(Tok.getString()) 2344 .Case("exhaustive", AT_exhaustive) 2345 .Case("extern_c", AT_extern_c) 2346 .Case("system", AT_system) 2347 .Default(AT_unknown); 2348 switch (Attribute) { 2349 case AT_unknown: 2350 Diags.Report(Tok.getLocation(), diag::warn_mmap_unknown_attribute) 2351 << Tok.getString(); 2352 break; 2353 2354 case AT_system: 2355 Attrs.IsSystem = true; 2356 break; 2357 2358 case AT_extern_c: 2359 Attrs.IsExternC = true; 2360 break; 2361 2362 case AT_exhaustive: 2363 Attrs.IsExhaustive = true; 2364 break; 2365 } 2366 consumeToken(); 2367 2368 // Consume the ']'. 2369 if (!Tok.is(MMToken::RSquare)) { 2370 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_rsquare); 2371 Diags.Report(LSquareLoc, diag::note_mmap_lsquare_match); 2372 skipUntil(MMToken::RSquare); 2373 HadError = true; 2374 } 2375 2376 if (Tok.is(MMToken::RSquare)) 2377 consumeToken(); 2378 } 2379 2380 return HadError; 2381 } 2382 2383 /// \brief Parse a module map file. 2384 /// 2385 /// module-map-file: 2386 /// module-declaration* 2387 bool ModuleMapParser::parseModuleMapFile() { 2388 do { 2389 switch (Tok.Kind) { 2390 case MMToken::EndOfFile: 2391 return HadError; 2392 2393 case MMToken::ExplicitKeyword: 2394 case MMToken::ExternKeyword: 2395 case MMToken::ModuleKeyword: 2396 case MMToken::FrameworkKeyword: 2397 parseModuleDecl(); 2398 break; 2399 2400 case MMToken::Comma: 2401 case MMToken::ConfigMacros: 2402 case MMToken::Conflict: 2403 case MMToken::Exclaim: 2404 case MMToken::ExcludeKeyword: 2405 case MMToken::ExportKeyword: 2406 case MMToken::HeaderKeyword: 2407 case MMToken::Identifier: 2408 case MMToken::LBrace: 2409 case MMToken::LinkKeyword: 2410 case MMToken::LSquare: 2411 case MMToken::Period: 2412 case MMToken::PrivateKeyword: 2413 case MMToken::RBrace: 2414 case MMToken::RSquare: 2415 case MMToken::RequiresKeyword: 2416 case MMToken::Star: 2417 case MMToken::StringLiteral: 2418 case MMToken::TextualKeyword: 2419 case MMToken::UmbrellaKeyword: 2420 case MMToken::UseKeyword: 2421 Diags.Report(Tok.getLocation(), diag::err_mmap_expected_module); 2422 HadError = true; 2423 consumeToken(); 2424 break; 2425 } 2426 } while (true); 2427 } 2428 2429 bool ModuleMap::parseModuleMapFile(const FileEntry *File, bool IsSystem, 2430 const DirectoryEntry *Dir, 2431 SourceLocation ExternModuleLoc) { 2432 llvm::DenseMap<const FileEntry *, bool>::iterator Known 2433 = ParsedModuleMap.find(File); 2434 if (Known != ParsedModuleMap.end()) 2435 return Known->second; 2436 2437 assert(Target && "Missing target information"); 2438 auto FileCharacter = IsSystem ? SrcMgr::C_System : SrcMgr::C_User; 2439 FileID ID = SourceMgr.createFileID(File, ExternModuleLoc, FileCharacter); 2440 const llvm::MemoryBuffer *Buffer = SourceMgr.getBuffer(ID); 2441 if (!Buffer) 2442 return ParsedModuleMap[File] = true; 2443 2444 // Parse this module map file. 2445 Lexer L(ID, SourceMgr.getBuffer(ID), SourceMgr, MMapLangOpts); 2446 SourceLocation Start = L.getSourceLocation(); 2447 ModuleMapParser Parser(L, SourceMgr, Target, Diags, *this, File, Dir, 2448 BuiltinIncludeDir, IsSystem); 2449 bool Result = Parser.parseModuleMapFile(); 2450 ParsedModuleMap[File] = Result; 2451 2452 // Notify callbacks that we parsed it. 2453 for (const auto &Cb : Callbacks) 2454 Cb->moduleMapFileRead(Start, *File, IsSystem); 2455 return Result; 2456 } 2457