summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--clang/include/clang/Basic/FileManager.h29
-rw-r--r--clang/lib/Basic/FileManager.cpp11
-rw-r--r--clang/lib/Frontend/CompilerInstance.cpp2
-rw-r--r--clang/lib/Lex/HeaderMap.cpp4
-rw-r--r--clang/lib/Lex/HeaderSearch.cpp18
-rw-r--r--llvm/include/llvm/Support/Error.h14
6 files changed, 50 insertions, 28 deletions
diff --git a/clang/include/clang/Basic/FileManager.h b/clang/include/clang/Basic/FileManager.h
index b22afec54e4..9e54669efc5 100644
--- a/clang/include/clang/Basic/FileManager.h
+++ b/clang/include/clang/Basic/FileManager.h
@@ -110,26 +110,27 @@ public:
/// accessed by the FileManager's client.
class FileEntryRef {
public:
+ FileEntryRef() = delete;
FileEntryRef(StringRef Name, const FileEntry &Entry)
- : Name(Name), Entry(Entry) {}
+ : Name(Name), Entry(&Entry) {}
const StringRef getName() const { return Name; }
- const FileEntry &getFileEntry() const { return Entry; }
+ const FileEntry &getFileEntry() const { return *Entry; }
- off_t getSize() const { return Entry.getSize(); }
+ off_t getSize() const { return Entry->getSize(); }
- unsigned getUID() const { return Entry.getUID(); }
+ unsigned getUID() const { return Entry->getUID(); }
const llvm::sys::fs::UniqueID &getUniqueID() const {
- return Entry.getUniqueID();
+ return Entry->getUniqueID();
}
- time_t getModificationTime() const { return Entry.getModificationTime(); }
+ time_t getModificationTime() const { return Entry->getModificationTime(); }
private:
StringRef Name;
- const FileEntry &Entry;
+ const FileEntry *Entry;
};
/// Implements support for file system lookup, file system caching,
@@ -284,9 +285,17 @@ public:
///
/// \param CacheFailure If true and the file does not exist, we'll cache
/// the failure to find this file.
- llvm::ErrorOr<FileEntryRef> getFileRef(StringRef Filename,
- bool OpenFile = false,
- bool CacheFailure = true);
+ llvm::Expected<FileEntryRef> getFileRef(StringRef Filename,
+ bool OpenFile = false,
+ bool CacheFailure = true);
+
+ /// Get a FileEntryRef if it exists, without doing anything on error.
+ llvm::Optional<FileEntryRef> getOptionalFileRef(StringRef Filename,
+ bool OpenFile = false,
+ bool CacheFailure = true) {
+ return llvm::expectedToOptional(
+ getFileRef(Filename, OpenFile, CacheFailure));
+ }
/// Returns the current file system options
FileSystemOptions &getFileSystemOpts() { return FileSystemOpts; }
diff --git a/clang/lib/Basic/FileManager.cpp b/clang/lib/Basic/FileManager.cpp
index 649e4d2239b..8e186713a92 100644
--- a/clang/lib/Basic/FileManager.cpp
+++ b/clang/lib/Basic/FileManager.cpp
@@ -187,10 +187,10 @@ FileManager::getFile(StringRef Filename, bool openFile, bool CacheFailure) {
auto Result = getFileRef(Filename, openFile, CacheFailure);
if (Result)
return &Result->getFileEntry();
- return Result.getError();
+ return llvm::errorToErrorCode(Result.takeError());
}
-llvm::ErrorOr<FileEntryRef>
+llvm::Expected<FileEntryRef>
FileManager::getFileRef(StringRef Filename, bool openFile, bool CacheFailure) {
++NumFileLookups;
@@ -199,7 +199,8 @@ FileManager::getFileRef(StringRef Filename, bool openFile, bool CacheFailure) {
SeenFileEntries.insert({Filename, std::errc::no_such_file_or_directory});
if (!SeenFileInsertResult.second) {
if (!SeenFileInsertResult.first->second)
- return SeenFileInsertResult.first->second.getError();
+ return llvm::errorCodeToError(
+ SeenFileInsertResult.first->second.getError());
// Construct and return and FileEntryRef, unless it's a redirect to another
// filename.
SeenFileEntryOrRedirect Value = *SeenFileInsertResult.first->second;
@@ -230,7 +231,7 @@ FileManager::getFileRef(StringRef Filename, bool openFile, bool CacheFailure) {
else
SeenFileEntries.erase(Filename);
- return DirInfoOrErr.getError();
+ return llvm::errorCodeToError(DirInfoOrErr.getError());
}
const DirectoryEntry *DirInfo = *DirInfoOrErr;
@@ -249,7 +250,7 @@ FileManager::getFileRef(StringRef Filename, bool openFile, bool CacheFailure) {
else
SeenFileEntries.erase(Filename);
- return statError;
+ return llvm::errorCodeToError(statError);
}
assert((openFile || !F) && "undesired open file");
diff --git a/clang/lib/Frontend/CompilerInstance.cpp b/clang/lib/Frontend/CompilerInstance.cpp
index f0227d0501c..a7b7114f791 100644
--- a/clang/lib/Frontend/CompilerInstance.cpp
+++ b/clang/lib/Frontend/CompilerInstance.cpp
@@ -833,6 +833,8 @@ bool CompilerInstance::InitializeSourceManager(
if (InputFile != "-") {
auto FileOrErr = FileMgr.getFileRef(InputFile, /*OpenFile=*/true);
if (!FileOrErr) {
+ // FIXME: include the error in the diagnostic.
+ consumeError(FileOrErr.takeError());
Diags.Report(diag::err_fe_error_reading) << InputFile;
return false;
}
diff --git a/clang/lib/Lex/HeaderMap.cpp b/clang/lib/Lex/HeaderMap.cpp
index 1c7fb1a4764..d44ef29c05d 100644
--- a/clang/lib/Lex/HeaderMap.cpp
+++ b/clang/lib/Lex/HeaderMap.cpp
@@ -204,9 +204,7 @@ Optional<FileEntryRef> HeaderMap::LookupFile(StringRef Filename,
if (Dest.empty())
return None;
- if (auto File = FM.getFileRef(Dest))
- return *File;
- return None;
+ return FM.getOptionalFileRef(Dest);
}
StringRef HeaderMapImpl::lookupFilename(StringRef Filename,
diff --git a/clang/lib/Lex/HeaderSearch.cpp b/clang/lib/Lex/HeaderSearch.cpp
index 84af65c30d5..0160677b2ec 100644
--- a/clang/lib/Lex/HeaderSearch.cpp
+++ b/clang/lib/Lex/HeaderSearch.cpp
@@ -314,7 +314,7 @@ Optional<FileEntryRef> HeaderSearch::getFileAndSuggestModule(
if (!File) {
// For rare, surprising errors (e.g. "out of file handles"), diag the EC
// message.
- std::error_code EC = File.getError();
+ std::error_code EC = llvm::errorToErrorCode(File.takeError());
if (EC != llvm::errc::no_such_file_or_directory &&
EC != llvm::errc::invalid_argument &&
EC != llvm::errc::is_a_directory && EC != llvm::errc::not_a_directory) {
@@ -401,7 +401,7 @@ Optional<FileEntryRef> DirectoryLookup::LookupFile(
FixupSearchPath();
return *Result;
}
- } else if (auto Res = HS.getFileMgr().getFileRef(Dest)) {
+ } else if (auto Res = HS.getFileMgr().getOptionalFileRef(Dest)) {
FixupSearchPath();
return *Res;
}
@@ -553,9 +553,8 @@ Optional<FileEntryRef> DirectoryLookup::DoFrameworkLookup(
FrameworkName.append(Filename.begin()+SlashPos+1, Filename.end());
- llvm::ErrorOr<FileEntryRef> File =
- FileMgr.getFileRef(FrameworkName, /*OpenFile=*/!SuggestedModule);
-
+ auto File =
+ FileMgr.getOptionalFileRef(FrameworkName, /*OpenFile=*/!SuggestedModule);
if (!File) {
// Check "/System/Library/Frameworks/Cocoa.framework/PrivateHeaders/file.h"
const char *Private = "Private";
@@ -565,7 +564,8 @@ Optional<FileEntryRef> DirectoryLookup::DoFrameworkLookup(
SearchPath->insert(SearchPath->begin()+OrigSize, Private,
Private+strlen(Private));
- File = FileMgr.getFileRef(FrameworkName, /*OpenFile=*/!SuggestedModule);
+ File = FileMgr.getOptionalFileRef(FrameworkName,
+ /*OpenFile=*/!SuggestedModule);
}
// If we found the header and are allowed to suggest a module, do so now.
@@ -1076,9 +1076,7 @@ Optional<FileEntryRef> HeaderSearch::LookupSubframeworkHeader(
}
HeadersFilename.append(Filename.begin()+SlashPos+1, Filename.end());
- llvm::ErrorOr<FileEntryRef> File =
- FileMgr.getFileRef(HeadersFilename, /*OpenFile=*/true);
-
+ auto File = FileMgr.getOptionalFileRef(HeadersFilename, /*OpenFile=*/true);
if (!File) {
// Check ".../Frameworks/HIToolbox.framework/PrivateHeaders/HIToolbox.h"
HeadersFilename = FrameworkName;
@@ -1090,7 +1088,7 @@ Optional<FileEntryRef> HeaderSearch::LookupSubframeworkHeader(
}
HeadersFilename.append(Filename.begin()+SlashPos+1, Filename.end());
- File = FileMgr.getFileRef(HeadersFilename, /*OpenFile=*/true);
+ File = FileMgr.getOptionalFileRef(HeadersFilename, /*OpenFile=*/true);
if (!File)
return None;
diff --git a/llvm/include/llvm/Support/Error.h b/llvm/include/llvm/Support/Error.h
index c0e4d362364..f961a29b33a 100644
--- a/llvm/include/llvm/Support/Error.h
+++ b/llvm/include/llvm/Support/Error.h
@@ -982,6 +982,20 @@ inline void consumeError(Error Err) {
handleAllErrors(std::move(Err), [](const ErrorInfoBase &) {});
}
+/// Convert an Expected to an Optional without doing anything. This method
+/// should be used only where an error can be considered a reasonable and
+/// expected return value.
+///
+/// Uses of this method are potentially indicative of problems: perhaps the
+/// error should be propagated further, or the error-producer should just
+/// return an Optional in the first place.
+template <typename T> Optional<T> expectedToOptional(Expected<T> &&E) {
+ if (E)
+ return std::move(*E);
+ consumeError(E.takeError());
+ return None;
+}
+
/// Helper for converting an Error to a bool.
///
/// This method returns true if Err is in an error state, or false if it is
OpenPOWER on IntegriCloud