1313#include " llvm/IRReader/IRReader.h"
1414#include " llvm/Support/Debug.h"
1515#include " llvm/Support/FormattedStream.h"
16+ #include " llvm/Support/MemoryBufferRef.h"
1617#include " llvm/Support/SourceMgr.h"
1718
1819#include < charconv>
1920
2021namespace psr {
2122
23+ std::unique_ptr<llvm::Module>
24+ LLVMProjectIRDB::getParsedIRModuleOrNull (llvm::MemoryBufferRef IRFileContent,
25+ llvm::LLVMContext &Ctx) noexcept {
26+
27+ llvm::SMDiagnostic Diag;
28+ std::unique_ptr<llvm::Module> M = llvm::parseIR (IRFileContent, Diag, Ctx);
29+ bool BrokenDebugInfo = false ;
30+ if (M == nullptr ) {
31+ Diag.print (nullptr , llvm::errs ());
32+ return nullptr ;
33+ }
34+ /* Crash in presence of llvm-3.9.1 module (segfault) */
35+ if (M == nullptr || llvm::verifyModule (*M, &llvm::errs (), &BrokenDebugInfo)) {
36+ PHASAR_LOG_LEVEL (ERROR, IRFileContent.getBufferIdentifier ()
37+ << " could not be parsed correctly!" );
38+ return nullptr ;
39+ }
40+ if (BrokenDebugInfo) {
41+ PHASAR_LOG_LEVEL (WARNING, " Debug info is broken!" );
42+ }
43+ return M;
44+ }
45+
46+ std::unique_ptr<llvm::Module>
47+ LLVMProjectIRDB::getParsedIRModuleOrNull (const llvm::Twine &IRFileName,
48+ llvm::LLVMContext &Ctx) noexcept {
49+ // Look at LLVM's IRReader.cpp for reference
50+
51+ auto FileOrErr =
52+ llvm::MemoryBuffer::getFileOrSTDIN (IRFileName, /* IsText=*/ true );
53+ if (std::error_code EC = FileOrErr.getError ()) {
54+ llvm::SmallString<128 > Buf;
55+ auto Err = llvm::SMDiagnostic (IRFileName.toStringRef (Buf),
56+ llvm::SourceMgr::DK_Error,
57+ " Could not open input file: " + EC.message ());
58+ Err.print (nullptr , llvm::errs ());
59+ return nullptr ;
60+ }
61+ return getParsedIRModuleOrNull (*FileOrErr.get (), Ctx);
62+ }
63+
2264LLVMProjectIRDB::LLVMProjectIRDB (const llvm::Twine &IRFileName) {
2365
24- std::unique_ptr<llvm::Module> M = getParsedIRModuleOrNull (IRFileName, Ctx);
66+ auto M = getParsedIRModuleOrNull (IRFileName, Ctx);
2567
2668 if (!M) {
2769 return ;
@@ -87,10 +129,16 @@ void LLVMProjectIRDB::preprocessModule(llvm::Module *NonConstMod) {
87129 assert (InstToId.size () == IdToInst.size ());
88130}
89131
90- LLVMProjectIRDB::LLVMProjectIRDB (llvm::Module *Mod) : Mod(Mod) {
132+ LLVMProjectIRDB::LLVMProjectIRDB (llvm::Module *Mod, bool DoPreprocessing)
133+ : Mod(Mod) {
91134 assert (Mod != nullptr );
92135 ModulesToSlotTracker::setMSTForModule (Mod);
93- initInstructionIds ();
136+
137+ if (DoPreprocessing) {
138+ preprocessModule (Mod);
139+ } else {
140+ initInstructionIds ();
141+ }
94142}
95143
96144LLVMProjectIRDB::LLVMProjectIRDB (std::unique_ptr<llvm::Module> Mod,
@@ -109,21 +157,10 @@ LLVMProjectIRDB::LLVMProjectIRDB(std::unique_ptr<llvm::Module> Mod,
109157
110158LLVMProjectIRDB::LLVMProjectIRDB (llvm::MemoryBufferRef Buf) {
111159 llvm::SMDiagnostic Diag;
112- std::unique_ptr<llvm::Module> M = llvm::parseIR (Buf, Diag, Ctx);
113- bool BrokenDebugInfo = false ;
114- if (M == nullptr ) {
115- Diag.print (nullptr , llvm::errs ());
116- return ;
117- }
118-
119- if (llvm::verifyModule (*M, &llvm::errs (), &BrokenDebugInfo)) {
120- PHASAR_LOG_LEVEL (ERROR, Buf.getBufferIdentifier ()
121- << " could not be parsed correctly!" );
160+ auto M = getParsedIRModuleOrNull (Buf, Ctx);
161+ if (!M) {
122162 return ;
123163 }
124- if (BrokenDebugInfo) {
125- PHASAR_LOG_LEVEL (WARNING, " Debug info is broken!" );
126- }
127164
128165 auto *NonConst = M.get ();
129166 Mod = std::move (M);
@@ -137,29 +174,6 @@ LLVMProjectIRDB::~LLVMProjectIRDB() {
137174 }
138175}
139176
140- std::unique_ptr<llvm::Module>
141- LLVMProjectIRDB::getParsedIRModuleOrNull (const llvm::Twine &IRFileName,
142- llvm::LLVMContext &Ctx) noexcept {
143- llvm::SMDiagnostic Diag;
144- llvm::SmallString<256 > Buf;
145- std::unique_ptr<llvm::Module> M =
146- llvm::parseIRFile (IRFileName.toStringRef (Buf), Diag, Ctx);
147- bool BrokenDebugInfo = false ;
148- if (M == nullptr ) {
149- Diag.print (nullptr , llvm::errs ());
150- return nullptr ;
151- }
152- /* Crash in presence of llvm-3.9.1 module (segfault) */
153- if (M == nullptr || llvm::verifyModule (*M, &llvm::errs (), &BrokenDebugInfo)) {
154- PHASAR_LOG_LEVEL (ERROR, IRFileName << " could not be parsed correctly!" );
155- return nullptr ;
156- }
157- if (BrokenDebugInfo) {
158- PHASAR_LOG_LEVEL (WARNING, " Debug info is broken!" );
159- }
160- return M;
161- }
162-
163177static llvm::Function *
164178internalGetFunctionDefinition (const llvm::Module &M,
165179 llvm::StringRef FunctionName) {
0 commit comments