[clang] Update code that assumes FileEntry::getName is absolute NFC

It's an accident that we started return asbolute paths from
FileEntry::getName for all relative paths. Prepare for getName to get
(closer to) return the requested path. Note: conceptually it might make
sense for the dependency scanner to allow relative paths and have the
DependencyConsumer decide if it wants to make them absolute, but we
currently document that it's absolute and I didn't want to change
behaviour here.

Differential Revision: https://reviews.llvm.org/D130934
This commit is contained in:
Ben Langmuir 2022-08-01 13:18:31 -07:00
parent 69cc240534
commit b4c6dc2e66
4 changed files with 47 additions and 17 deletions

View File

@ -156,11 +156,15 @@ groupReplacements(const TUReplacements &TUs, const TUDiagnostics &TUDs,
const tooling::TranslationUnitDiagnostics *SourceTU,
const llvm::Optional<std::string> BuildDir) {
// Use the file manager to deduplicate paths. FileEntries are
// automatically canonicalized.
auto PrevWorkingDir = SM.getFileManager().getFileSystemOpts().WorkingDir;
// automatically canonicalized. Since relative paths can come from different
// build directories, make them absolute immediately.
SmallString<128> Path = R.getFilePath();
if (BuildDir)
SM.getFileManager().getFileSystemOpts().WorkingDir = std::move(*BuildDir);
if (auto Entry = SM.getFileManager().getFile(R.getFilePath())) {
llvm::sys::fs::make_absolute(*BuildDir, Path);
else
SM.getFileManager().makeAbsolutePath(Path);
if (auto Entry = SM.getFileManager().getFile(Path)) {
if (SourceTU) {
auto &Replaces = DiagReplacements[*Entry];
auto It = Replaces.find(R);
@ -171,11 +175,10 @@ groupReplacements(const TUReplacements &TUs, const TUDiagnostics &TUDs,
return;
}
GroupedReplacements[*Entry].push_back(R);
} else if (Warned.insert(R.getFilePath()).second) {
} else if (Warned.insert(Path).second) {
errs() << "Described file '" << R.getFilePath()
<< "' doesn't exist. Ignoring...\n";
}
SM.getFileManager().getFileSystemOpts().WorkingDir = PrevWorkingDir;
};
for (const auto &TU : TUs)

View File

@ -233,6 +233,11 @@ private:
/// Checks whether the module is known as being prebuilt.
bool isPrebuiltModule(const Module *M);
/// Adds \p Path to \c FileDeps, making it absolute if necessary.
void addFileDep(StringRef Path);
/// Adds \p Path to \c MD.FileDeps, making it absolute if necessary.
void addFileDep(ModuleDeps &MD, StringRef Path);
/// Constructs a CompilerInvocation that can be used to build the given
/// module, excluding paths to discovered modular dependencies that are yet to
/// be built.

View File

@ -28,8 +28,9 @@ namespace {
class DependencyConsumerForwarder : public DependencyFileGenerator {
public:
DependencyConsumerForwarder(std::unique_ptr<DependencyOutputOptions> Opts,
DependencyConsumer &C)
: DependencyFileGenerator(*Opts), Opts(std::move(Opts)), C(C) {}
StringRef WorkingDirectory, DependencyConsumer &C)
: DependencyFileGenerator(*Opts), WorkingDirectory(WorkingDirectory),
Opts(std::move(Opts)), C(C) {}
void finishedMainFile(DiagnosticsEngine &Diags) override {
C.handleDependencyOutputOpts(*Opts);
@ -37,11 +38,13 @@ public:
for (const auto &File : getDependencies()) {
CanonPath = File;
llvm::sys::path::remove_dots(CanonPath, /*remove_dot_dot=*/true);
llvm::sys::fs::make_absolute(WorkingDirectory, CanonPath);
C.handleFileDependency(CanonPath);
}
}
private:
StringRef WorkingDirectory;
std::unique_ptr<DependencyOutputOptions> Opts;
DependencyConsumer &C;
};
@ -221,8 +224,8 @@ public:
switch (Format) {
case ScanningOutputFormat::Make:
ScanInstance.addDependencyCollector(
std::make_shared<DependencyConsumerForwarder>(std::move(Opts),
Consumer));
std::make_shared<DependencyConsumerForwarder>(
std::move(Opts), WorkingDirectory, Consumer));
break;
case ScanningOutputFormat::Full:
ScanInstance.addDependencyCollector(std::make_shared<ModuleDepCollector>(

View File

@ -240,8 +240,7 @@ void ModuleDepCollectorPP::FileChanged(SourceLocation Loc,
// We do not want #line markers to affect dependency generation!
if (Optional<StringRef> Filename =
SM.getNonBuiltinFilenameForID(SM.getFileID(SM.getExpansionLoc(Loc))))
MDC.FileDeps.push_back(
std::string(llvm::sys::path::remove_leading_dotslash(*Filename)));
MDC.addFileDep(llvm::sys::path::remove_leading_dotslash(*Filename));
}
void ModuleDepCollectorPP::InclusionDirective(
@ -252,7 +251,7 @@ void ModuleDepCollectorPP::InclusionDirective(
if (!File && !Imported) {
// This is a non-modular include that HeaderSearch failed to find. Add it
// here as `FileChanged` will never see it.
MDC.FileDeps.push_back(std::string(FileName));
MDC.addFileDep(FileName);
}
handleImport(Imported);
}
@ -282,8 +281,7 @@ void ModuleDepCollectorPP::EndOfMainFile() {
->getName());
if (!MDC.ScanInstance.getPreprocessorOpts().ImplicitPCHInclude.empty())
MDC.FileDeps.push_back(
MDC.ScanInstance.getPreprocessorOpts().ImplicitPCHInclude);
MDC.addFileDep(MDC.ScanInstance.getPreprocessorOpts().ImplicitPCHInclude);
for (const Module *M : DirectModularDeps) {
// A top-level module might not be actually imported as a module when
@ -346,10 +344,10 @@ ModuleID ModuleDepCollectorPP::handleTopLevelModule(const Module *M) {
// handle it like normal. With explicitly built modules we don't need
// to play VFS tricks, so replace it with the correct module map.
if (IF.getFile()->getName().endswith("__inferred_module.map")) {
MD.FileDeps.insert(ModuleMap->getName());
MDC.addFileDep(MD, ModuleMap->getName());
return;
}
MD.FileDeps.insert(IF.getFile()->getName());
MDC.addFileDep(MD, IF.getFile()->getName());
});
// We usually don't need to list the module map files of our dependencies when
@ -494,3 +492,24 @@ bool ModuleDepCollector::isPrebuiltModule(const Module *M) {
PrebuiltModuleFileIt->second == M->getASTFile()->getName());
return true;
}
static StringRef makeAbsolute(CompilerInstance &CI, StringRef Path,
SmallVectorImpl<char> &Storage) {
if (llvm::sys::path::is_absolute(Path))
return Path;
Storage.assign(Path.begin(), Path.end());
CI.getFileManager().makeAbsolutePath(Storage);
return StringRef(Storage.data(), Storage.size());
}
void ModuleDepCollector::addFileDep(StringRef Path) {
llvm::SmallString<256> Storage;
Path = makeAbsolute(ScanInstance, Path, Storage);
FileDeps.push_back(std::string(Path));
}
void ModuleDepCollector::addFileDep(ModuleDeps &MD, StringRef Path) {
llvm::SmallString<256> Storage;
Path = makeAbsolute(ScanInstance, Path, Storage);
MD.FileDeps.insert(Path);
}