19#include "llvm/ADT/StringExtras.h"
20#include "llvm/ADT/StringSwitch.h"
21#include "llvm/Analysis/GlobalsModRef.h"
22#include "llvm/Analysis/RuntimeLibcallInfo.h"
23#include "llvm/Analysis/TargetLibraryInfo.h"
24#include "llvm/Analysis/TargetTransformInfo.h"
25#include "llvm/BinaryFormat/ELF.h"
26#include "llvm/Bitcode/BitcodeReader.h"
27#include "llvm/Bitcode/BitcodeWriter.h"
28#include "llvm/Bitcode/BitcodeWriterPass.h"
29#include "llvm/CodeGen/MachineModuleInfo.h"
30#include "llvm/CodeGen/TargetSubtargetInfo.h"
31#include "llvm/Config/llvm-config.h"
32#include "llvm/Frontend/Driver/CodeGenOptions.h"
33#include "llvm/IR/DataLayout.h"
34#include "llvm/IR/DebugInfo.h"
35#include "llvm/IR/LLVMRemarkStreamer.h"
36#include "llvm/IR/LegacyPassManager.h"
37#include "llvm/IR/Module.h"
38#include "llvm/IR/ModuleSummaryIndex.h"
39#include "llvm/IR/PassManager.h"
40#include "llvm/IR/Verifier.h"
41#include "llvm/IRPrinter/IRPrintingPasses.h"
42#include "llvm/LTO/LTOBackend.h"
43#include "llvm/MC/MCTargetOptions.h"
44#include "llvm/MC/TargetRegistry.h"
45#include "llvm/Object/OffloadBinary.h"
46#include "llvm/Passes/PassBuilder.h"
47#include "llvm/Passes/RunCodeGen.h"
48#include "llvm/Passes/StandardInstrumentations.h"
49#include "llvm/Plugins/PassPlugin.h"
50#include "llvm/ProfileData/InstrProfCorrelator.h"
51#include "llvm/Support/BuryPointer.h"
52#include "llvm/Support/CodeGen.h"
53#include "llvm/Support/CommandLine.h"
54#include "llvm/Support/Compiler.h"
55#include "llvm/Support/IOSandbox.h"
56#include "llvm/Support/MemoryBuffer.h"
57#include "llvm/Support/PrettyStackTrace.h"
58#include "llvm/Support/Program.h"
59#include "llvm/Support/TimeProfiler.h"
60#include "llvm/Support/Timer.h"
61#include "llvm/Support/ToolOutputFile.h"
62#include "llvm/Support/VirtualFileSystem.h"
63#include "llvm/Support/raw_ostream.h"
64#include "llvm/Target/TargetMachine.h"
65#include "llvm/Target/TargetOptions.h"
66#include "llvm/TargetParser/SubtargetFeature.h"
67#include "llvm/TargetParser/Triple.h"
68#include "llvm/Transforms/HipStdPar/HipStdPar.h"
69#include "llvm/Transforms/IPO/DeadArgumentElimination.h"
70#include "llvm/Transforms/IPO/EmbedBitcodePass.h"
71#include "llvm/Transforms/IPO/ForceFunctionAttrs.h"
72#include "llvm/Transforms/IPO/FunctionAttrs.h"
73#include "llvm/Transforms/IPO/GlobalOpt.h"
74#include "llvm/Transforms/IPO/InferFunctionAttrs.h"
75#include "llvm/Transforms/IPO/LowerTypeTests.h"
76#include "llvm/Transforms/IPO/SCCP.h"
77#include "llvm/Transforms/IPO/ThinLTOBitcodeWriter.h"
78#include "llvm/Transforms/InstCombine/InstCombine.h"
79#include "llvm/Transforms/Instrumentation/AddressSanitizer.h"
80#include "llvm/Transforms/Instrumentation/AddressSanitizerOptions.h"
81#include "llvm/Transforms/Instrumentation/BoundsChecking.h"
82#include "llvm/Transforms/Instrumentation/CopyProf.h"
83#include "llvm/Transforms/Instrumentation/DataFlowSanitizer.h"
84#include "llvm/Transforms/Instrumentation/GCOVProfiler.h"
85#include "llvm/Transforms/Instrumentation/HWAddressSanitizer.h"
86#include "llvm/Transforms/Instrumentation/InstrProfiling.h"
87#include "llvm/Transforms/Instrumentation/KCFI.h"
88#include "llvm/Transforms/Instrumentation/LowerAllowCheckPass.h"
89#include "llvm/Transforms/Instrumentation/MemProfInstrumentation.h"
90#include "llvm/Transforms/Instrumentation/MemProfUse.h"
91#include "llvm/Transforms/Instrumentation/MemorySanitizer.h"
92#include "llvm/Transforms/Instrumentation/NumericalStabilitySanitizer.h"
93#include "llvm/Transforms/Instrumentation/PGOInstrumentation.h"
94#include "llvm/Transforms/Instrumentation/RealtimeSanitizer.h"
95#include "llvm/Transforms/Instrumentation/SanitizerBinaryMetadata.h"
96#include "llvm/Transforms/Instrumentation/SanitizerCoverage.h"
97#include "llvm/Transforms/Instrumentation/ThreadSanitizer.h"
98#include "llvm/Transforms/Instrumentation/TypeSanitizer.h"
99#include "llvm/Transforms/ObjCARC.h"
100#include "llvm/Transforms/Scalar/EarlyCSE.h"
101#include "llvm/Transforms/Scalar/GVN.h"
102#include "llvm/Transforms/Scalar/JumpThreading.h"
103#include "llvm/Transforms/Scalar/LowerExpectIntrinsic.h"
104#include "llvm/Transforms/Scalar/SROA.h"
105#include "llvm/Transforms/Scalar/SimplifyCFG.h"
106#include "llvm/Transforms/Utils/AssignGUID.h"
107#include "llvm/Transforms/Utils/Debugify.h"
108#include "llvm/Transforms/Utils/DynamicDebugging.h"
109#include "llvm/Transforms/Utils/Mem2Reg.h"
110#include "llvm/Transforms/Utils/ModuleUtils.h"
114using namespace clang;
117#define HANDLE_EXTENSION(Ext) \
118 llvm::PassPluginLibraryInfo get##Ext##PluginInfo();
119#include "llvm/Support/Extension.def"
124 "sanitizer-early-opt-ep",
125 cl::desc(
"Insert sanitizers on OptimizerEarlyEP."));
130 "pgo-cold-func-opt", cl::init(PGOOptions::ColdFuncOpt::Default), cl::Hidden,
132 "Function attribute to apply to cold functions as determined by PGO"),
133 cl::values(clEnumValN(PGOOptions::ColdFuncOpt::Default,
"default",
134 "Default (no attribute)"),
135 clEnumValN(PGOOptions::ColdFuncOpt::OptSize,
"optsize",
136 "Mark cold functions with optsize."),
137 clEnumValN(PGOOptions::ColdFuncOpt::MinSize,
"minsize",
138 "Mark cold functions with minsize."),
139 clEnumValN(PGOOptions::ColdFuncOpt::OptNone,
"optnone",
140 "Mark cold functions with optnone.")));
152 ? llvm::driver::getDefaultProfileGenName(LibraryOptions)
154 if (CodeGenOpts.ContinuousProfileSync)
161class EmitAssemblyHelper {
162 CompilerInstance &CI;
163 DiagnosticsEngine &Diags;
164 const CodeGenOptions &CodeGenOpts;
165 const clang::TargetOptions &TargetOpts;
166 const LangOptions &LangOpts;
167 llvm::Module *TheModule;
168 IntrusiveRefCntPtr<llvm::vfs::FileSystem> VFS;
170 std::unique_ptr<raw_pwrite_stream> OS;
174 TargetIRAnalysis getTargetIRAnalysis()
const {
176 return TM->getTargetIRAnalysis();
178 return TargetIRAnalysis();
189 void CreateTargetMachine(
bool MustCreateTM);
191 std::unique_ptr<llvm::ToolOutputFile> openOutputFile(StringRef Path) {
193 auto F = std::make_unique<llvm::ToolOutputFile>(Path, EC,
194 llvm::sys::fs::OF_None);
196 Diags.Report(diag::err_fe_unable_to_open_output) << Path << EC.message();
202 void RunOptimizationPipeline(
203 BackendAction Action, std::unique_ptr<raw_pwrite_stream> &OS,
204 std::unique_ptr<llvm::ToolOutputFile> &ThinLinkOS, BackendConsumer *BC);
206 std::unique_ptr<raw_pwrite_stream> &OS,
207 std::unique_ptr<llvm::ToolOutputFile> &DwoOS);
208 void TimeCodegenPasses(llvm::function_ref<
void()> RunPasses);
215 bool shouldEmitRegularLTOSummary()
const {
216 return CodeGenOpts.PrepareForLTO && !CodeGenOpts.DisableLLVMPasses &&
217 TargetTriple.getVendor() != llvm::Triple::Apple;
223 bool shouldEmitUnifiedLTOModueFlag()
const {
224 return CodeGenOpts.UnifiedLTO &&
225 (CodeGenOpts.PrepareForThinLTO || shouldEmitRegularLTOSummary());
229 EmitAssemblyHelper(CompilerInstance &CI, CodeGenOptions &CGOpts,
231 IntrusiveRefCntPtr<llvm::vfs::FileSystem> VFS)
232 : CI(CI), Diags(CI.getDiagnostics()), CodeGenOpts(CGOpts),
233 TargetOpts(CI.getTargetOpts()), LangOpts(CI.getLangOpts()),
234 TheModule(M), VFS(std::move(VFS)),
235 TargetTriple(TheModule->getTargetTriple()) {}
237 ~EmitAssemblyHelper() {
238 if (CodeGenOpts.DisableFree)
239 BuryPointer(std::move(TM));
242 std::unique_ptr<TargetMachine> TM;
245 void emitAssembly(
BackendAction Action, std::unique_ptr<raw_pwrite_stream> OS,
246 BackendConsumer *BC);
250static SanitizerCoverageOptions
252 SanitizerCoverageOptions Opts;
254 static_cast<SanitizerCoverageOptions::Type
>(CGOpts.SanitizeCoverageType);
255 Opts.IndirectCalls = CGOpts.SanitizeCoverageIndirectCalls;
256 Opts.TraceBB = CGOpts.SanitizeCoverageTraceBB;
257 Opts.TraceCmp = CGOpts.SanitizeCoverageTraceCmp;
258 Opts.TraceDiv = CGOpts.SanitizeCoverageTraceDiv;
259 Opts.TraceGep = CGOpts.SanitizeCoverageTraceGep;
260 Opts.Use8bitCounters = CGOpts.SanitizeCoverage8bitCounters;
261 Opts.TracePC = CGOpts.SanitizeCoverageTracePC;
262 Opts.TracePCEntryExit = CGOpts.SanitizeCoverageTracePCEntryExit;
263 Opts.TracePCGuard = CGOpts.SanitizeCoverageTracePCGuard;
264 Opts.NoPrune = CGOpts.SanitizeCoverageNoPrune;
265 Opts.Inline8bitCounters = CGOpts.SanitizeCoverageInline8bitCounters;
266 Opts.InlineBoolFlag = CGOpts.SanitizeCoverageInlineBoolFlag;
267 Opts.PCTable = CGOpts.SanitizeCoveragePCTable;
268 Opts.StackDepth = CGOpts.SanitizeCoverageStackDepth;
269 Opts.StackDepthCallbackMin = CGOpts.SanitizeCoverageStackDepthCallbackMin;
270 Opts.TraceLoads = CGOpts.SanitizeCoverageTraceLoads;
271 Opts.TraceStores = CGOpts.SanitizeCoverageTraceStores;
272 Opts.CollectControlFlow = CGOpts.SanitizeCoverageControlFlow;
276static SanitizerBinaryMetadataOptions
278 SanitizerBinaryMetadataOptions Opts;
279 Opts.Covered = CGOpts.SanitizeBinaryMetadataCovered;
280 Opts.Atomics = CGOpts.SanitizeBinaryMetadataAtomics;
281 Opts.UAR = CGOpts.SanitizeBinaryMetadataUAR;
290 if (!CGOpts.SanitizeAddressGlobalsDeadStripping)
292 switch (
T.getObjectFormat()) {
297 return !CGOpts.DisableIntegratedAS;
299 llvm::report_fatal_error(
"ASan not implemented for GOFF");
301 llvm::report_fatal_error(
"ASan not implemented for XCOFF.");
303 case Triple::DXContainer:
305 case Triple::UnknownObjectFormat:
311static std::optional<llvm::CodeModel::Model>
313 unsigned CodeModel = llvm::StringSwitch<unsigned>(CodeGenOpts.
CodeModel)
314 .Case(
"tiny", llvm::CodeModel::Tiny)
315 .Case(
"small", llvm::CodeModel::Small)
316 .Case(
"kernel", llvm::CodeModel::Kernel)
317 .Case(
"medium", llvm::CodeModel::Medium)
318 .Case(
"large", llvm::CodeModel::Large)
319 .Cases({
"default",
""}, ~1u)
321 assert(CodeModel != ~0u &&
"invalid code model!");
322 if (CodeModel == ~1u)
324 return static_cast<llvm::CodeModel::Model
>(CodeModel);
329 return CodeGenFileType::ObjectFile;
331 return CodeGenFileType::Null;
334 return CodeGenFileType::AssemblyFile;
344 StringRef MainFilename,
347 return std::string{};
349 std::string FlatCmdLine;
350 raw_string_ostream OS(FlatCmdLine);
351 bool PrintedOneArg =
false;
352 if (!StringRef(Args[0]).
contains(
"-cc1")) {
353 llvm::sys::printArg(OS,
"-cc1",
true);
354 PrintedOneArg =
true;
356 for (
unsigned i = 0; i < Args.size(); i++) {
357 StringRef Arg = Args[i];
360 if (Arg ==
"-main-file-name" || Arg ==
"-o") {
364 if (Arg.starts_with(
"-object-file-name"))
372 if (Arg == MainFilename || llvm::is_contained(InputFiles, Arg))
375 if (Arg.starts_with(
"-fmessage-length"))
379 llvm::sys::printArg(OS, Arg,
true);
380 PrintedOneArg =
true;
387 llvm::TargetOptions &Options) {
393 Options.MCOptions.BinutilsVersion =
394 llvm::MCTargetOptions::parseBinutilsVersion(CodeGenOpts.
BinutilsVersion);
395 Options.UseInitArray = CodeGenOpts.UseInitArray;
396 Options.MCOptions.DisableIntegratedAS = CodeGenOpts.DisableIntegratedAS;
399 Options.ExceptionModel = llvm::ExceptionHandling::SjLj;
401 Options.ExceptionModel = llvm::ExceptionHandling::WinEH;
403 Options.ExceptionModel = llvm::ExceptionHandling::DwarfCFI;
405 Options.ExceptionModel = llvm::ExceptionHandling::Wasm;
407 Options.ExceptionModel = llvm::ExceptionHandling::Emscripten;
409 Options.NoZerosInBSS = CodeGenOpts.NoZeroInitializedInBSS;
411 Options.BBAddrMap = CodeGenOpts.BBAddrMap;
413 llvm::StringSwitch<llvm::BasicBlockSection>(CodeGenOpts.
BBSections)
414 .Case(
"all", llvm::BasicBlockSection::All)
415 .StartsWith(
"list=", llvm::BasicBlockSection::List)
416 .Case(
"none", llvm::BasicBlockSection::None)
417 .Default(llvm::BasicBlockSection::None);
419 if (Options.BBSections == llvm::BasicBlockSection::List) {
420 ErrorOr<std::unique_ptr<MemoryBuffer>> MBOrErr =
424 Diags.
Report(diag::err_fe_unable_to_load_basic_block_sections_file)
425 << MBOrErr.getError().message();
428 Options.BBSectionsFuncListBuf = std::move(*MBOrErr);
431 if (CodeGenOpts.SplitMachineFunctions)
432 Options.FunctionSplitting = llvm::FunctionSplittingMode::All;
433 Options.EnableStaticDataPartitioning =
434 CodeGenOpts.PartitionStaticDataSections;
435 Options.FunctionSections = CodeGenOpts.FunctionSections;
436 Options.DataSections = CodeGenOpts.DataSections;
437 Options.IgnoreXCOFFVisibility = LangOpts.IgnoreXCOFFVisibility;
438 Options.UniqueSectionNames = CodeGenOpts.UniqueSectionNames;
439 Options.UniqueBasicBlockSectionNames =
440 CodeGenOpts.UniqueBasicBlockSectionNames;
441 Options.SeparateNamedSections = CodeGenOpts.SeparateNamedSections;
442 Options.TLSSize = CodeGenOpts.TLSSize;
443 Options.EnableTLSDESC = CodeGenOpts.EnableTLSDESC;
444 Options.EmulatedTLS = CodeGenOpts.EmulatedTLS;
445 Options.DebuggerTuning = CodeGenOpts.getDebuggerTuning();
446 Options.EmitStackSizeSection = CodeGenOpts.StackSizeSection;
448 Options.EmitAddrsig = CodeGenOpts.Addrsig;
449 Options.ForceDwarfFrameSection = CodeGenOpts.ForceDwarfFrameSection;
450 Options.EmitCallGraphSection = CodeGenOpts.CallGraphSection;
451 Options.EmitCallSiteInfo = CodeGenOpts.EmitCallSiteInfo;
452 Options.XRayFunctionIndex = CodeGenOpts.XRayFunctionIndex;
453 Options.LoopAlignment = CodeGenOpts.LoopAlignment;
454 Options.DebugStrictDwarf = CodeGenOpts.DebugStrictDwarf;
457 Options.JMCInstrument = CodeGenOpts.JMCInstrument;
458 Options.XCOFFReadOnlyPointers = CodeGenOpts.XCOFFReadOnlyPointers;
460 convertDriverVectorLibraryToVectorLibrary(CodeGenOpts.getVecLib());
462 switch (CodeGenOpts.getSwiftAsyncFramePointer()) {
464 Options.SwiftAsyncFramePointer =
465 SwiftAsyncFramePointerMode::DeploymentBased;
469 Options.SwiftAsyncFramePointer = SwiftAsyncFramePointerMode::Always;
473 Options.SwiftAsyncFramePointer = SwiftAsyncFramePointerMode::Never;
478 Options.MCOptions.EmitDwarfUnwind = CodeGenOpts.getEmitDwarfUnwind();
479 Options.MCOptions.EmitCompactUnwindNonCanonical =
480 CodeGenOpts.EmitCompactUnwindNonCanonical;
481 Options.MCOptions.EmitSFrameUnwind = CodeGenOpts.EmitSFrameUnwind;
482 Options.MCOptions.MCRelaxAll = CodeGenOpts.RelaxAll;
483 Options.MCOptions.MCSaveTempLabels = CodeGenOpts.SaveTempLabels;
484 Options.MCOptions.MCUseDwarfDirectory =
485 CodeGenOpts.NoDwarfDirectoryAsm
486 ? llvm::MCTargetOptions::DisableDwarfDirectory
487 : llvm::MCTargetOptions::EnableDwarfDirectory;
488 Options.MCOptions.MCNoExecStack = CodeGenOpts.NoExecStack;
489 Options.MCOptions.MCIncrementalLinkerCompatible =
490 CodeGenOpts.IncrementalLinkerCompatible;
491 Options.MCOptions.MCFatalWarnings = CodeGenOpts.FatalWarnings;
492 Options.MCOptions.MCNoWarn = CodeGenOpts.NoWarn;
493 Options.MCOptions.AsmVerbose = CodeGenOpts.AsmVerbose;
494 Options.MCOptions.Dwarf64 = CodeGenOpts.Dwarf64;
495 Options.MCOptions.PreserveAsmComments = CodeGenOpts.PreserveAsmComments;
496 Options.MCOptions.Crel = CodeGenOpts.Crel;
497 Options.MCOptions.RelocSectionSym = CodeGenOpts.getRelocSectionSym();
498 Options.MCOptions.ImplicitMapSyms = CodeGenOpts.ImplicitMapSyms;
499 Options.MCOptions.X86RelaxRelocations = CodeGenOpts.X86RelaxRelocations;
500 Options.MCOptions.CompressDebugSections =
501 CodeGenOpts.getCompressDebugSections();
502 if (CodeGenOpts.OutputAsmVariant != 3)
503 Options.MCOptions.OutputAsmVariant = CodeGenOpts.OutputAsmVariant;
504 Options.MCOptions.ABIName = TargetOpts.
ABI;
505 for (
const auto &Entry : HSOpts.UserEntries)
506 if (!Entry.IsFramework &&
510 Options.MCOptions.IASSearchPaths.push_back(
511 Entry.IgnoreSysRoot ? Entry.Path : HSOpts.Sysroot + Entry.Path);
512 Options.MCOptions.Argv0 = CodeGenOpts.
Argv0 ? CodeGenOpts.
Argv0 :
"";
519 InputFiles.push_back(Input.getFile());
523 Options.MCOptions.PPCUseFullRegisterNames =
524 CodeGenOpts.PPCUseFullRegisterNames;
525 Options.MisExpect = CodeGenOpts.MisExpect;
530static std::optional<GCOVOptions>
541 Options.NoRedZone = CodeGenOpts.DisableRedZone;
544 Options.Atomic = CodeGenOpts.AtomicProfileUpdate;
548static std::optional<InstrProfOptions>
553 InstrProfOptions Options;
554 Options.NoRedZone = CodeGenOpts.DisableRedZone;
558 Options.Atomic = CodeGenOpts.AtomicProfileUpdate;
563 vfs::FileSystem &VFS) {
565 BackendArgs.push_back(
"clang");
567 BackendArgs.push_back(
"-debug-pass");
568 BackendArgs.push_back(CodeGenOpts.
DebugPass.c_str());
571 BackendArgs.push_back(
"-limit-float-precision");
578 if (BackendArgs.size() == 1)
580 BackendArgs.push_back(
nullptr);
584 llvm::cl::ParseCommandLineOptions(BackendArgs.size() - 1, BackendArgs.data(),
589void EmitAssemblyHelper::CreateTargetMachine(
bool MustCreateTM) {
592 const llvm::Triple &Triple = TheModule->getTargetTriple();
593 const llvm::Target *TheTarget = TargetRegistry::lookupTarget(Triple,
Error);
596 Diags.
Report(diag::err_fe_unable_to_create_target) <<
Error;
600 std::optional<llvm::CodeModel::Model> CM =
getCodeModel(CodeGenOpts);
601 std::string FeaturesStr =
604 std::optional<CodeGenOptLevel> OptLevelOrNone =
605 CodeGenOpt::getLevel(CodeGenOpts.OptimizationLevel);
606 assert(OptLevelOrNone &&
"Invalid optimization level!");
607 CodeGenOptLevel OptLevel = *OptLevelOrNone;
609 llvm::TargetOptions Options;
612 Options.MCOptions.LibraryOptions =
613 &TheModule->getContext().getLibraryOptions();
614 TM.reset(TheTarget->createTargetMachine(Triple, TargetOpts.
CPU, FeaturesStr,
615 Options, RM, CM, OptLevel));
621 switch (Opts.OptimizationLevel) {
623 llvm_unreachable(
"Invalid optimization level!");
626 return OptimizationLevel::O0;
629 return OptimizationLevel::O1;
632 return OptimizationLevel::O2;
635 return OptimizationLevel::O3;
642 if (TargetTriple.getArch() == llvm::Triple::x86_64 ||
643 TargetTriple.isAArch64(64) || TargetTriple.isRISCV() ||
644 TargetTriple.isARM() || TargetTriple.isThumb() ||
645 TargetTriple.getArch() == llvm::Triple::hexagon)
649 PB.registerOptimizerLastEPCallback(
650 [&](ModulePassManager &MPM, OptimizationLevel Level, ThinOrFullLTOPhase) {
651 if (Level == OptimizationLevel::O0 &&
653 MPM.addPass(createModuleToFunctionPassAdaptor(KCFIPass()));
658 PB.registerPeepholeEPCallback(
659 [&](FunctionPassManager &FPM, OptimizationLevel Level) {
660 if (Level != OptimizationLevel::O0 &&
662 FPM.addPass(KCFIPass());
669 auto SanitizersCallback = [&](ModulePassManager &MPM, OptimizationLevel Level,
670 ThinOrFullLTOPhase) {
674 SanitizerCoveragePass(SancovOpts, PB.getVirtualFileSystemPtr(),
680 MPM.addPass(SanitizerBinaryMetadataPass(
682 PB.getVirtualFileSystemPtr(),
686 auto MSanPass = [&](
SanitizerMask Mask,
bool CompileKernel) {
688 int TrackOrigins = CodeGenOpts.SanitizeMemoryTrackOrigins;
691 MemorySanitizerOptions
options(TrackOrigins, Recover, CompileKernel,
692 CodeGenOpts.SanitizeMemoryParamRetval);
693 MPM.addPass(MemorySanitizerPass(
options));
694 if (Level != OptimizationLevel::O0) {
699 MPM.addPass(RequireAnalysisPass<GlobalsAA, llvm::Module>());
700 FunctionPassManager FPM;
701 FPM.addPass(EarlyCSEPass(
true ));
702 FPM.addPass(InstCombinePass());
703 FPM.addPass(JumpThreadingPass());
704 FPM.addPass(GVNPass());
705 FPM.addPass(InstCombinePass());
706 MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));
710 MSanPass(SanitizerKind::Memory,
false);
711 MSanPass(SanitizerKind::KernelMemory,
true);
713 if (LangOpts.
Sanitize.
has(SanitizerKind::Thread)) {
714 MPM.addPass(ModuleThreadSanitizerPass());
715 MPM.addPass(createModuleToFunctionPassAdaptor(ThreadSanitizerPass()));
719 MPM.addPass(TypeSanitizerPass());
721 if (LangOpts.
Sanitize.
has(SanitizerKind::NumericalStability))
722 MPM.addPass(NumericalStabilitySanitizerPass());
724 if (LangOpts.
Sanitize.
has(SanitizerKind::Realtime))
725 MPM.addPass(RealtimeSanitizerPass());
727 auto ASanPass = [&](
SanitizerMask Mask,
bool CompileKernel) {
730 bool UseOdrIndicator = CodeGenOpts.SanitizeAddressUseOdrIndicator;
731 llvm::AsanDtorKind DestructorKind =
732 CodeGenOpts.getSanitizeAddressDtor();
733 AddressSanitizerOptions Opts;
734 Opts.CompileKernel = CompileKernel;
736 Opts.UseAfterScope = CodeGenOpts.SanitizeAddressUseAfterScope;
737 Opts.UseAfterReturn = CodeGenOpts.getSanitizeAddressUseAfterReturn();
738 MPM.addPass(AddressSanitizerPass(Opts, UseGlobalGC, UseOdrIndicator,
742 ASanPass(SanitizerKind::Address,
false);
743 ASanPass(SanitizerKind::KernelAddress,
true);
745 auto HWASanPass = [&](
SanitizerMask Mask,
bool CompileKernel) {
748 MPM.addPass(HWAddressSanitizerPass(
749 {CompileKernel, Recover,
750 CodeGenOpts.OptimizationLevel == 0}));
753 HWASanPass(SanitizerKind::HWAddress,
false);
754 HWASanPass(SanitizerKind::KernelHWAddress,
true);
756 if (LangOpts.
Sanitize.
has(SanitizerKind::DataFlow)) {
758 PB.getVirtualFileSystemPtr()));
762 PB.registerOptimizerEarlyEPCallback(
763 [SanitizersCallback](ModulePassManager &MPM, OptimizationLevel Level,
764 ThinOrFullLTOPhase Phase) {
765 ModulePassManager NewMPM;
766 SanitizersCallback(NewMPM, Level, Phase);
767 if (!NewMPM.isEmpty()) {
769 NewMPM.addPass(RequireAnalysisPass<GlobalsAA, llvm::Module>());
770 MPM.addPass(std::move(NewMPM));
775 PB.registerOptimizerLastEPCallback(SanitizersCallback);
785 uint64_t AllowRuntimeCheckSkipHotCutoff =
790 SanitizerKind::Address | SanitizerKind::KernelAddress |
791 SanitizerKind::Thread | SanitizerKind::Memory |
792 SanitizerKind::KernelMemory | SanitizerKind::HWAddress |
793 SanitizerKind::KernelHWAddress);
796 if (LowerAllowCheckPass::isRequested(LibraryOptions) ||
797 ScaledCutoffs.has_value() ||
799 LowerAllowSanitize) {
801 PB.registerOptimizerEarlyEPCallback(
802 [ScaledCutoffs, AllowRuntimeCheckSkipHotCutoff](
803 ModulePassManager &MPM, OptimizationLevel Level,
804 ThinOrFullLTOPhase Phase) {
805 LowerAllowCheckPass::Options Opts;
807 if (ScaledCutoffs.has_value())
808 Opts.cutoffs = ScaledCutoffs.value();
809 Opts.runtime_check = AllowRuntimeCheckSkipHotCutoff;
811 createModuleToFunctionPassAdaptor(LowerAllowCheckPass(Opts)));
827 MPM.addPass(createModuleToFunctionPassAdaptor(LowerExpectIntrinsicPass()));
828 MPM.addPass(createModuleToFunctionPassAdaptor(SimplifyCFGPass()));
830 createModuleToFunctionPassAdaptor(SROAPass(SROAOptions::PreserveCFG)));
831 MPM.addPass(createModuleToFunctionPassAdaptor(EarlyCSEPass()));
836 MPM.addPass(ForceFunctionAttrsPass());
837 MPM.addPass(InferFunctionAttrsPass());
838 MPM.addPass(IPSCCPPass());
839 MPM.addPass(GlobalOptPass());
840 MPM.addPass(createModuleToFunctionPassAdaptor(PromotePass()));
841 MPM.addPass(DeadArgumentEliminationPass());
842 MPM.addPass(createModuleToFunctionPassAdaptor(InstCombinePass()));
843 MPM.addPass(createModuleToFunctionPassAdaptor(SimplifyCFGPass()));
845 createModuleToPostOrderCGSCCPassAdaptor(PostOrderFunctionAttrsPass()));
848void EmitAssemblyHelper::RunOptimizationPipeline(
849 BackendAction Action, std::unique_ptr<raw_pwrite_stream> &OS,
850 std::unique_ptr<llvm::ToolOutputFile> &ThinLinkOS, BackendConsumer *BC) {
851 const cl::LibraryOptionsContext &LibraryOptions =
852 TheModule->getContext().getLibraryOptions();
853 std::optional<PGOOptions> PGOOpt;
860 CodeGenOpts.DebugInfoForProfiling,
862 CodeGenOpts.AtomicProfileUpdate);
866 : PGOOptions::NoCSAction;
871 CodeGenOpts.DebugInfoForProfiling);
878 CodeGenOpts.DebugInfoForProfiling, CodeGenOpts.PseudoProbeForProfiling);
882 PGOOptions::NoAction, PGOOptions::NoCSAction,
884 else if (CodeGenOpts.PseudoProbeForProfiling)
886 PGOOpt = PGOOptions(
"",
"",
"",
"", PGOOptions::NoAction,
888 CodeGenOpts.DebugInfoForProfiling,
true);
889 else if (CodeGenOpts.DebugInfoForProfiling)
891 PGOOpt = PGOOptions(
"",
"",
"",
"", PGOOptions::NoAction,
897 "Cannot have both CSProfileUse pass and CSProfileGen pass at "
900 assert(PGOOpt->Action != PGOOptions::IRInstr &&
901 PGOOpt->Action != PGOOptions::SampleUse &&
902 "Cannot run CSProfileGen pass with ProfileGen or SampleUse "
905 PGOOpt->CSAction = PGOOptions::CSIRInstr;
909 "", PGOOptions::NoAction, PGOOptions::CSIRInstr,
913 TM->setPGOOption(PGOOpt);
915 PipelineTuningOptions PTO(&LibraryOptions);
916 PTO.LoopUnrolling = CodeGenOpts.UnrollLoops;
917 PTO.LoopInterchange = CodeGenOpts.InterchangeLoops;
918 PTO.LoopFusion = CodeGenOpts.FuseLoops;
921 PTO.LoopInterleaving = CodeGenOpts.UnrollLoops;
922 PTO.LoopVectorization = CodeGenOpts.VectorizeLoop;
923 PTO.SLPVectorization = CodeGenOpts.VectorizeSLP;
924 PTO.MergeFunctions = CodeGenOpts.MergeFunctions;
927 PTO.CallGraphProfile = !CodeGenOpts.DisableIntegratedAS;
928 PTO.UnifiedLTO = CodeGenOpts.UnifiedLTO;
929 PTO.DevirtualizeSpeculatively = CodeGenOpts.DevirtualizeSpeculatively;
931 LoopAnalysisManager LAM;
932 FunctionAnalysisManager FAM;
933 CGSCCAnalysisManager CGAM;
934 ModuleAnalysisManager MAM;
936 bool DebugPassStructure = CodeGenOpts.
DebugPass ==
"Structure";
937 PassInstrumentationCallbacks PIC;
938 PrintPassOptions PrintPassOpts;
939 PrintPassOpts.Indent = DebugPassStructure;
940 PrintPassOpts.SkipAnalyses = DebugPassStructure;
941 StandardInstrumentations SI(
942 TheModule->getContext(),
943 (CodeGenOpts.DebugPassManager || DebugPassStructure),
944 CodeGenOpts.VerifyEach, PrintPassOpts);
945 SI.registerCallbacks(PIC, &MAM);
949 switch (CodeGenOpts.getAssignmentTrackingMode()) {
950 case CodeGenOptions::AssignmentTrackingOpts::Forced:
951 PB.registerPipelineStartEPCallback(
952 [&](ModulePassManager &MPM, OptimizationLevel
Level) {
953 MPM.addPass(AssignmentTrackingPass());
956 case CodeGenOptions::AssignmentTrackingOpts::Enabled:
959 if (!CodeGenOpts.PrepareForThinLTO && !CodeGenOpts.PrepareForLTO &&
960 CodeGenOpts.getDebuggerTuning() != llvm::DebuggerKind::LLDB) {
961 PB.registerPipelineStartEPCallback(
962 [&](ModulePassManager &MPM, OptimizationLevel
Level) {
964 if (
Level != OptimizationLevel::O0)
965 MPM.addPass(AssignmentTrackingPass());
969 case CodeGenOptions::AssignmentTrackingOpts::Disabled:
974 DebugifyEachInstrumentation Debugify;
975 DebugInfoPerPass DebugInfoBeforePass;
976 if (CodeGenOpts.EnableDIPreservationVerify) {
977 Debugify.setDebugifyMode(DebugifyMode::OriginalDebugInfo);
978 Debugify.setDebugInfoBeforePass(DebugInfoBeforePass);
981 Debugify.setOrigDIVerifyBugsReportFilePath(
983 Debugify.registerCallbacks(PIC, MAM);
985#if LLVM_ENABLE_DEBUGLOC_TRACKING_COVERAGE
992 if (!F.getSubprogram())
994 for (BasicBlock &BB : F)
995 for (Instruction &I : BB)
996 if (!I.getDebugLoc())
997 I.setDebugLoc(DebugLoc::getCompilerGenerated());
1002 for (
const std::unique_ptr<PassPlugin> &Plugin : CI.
getPassPlugins())
1003 Plugin->registerPassBuilderCallbacks(PB);
1006#define HANDLE_EXTENSION(Ext) \
1007 get##Ext##PluginInfo().RegisterPassBuilderCallbacks(PB);
1008#include "llvm/Support/Extension.def"
1012 std::unique_ptr<TargetLibraryInfoImpl> TLII(
1013 llvm::driver::createTLII(TargetTriple, CodeGenOpts.getVecLib()));
1014 FAM.registerPass([&] {
return TargetLibraryAnalysis(*TLII); });
1017 PB.registerModuleAnalyses(MAM);
1018 PB.registerCGSCCAnalyses(CGAM);
1019 PB.registerFunctionAnalyses(FAM);
1020 PB.registerLoopAnalyses(LAM);
1021 PB.crossRegisterProxies(LAM, FAM, CGAM, MAM);
1023 ModulePassManager MPM;
1025 if (CodeGenOpts.VerifyModule)
1026 MPM.addPass(VerifierPass());
1028 if (!CodeGenOpts.DisableLLVMPasses) {
1033 const bool PrepareForThinLTO = CodeGenOpts.PrepareForThinLTO;
1034 const bool PrepareForLTO = CodeGenOpts.PrepareForLTO;
1036 if (LangOpts.ObjCAutoRefCount) {
1037 PB.registerPipelineStartEPCallback(
1038 [](ModulePassManager &MPM, OptimizationLevel
Level) {
1039 if (
Level != OptimizationLevel::O0)
1041 createModuleToFunctionPassAdaptor(ObjCARCExpandPass()));
1043 PB.registerScalarOptimizerLateEPCallback(
1044 [](FunctionPassManager &FPM, OptimizationLevel
Level) {
1045 if (
Level != OptimizationLevel::O0)
1046 FPM.addPass(ObjCARCOptPass());
1056 if (IsThinLTOPostLink)
1057 PB.registerPipelineStartEPCallback(
1058 [](ModulePassManager &MPM, OptimizationLevel
Level) {
1059 MPM.addPass(DropTypeTestsPass());
1064 if (LangOpts.
Sanitize.
has(SanitizerKind::LocalBounds))
1065 PB.registerScalarOptimizerLateEPCallback([
this](FunctionPassManager &FPM,
1066 OptimizationLevel
Level) {
1067 BoundsCheckingPass::Options Options;
1070 static_assert(SanitizerKind::SO_LocalBounds <=
1071 std::numeric_limits<
1072 decltype(Options.GuardKind)::value_type>
::max(),
1073 "Update type of llvm.allow.ubsan.check to represent "
1074 "SanitizerKind::SO_LocalBounds.");
1075 Options.GuardKind = SanitizerKind::SO_LocalBounds;
1082 CodeGenOpts.SanitizeMinimalRuntime),
1086 static_cast<bool>(CodeGenOpts.SanitizeHandlerPreserveAllRegs),
1089 FPM.addPass(BoundsCheckingPass(Options));
1092 if (!IsThinLTOPostLink) {
1098 PB.registerPipelineStartEPCallback(
1099 [&](ModulePassManager &MPM, OptimizationLevel
Level) {
1100 if (
Level == OptimizationLevel::O0 &&
1101 LangOpts.
Sanitize.
has(SanitizerKind::AllocToken)) {
1107 MPM.addPass(InferFunctionAttrsPass());
1111 if (CodeGenOpts.CopyProf) {
1114 PB.registerPipelineEarlySimplificationEPCallback(
1115 [](ModulePassManager &MPM, OptimizationLevel, ThinOrFullLTOPhase) {
1116 MPM.addPass(createModuleToFunctionPassAdaptor(CopyProfPass()));
1117 MPM.addPass(ModuleCopyProfPass());
1121 PB.registerOptimizerLastEPCallback([](ModulePassManager &MPM,
1123 ThinOrFullLTOPhase) {
1124 MPM.addPass(createModuleToFunctionPassAdaptor(CopyProfStoresPass()));
1129 if (std::optional<GCOVOptions> Options =
1131 PB.registerPipelineStartEPCallback(
1132 [
this, Options](ModulePassManager &MPM, OptimizationLevel
Level) {
1136 if (std::optional<InstrProfOptions> Options =
1138 PB.registerPipelineStartEPCallback(
1139 [Options](ModulePassManager &MPM, OptimizationLevel
Level) {
1140 MPM.addPass(InstrProfilingLoweringPass(*Options,
false));
1146 PB.registerOptimizerLastEPCallback([](ModulePassManager &MPM,
1147 OptimizationLevel
Level,
1148 ThinOrFullLTOPhase) {
1149 MPM.addPass(createModuleToFunctionPassAdaptor(MemProfilerPass()));
1150 MPM.addPass(ModuleMemProfilerPass());
1154 if (CodeGenOpts.FatLTO) {
1155 MPM.addPass(PB.buildFatLTODefaultPipeline(
1156 Level, PrepareForThinLTO,
1157 PrepareForThinLTO || shouldEmitRegularLTOSummary(),
1158 CodeGenOpts.VerifyModule));
1159 }
else if (PrepareForThinLTO) {
1160 MPM.addPass(PB.buildThinLTOPreLinkDefaultPipeline(
Level));
1161 }
else if (PrepareForLTO) {
1162 MPM.addPass(PB.buildLTOPreLinkDefaultPipeline(
Level));
1164 MPM.addPass(PB.buildPerModuleDefaultPipeline(
Level));
1166 }
else if (
mapToLevel(CodeGenOpts) > OptimizationLevel::O0 &&
1167 CodeGenOpts.AMDGCNSPIRVSizeOptimization) {
1168 if (!TargetTriple.isSPIRV() ||
1169 (TargetTriple.getVendor() != llvm::Triple::VendorType::AMD)) {
1170 Diags.
Report(diag::err_opt_not_valid_on_target)
1171 <<
"fenable-spirv-size-optimization";
1178 if (CodeGenOpts.LinkBitcodePostopt) {
1179 MPM.addPass(LinkInModulesPass(BC));
1180 MPM.addPass(AssignGUIDPass());
1183 if (LangOpts.HIPStdPar && !LangOpts.CUDAIsDevice &&
1184 LangOpts.HIPStdParInterposeAlloc)
1185 MPM.addPass(HipStdParAllocationInterpositionPass());
1193 MPM.addPass(VerifierPass());
1196 CodeGenOpts.FatLTO) {
1197 if (CodeGenOpts.PrepareForThinLTO && !CodeGenOpts.DisableLLVMPasses) {
1198 if (!TheModule->getModuleFlag(
"EnableSplitLTOUnit"))
1199 TheModule->addModuleFlag(llvm::Module::Error,
"EnableSplitLTOUnit",
1200 CodeGenOpts.EnableSplitLTOUnit);
1207 MPM.addPass(ThinLTOBitcodeWriterPass(
1208 *OS, ThinLinkOS ? &ThinLinkOS->os() :
nullptr));
1210 MPM.addPass(PrintModulePass(*OS,
"", CodeGenOpts.EmitLLVMUseLists,
1217 bool EmitLTOSummary = shouldEmitRegularLTOSummary();
1218 if (EmitLTOSummary) {
1219 if (!TheModule->getModuleFlag(
"ThinLTO") && !CodeGenOpts.UnifiedLTO)
1220 TheModule->addModuleFlag(llvm::Module::Error,
"ThinLTO",
uint32_t(0));
1221 if (!TheModule->getModuleFlag(
"EnableSplitLTOUnit"))
1222 TheModule->addModuleFlag(llvm::Module::Error,
"EnableSplitLTOUnit",
1226 MPM.addPass(BitcodeWriterPass(*OS, CodeGenOpts.EmitLLVMUseLists,
1229 MPM.addPass(PrintModulePass(*OS,
"", CodeGenOpts.EmitLLVMUseLists,
1235 if (shouldEmitUnifiedLTOModueFlag() &&
1236 !TheModule->getModuleFlag(
"UnifiedLTO"))
1237 TheModule->addModuleFlag(llvm::Module::Error,
"UnifiedLTO",
uint32_t(1));
1244 if (PB.getPrintPipelinePasses()) {
1245 MPM.printPipeline(outs(), [&PIC](StringRef ClassName) {
1246 auto PassName = PIC.getPassNameForClassName(ClassName);
1247 return PassName.empty() ? ClassName : PassName;
1255 PrettyStackTraceString CrashInfo(
"Optimizer");
1256 llvm::TimeTraceScope TimeScope(
"Optimizer");
1262 MPM.run(*TheModule, MAM);
1268void EmitAssemblyHelper::RunCodegenPipeline(
1269 BackendAction Action, std::unique_ptr<raw_pwrite_stream> &OS,
1270 std::unique_ptr<llvm::ToolOutputFile> &DwoOS) {
1280 for (
const std::unique_ptr<llvm::PassPlugin> &Plugin : CI.
getPassPlugins()) {
1281 if (Plugin->invokePreCodeGenCallback(*TheModule, *TM, CGFT, *OS))
1291 TimeCodegenPasses([&]() {
1292 Error CodeGenError = runCodeGenPipeline(
1293 *TM, *TheModule, *OS, DwoOS, CGFT, !CodeGenOpts.VerifyModule,
1296 Diags.
Report(diag::err_fe_unable_to_interface_with_target);
1300void EmitAssemblyHelper::TimeCodegenPasses(
1301 llvm::function_ref<
void()> RunPasses) {
1302 PrettyStackTraceString CrashInfo(
"Code generation");
1303 llvm::TimeTraceScope TimeScope(
"CodeGenPasses");
1306 timer.init(
"codegen",
"Machine code generation", CI.
getTimerGroup());
1315 std::unique_ptr<raw_pwrite_stream> OS,
1316 BackendConsumer *BC) {
1320 CreateTargetMachine(RequiresCodeGen);
1322 if (RequiresCodeGen && !TM)
1324 if (TM && TheModule->getDataLayout().isDefault())
1325 TheModule->setDataLayout(TheModule->getTargetTriple().computeDataLayout(
1326 TM->getTargetABIName(*TheModule)));
1329 cl::PrintOptionValues();
1331 std::unique_ptr<llvm::ToolOutputFile> ThinLinkOS, DwoOS;
1332 RunOptimizationPipeline(Action, OS, ThinLinkOS, BC);
1333 RunCodegenPipeline(Action, OS, DwoOS);
1343 llvm::Module *M, std::unique_ptr<raw_pwrite_stream> OS,
1344 std::string SampleProfile, std::string ProfileRemapping,
1349 DenseMap<StringRef, DenseMap<GlobalValue::GUID, GlobalValueSummary *>>
1350 ModuleToDefinedGVSummaries;
1351 CombinedIndex->collectDefinedGVSummariesPerModule(ModuleToDefinedGVSummaries);
1358 FunctionImporter::ImportIDTable ImportIDs;
1359 FunctionImporter::ImportMapTy ImportList(ImportIDs);
1360 if (!lto::initImportList(*M, *CombinedIndex, ImportList))
1363 auto AddStream = [&](
size_t Task,
const Twine &ModuleName) {
1364 return std::make_unique<CachedFileStream>(std::move(OS),
1365 CGOpts.ObjectFilenameForDebug);
1368 if (CGOpts.SaveTempsFilePrefix !=
"") {
1369 if (
Error E = Conf.addSaveTemps(CGOpts.SaveTempsFilePrefix +
".",
1371 handleAllErrors(std::move(E), [&](ErrorInfoBase &EIB) {
1372 errs() <<
"Error setting up ThinLTO save-temps: " << EIB.message()
1377 Conf.CPU = TOpts.CPU;
1379 Conf.MAttrs = TOpts.Features;
1380 Conf.RelocModel = CGOpts.RelocationModel;
1381 std::optional<CodeGenOptLevel> OptLevelOrNone =
1382 CodeGenOpt::getLevel(CGOpts.OptimizationLevel);
1383 assert(OptLevelOrNone &&
"Invalid optimization level!");
1384 Conf.CGOptLevel = *OptLevelOrNone;
1385 Conf.OptLevel = CGOpts.OptimizationLevel;
1387 Conf.SampleProfile = std::move(SampleProfile);
1388 const cl::LibraryOptionsContext &LibraryOptions =
1389 M->getContext().getLibraryOptions();
1390 Conf.PTO = PipelineTuningOptions(&LibraryOptions);
1391 Conf.PTO.LoopUnrolling = CGOpts.UnrollLoops;
1392 Conf.PTO.LoopInterchange = CGOpts.InterchangeLoops;
1393 Conf.PTO.LoopFusion = CGOpts.FuseLoops;
1396 Conf.PTO.LoopInterleaving = CGOpts.UnrollLoops;
1397 Conf.PTO.LoopVectorization = CGOpts.VectorizeLoop;
1398 Conf.PTO.SLPVectorization = CGOpts.VectorizeSLP;
1401 Conf.PTO.CallGraphProfile = !CGOpts.DisableIntegratedAS;
1404 if (CGOpts.hasProfileCSIRInstr()) {
1405 Conf.RunCSIRInstr =
true;
1407 }
else if (CGOpts.hasProfileCSIRUse()) {
1408 Conf.RunCSIRInstr =
false;
1409 Conf.CSIRProfile = std::move(CGOpts.ProfileInstrumentUsePath);
1412 Conf.ProfileRemapping = std::move(ProfileRemapping);
1413 Conf.DebugPassManager = CGOpts.DebugPassManager;
1414 Conf.VerifyEach = CGOpts.VerifyEach;
1415 Conf.RemarksWithHotness = CGOpts.DiagnosticsWithHotness;
1416 Conf.RemarksFilename = CGOpts.OptRecordFile;
1417 Conf.RemarksPasses = CGOpts.OptRecordPasses;
1418 Conf.RemarksFormat = CGOpts.OptRecordFormat;
1419 Conf.SplitDwarfFile = CGOpts.SplitDwarfFile;
1420 Conf.SplitDwarfOutput = CGOpts.SplitDwarfOutput;
1422 Conf.LoadedPassPlugins.push_back(Plugin.get());
1425 Conf.PreCodeGenModuleHook = [](
size_t Task,
const llvm::Module &Mod) {
1430 Conf.PreCodeGenModuleHook = [&](
size_t Task,
const llvm::Module &Mod) {
1431 M->renumberMetadataForAssembly();
1432 M->print(*OS,
nullptr, CGOpts.EmitLLVMUseLists);
1437 Conf.PreCodeGenModuleHook = [&](
size_t Task,
const llvm::Module &Mod) {
1438 WriteBitcodeToFile(*M, *OS, CGOpts.EmitLLVMUseLists);
1451 finalizeLLVMOptimizationRemarks(M->getContext());
1452 if (
Error E = thinBackend(
1453 Conf, -1, AddStream, *M, *CombinedIndex, ImportList,
1454 ModuleToDefinedGVSummaries[M->getModuleIdentifier()],
1455 nullptr, Conf.CodeGenOnly, {},
1456 nullptr, CGOpts.CmdArgs)) {
1457 handleAllErrors(std::move(E), [&](ErrorInfoBase &EIB) {
1458 errs() <<
"Error running ThinLTO backend: " << EIB.message() <<
'\n';
1467 auto SaveModule = [&](StringRef Name, llvm::Module &M) {
1473 raw_fd_ostream OS(Path, EC, sys::fs::OpenFlags::OF_None);
1477 errs() <<
"failed to open " << Path <<
": " << EC.message() <<
'\n';
1481 M.print(OS,
nullptr);
1485 std::string PromotionSuffix;
1492 for (
auto *CU : M->debug_compile_units()) {
1493 if (CU->getDirectory().size() > 0)
1494 Hash.update(CU->getDirectory());
1496 Hash.update(CU->getFilename());
1501 PromotionSuffix =
".dyndbg." + utohexstr(
Result.low());
1504 SaveModule(
"dyndbg.0.input", *M);
1506 auto UnoptM = prepareForDynamicDebugging(M, PromotionSuffix);
1507 SaveModule(
"dyndbg.1.inner", *UnoptM);
1509 if (!CGOpts.DiscardDynamicDebuggingDebugModule) {
1511 UnoptOpts.OptimizationLevel = 0;
1512 UnoptOpts.OptimizeSize = 0;
1513 EmitAssemblyHelper AsmHelper(CI, UnoptOpts, UnoptM.get(), VFS);
1517 std::unique_ptr<llvm::raw_pwrite_stream> UnoptOS =
1518 std::make_unique<llvm::raw_svector_ostream>(UnoptBuf);
1525 assert(!UnoptBuf.empty() &&
"Expected emitAssembly to fill UnoptBuf");
1528 StringRef SR(UnoptBuf.data(), UnoptBuf.size());
1529 std::unique_ptr<MemoryBuffer> Buf =
1530 MemoryBuffer::getMemBuffer(SR,
"",
false);
1532 GlobalVariable *EmbeddedGV =
1533 llvm::embedBufferInModule(*M, *Buf,
".debug_llvm_dyndbg", Align(8),
1536 auto &
C = M->getContext();
1537 auto getU32Metadata = [&
C](
unsigned Val) {
1538 return ConstantAsMetadata::get(ConstantInt::get(
C, APInt(32, Val)));
1540 EmbeddedGV->addMetadata(
1541 LLVMContext::MD_elf_section_properties,
1542 *MDTuple::get(
C, { getU32Metadata(ELF::SHT_LLVM_DYNDBG_ELF),
1543 getU32Metadata(0)}));
1545 SaveModule(
"dyndbg.2.outer", *M);
1551 std::unique_ptr<raw_pwrite_stream> OS,
1553 llvm::TimeTraceScope TimeScope(
"Backend");
1556 std::unique_ptr<llvm::Module> EmptyModule;
1559 auto BypassSandbox = sys::sandbox::scopedDisable();
1563 std::unique_ptr<ModuleSummaryIndex> CombinedIndex;
1564 if (
Error E = llvm::getModuleSummaryIndexForFile(
1567 .moveInto(CombinedIndex)) {
1568 logAllUnhandledErrors(std::move(E), errs(),
1569 "Error loading index file '" +
1577 if (CombinedIndex) {
1578 if (!CombinedIndex->skipModuleByDistributedBackend()) {
1590 EmptyModule = std::make_unique<llvm::Module>(
"empty", M->getContext());
1591 EmptyModule->setTargetTriple(M->getTargetTriple());
1592 M = EmptyModule.get();
1596 bool EnableDynamicDebugging = CGOpts.DynamicDebugging;
1597 if (EnableDynamicDebugging) {
1601 const llvm::Target *TheTarget =
1602 TargetRegistry::lookupTarget(M->getTargetTriple(),
Error);
1603 if (!TheTarget && !CGOpts.DiscardDynamicDebuggingDebugModule) {
1604 Diags.
Report(diag::warn_dyndbg_unable_to_create_target) <<
Error;
1605 EnableDynamicDebugging =
false;
1612 if (CGOpts.getProfileInstr() != driver::ProfileInstrKind::ProfileNone) {
1613 Diags.
Report(diag::err_dyndbg_no_instrumentation);
1614 EnableDynamicDebugging =
false;
1617 if (EnableDynamicDebugging)
1620 EmitAssemblyHelper AsmHelper(CI, CGOpts, M, VFS);
1621 AsmHelper.emitAssembly(Action, std::move(OS), BC);
1627 std::string DLDesc = M->getDataLayout().getStringRepresentation();
1628 std::string TDesc = M->getTargetTriple().computeDataLayout(
1629 AsmHelper.TM->getTargetABIName(*M));
1630 if (DLDesc != TDesc)
1631 Diags.
Report(diag::err_data_layout_mismatch) << DLDesc << TDesc;
1638 llvm::MemoryBufferRef Buf) {
1641 llvm::embedBitcodeInModule(
1653 llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>> ObjectOrErr =
1654 VFS.getBufferForFile(OffloadObject);
1655 if (ObjectOrErr.getError()) {
1656 Diags.
Report(diag::err_failed_to_open_for_embedding) << OffloadObject;
1660 llvm::embedBufferInModule(*M, **ObjectOrErr,
".llvm.offloading",
1661 Align(object::OffloadBinary::getAlignment()));
static bool actionRequiresCodeGen(BackendAction Action)
static void addSanitizers(const Triple &TargetTriple, const CodeGenOptions &CodeGenOpts, const LangOptions &LangOpts, PassBuilder &PB)
static std::optional< llvm::CodeModel::Model > getCodeModel(const CodeGenOptions &CodeGenOpts)
static void runThinLTOBackend(CompilerInstance &CI, ModuleSummaryIndex *CombinedIndex, llvm::Module *M, std::unique_ptr< raw_pwrite_stream > OS, std::string SampleProfile, std::string ProfileRemapping, BackendAction Action)
static std::string getProfileGenName(const cl::LibraryOptionsContext &LibraryOptions, const CodeGenOptions &CodeGenOpts)
static void createAndEmbedModuleForDynamicDebugging(CompilerInstance &CI, CodeGenOptions &CGOpts, llvm::Module *M, IntrusiveRefCntPtr< llvm::vfs::FileSystem > VFS, BackendConsumer *BC)
static SanitizerBinaryMetadataOptions getSanitizerBinaryMetadataOptions(const CodeGenOptions &CGOpts)
static std::optional< GCOVOptions > getGCOVOptions(const CodeGenOptions &CodeGenOpts, const LangOptions &LangOpts)
static bool initTargetOptions(const CompilerInstance &CI, DiagnosticsEngine &Diags, llvm::TargetOptions &Options)
static void setCommandLineOpts(const CodeGenOptions &CodeGenOpts, vfs::FileSystem &VFS)
static void addKCFIPass(const Triple &TargetTriple, const LangOptions &LangOpts, PassBuilder &PB)
static void addAMDGCNSPIRVSizeOptimizationPasses(ModulePassManager &MPM)
static SanitizerCoverageOptions getSancovOptsFromCGOpts(const CodeGenOptions &CGOpts)
static OptimizationLevel mapToLevel(const CodeGenOptions &Opts)
void addLowerAllowCheckPass(const cl::LibraryOptionsContext &LibraryOptions, const CodeGenOptions &CodeGenOpts, const LangOptions &LangOpts, PassBuilder &PB)
static std::string flattenClangCommandLine(ArrayRef< std::string > Args, StringRef MainFilename, ArrayRef< StringRef > InputFiles)
static std::optional< InstrProfOptions > getInstrProfOptions(const CodeGenOptions &CodeGenOpts, const LangOptions &LangOpts)
static bool asanUseGlobalsGC(const Triple &T, const CodeGenOptions &CGOpts)
static CodeGenFileType getCodeGenFileType(BackendAction Action)
Defines the Diagnostic-related interfaces.
Result
Implement __builtin_bit_cast and related operations.
Defines the clang::LangOptions interface.
This file provides a pass to link in Modules from a provided BackendConsumer.
static bool contains(const std::set< tok::TokenKind > &Terminators, const Token &Tok)
Defines the clang::TargetOptions class.
__DEVICE__ int max(int __a, int __b)
CodeGenOptions - Track various options which control how the code is optimized and passed to the back...
SanitizerSet SanitizeMergeHandlers
Set of sanitizer checks that can merge handlers (smaller code size at the expense of debuggability).
std::string StackUsageFile
Name of the stack usage file (i.e., .su file) if user passes -fstack-usage.
std::string InstrProfileOutput
Name of the profile file to use as output for -fprofile-instr-generate, -fprofile-generate,...
std::string BinutilsVersion
bool hasEmscriptenExceptions() const
bool hasDWARFExceptions() const
bool hasProfileIRUse() const
Check if IR level profile use is on.
char CoverageVersion[4]
The version string to put into coverage files.
std::string ThinLinkBitcodeFile
Name of a file that can optionally be written with minimized bitcode to be used as input for the Thin...
bool hasProfileCSIRInstr() const
Check if CS IR level profile instrumentation is on.
std::string DebugPass
Enable additional debugging information.
llvm::Reloc::Model RelocationModel
The name of the relocation model to use.
std::string CoverageNotesFile
The filename with path we use for coverage notes files.
std::string ProfileInstrumentUsePath
Name of the profile file to use as input for -fprofile-instr-use.
std::string SampleProfileFile
Name of the profile file to use with -fprofile-sample-use.
uint64_t LargeDataThreshold
The code model-specific large data threshold to use (-mlarge-data-threshold).
std::string MemoryProfileOutput
Name of the profile file to use as output for with -fmemory-profile.
std::vector< std::function< void(llvm::PassBuilder &)> > PassBuilderCallbacks
List of pass builder callbacks.
std::string LimitFloatPrecision
The float precision limit to use, if non-empty.
std::string CodeModel
The code model to use (-mcmodel).
std::string CoverageDataFile
The filename with path we use for coverage data files.
bool hasProfileClangInstr() const
Check if Clang profile instrumenation is on.
std::vector< std::string > SanitizeCoverageAllowlistFiles
Path to allowlist file specifying which objects (files, functions) should exclusively be instrumented...
std::vector< std::string > SanitizeCoverageIgnorelistFiles
Path to ignorelist file specifying which objects (files, functions) listed for instrumentation by san...
bool hasSanitizeCoverage() const
std::string MainFileName
The user provided name for the "main file", if non-empty.
bool hasProfileIRInstr() const
Check if IR level profile instrumentation is on.
bool hasProfileCSIRUse() const
Check if CSIR profile use is on.
SanitizerSet SanitizeTrap
Set of sanitizer checks that trap rather than diagnose.
std::vector< std::string > SanitizeMetadataIgnorelistFiles
Path to ignorelist file specifying which objects (files, functions) listed for instrumentation by san...
SanitizerSet SanitizeRecover
Set of sanitizer checks that are non-fatal (i.e.
std::string ProfileExcludeFiles
Regexes separated by a semi-colon to filter the files to not instrument.
std::string AsSecureLogFile
The name of a file to use with .secure_log_unique directives.
std::string ProfileRemappingFile
Name of the profile remapping file to apply to the profile data supplied by -fprofile-sample-use or -...
bool hasSanitizeBinaryMetadata() const
std::string ThinLTOIndexFile
Name of the function summary index file to use for ThinLTO function importing.
const char * Argv0
Executable and command-line used to create a given CompilerInvocation.
bool hasWasmExceptions() const
bool hasSjLjExceptions() const
std::string remapDebugPathPrefix(StringRef Path) const
Remap specified path prefix using provided DebugPrefixMap map.
SanitizerMaskCutoffs SanitizeSkipHotCutoffs
Set of thresholds in a range [0.0, 1.0]: the top hottest code responsible for the given fraction of P...
std::string SplitDwarfFile
The name for the split debug info file used for the DW_AT_[GNU_]dwo_name attribute in the skeleton CU...
std::vector< uint8_t > CmdArgs
List of backend command-line options for -fembed-bitcode.
std::optional< double > AllowRuntimeCheckSkipHotCutoff
std::vector< std::string > CommandLineArgs
bool hasSEHExceptions() const
std::string MemoryProfileUsePath
Name of the profile file to use as input for -fmemory-profile-use.
std::vector< std::string > OffloadObjects
List of filenames passed in using the -fembed-offload-object option.
std::string ProfileFilterFiles
Regexes separated by a semi-colon to filter the files to instrument.
std::string ObjectFilenameForDebug
Output filename used in the COFF debug information.
std::string SplitDwarfOutput
Output filename for the split debug info, not used in the skeleton CU.
std::string DIBugsReportFilePath
The file to use for dumping bug report by Debugify for original debug info.
std::string SaveDynDbgTempsFilePrefix
Prefix to use for -save-dynamic-debugging-temps output.
CompilerInstance - Helper class for managing a single instance of the Clang compiler.
DiagnosticsEngine & getDiagnostics() const
Get the current diagnostics engine.
llvm::TimerGroup & getTimerGroup() const
llvm::Timer & getFrontendTimer() const
IntrusiveRefCntPtr< llvm::vfs::FileSystem > getVirtualFileSystemPtr() const
TargetOptions & getTargetOpts()
FrontendOptions & getFrontendOpts()
HeaderSearchOptions & getHeaderSearchOpts()
llvm::vfs::FileSystem & getVirtualFileSystem() const
LangOptions & getLangOpts()
llvm::ArrayRef< std::unique_ptr< llvm::PassPlugin > > getPassPlugins() const
CodeGenOptions & getCodeGenOpts()
Concrete class used by the front-end to report problems and issues.
DiagnosticBuilder Report(SourceLocation Loc, unsigned DiagID)
Issue the message to the client.
SmallVector< FrontendInputFile, 0 > Inputs
The input files and their types.
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
SanitizerSet Sanitize
Set of enabled sanitizers.
std::vector< std::string > NoSanitizeFiles
Paths to files specifying which objects (files, functions, variables) should not be instrumented.
std::optional< std::vector< unsigned > > getAllScaled(unsigned ScalingFactor) const
std::vector< std::string > Features
The list of target specific features to enable or disable – this should be a list of strings starting...
std::string ABI
If given, the name of the target ABI to use.
std::string CPU
If given, the name of the target CPU to generate code for.
@ Angled
Paths for '#include <>' added by '-I'.
@ System
Like Angled, but marks system directories.
@ Quoted
'#include ""' paths, added by 'gcc -iquote'.
Top level wrappers for InstallAPI frontend operations.
@ Default
Set to the current date and time.
const FunctionProtoType * T
llvm::cl::opt< bool > ClSanitizeGuardChecks
void EmbedObject(llvm::Module *M, const CodeGenOptions &CGOpts, llvm::vfs::FileSystem &VFS, DiagnosticsEngine &Diags)
void emitBackendOutput(CompilerInstance &CI, CodeGenOptions &CGOpts, llvm::Module *M, BackendAction Action, llvm::IntrusiveRefCntPtr< llvm::vfs::FileSystem > VFS, std::unique_ptr< raw_pwrite_stream > OS, BackendConsumer *BC=nullptr)
void EmbedBitcode(llvm::Module *M, const CodeGenOptions &CGOpts, llvm::MemoryBufferRef Buf)
@ Backend_EmitAssembly
Emit native assembly files.
@ Backend_EmitLL
Emit human-readable LLVM assembly.
@ Backend_EmitBC
Emit LLVM bitcode files.
@ Backend_EmitObj
Emit native object files.
@ Backend_EmitMCNull
Run CodeGen, but don't emit anything.
@ Backend_EmitNothing
Don't emit anything (benchmarking mode)
Diagnostic wrappers for TextAPI types for error reporting.
static cl::opt< PGOOptions::ColdFuncOpt > ClPGOColdFuncAttr("pgo-cold-func-opt", cl::init(PGOOptions::ColdFuncOpt::Default), cl::Hidden, cl::desc("Function attribute to apply to cold functions as determined by PGO"), cl::values(clEnumValN(PGOOptions::ColdFuncOpt::Default, "default", "Default (no attribute)"), clEnumValN(PGOOptions::ColdFuncOpt::OptSize, "optsize", "Mark cold functions with optsize."), clEnumValN(PGOOptions::ColdFuncOpt::MinSize, "minsize", "Mark cold functions with minsize."), clEnumValN(PGOOptions::ColdFuncOpt::OptNone, "optnone", "Mark cold functions with optnone.")))
static cl::opt< bool > ClSanitizeOnOptimizerEarlyEP("sanitizer-early-opt-ep", cl::desc("Insert sanitizers on OptimizerEarlyEP."))
bool has(SanitizerMask K) const
Check if a certain (single) sanitizer is enabled.
bool hasOneOf(SanitizerMask K) const
Check if one or more sanitizers are enabled.