946 lines · cpp
1//===- optdriver.cpp - The LLVM Modular Optimizer -------------------------===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8//9// Optimizations may be specified an arbitrary number of times on the command10// line, They are run in the order specified. Common driver library for re-use11// by potential downstream opt-variants.12//13//===----------------------------------------------------------------------===//14 15#include "NewPMDriver.h"16#include "llvm/Analysis/CallGraph.h"17#include "llvm/Analysis/CallGraphSCCPass.h"18#include "llvm/Analysis/LoopPass.h"19#include "llvm/Analysis/RegionPass.h"20#include "llvm/Analysis/RuntimeLibcallInfo.h"21#include "llvm/Analysis/TargetLibraryInfo.h"22#include "llvm/Analysis/TargetTransformInfo.h"23#include "llvm/AsmParser/Parser.h"24#include "llvm/CodeGen/CommandFlags.h"25#include "llvm/CodeGen/TargetPassConfig.h"26#include "llvm/Config/llvm-config.h"27#include "llvm/IR/DataLayout.h"28#include "llvm/IR/DebugInfo.h"29#include "llvm/IR/LLVMContext.h"30#include "llvm/IR/LLVMRemarkStreamer.h"31#include "llvm/IR/LegacyPassManager.h"32#include "llvm/IR/LegacyPassNameParser.h"33#include "llvm/IR/Module.h"34#include "llvm/IR/ModuleSummaryIndex.h"35#include "llvm/IR/Verifier.h"36#include "llvm/IRReader/IRReader.h"37#include "llvm/InitializePasses.h"38#include "llvm/LinkAllIR.h"39#include "llvm/LinkAllPasses.h"40#include "llvm/MC/MCTargetOptionsCommandFlags.h"41#include "llvm/MC/TargetRegistry.h"42#include "llvm/Passes/PassPlugin.h"43#include "llvm/Remarks/HotnessThresholdParser.h"44#include "llvm/Support/Debug.h"45#include "llvm/Support/ErrorHandling.h"46#include "llvm/Support/FileSystem.h"47#include "llvm/Support/InitLLVM.h"48#include "llvm/Support/PluginLoader.h"49#include "llvm/Support/SourceMgr.h"50#include "llvm/Support/SystemUtils.h"51#include "llvm/Support/TargetSelect.h"52#include "llvm/Support/TimeProfiler.h"53#include "llvm/Support/ToolOutputFile.h"54#include "llvm/Support/YAMLTraits.h"55#include "llvm/Target/TargetMachine.h"56#include "llvm/TargetParser/Host.h"57#include "llvm/TargetParser/SubtargetFeature.h"58#include "llvm/TargetParser/Triple.h"59#include "llvm/Transforms/IPO/WholeProgramDevirt.h"60#include "llvm/Transforms/Utils/Cloning.h"61#include "llvm/Transforms/Utils/Debugify.h"62#include <algorithm>63#include <memory>64#include <optional>65using namespace llvm;66using namespace opt_tool;67 68static codegen::RegisterCodeGenFlags CFG;69static codegen::RegisterSaveStatsFlag SSF;70 71// The OptimizationList is automatically populated with registered Passes by the72// PassNameParser.73static cl::list<const PassInfo *, bool, PassNameParser> PassList(cl::desc(74 "Optimizations available (use \"-passes=\" for the new pass manager)"));75 76static cl::opt<bool> EnableLegacyPassManager(77 "bugpoint-enable-legacy-pm",78 cl::desc(79 "Enable the legacy pass manager. This is strictly for bugpoint "80 "due to it not working with the new PM, please do not use otherwise."),81 cl::init(false));82 83// This flag specifies a textual description of the optimization pass pipeline84// to run over the module. This flag switches opt to use the new pass manager85// infrastructure, completely disabling all of the flags specific to the old86// pass management.87static cl::opt<std::string> PassPipeline(88 "passes",89 cl::desc(90 "A textual (comma separated) description of the pass pipeline e.g.,"91 "-passes=\"foo,bar\", to have analysis passes available before a pass, "92 "add \"require<foo-analysis>\". See "93 "https://llvm.org/docs/NewPassManager.html#invoking-opt "94 "for more details on the pass pipeline syntax. "));95 96static cl::alias PassPipeline2("p", cl::aliasopt(PassPipeline),97 cl::desc("Alias for -passes"));98 99static cl::opt<bool> PrintPasses("print-passes",100 cl::desc("Print available passes that can be "101 "specified in -passes=foo and exit"));102 103static cl::opt<std::string> InputFilename(cl::Positional,104 cl::desc("<input bitcode file>"),105 cl::init("-"),106 cl::value_desc("filename"));107 108static cl::opt<std::string> OutputFilename("o",109 cl::desc("Override output filename"),110 cl::value_desc("filename"));111 112static cl::opt<bool> Force("f", cl::desc("Enable binary output on terminals"));113 114static cl::opt<bool> NoOutput("disable-output",115 cl::desc("Do not write result bitcode file"),116 cl::Hidden);117 118static cl::opt<bool> OutputAssembly("S",119 cl::desc("Write output as LLVM assembly"));120 121static cl::opt<bool>122 OutputThinLTOBC("thinlto-bc",123 cl::desc("Write output as ThinLTO-ready bitcode"));124 125static cl::opt<bool>126 SplitLTOUnit("thinlto-split-lto-unit",127 cl::desc("Enable splitting of a ThinLTO LTOUnit"));128 129static cl::opt<bool>130 UnifiedLTO("unified-lto",131 cl::desc("Use unified LTO piplines. Ignored unless -thinlto-bc "132 "is also specified."),133 cl::Hidden, cl::init(false));134 135static cl::opt<std::string> ThinLinkBitcodeFile(136 "thin-link-bitcode-file", cl::value_desc("filename"),137 cl::desc(138 "A file in which to write minimized bitcode for the thin link only"));139 140static cl::opt<bool> NoVerify("disable-verify",141 cl::desc("Do not run the verifier"), cl::Hidden);142 143static cl::opt<bool> NoUpgradeDebugInfo("disable-upgrade-debug-info",144 cl::desc("Generate invalid output"),145 cl::ReallyHidden);146 147static cl::opt<bool> VerifyEach("verify-each",148 cl::desc("Verify after each transform"));149 150static cl::opt<bool>151 DisableDITypeMap("disable-debug-info-type-map",152 cl::desc("Don't use a uniquing type map for debug info"));153 154static cl::opt<bool>155 StripDebug("strip-debug",156 cl::desc("Strip debugger symbol info from translation unit"));157 158static cl::opt<bool>159 StripNamedMetadata("strip-named-metadata",160 cl::desc("Strip module-level named metadata"));161 162static cl::opt<bool>163 OptLevelO0("O0", cl::desc("Optimization level 0. Similar to clang -O0. "164 "Same as -passes=\"default<O0>\""));165 166static cl::opt<bool>167 OptLevelO1("O1", cl::desc("Optimization level 1. Similar to clang -O1. "168 "Same as -passes=\"default<O1>\""));169 170static cl::opt<bool>171 OptLevelO2("O2", cl::desc("Optimization level 2. Similar to clang -O2. "172 "Same as -passes=\"default<O2>\""));173 174static cl::opt<bool>175 OptLevelOs("Os", cl::desc("Like -O2 but size-conscious. Similar to clang "176 "-Os. Same as -passes=\"default<Os>\""));177 178static cl::opt<bool> OptLevelOz(179 "Oz",180 cl::desc("Like -O2 but optimize for code size above all else. Similar to "181 "clang -Oz. Same as -passes=\"default<Oz>\""));182 183static cl::opt<bool>184 OptLevelO3("O3", cl::desc("Optimization level 3. Similar to clang -O3. "185 "Same as -passes=\"default<O3>\""));186 187static cl::opt<unsigned> CodeGenOptLevelCL(188 "codegen-opt-level",189 cl::desc("Override optimization level for codegen hooks, legacy PM only"));190 191static cl::opt<std::string>192 TargetTriple("mtriple", cl::desc("Override target triple for module"));193 194static cl::opt<bool> EmitSummaryIndex("module-summary",195 cl::desc("Emit module summary index"),196 cl::init(false));197 198static cl::opt<bool> EmitModuleHash("module-hash", cl::desc("Emit module hash"),199 cl::init(false));200 201static cl::opt<bool>202 DisableSimplifyLibCalls("disable-simplify-libcalls",203 cl::desc("Disable simplify-libcalls"));204 205static cl::list<std::string> DisableBuiltins(206 "disable-builtin",207 cl::desc("Disable specific target library builtin function"));208 209static cl::list<std::string> EnableBuiltins(210 "enable-builtin",211 cl::desc("Enable specific target library builtin functions"));212 213static cl::opt<bool> EnableDebugify(214 "enable-debugify",215 cl::desc(216 "Start the pipeline with debugify and end it with check-debugify"));217 218static cl::opt<bool> VerifyDebugInfoPreserve(219 "verify-debuginfo-preserve",220 cl::desc("Start the pipeline with collecting and end it with checking of "221 "debug info preservation."));222 223static cl::opt<bool> EnableProfileVerification(224 "enable-profcheck",225#if defined(LLVM_ENABLE_PROFCHECK)226 cl::init(true),227#else228 cl::init(false),229#endif230 cl::desc(231 "Start the pipeline with prof-inject and end it with prof-verify"));232 233static cl::opt<std::string> ClDataLayout("data-layout",234 cl::desc("data layout string to use"),235 cl::value_desc("layout-string"),236 cl::init(""));237 238static cl::opt<bool> RunTwice("run-twice",239 cl::desc("Run all passes twice, re-using the "240 "same pass manager (legacy PM only)."),241 cl::init(false), cl::Hidden);242 243static cl::opt<bool> DiscardValueNames(244 "discard-value-names",245 cl::desc("Discard names from Value (other than GlobalValue)."),246 cl::init(false), cl::Hidden);247 248static cl::opt<bool> TimeTrace("time-trace", cl::desc("Record time trace"));249 250static cl::opt<unsigned> TimeTraceGranularity(251 "time-trace-granularity",252 cl::desc(253 "Minimum time granularity (in microseconds) traced by time profiler"),254 cl::init(500), cl::Hidden);255 256static cl::opt<std::string>257 TimeTraceFile("time-trace-file",258 cl::desc("Specify time trace file destination"),259 cl::value_desc("filename"));260 261static cl::opt<bool> RemarksWithHotness(262 "pass-remarks-with-hotness",263 cl::desc("With PGO, include profile count in optimization remarks"),264 cl::Hidden);265 266static cl::opt<std::optional<uint64_t>, false, remarks::HotnessThresholdParser>267 RemarksHotnessThreshold(268 "pass-remarks-hotness-threshold",269 cl::desc("Minimum profile count required for "270 "an optimization remark to be output. "271 "Use 'auto' to apply the threshold from profile summary"),272 cl::value_desc("N or 'auto'"), cl::init(0), cl::Hidden);273 274static cl::opt<std::string>275 RemarksFilename("pass-remarks-output",276 cl::desc("Output filename for pass remarks"),277 cl::value_desc("filename"));278 279static cl::opt<std::string>280 RemarksPasses("pass-remarks-filter",281 cl::desc("Only record optimization remarks from passes whose "282 "names match the given regular expression"),283 cl::value_desc("regex"));284 285static cl::opt<std::string> RemarksFormat(286 "pass-remarks-format",287 cl::desc("The format used for serializing remarks (default: YAML)"),288 cl::value_desc("format"), cl::init("yaml"));289 290static cl::list<std::string>291 PassPlugins("load-pass-plugin",292 cl::desc("Load passes from plugin library"));293 294//===----------------------------------------------------------------------===//295// CodeGen-related helper functions.296//297 298static CodeGenOptLevel GetCodeGenOptLevel() {299 return static_cast<CodeGenOptLevel>(unsigned(CodeGenOptLevelCL));300}301 302namespace {303struct TimeTracerRAII {304 TimeTracerRAII(StringRef ProgramName) {305 if (TimeTrace)306 timeTraceProfilerInitialize(TimeTraceGranularity, ProgramName);307 }308 ~TimeTracerRAII() {309 if (!TimeTrace)310 return;311 if (auto E = timeTraceProfilerWrite(TimeTraceFile, OutputFilename)) {312 handleAllErrors(std::move(E), [&](const StringError &SE) {313 errs() << SE.getMessage() << "\n";314 });315 return;316 }317 timeTraceProfilerCleanup();318 }319};320} // namespace321 322// For use in NPM transition. Currently this contains most codegen-specific323// passes. Remove passes from here when porting to the NPM.324// TODO: use a codegen version of PassRegistry.def/PassBuilder::is*Pass() once325// it exists.326static bool shouldPinPassToLegacyPM(StringRef Pass) {327 static constexpr StringLiteral PassNameExactToIgnore[] = {328 "nvvm-reflect",329 "nvvm-intr-range",330 "amdgpu-simplifylib",331 "amdgpu-image-intrinsic-opt",332 "amdgpu-usenative",333 "amdgpu-promote-alloca",334 "amdgpu-promote-alloca-to-vector",335 "amdgpu-lower-kernel-attributes",336 "amdgpu-propagate-attributes-early",337 "amdgpu-propagate-attributes-late",338 "amdgpu-printf-runtime-binding",339 "amdgpu-always-inline"};340 if (llvm::is_contained(PassNameExactToIgnore, Pass))341 return false;342 343 static constexpr StringLiteral PassNamePrefix[] = {344 "x86-", "xcore-", "wasm-", "systemz-", "ppc-", "nvvm-",345 "nvptx-", "mips-", "lanai-", "hexagon-", "bpf-", "avr-",346 "thumb2-", "arm-", "si-", "gcn-", "amdgpu-", "aarch64-",347 "amdgcn-", "polly-", "riscv-", "dxil-"};348 static constexpr StringLiteral PassNameContain[] = {"-eh-prepare"};349 static constexpr StringLiteral PassNameExact[] = {350 "safe-stack",351 "cost-model",352 "codegenprepare",353 "interleaved-load-combine",354 "unreachableblockelim",355 "verify-safepoint-ir",356 "atomic-expand",357 "expandvp",358 "mve-tail-predication",359 "interleaved-access",360 "global-merge",361 "pre-isel-intrinsic-lowering",362 "expand-reductions",363 "indirectbr-expand",364 "generic-to-nvvm",365 "expand-memcmp",366 "loop-reduce",367 "lower-amx-type",368 "lower-amx-intrinsics",369 "polyhedral-info",370 "print-polyhedral-info",371 "replace-with-veclib",372 "jmc-instrumenter",373 "dot-regions",374 "dot-regions-only",375 "view-regions",376 "view-regions-only",377 "select-optimize",378 "expand-large-div-rem",379 "structurizecfg",380 "fix-irreducible",381 "expand-fp",382 "callbrprepare",383 "scalarizer",384 };385 for (StringLiteral P : PassNamePrefix)386 if (Pass.starts_with(P))387 return true;388 for (StringLiteral P : PassNameContain)389 if (Pass.contains(P))390 return true;391 return llvm::is_contained(PassNameExact, Pass);392}393 394// For use in NPM transition.395static bool shouldForceLegacyPM() {396 for (const PassInfo *P : PassList) {397 StringRef Arg = P->getPassArgument();398 if (shouldPinPassToLegacyPM(Arg))399 return true;400 }401 return false;402}403 404//===----------------------------------------------------------------------===//405// main for opt406//407extern "C" int408optMain(int argc, char **argv,409 ArrayRef<std::function<void(PassBuilder &)>> PassBuilderCallbacks) {410 InitLLVM X(argc, argv);411 412 // Enable debug stream buffering.413 EnableDebugBuffering = true;414 415 InitializeAllTargets();416 InitializeAllTargetMCs();417 InitializeAllAsmPrinters();418 InitializeAllAsmParsers();419 420 // Initialize passes421 PassRegistry &Registry = *PassRegistry::getPassRegistry();422 initializeCore(Registry);423 initializeScalarOpts(Registry);424 initializeVectorization(Registry);425 initializeIPO(Registry);426 initializeAnalysis(Registry);427 initializeTransformUtils(Registry);428 initializeInstCombine(Registry);429 initializeTarget(Registry);430 // For codegen passes, only passes that do IR to IR transformation are431 // supported.432 initializeExpandLargeDivRemLegacyPassPass(Registry);433 initializeExpandFpLegacyPassPass(Registry);434 initializeExpandMemCmpLegacyPassPass(Registry);435 initializeScalarizeMaskedMemIntrinLegacyPassPass(Registry);436 initializeSelectOptimizePass(Registry);437 initializeCallBrPreparePass(Registry);438 initializeCodeGenPrepareLegacyPassPass(Registry);439 initializeAtomicExpandLegacyPass(Registry);440 initializeWinEHPreparePass(Registry);441 initializeDwarfEHPrepareLegacyPassPass(Registry);442 initializeSafeStackLegacyPassPass(Registry);443 initializeSjLjEHPreparePass(Registry);444 initializePreISelIntrinsicLoweringLegacyPassPass(Registry);445 initializeGlobalMergePass(Registry);446 initializeIndirectBrExpandLegacyPassPass(Registry);447 initializeInterleavedLoadCombinePass(Registry);448 initializeInterleavedAccessPass(Registry);449 initializePostInlineEntryExitInstrumenterPass(Registry);450 initializeUnreachableBlockElimLegacyPassPass(Registry);451 initializeExpandReductionsPass(Registry);452 initializeWasmEHPreparePass(Registry);453 initializeWriteBitcodePassPass(Registry);454 initializeReplaceWithVeclibLegacyPass(Registry);455 initializeJMCInstrumenterPass(Registry);456 457 SmallVector<PassPlugin, 1> PluginList;458 PassPlugins.setCallback([&](const std::string &PluginPath) {459 auto Plugin = PassPlugin::Load(PluginPath);460 if (!Plugin)461 reportFatalUsageError(Plugin.takeError());462 PluginList.emplace_back(Plugin.get());463 });464 465 // Register the Target and CPU printer for --version.466 cl::AddExtraVersionPrinter(sys::printDefaultTargetAndDetectedCPU);467 468 cl::ParseCommandLineOptions(469 argc, argv, "llvm .bc -> .bc modular optimizer and analysis printer\n");470 471 LLVMContext Context;472 473 // TODO: remove shouldForceLegacyPM().474 const bool UseNPM = (!EnableLegacyPassManager && !shouldForceLegacyPM()) ||475 PassPipeline.getNumOccurrences() > 0;476 477 if (UseNPM && !PassList.empty()) {478 errs() << "The `opt -passname` syntax for the new pass manager is "479 "not supported, please use `opt -passes=<pipeline>` (or the `-p` "480 "alias for a more concise version).\n";481 errs() << "See https://llvm.org/docs/NewPassManager.html#invoking-opt "482 "for more details on the pass pipeline syntax.\n\n";483 return 1;484 }485 486 if (!UseNPM && PluginList.size()) {487 errs() << argv[0] << ": " << PassPlugins.ArgStr488 << " specified with legacy PM.\n";489 return 1;490 }491 492 // FIXME: once the legacy PM code is deleted, move runPassPipeline() here and493 // construct the PassBuilder before parsing IR so we can reuse the same494 // PassBuilder for print passes.495 if (PrintPasses) {496 printPasses(outs());497 return 0;498 }499 500 TimeTracerRAII TimeTracer(argv[0]);501 502 SMDiagnostic Err;503 504 Context.setDiscardValueNames(DiscardValueNames);505 if (!DisableDITypeMap)506 Context.enableDebugTypeODRUniquing();507 508 Expected<LLVMRemarkFileHandle> RemarksFileOrErr =509 setupLLVMOptimizationRemarks(Context, RemarksFilename, RemarksPasses,510 RemarksFormat, RemarksWithHotness,511 RemarksHotnessThreshold);512 if (Error E = RemarksFileOrErr.takeError()) {513 errs() << toString(std::move(E)) << '\n';514 return 1;515 }516 LLVMRemarkFileHandle RemarksFile = std::move(*RemarksFileOrErr);517 518 codegen::MaybeEnableStatistics();519 520 StringRef ABIName = mc::getABIName(); // FIXME: Handle module flag.521 522 // Load the input module...523 auto SetDataLayout = [&](StringRef IRTriple,524 StringRef IRLayout) -> std::optional<std::string> {525 // Data layout specified on the command line has the highest priority.526 if (!ClDataLayout.empty())527 return ClDataLayout;528 // If an explicit data layout is already defined in the IR, don't infer.529 if (!IRLayout.empty())530 return std::nullopt;531 532 // If an explicit triple was specified (either in the IR or on the533 // command line), use that to infer the default data layout. However, the534 // command line target triple should override the IR file target triple.535 std::string TripleStr =536 TargetTriple.empty() ? IRTriple.str() : Triple::normalize(TargetTriple);537 // If the triple string is still empty, we don't fall back to538 // sys::getDefaultTargetTriple() since we do not want to have differing539 // behaviour dependent on the configured default triple. Therefore, if the540 // user did not pass -mtriple or define an explicit triple/datalayout in541 // the IR, we should default to an empty (default) DataLayout.542 if (TripleStr.empty())543 return std::nullopt;544 545 Triple TT(TripleStr);546 547 std::string Str = TT.computeDataLayout(ABIName);548 if (Str.empty()) {549 errs() << argv[0]550 << ": warning: failed to infer data layout from target triple\n";551 return std::nullopt;552 }553 return Str;554 };555 std::unique_ptr<Module> M;556 if (NoUpgradeDebugInfo)557 M = parseAssemblyFileWithIndexNoUpgradeDebugInfo(558 InputFilename, Err, Context, nullptr, SetDataLayout)559 .Mod;560 else561 M = parseIRFile(InputFilename, Err, Context,562 ParserCallbacks(SetDataLayout));563 564 if (!M) {565 Err.print(argv[0], errs());566 return 1;567 }568 569 // Strip debug info before running the verifier.570 if (StripDebug)571 StripDebugInfo(*M);572 573 // Erase module-level named metadata, if requested.574 if (StripNamedMetadata) {575 while (!M->named_metadata_empty()) {576 NamedMDNode *NMD = &*M->named_metadata_begin();577 M->eraseNamedMetadata(NMD);578 }579 }580 581 // If we are supposed to override the target triple, do so now.582 if (!TargetTriple.empty())583 M->setTargetTriple(Triple(Triple::normalize(TargetTriple)));584 585 // Immediately run the verifier to catch any problems before starting up the586 // pass pipelines. Otherwise we can crash on broken code during587 // doInitialization().588 if (!NoVerify && verifyModule(*M, &errs())) {589 errs() << argv[0] << ": " << InputFilename590 << ": error: input module is broken!\n";591 return 1;592 }593 594 // Enable testing of whole program devirtualization on this module by invoking595 // the facility for updating public visibility to linkage unit visibility when596 // specified by an internal option. This is normally done during LTO which is597 // not performed via opt.598 updateVCallVisibilityInModule(599 *M,600 /*WholeProgramVisibilityEnabledInLTO=*/false,601 // FIXME: These need linker information via a602 // TBD new interface.603 /*DynamicExportSymbols=*/{},604 /*ValidateAllVtablesHaveTypeInfos=*/false,605 /*IsVisibleToRegularObj=*/[](StringRef) { return true; });606 607 // Figure out what stream we are supposed to write to...608 std::unique_ptr<ToolOutputFile> Out;609 std::unique_ptr<ToolOutputFile> ThinLinkOut;610 if (NoOutput) {611 if (!OutputFilename.empty())612 errs() << "WARNING: The -o (output filename) option is ignored when\n"613 "the --disable-output option is used.\n";614 } else {615 // Default to standard output.616 if (OutputFilename.empty())617 OutputFilename = "-";618 619 std::error_code EC;620 sys::fs::OpenFlags Flags =621 OutputAssembly ? sys::fs::OF_TextWithCRLF : sys::fs::OF_None;622 Out.reset(new ToolOutputFile(OutputFilename, EC, Flags));623 if (EC) {624 errs() << EC.message() << '\n';625 return 1;626 }627 628 if (!ThinLinkBitcodeFile.empty()) {629 ThinLinkOut.reset(630 new ToolOutputFile(ThinLinkBitcodeFile, EC, sys::fs::OF_None));631 if (EC) {632 errs() << EC.message() << '\n';633 return 1;634 }635 }636 }637 638 Triple ModuleTriple(M->getTargetTriple());639 std::string CPUStr, FeaturesStr;640 std::unique_ptr<TargetMachine> TM;641 if (ModuleTriple.getArch()) {642 CPUStr = codegen::getCPUStr();643 FeaturesStr = codegen::getFeaturesStr();644 Expected<std::unique_ptr<TargetMachine>> ExpectedTM =645 codegen::createTargetMachineForTriple(ModuleTriple.str(),646 GetCodeGenOptLevel());647 if (auto E = ExpectedTM.takeError()) {648 errs() << argv[0] << ": WARNING: failed to create target machine for '"649 << ModuleTriple.str() << "': " << toString(std::move(E)) << "\n";650 } else {651 TM = std::move(*ExpectedTM);652 }653 } else if (ModuleTriple.getArchName() != "unknown" &&654 ModuleTriple.getArchName() != "") {655 errs() << argv[0] << ": unrecognized architecture '"656 << ModuleTriple.getArchName() << "' provided.\n";657 return 1;658 }659 660 // Override function attributes based on CPUStr, FeaturesStr, and command line661 // flags.662 codegen::setFunctionAttributes(CPUStr, FeaturesStr, *M);663 664 // If the output is set to be emitted to standard out, and standard out is a665 // console, print out a warning message and refuse to do it. We don't666 // impress anyone by spewing tons of binary goo to a terminal.667 if (!Force && !NoOutput && !OutputAssembly)668 if (CheckBitcodeOutputToConsole(Out->os()))669 NoOutput = true;670 671 if (OutputThinLTOBC) {672 M->addModuleFlag(Module::Error, "EnableSplitLTOUnit", SplitLTOUnit);673 if (UnifiedLTO)674 M->addModuleFlag(Module::Error, "UnifiedLTO", 1);675 }676 677 VectorLibrary VecLib = codegen::getVectorLibrary();678 // Add an appropriate TargetLibraryInfo pass for the module's triple.679 TargetLibraryInfoImpl TLII(ModuleTriple, VecLib);680 681 RTLIB::RuntimeLibcallsInfo RTLCI(ModuleTriple, codegen::getExceptionModel(),682 codegen::getFloatABIForCalls(),683 codegen::getEABIVersion(), ABIName, VecLib);684 685 // The -disable-simplify-libcalls flag actually disables all builtin optzns.686 if (DisableSimplifyLibCalls)687 TLII.disableAllFunctions();688 else {689 // Disable individual builtin functions in TargetLibraryInfo.690 LibFunc F;691 for (const std::string &FuncName : DisableBuiltins) {692 if (TLII.getLibFunc(FuncName, F))693 TLII.setUnavailable(F);694 else {695 errs() << argv[0] << ": cannot disable nonexistent builtin function "696 << FuncName << '\n';697 return 1;698 }699 }700 701 for (const std::string &FuncName : EnableBuiltins) {702 if (TLII.getLibFunc(FuncName, F))703 TLII.setAvailable(F);704 else {705 errs() << argv[0] << ": cannot enable nonexistent builtin function "706 << FuncName << '\n';707 return 1;708 }709 }710 }711 712 if (UseNPM) {713 if (legacy::debugPassSpecified()) {714 errs() << "-debug-pass does not work with the new PM, either use "715 "-debug-pass-manager, or use the legacy PM\n";716 return 1;717 }718 auto NumOLevel = OptLevelO0 + OptLevelO1 + OptLevelO2 + OptLevelO3 +719 OptLevelOs + OptLevelOz;720 if (NumOLevel > 1) {721 errs() << "Cannot specify multiple -O#\n";722 return 1;723 }724 if (NumOLevel > 0 && (PassPipeline.getNumOccurrences() > 0)) {725 errs() << "Cannot specify -O# and --passes=/--foo-pass, use "726 "-passes='default<O#>,other-pass'\n";727 return 1;728 }729 std::string Pipeline = PassPipeline;730 731 if (OptLevelO0)732 Pipeline = "default<O0>";733 if (OptLevelO1)734 Pipeline = "default<O1>";735 if (OptLevelO2)736 Pipeline = "default<O2>";737 if (OptLevelO3)738 Pipeline = "default<O3>";739 if (OptLevelOs)740 Pipeline = "default<Os>";741 if (OptLevelOz)742 Pipeline = "default<Oz>";743 OutputKind OK = OK_NoOutput;744 if (!NoOutput)745 OK = OutputAssembly746 ? OK_OutputAssembly747 : (OutputThinLTOBC ? OK_OutputThinLTOBitcode : OK_OutputBitcode);748 749 VerifierKind VK = VerifierKind::InputOutput;750 if (NoVerify)751 VK = VerifierKind::None;752 else if (VerifyEach)753 VK = VerifierKind::EachPass;754 755 // The user has asked to use the new pass manager and provided a pipeline756 // string. Hand off the rest of the functionality to the new code for that757 // layer.758 if (!runPassPipeline(759 argv[0], *M, TM.get(), &TLII, RTLCI, Out.get(), ThinLinkOut.get(),760 RemarksFile.get(), Pipeline, PluginList, PassBuilderCallbacks, OK,761 VK, /* ShouldPreserveAssemblyUseListOrder */ false,762 /* ShouldPreserveBitcodeUseListOrder */ true, EmitSummaryIndex,763 EmitModuleHash, EnableDebugify, VerifyDebugInfoPreserve,764 EnableProfileVerification, UnifiedLTO))765 return 1;766 return codegen::MaybeSaveStatistics(OutputFilename, "opt");767 }768 769 if (OptLevelO0 || OptLevelO1 || OptLevelO2 || OptLevelOs || OptLevelOz ||770 OptLevelO3) {771 errs() << "Cannot use -O# with legacy PM.\n";772 return 1;773 }774 if (EmitSummaryIndex) {775 errs() << "Cannot use -module-summary with legacy PM.\n";776 return 1;777 }778 if (EmitModuleHash) {779 errs() << "Cannot use -module-hash with legacy PM.\n";780 return 1;781 }782 if (OutputThinLTOBC) {783 errs() << "Cannot use -thinlto-bc with legacy PM.\n";784 return 1;785 }786 // Create a PassManager to hold and optimize the collection of passes we are787 // about to build. If the -debugify-each option is set, wrap each pass with788 // the (-check)-debugify passes.789 DebugifyCustomPassManager Passes;790 DebugifyStatsMap DIStatsMap;791 DebugInfoPerPass DebugInfoBeforePass;792 if (DebugifyEach) {793 Passes.setDebugifyMode(DebugifyMode::SyntheticDebugInfo);794 Passes.setDIStatsMap(DIStatsMap);795 } else if (VerifyEachDebugInfoPreserve) {796 Passes.setDebugifyMode(DebugifyMode::OriginalDebugInfo);797 Passes.setDebugInfoBeforePass(DebugInfoBeforePass);798 if (!VerifyDIPreserveExport.empty())799 Passes.setOrigDIVerifyBugsReportFilePath(VerifyDIPreserveExport);800 }801 802 bool AddOneTimeDebugifyPasses =803 (EnableDebugify && !DebugifyEach) ||804 (VerifyDebugInfoPreserve && !VerifyEachDebugInfoPreserve);805 806 Passes.add(new TargetLibraryInfoWrapperPass(TLII));807 808 // Add internal analysis passes from the target machine.809 Passes.add(createTargetTransformInfoWrapperPass(TM ? TM->getTargetIRAnalysis()810 : TargetIRAnalysis()));811 812 if (AddOneTimeDebugifyPasses) {813 if (EnableDebugify) {814 Passes.setDIStatsMap(DIStatsMap);815 Passes.add(createDebugifyModulePass());816 } else if (VerifyDebugInfoPreserve) {817 Passes.setDebugInfoBeforePass(DebugInfoBeforePass);818 Passes.add(createDebugifyModulePass(DebugifyMode::OriginalDebugInfo, "",819 &(Passes.getDebugInfoPerPass())));820 }821 }822 823 if (TM) {824 Pass *TPC = TM->createPassConfig(Passes);825 if (!TPC) {826 errs() << "Target Machine pass config creation failed.\n";827 return 1;828 }829 Passes.add(TPC);830 }831 832 // Create a new optimization pass for each one specified on the command line.833 for (const PassInfo *PassInf : PassList) {834 if (PassInf->getNormalCtor()) {835 Pass *P = PassInf->getNormalCtor()();836 if (P) {837 // Add the pass to the pass manager.838 Passes.add(P);839 // If we are verifying all of the intermediate steps, add the verifier.840 if (VerifyEach)841 Passes.add(createVerifierPass());842 }843 } else {844 errs() << argv[0] << ": cannot create pass: " << PassInf->getPassName()845 << "\n";846 }847 }848 849 // Check that the module is well formed on completion of optimization850 if (!NoVerify && !VerifyEach)851 Passes.add(createVerifierPass());852 853 if (AddOneTimeDebugifyPasses) {854 if (EnableDebugify)855 Passes.add(createCheckDebugifyModulePass(false));856 else if (VerifyDebugInfoPreserve) {857 if (!VerifyDIPreserveExport.empty())858 Passes.setOrigDIVerifyBugsReportFilePath(VerifyDIPreserveExport);859 Passes.add(createCheckDebugifyModulePass(860 false, "", nullptr, DebugifyMode::OriginalDebugInfo,861 &(Passes.getDebugInfoPerPass()), VerifyDIPreserveExport));862 }863 }864 865 // In run twice mode, we want to make sure the output is bit-by-bit866 // equivalent if we run the pass manager again, so setup two buffers and867 // a stream to write to them. Note that llc does something similar and it868 // may be worth to abstract this out in the future.869 SmallVector<char, 0> Buffer;870 SmallVector<char, 0> FirstRunBuffer;871 std::unique_ptr<raw_svector_ostream> BOS;872 raw_ostream *OS = nullptr;873 874 const bool ShouldEmitOutput = !NoOutput;875 876 // Write bitcode or assembly to the output as the last step...877 if (ShouldEmitOutput || RunTwice) {878 assert(Out);879 OS = &Out->os();880 if (RunTwice) {881 BOS = std::make_unique<raw_svector_ostream>(Buffer);882 OS = BOS.get();883 }884 if (OutputAssembly)885 Passes.add(createPrintModulePass(886 *OS, "", /* ShouldPreserveAssemblyUseListOrder */ false));887 else888 Passes.add(createBitcodeWriterPass(889 *OS, /* ShouldPreserveBitcodeUseListOrder */ true));890 }891 892 // Before executing passes, print the final values of the LLVM options.893 cl::PrintOptionValues();894 895 if (!RunTwice) {896 // Now that we have all of the passes ready, run them.897 Passes.run(*M);898 } else {899 // If requested, run all passes twice with the same pass manager to catch900 // bugs caused by persistent state in the passes.901 std::unique_ptr<Module> M2(CloneModule(*M));902 // Run all passes on the original module first, so the second run processes903 // the clone to catch CloneModule bugs.904 Passes.run(*M);905 FirstRunBuffer = Buffer;906 Buffer.clear();907 908 Passes.run(*M2);909 910 // Compare the two outputs and make sure they're the same911 assert(Out);912 if (Buffer.size() != FirstRunBuffer.size() ||913 (memcmp(Buffer.data(), FirstRunBuffer.data(), Buffer.size()) != 0)) {914 errs()915 << "Running the pass manager twice changed the output.\n"916 "Writing the result of the second run to the specified output.\n"917 "To generate the one-run comparison binary, just run without\n"918 "the compile-twice option\n";919 if (ShouldEmitOutput) {920 Out->os() << BOS->str();921 Out->keep();922 }923 if (RemarksFile)924 RemarksFile->keep();925 return 1;926 }927 if (ShouldEmitOutput)928 Out->os() << BOS->str();929 }930 931 if (DebugifyEach && !DebugifyExport.empty())932 exportDebugifyStats(DebugifyExport, Passes.getDebugifyStatsMap());933 934 // Declare success.935 if (!NoOutput)936 Out->keep();937 938 if (RemarksFile)939 RemarksFile->keep();940 941 if (ThinLinkOut)942 ThinLinkOut->keep();943 944 return codegen::MaybeSaveStatistics(OutputFilename, "opt");945}946