@@ -208,142 +208,142 @@ Compile(const char *pszProgramSource, const char **pInputHeaders,
208
208
try {
209
209
std::unique_ptr<OCLFEBinaryResult> pResult (new OCLFEBinaryResult ());
210
210
211
- // LLVM doesn't guarantee thread safety,
212
- // therefore we serialize execution of LLVM code.
213
- llvm::sys::SmartScopedLock< true > compileGuard {*compileMutex} ;
211
+ // Create the clang compiler
212
+ std::unique_ptr<clang::CompilerInstance> compiler (
213
+ new clang::CompilerInstance ()) ;
214
214
215
- // Parse options
216
215
CompileOptionsParser optionsParser (pszOpenCLVer);
217
- optionsParser.processOptions (pszOptions, pszOptionsEx);
218
-
219
216
// Prepare error log
220
217
llvm::raw_string_ostream err_ostream (pResult->getLogRef ());
221
-
222
- // Prepare our diagnostic client.
223
- llvm::IntrusiveRefCntPtr<clang::DiagnosticIDs> DiagID (
224
- new clang::DiagnosticIDs ());
225
- llvm::IntrusiveRefCntPtr<clang::DiagnosticOptions> DiagOpts (
226
- new clang::DiagnosticOptions ());
227
- DiagOpts->ShowPresumedLoc = true ;
228
- clang::TextDiagnosticPrinter *DiagsPrinter =
218
+ {
219
+ llvm::sys::SmartScopedLock<true > compileGuard {*compileMutex};
220
+
221
+ // Parse options
222
+ optionsParser.processOptions (pszOptions, pszOptionsEx);
223
+
224
+ // Prepare our diagnostic client.
225
+ llvm::IntrusiveRefCntPtr<clang::DiagnosticIDs> DiagID (
226
+ new clang::DiagnosticIDs ());
227
+ llvm::IntrusiveRefCntPtr<clang::DiagnosticOptions> DiagOpts (
228
+ new clang::DiagnosticOptions ());
229
+ DiagOpts->ShowPresumedLoc = true ;
230
+ clang::TextDiagnosticPrinter *DiagsPrinter =
229
231
new clang::TextDiagnosticPrinter (err_ostream, &*DiagOpts);
230
- llvm::IntrusiveRefCntPtr<clang::DiagnosticsEngine> Diags (
231
- new clang::DiagnosticsEngine (DiagID, &*DiagOpts, DiagsPrinter));
232
-
233
- // Create the clang compiler
234
- std::unique_ptr<clang::CompilerInstance> compiler (
235
- new clang::CompilerInstance ());
232
+ llvm::IntrusiveRefCntPtr<clang::DiagnosticsEngine> Diags (
233
+ new clang::DiagnosticsEngine (DiagID, &*DiagOpts, DiagsPrinter));
236
234
237
- // Prepare output buffer
238
- std::unique_ptr<llvm::raw_pwrite_stream>
235
+ // Prepare output buffer
236
+ std::unique_ptr<llvm::raw_pwrite_stream>
239
237
ir_ostream (new llvm::raw_svector_ostream (pResult->getIRBufferRef ()));
240
- // Set buffers
241
- // CompilerInstance takes ownership over output stream
242
- compiler->setOutputStream (std::move (ir_ostream));
238
+ // Set buffers
239
+ // CompilerInstance takes ownership over output stream
240
+ compiler->setOutputStream (std::move (ir_ostream));
243
241
244
- compiler->setDiagnostics (&*Diags);
242
+ compiler->setDiagnostics (&*Diags);
245
243
246
- llvm::IntrusiveRefCntPtr<llvm::vfs::OverlayFileSystem> OverlayFS (
247
- new llvm::vfs::OverlayFileSystem (llvm::vfs::getRealFileSystem ()));
248
- llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> MemFS (
249
- new llvm::vfs::InMemoryFileSystem);
250
- OverlayFS->pushOverlay (MemFS);
244
+ llvm::IntrusiveRefCntPtr<llvm::vfs::OverlayFileSystem> OverlayFS (
245
+ new llvm::vfs::OverlayFileSystem (llvm::vfs::getRealFileSystem ()));
246
+ llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> MemFS (
247
+ new llvm::vfs::InMemoryFileSystem);
248
+ OverlayFS->pushOverlay (MemFS);
251
249
252
- compiler->createFileManager (OverlayFS);
253
- compiler->createSourceManager (compiler->getFileManager ());
250
+ compiler->createFileManager (OverlayFS);
251
+ compiler->createSourceManager (compiler->getFileManager ());
254
252
255
- // Create compiler invocation from user args before trickering with it
256
- clang::CompilerInvocation::CreateFromArgs (compiler->getInvocation (),
257
- optionsParser.beginArgs (),
258
- optionsParser.endArgs (), *Diags);
253
+ // Create compiler invocation from user args before trickering with it
254
+ clang::CompilerInvocation::CreateFromArgs (compiler->getInvocation (),
255
+ optionsParser.beginArgs (),
256
+ optionsParser.endArgs (), *Diags);
259
257
260
- // Configure our handling of diagnostics.
261
- ProcessWarningOptions (*Diags, compiler->getDiagnosticOpts ());
258
+ // Configure our handling of diagnostics.
259
+ ProcessWarningOptions (*Diags, compiler->getDiagnosticOpts ());
262
260
263
- // Map memory buffers to a virtual file system
261
+ // Map memory buffers to a virtual file system
264
262
265
- // Source file
266
- MemFS->addFile (
267
- optionsParser.getSourceName (), (time_t )0 ,
268
- llvm::MemoryBuffer::getMemBuffer (
263
+ // Source file
264
+ MemFS->addFile (
265
+ optionsParser.getSourceName (), (time_t )0 ,
266
+ llvm::MemoryBuffer::getMemBuffer (
269
267
llvm::StringRef (pszProgramSource), optionsParser.getSourceName ()));
270
268
271
- // Input header with OpenCL defines.
272
- std::vector<Resource> vHeaderWithDefs;
273
- if (!GetHeaders (vHeaderWithDefs)) {
274
- return CL_COMPILE_PROGRAM_FAILURE;
275
- }
269
+ // Input header with OpenCL defines.
270
+ std::vector<Resource> vHeaderWithDefs;
271
+ if (!GetHeaders (vHeaderWithDefs)) {
272
+ return CL_COMPILE_PROGRAM_FAILURE;
273
+ }
276
274
277
- for (const auto &Header:vHeaderWithDefs) {
278
- auto Buf = llvm::MemoryBuffer::getMemBuffer (
279
- llvm::StringRef (Header.m_data , Header.m_size ),
280
- Header.m_name );
275
+ for (const auto &Header:vHeaderWithDefs) {
276
+ auto Buf = llvm::MemoryBuffer::getMemBuffer (
277
+ llvm::StringRef (Header.m_data , Header.m_size ),
278
+ Header.m_name );
281
279
282
- MemFS->addFile (Header.m_name ,(time_t )0 , std::move (Buf));
283
- }
280
+ MemFS->addFile (Header.m_name ,(time_t )0 , std::move (Buf));
281
+ }
284
282
285
- // Input Headers
286
- for (unsigned int i = 0 ; i < uiNumInputHeaders; ++i) {
287
- auto Header = llvm::MemoryBuffer::getMemBuffer (
288
- pInputHeaders[i], pInputHeadersNames[i]);
289
- MemFS->addFile (pInputHeadersNames[i], (time_t )0 , std::move (Header));
283
+ // Input Headers
284
+ for (unsigned int i = 0 ; i < uiNumInputHeaders; ++i) {
285
+ auto Header = llvm::MemoryBuffer::getMemBuffer (
286
+ pInputHeaders[i], pInputHeadersNames[i]);
287
+ MemFS->addFile (pInputHeadersNames[i], (time_t )0 , std::move (Header));
288
+ }
290
289
}
291
290
292
-
293
291
// Execute the frontend actions.
294
292
bool success = false ;
295
293
try {
296
294
success = clang::ExecuteCompilerInvocation (compiler.get ());
297
295
} catch (const std::exception &) {
298
296
}
297
+ {
298
+ llvm::sys::SmartScopedLock<true > compileGuard {*compileMutex};
299
+ pResult->setIRType (IR_TYPE_COMPILED_OBJECT);
300
+ pResult->setIRName (optionsParser.getSourceName ());
301
+
302
+ // Our error handler depends on the Diagnostics object, which we're
303
+ // potentially about to delete. Uninstall the handler now so that any
304
+ // later errors use the default handling behavior instead.
305
+ // (currently commented out since setting the llvm error handling in
306
+ // multi-threaded environment is unsupported)
307
+ // llvm::remove_fatal_error_handler();
308
+ err_ostream.flush ();
299
309
300
- pResult->setIRType (IR_TYPE_COMPILED_OBJECT);
301
- pResult->setIRName (optionsParser.getSourceName ());
302
-
303
- // Our error handler depends on the Diagnostics object, which we're
304
- // potentially about to delete. Uninstall the handler now so that any
305
- // later errors use the default handling behavior instead.
306
- // (currently commented out since setting the llvm error handling in
307
- // multi-threaded environment is unsupported)
308
- // llvm::remove_fatal_error_handler();
309
- err_ostream.flush ();
310
-
311
- if (success && (optionsParser.hasEmitSPIRV () || optionsParser.hasEmitSPIRVText ())) {
312
- // Translate LLVM IR to SPIR-V.
313
- if (optionsParser.hasEmitSPIRVText ())
314
- SPIRV::SPIRVUseTextFormat = true ;
315
- llvm::StringRef LLVM_IR (static_cast <const char *>(pResult->GetIR ()),
316
- pResult->GetIRSize ());
317
- std::unique_ptr<llvm::MemoryBuffer> MB = llvm::MemoryBuffer::getMemBuffer (LLVM_IR, pResult->GetIRName (), false );
318
- llvm::LLVMContext Context;
319
- auto E = llvm::getOwningLazyBitcodeModule (std::move (MB), Context,
320
- /* ShouldLazyLoadMetadata=*/ true );
321
- llvm::logAllUnhandledErrors (E.takeError (), err_ostream, " error: " );
322
- std::unique_ptr<llvm::Module> M = std::move (*E);
323
-
324
- if (M->materializeAll ()) {
325
- if (pBinaryResult) {
326
- *pBinaryResult = nullptr ;
310
+ if (success && (optionsParser.hasEmitSPIRV () || optionsParser.hasEmitSPIRVText ())) {
311
+ // Translate LLVM IR to SPIR-V.
312
+ if (optionsParser.hasEmitSPIRVText ())
313
+ SPIRV::SPIRVUseTextFormat = true ;
314
+ llvm::StringRef LLVM_IR (static_cast <const char *>(pResult->GetIR ()),
315
+ pResult->GetIRSize ());
316
+ std::unique_ptr<llvm::MemoryBuffer> MB = llvm::MemoryBuffer::getMemBuffer (LLVM_IR, pResult->GetIRName (), false );
317
+ llvm::LLVMContext Context;
318
+ auto E = llvm::getOwningLazyBitcodeModule (std::move (MB), Context,
319
+ /* ShouldLazyLoadMetadata=*/ true );
320
+ llvm::logAllUnhandledErrors (E.takeError (), err_ostream, " error: " );
321
+ std::unique_ptr<llvm::Module> M = std::move (*E);
322
+
323
+ if (M->materializeAll ()) {
324
+ if (pBinaryResult) {
325
+ *pBinaryResult = nullptr ;
326
+ }
327
+ assert (!" Failed to read just compiled LLVM IR!" );
328
+ return CL_COMPILE_PROGRAM_FAILURE;
327
329
}
328
- assert (!" Failed to read just compiled LLVM IR!" );
329
- return CL_COMPILE_PROGRAM_FAILURE;
330
- }
331
- pResult->getIRBufferRef ().clear ();
332
- SmallVectorBuffer StreamBuf (pResult->getIRBufferRef ());
333
- std::ostream OS (&StreamBuf);
334
- std::string Err;
335
- SPIRV::TranslatorOpts SPIRVOpts;
336
- SPIRVOpts.enableAllExtensions ();
337
- if (!optionsParser.hasOptDisable ()) {
338
- SPIRVOpts.setMemToRegEnabled (true );
330
+ pResult->getIRBufferRef ().clear ();
331
+ SmallVectorBuffer StreamBuf (pResult->getIRBufferRef ());
332
+ std::ostream OS (&StreamBuf);
333
+ std::string Err;
334
+ SPIRV::TranslatorOpts SPIRVOpts;
335
+ SPIRVOpts.enableAllExtensions ();
336
+ if (!optionsParser.hasOptDisable ()) {
337
+ SPIRVOpts.setMemToRegEnabled (true );
338
+ }
339
+ success = llvm::writeSpirv (M.get (), SPIRVOpts, OS, Err);
340
+ err_ostream << Err.c_str ();
341
+ err_ostream.flush ();
339
342
}
340
- success = llvm::writeSpirv (M.get (), SPIRVOpts, OS, Err);
341
- err_ostream << Err.c_str ();
342
- err_ostream.flush ();
343
- }
344
343
345
- if (pBinaryResult) {
346
- *pBinaryResult = pResult.release ();
344
+ if (pBinaryResult) {
345
+ *pBinaryResult = pResult.release ();
346
+ }
347
347
}
348
348
return success ? CL_SUCCESS : CL_COMPILE_PROGRAM_FAILURE;
349
349
} catch (std::bad_alloc &) {
0 commit comments