diff options
author | Richard Smith <richard-llvm@metafoo.co.uk> | 2014-12-10 03:09:48 +0000 |
---|---|---|
committer | Richard Smith <richard-llvm@metafoo.co.uk> | 2014-12-10 03:09:48 +0000 |
commit | 9acb99e342376c6269fb70d1e9665c2790b93b12 (patch) | |
tree | 62e72141d8eb9828e0cb78f3eff7e4309fdf2060 /clang/lib/Lex/HeaderSearch.cpp | |
parent | 49475327fffdfb4cde572b5955d7d94d801d84bf (diff) | |
download | llvm-9acb99e342376c6269fb70d1e9665c2790b93b12.zip llvm-9acb99e342376c6269fb70d1e9665c2790b93b12.tar.gz llvm-9acb99e342376c6269fb70d1e9665c2790b93b12.tar.bz2 |
Reinstate r223753, reverted in r223759 due to breakage of clang-tools-extra.
Original commit message:
[modules] Add experimental -fmodule-map-file-home-is-cwd flag to -cc1.
For files named by -fmodule-map-file=, and files found by 'extern module'
directives, this flag specifies that we should resolve filenames relative to
the current working directory rather than relative to the directory in which
the module map file resides. This is aimed at fixing path handling, in
particular for relative -I paths, when building modules that represent
components of the current project (rather than libraries installed on the
current system, which the current project has as dependencies, where we'd
typically expect the module map files to be looked up implicitly).
llvm-svn: 223913
Diffstat (limited to 'clang/lib/Lex/HeaderSearch.cpp')
-rw-r--r-- | clang/lib/Lex/HeaderSearch.cpp | 40 |
1 files changed, 29 insertions, 11 deletions
diff --git a/clang/lib/Lex/HeaderSearch.cpp b/clang/lib/Lex/HeaderSearch.cpp index a3f3737..02fd87c 100644 --- a/clang/lib/Lex/HeaderSearch.cpp +++ b/clang/lib/Lex/HeaderSearch.cpp @@ -1113,11 +1113,10 @@ HeaderSearch::findModuleForHeader(const FileEntry *File) const { return ModMap.findModuleForHeader(File); } -static const FileEntry *getPrivateModuleMap(StringRef ModuleMapPath, - const DirectoryEntry *Directory, +static const FileEntry *getPrivateModuleMap(const FileEntry *File, FileManager &FileMgr) { - StringRef Filename = llvm::sys::path::filename(ModuleMapPath); - SmallString<128> PrivateFilename(Directory->getName()); + StringRef Filename = llvm::sys::path::filename(File->getName()); + SmallString<128> PrivateFilename(File->getDir()->getName()); if (Filename == "module.map") llvm::sys::path::append(PrivateFilename, "module_private.map"); else if (Filename == "module.modulemap") @@ -1128,7 +1127,25 @@ static const FileEntry *getPrivateModuleMap(StringRef ModuleMapPath, } bool HeaderSearch::loadModuleMapFile(const FileEntry *File, bool IsSystem) { - switch (loadModuleMapFileImpl(File, IsSystem)) { + // Find the directory for the module. For frameworks, that may require going + // up from the 'Modules' directory. + const DirectoryEntry *Dir = nullptr; + if (getHeaderSearchOpts().ModuleMapFileHomeIsCwd) + Dir = FileMgr.getDirectory("."); + else { + Dir = File->getDir(); + StringRef DirName(Dir->getName()); + if (llvm::sys::path::filename(DirName) == "Modules") { + DirName = llvm::sys::path::parent_path(DirName); + if (DirName.endswith(".framework")) + Dir = FileMgr.getDirectory(DirName); + // FIXME: This assert can fail if there's a race between the above check + // and the removal of the directory. + assert(Dir && "parent must exist"); + } + } + + switch (loadModuleMapFileImpl(File, IsSystem, Dir)) { case LMM_AlreadyLoaded: case LMM_NewlyLoaded: return false; @@ -1140,7 +1157,8 @@ bool HeaderSearch::loadModuleMapFile(const FileEntry *File, bool IsSystem) { } HeaderSearch::LoadModuleMapResult -HeaderSearch::loadModuleMapFileImpl(const FileEntry *File, bool IsSystem) { +HeaderSearch::loadModuleMapFileImpl(const FileEntry *File, bool IsSystem, + const DirectoryEntry *Dir) { assert(File && "expected FileEntry"); // Check whether we've already loaded this module map, and mark it as being @@ -1149,15 +1167,14 @@ HeaderSearch::loadModuleMapFileImpl(const FileEntry *File, bool IsSystem) { if (!AddResult.second) return AddResult.first->second ? LMM_AlreadyLoaded : LMM_InvalidModuleMap; - if (ModMap.parseModuleMapFile(File, IsSystem)) { + if (ModMap.parseModuleMapFile(File, IsSystem, Dir)) { LoadedModuleMaps[File] = false; return LMM_InvalidModuleMap; } // Try to load a corresponding private module map. - if (const FileEntry *PMMFile = - getPrivateModuleMap(File->getName(), File->getDir(), FileMgr)) { - if (ModMap.parseModuleMapFile(PMMFile, IsSystem)) { + if (const FileEntry *PMMFile = getPrivateModuleMap(File, FileMgr)) { + if (ModMap.parseModuleMapFile(PMMFile, IsSystem, Dir)) { LoadedModuleMaps[File] = false; return LMM_InvalidModuleMap; } @@ -1231,7 +1248,8 @@ HeaderSearch::loadModuleMapFile(const DirectoryEntry *Dir, bool IsSystem, return KnownDir->second ? LMM_AlreadyLoaded : LMM_InvalidModuleMap; if (const FileEntry *ModuleMapFile = lookupModuleMapFile(Dir, IsFramework)) { - LoadModuleMapResult Result = loadModuleMapFileImpl(ModuleMapFile, IsSystem); + LoadModuleMapResult Result = + loadModuleMapFileImpl(ModuleMapFile, IsSystem, Dir); // Add Dir explicitly in case ModuleMapFile is in a subdirectory. // E.g. Foo.framework/Modules/module.modulemap // ^Dir ^ModuleMapFile |