diff options
-rw-r--r-- | llvm/include/llvm/DebugInfo/PDB/DIA/DIASession.h | 3 | ||||
-rw-r--r-- | llvm/include/llvm/DebugInfo/PDB/PDB.h | 4 | ||||
-rw-r--r-- | llvm/include/llvm/DebugInfo/PDB/PDBTypes.h | 11 | ||||
-rw-r--r-- | llvm/lib/DebugInfo/PDB/DIA/DIASession.cpp | 45 | ||||
-rw-r--r-- | llvm/lib/DebugInfo/PDB/PDB.cpp | 8 | ||||
-rw-r--r-- | llvm/tools/llvm-pdbdump/llvm-pdbdump.cpp | 25 |
6 files changed, 70 insertions, 26 deletions
diff --git a/llvm/include/llvm/DebugInfo/PDB/DIA/DIASession.h b/llvm/include/llvm/DebugInfo/PDB/DIA/DIASession.h index 141b9b0d989..6c72c3e6fc6 100644 --- a/llvm/include/llvm/DebugInfo/PDB/DIA/DIASession.h +++ b/llvm/include/llvm/DebugInfo/PDB/DIA/DIASession.h @@ -19,7 +19,8 @@ class DIASession : public IPDBSession { public: explicit DIASession(CComPtr<IDiaSession> DiaSession); - static DIASession *createFromPdb(StringRef Path); + static PDB_ErrorCode createFromPdb(StringRef Path, + std::unique_ptr<IPDBSession> &Session); uint64_t getLoadAddress() const override; void setLoadAddress(uint64_t Address) override; diff --git a/llvm/include/llvm/DebugInfo/PDB/PDB.h b/llvm/include/llvm/DebugInfo/PDB/PDB.h index 7193eef1b3c..67878e9ccf6 100644 --- a/llvm/include/llvm/DebugInfo/PDB/PDB.h +++ b/llvm/include/llvm/DebugInfo/PDB/PDB.h @@ -16,8 +16,8 @@ namespace llvm { class StringRef; -std::unique_ptr<IPDBSession> createPDBReader(PDB_ReaderType Type, - StringRef Path); +PDB_ErrorCode createPDBReader(PDB_ReaderType Type, StringRef Path, + std::unique_ptr<IPDBSession> &Session); } #endif diff --git a/llvm/include/llvm/DebugInfo/PDB/PDBTypes.h b/llvm/include/llvm/DebugInfo/PDB/PDBTypes.h index 75b64750129..2bee60860b0 100644 --- a/llvm/include/llvm/DebugInfo/PDB/PDBTypes.h +++ b/llvm/include/llvm/DebugInfo/PDB/PDBTypes.h @@ -418,6 +418,17 @@ enum class PDB_RegisterId { enum class PDB_MemberAccess { Private = 1, Protected = 2, Public = 3 }; +enum class PDB_ErrorCode { + Success, + NoPdbImpl, + InvalidPath, + InvalidFileFormat, + InvalidParameter, + AlreadyLoaded, + UnknownError, + NoMemory +}; + struct VersionInfo { uint32_t Major; uint32_t Minor; diff --git a/llvm/lib/DebugInfo/PDB/DIA/DIASession.cpp b/llvm/lib/DebugInfo/PDB/DIA/DIASession.cpp index 24791f2afa1..4966bea96f6 100644 --- a/llvm/lib/DebugInfo/PDB/DIA/DIASession.cpp +++ b/llvm/lib/DebugInfo/PDB/DIA/DIASession.cpp @@ -23,28 +23,45 @@ namespace {} DIASession::DIASession(CComPtr<IDiaSession> DiaSession) : Session(DiaSession) {} -DIASession *DIASession::createFromPdb(StringRef Path) { - CComPtr<IDiaDataSource> DataSource; - CComPtr<IDiaSession> Session; +PDB_ErrorCode DIASession::createFromPdb(StringRef Path, + std::unique_ptr<IPDBSession> &Session) { + CComPtr<IDiaDataSource> DiaDataSource; + CComPtr<IDiaSession> DiaSession; // We assume that CoInitializeEx has already been called by the executable. - HRESULT Result = ::CoCreateInstance(CLSID_DiaSource, nullptr, - CLSCTX_INPROC_SERVER, IID_IDiaDataSource, - reinterpret_cast<LPVOID *>(&DataSource)); + HRESULT Result = ::CoCreateInstance( + CLSID_DiaSource, nullptr, CLSCTX_INPROC_SERVER, IID_IDiaDataSource, + reinterpret_cast<LPVOID *>(&DiaDataSource)); if (FAILED(Result)) - return nullptr; + return PDB_ErrorCode::NoPdbImpl; llvm::SmallVector<UTF16, 128> Path16; if (!llvm::convertUTF8ToUTF16String(Path, Path16)) - return nullptr; + return PDB_ErrorCode::InvalidPath; const wchar_t *Path16Str = reinterpret_cast<const wchar_t*>(Path16.data()); - if (FAILED(DataSource->loadDataFromPdb(Path16Str))) - return nullptr; - - if (FAILED(DataSource->openSession(&Session))) - return nullptr; - return new DIASession(Session); + if (FAILED(Result = DiaDataSource->loadDataFromPdb(Path16Str))) { + if (Result == E_PDB_NOT_FOUND) + return PDB_ErrorCode::InvalidPath; + else if (Result == E_PDB_FORMAT) + return PDB_ErrorCode::InvalidFileFormat; + else if (Result == E_INVALIDARG) + return PDB_ErrorCode::InvalidParameter; + else if (Result == E_UNEXPECTED) + return PDB_ErrorCode::AlreadyLoaded; + else + return PDB_ErrorCode::UnknownError; + } + + if (FAILED(Result = DiaDataSource->openSession(&DiaSession))) { + if (Result == E_OUTOFMEMORY) + return PDB_ErrorCode::NoMemory; + else + return PDB_ErrorCode::UnknownError; + } + + Session.reset(new DIASession(DiaSession)); + return PDB_ErrorCode::Success; } uint64_t DIASession::getLoadAddress() const { diff --git a/llvm/lib/DebugInfo/PDB/PDB.cpp b/llvm/lib/DebugInfo/PDB/PDB.cpp index aa84c288287..a07396d1a17 100644 --- a/llvm/lib/DebugInfo/PDB/PDB.cpp +++ b/llvm/lib/DebugInfo/PDB/PDB.cpp @@ -20,11 +20,11 @@ using namespace llvm; -std::unique_ptr<IPDBSession> llvm::createPDBReader(PDB_ReaderType Type, - StringRef Path) { +PDB_ErrorCode llvm::createPDBReader(PDB_ReaderType Type, StringRef Path, + std::unique_ptr<IPDBSession> &Session) { // Create the correct concrete instance type based on the value of Type. #if HAVE_DIA_SDK - return std::unique_ptr<DIASession>(DIASession::createFromPdb(Path)); + return DIASession::createFromPdb(Path, Session); #endif - return nullptr; + return PDB_ErrorCode::NoPdbImpl; } diff --git a/llvm/tools/llvm-pdbdump/llvm-pdbdump.cpp b/llvm/tools/llvm-pdbdump/llvm-pdbdump.cpp index 5bc33d06e38..98b26144e34 100644 --- a/llvm/tools/llvm-pdbdump/llvm-pdbdump.cpp +++ b/llvm/tools/llvm-pdbdump/llvm-pdbdump.cpp @@ -66,11 +66,26 @@ cl::opt<bool> ClassDefs("class-definitions", } static void dumpInput(StringRef Path) { - std::unique_ptr<IPDBSession> Session( - llvm::createPDBReader(PDB_ReaderType::DIA, Path)); - if (!Session) { - outs() << "Unable to create PDB reader. Check that a valid implementation"; - outs() << " is available for your platform."; + std::unique_ptr<IPDBSession> Session; + PDB_ErrorCode Error = + llvm::createPDBReader(PDB_ReaderType::DIA, Path, Session); + switch (Error) { + case PDB_ErrorCode::Success: + break; + case PDB_ErrorCode::NoPdbImpl: + outs() << "Reading PDBs is not supported on this platform.\n"; + return; + case PDB_ErrorCode::InvalidPath: + outs() << "Unable to load PDB at '" << Path + << "'. Check that the file exists and is readable.\n"; + return; + case PDB_ErrorCode::InvalidFileFormat: + outs() << "Unable to load PDB at '" << Path + << "'. The file has an unrecognized format.\n"; + return; + default: + outs() << "Unable to load PDB at '" << Path + << "'. An unknown error occured.\n"; return; } |