aeubanks created this revision.
Herald added subscribers: ormris, steven_wu, hiraditya, arichardson, inglorion,
sbc100, mgorny, emaste.
Herald added a reviewer: MaskRay.
Herald added a reviewer: gkm.
Herald added a project: lld-macho.
Herald added a reviewer: lld-macho.
aeubanks requested review of this revision.
Herald added subscribers: llvm-commits, cfe-commits, aheejin.
Herald added projects: clang, LLVM.
Repository:
rG LLVM Github Monorepo
https://reviews.llvm.org/D113738
Files:
clang/lib/CodeGen/BackendUtil.cpp
lld/COFF/Config.h
lld/COFF/Driver.cpp
lld/Common/Args.cpp
lld/Common/CMakeLists.txt
lld/ELF/Config.h
lld/ELF/Driver.cpp
lld/ELF/LTO.cpp
lld/MachO/Config.h
lld/MachO/Driver.cpp
lld/include/lld/Common/Args.h
lld/test/COFF/lto-opt-level.ll
lld/test/ELF/lto/opt-level.ll
lld/test/MachO/lto-opt-level.ll
lld/test/wasm/lto/opt-level.ll
lld/wasm/Config.h
lld/wasm/Driver.cpp
llvm/include/llvm/LTO/Config.h
llvm/include/llvm/LTO/legacy/LTOCodeGenerator.h
llvm/include/llvm/LTO/legacy/ThinLTOCodeGenerator.h
llvm/include/llvm/Passes/OptimizationLevel.h
llvm/lib/LTO/LTO.cpp
llvm/lib/LTO/LTOBackend.cpp
llvm/lib/LTO/LTOCodeGenerator.cpp
llvm/lib/LTO/ThinLTOCodeGenerator.cpp
llvm/tools/llvm-lto/llvm-lto.cpp
llvm/tools/llvm-lto2/llvm-lto2.cpp
llvm/tools/lto/lto.cpp
llvm/utils/gn/secondary/lld/Common/BUILD.gn
Index: llvm/utils/gn/secondary/lld/Common/BUILD.gn
===================================================================
--- llvm/utils/gn/secondary/lld/Common/BUILD.gn
+++ llvm/utils/gn/secondary/lld/Common/BUILD.gn
@@ -27,6 +27,7 @@
"//llvm/lib/IR",
"//llvm/lib/MC",
"//llvm/lib/Option",
+ "//llvm/lib/Passes",
"//llvm/lib/Support",
"//llvm/lib/Target",
]
Index: llvm/tools/lto/lto.cpp
===================================================================
--- llvm/tools/lto/lto.cpp
+++ llvm/tools/lto/lto.cpp
@@ -23,6 +23,7 @@
#include "llvm/LTO/legacy/LTOCodeGenerator.h"
#include "llvm/LTO/legacy/LTOModule.h"
#include "llvm/LTO/legacy/ThinLTOCodeGenerator.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Support/MemoryBuffer.h"
#include "llvm/Support/Signals.h"
#include "llvm/Support/TargetSelect.h"
@@ -34,12 +35,10 @@
// extra command-line flags needed for LTOCodeGenerator
static cl::opt<char>
-OptLevel("O",
- cl::desc("Optimization level. [-O0, -O1, -O2, or -O3] "
- "(default = '-O2')"),
- cl::Prefix,
- cl::ZeroOrMore,
- cl::init('2'));
+ OptLevel("O",
+ cl::desc("Optimization level. [-O0, -O1, -O2, -O3, -Os, or -Oz] "
+ "(default = '-O2')"),
+ cl::Prefix, cl::ZeroOrMore, cl::init('2'));
static cl::opt<bool> EnableFreestanding(
"lto-freestanding", cl::init(false),
@@ -152,9 +151,10 @@
LTOCodeGenerator *CG = unwrap(cg);
CG->setAttrs(codegen::getMAttrs());
- if (OptLevel < '0' || OptLevel > '3')
- report_fatal_error("Optimization level must be between 0 and 3");
- CG->setOptLevel(OptLevel - '0');
+ Optional<OptimizationLevel> OL = OptimizationLevel::forChar(OptLevel);
+ if (!OL)
+ report_fatal_error("invalid optimization level: -O" + Twine(OptLevel));
+ CG->setOptLevel(*OL);
CG->setFreestanding(EnableFreestanding);
CG->setDisableVerify(DisableVerify);
}
@@ -525,20 +525,21 @@
CodeGen->setFreestanding(EnableFreestanding);
if (OptLevel.getNumOccurrences()) {
- if (OptLevel < '0' || OptLevel > '3')
- report_fatal_error("Optimization level must be between 0 and 3");
- CodeGen->setOptLevel(OptLevel - '0');
- switch (OptLevel) {
- case '0':
+ Optional<OptimizationLevel> OL = OptimizationLevel::forChar(OptLevel);
+ if (!OL)
+ report_fatal_error("Invalid optimization level: " + Twine(OptLevel));
+ CodeGen->setOptLevel(*OL);
+ switch (OL->getSpeedupLevel()) {
+ case 0:
CodeGen->setCodeGenOptLevel(CodeGenOpt::None);
break;
- case '1':
+ case 1:
CodeGen->setCodeGenOptLevel(CodeGenOpt::Less);
break;
- case '2':
+ case 2:
CodeGen->setCodeGenOptLevel(CodeGenOpt::Default);
break;
- case '3':
+ case 3:
CodeGen->setCodeGenOptLevel(CodeGenOpt::Aggressive);
break;
}
Index: llvm/tools/llvm-lto2/llvm-lto2.cpp
===================================================================
--- llvm/tools/llvm-lto2/llvm-lto2.cpp
+++ llvm/tools/llvm-lto2/llvm-lto2.cpp
@@ -20,6 +20,7 @@
#include "llvm/Config/llvm-config.h"
#include "llvm/IR/DiagnosticPrinter.h"
#include "llvm/LTO/LTO.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Passes/PassPlugin.h"
#include "llvm/Remarks/HotnessThresholdParser.h"
#include "llvm/Support/Caching.h"
@@ -36,8 +37,9 @@
static codegen::RegisterCodeGenFlags CGF;
static cl::opt<char>
- OptLevel("O", cl::desc("Optimization level. [-O0, -O1, -O2, or -O3] "
- "(default = '-O2')"),
+ OptLevel("O",
+ cl::desc("Optimization level. [-O0, -O1, -O2, -O3, -Os, or -Oz] "
+ "(default = '-O2')"),
cl::Prefix, cl::ZeroOrMore, cl::init('2'));
static cl::opt<char> CGOptLevel(
@@ -272,7 +274,12 @@
Conf.OptPipeline = OptPipeline;
Conf.AAPipeline = AAPipeline;
- Conf.OptLevel = OptLevel - '0';
+ if (auto OL = OptimizationLevel::forChar(OptLevel)) {
+ Conf.OptLevel = *OL;
+ } else {
+ llvm::errs() << "invalid -O level: -O" << OptLevel << "\n";
+ return 1;
+ }
Conf.UseNewPM = UseNewPM;
Conf.Freestanding = EnableFreestanding;
for (auto &PluginFN : PassPlugins)
@@ -301,8 +308,8 @@
Conf.OverrideTriple = OverrideTriple;
Conf.DefaultTriple = DefaultTriple;
Conf.StatsFile = StatsFile;
- Conf.PTO.LoopVectorization = Conf.OptLevel > 1;
- Conf.PTO.SLPVectorization = Conf.OptLevel > 1;
+ Conf.PTO.LoopVectorization = Conf.OptLevel.getSpeedupLevel() > 1;
+ Conf.PTO.SLPVectorization = Conf.OptLevel.getSpeedupLevel() > 1;
ThinBackend Backend;
if (ThinLTODistributedIndexes)
Index: llvm/tools/llvm-lto/llvm-lto.cpp
===================================================================
--- llvm/tools/llvm-lto/llvm-lto.cpp
+++ llvm/tools/llvm-lto/llvm-lto.cpp
@@ -68,7 +68,7 @@
static cl::opt<char>
OptLevel("O",
- cl::desc("Optimization level. [-O0, -O1, -O2, or -O3] "
+ cl::desc("Optimization level. [-O0, -O1, -O2, -O3, -Os, or -Oz] "
"(default = '-O2')"),
cl::Prefix, cl::ZeroOrMore, cl::init('2'), cl::cat(LTOCategory));
@@ -940,9 +940,6 @@
cl::HideUnrelatedOptions({<OCategory, &getColorCategory()});
cl::ParseCommandLineOptions(argc, argv, "llvm LTO linker\n");
- if (OptLevel < '0' || OptLevel > '3')
- error("optimization level must be between 0 and 3");
-
// Initialize the configured targets.
InitializeAllTargets();
InitializeAllTargetMCs();
@@ -1065,7 +1062,11 @@
// Set cpu and attrs strings for the default target/subtarget.
CodeGen.setCpu(codegen::getMCPU());
- CodeGen.setOptLevel(OptLevel - '0');
+ Optional<OptimizationLevel> OL = OptimizationLevel::forChar(OptLevel);
+ if (!OL)
+ error("invalid optimization level: -O" + Twine(OptLevel));
+ CodeGen.setOptLevel(*OL);
+
CodeGen.setAttrs(codegen::getMAttrs());
CodeGen.setUseNewPM(UseNewPM);
Index: llvm/lib/LTO/ThinLTOCodeGenerator.cpp
===================================================================
--- llvm/lib/LTO/ThinLTOCodeGenerator.cpp
+++ llvm/lib/LTO/ThinLTOCodeGenerator.cpp
@@ -40,6 +40,7 @@
#include "llvm/MC/SubtargetFeature.h"
#include "llvm/MC/TargetRegistry.h"
#include "llvm/Object/IRObjectFile.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Passes/PassBuilder.h"
#include "llvm/Passes/StandardInstrumentations.h"
#include "llvm/Remarks/HotnessThresholdParser.h"
@@ -238,7 +239,7 @@
}
static void optimizeModule(Module &TheModule, TargetMachine &TM,
- unsigned OptLevel, bool Freestanding,
+ OptimizationLevel OptLevel, bool Freestanding,
ModuleSummaryIndex *Index) {
// Populate the PassManager
PassManagerBuilder PMB;
@@ -247,7 +248,8 @@
PMB.LibraryInfo->disableAllFunctions();
PMB.Inliner = createFunctionInliningPass();
// FIXME: should get it from the bitcode?
- PMB.OptLevel = OptLevel;
+ PMB.OptLevel = OptLevel.getSpeedupLevel();
+ PMB.SizeLevel = OptLevel.getSizeLevel();
PMB.LoopVectorize = true;
PMB.SLPVectorize = true;
// Already did this in verifyLoadedModule().
@@ -268,7 +270,7 @@
}
static void optimizeModuleNewPM(Module &TheModule, TargetMachine &TM,
- unsigned OptLevel, bool Freestanding,
+ OptimizationLevel OptLevel, bool Freestanding,
bool DebugPassManager,
ModuleSummaryIndex *Index) {
Optional<PGOOptions> PGOOpt;
@@ -300,26 +302,7 @@
ModulePassManager MPM;
- OptimizationLevel OL;
-
- switch (OptLevel) {
- default:
- llvm_unreachable("Invalid optimization level");
- case 0:
- OL = OptimizationLevel::O0;
- break;
- case 1:
- OL = OptimizationLevel::O1;
- break;
- case 2:
- OL = OptimizationLevel::O2;
- break;
- case 3:
- OL = OptimizationLevel::O3;
- break;
- }
-
- MPM.addPass(PB.buildThinLTODefaultPipeline(OL, Index));
+ MPM.addPass(PB.buildThinLTODefaultPipeline(OptLevel, Index));
MPM.run(TheModule, MAM);
}
@@ -394,7 +377,7 @@
const FunctionImporter::ImportMapTy &ImportList,
const FunctionImporter::ExportSetTy &ExportList,
const std::map<GlobalValue::GUID, GlobalValue::LinkageTypes> &ResolvedODR,
- const GVSummaryMapTy &DefinedGVSummaries, unsigned OptLevel,
+ const GVSummaryMapTy &DefinedGVSummaries, OptimizationLevel OptLevel,
bool Freestanding, const TargetMachineBuilder &TMBuilder) {
if (CachePath.empty())
return;
@@ -483,8 +466,8 @@
const GVSummaryMapTy &DefinedGlobals,
const ThinLTOCodeGenerator::CachingOptions &CacheOptions,
bool DisableCodeGen, StringRef SaveTempsDir,
- bool Freestanding, unsigned OptLevel, unsigned count,
- bool UseNewPM, bool DebugPassManager) {
+ bool Freestanding, OptimizationLevel OptLevel,
+ unsigned count, bool UseNewPM, bool DebugPassManager) {
// "Benchmark"-like optimization: single-source case
bool SingleModule = (ModuleMap.size() == 1);
Index: llvm/lib/LTO/LTOCodeGenerator.cpp
===================================================================
--- llvm/lib/LTO/LTOCodeGenerator.cpp
+++ llvm/lib/LTO/LTOCodeGenerator.cpp
@@ -45,6 +45,7 @@
#include "llvm/MC/MCContext.h"
#include "llvm/MC/SubtargetFeature.h"
#include "llvm/MC/TargetRegistry.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Remarks/HotnessThresholdParser.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/FileSystem.h"
@@ -184,11 +185,11 @@
llvm_unreachable("Unknown debug format!");
}
-void LTOCodeGenerator::setOptLevel(unsigned Level) {
+void LTOCodeGenerator::setOptLevel(OptimizationLevel Level) {
Config.OptLevel = Level;
- Config.PTO.LoopVectorization = Config.OptLevel > 1;
- Config.PTO.SLPVectorization = Config.OptLevel > 1;
- switch (Config.OptLevel) {
+ Config.PTO.LoopVectorization = Config.OptLevel.getSpeedupLevel() > 1;
+ Config.PTO.SLPVectorization = Config.OptLevel.getSpeedupLevel() > 1;
+ switch (Config.OptLevel.getSpeedupLevel()) {
case 0:
Config.CGOptLevel = CodeGenOpt::None;
return;
Index: llvm/lib/LTO/LTOBackend.cpp
===================================================================
--- llvm/lib/LTO/LTOBackend.cpp
+++ llvm/lib/LTO/LTOBackend.cpp
@@ -210,8 +210,7 @@
}
static void runNewPMPasses(const Config &Conf, Module &Mod, TargetMachine *TM,
- unsigned OptLevel, bool IsThinLTO,
- ModuleSummaryIndex *ExportSummary,
+ bool IsThinLTO, ModuleSummaryIndex *ExportSummary,
const ModuleSummaryIndex *ImportSummary) {
Optional<PGOOptions> PGOOpt;
if (!Conf.SampleProfile.empty())
@@ -274,25 +273,6 @@
if (!Conf.DisableVerify)
MPM.addPass(VerifierPass());
- OptimizationLevel OL;
-
- switch (OptLevel) {
- default:
- llvm_unreachable("Invalid optimization level");
- case 0:
- OL = OptimizationLevel::O0;
- break;
- case 1:
- OL = OptimizationLevel::O1;
- break;
- case 2:
- OL = OptimizationLevel::O2;
- break;
- case 3:
- OL = OptimizationLevel::O3;
- break;
- }
-
// Parse a custom pipeline if asked to.
if (!Conf.OptPipeline.empty()) {
if (auto Err = PB.parsePassPipeline(MPM, Conf.OptPipeline)) {
@@ -300,9 +280,9 @@
Conf.OptPipeline + "': " + toString(std::move(Err)));
}
} else if (IsThinLTO) {
- MPM.addPass(PB.buildThinLTODefaultPipeline(OL, ImportSummary));
+ MPM.addPass(PB.buildThinLTODefaultPipeline(Conf.OptLevel, ImportSummary));
} else {
- MPM.addPass(PB.buildLTODefaultPipeline(OL, ExportSummary));
+ MPM.addPass(PB.buildLTODefaultPipeline(Conf.OptLevel, ExportSummary));
}
if (!Conf.DisableVerify)
@@ -330,7 +310,8 @@
PMB.VerifyOutput = !Conf.DisableVerify;
PMB.LoopVectorize = true;
PMB.SLPVectorize = true;
- PMB.OptLevel = Conf.OptLevel;
+ PMB.OptLevel = Conf.OptLevel.getSpeedupLevel();
+ PMB.SizeLevel = Conf.OptLevel.getSizeLevel();
PMB.PGOSampleUse = Conf.SampleProfile;
PMB.EnablePGOCSInstrGen = Conf.RunCSIRInstr;
if (!Conf.RunCSIRInstr && !Conf.CSIRProfile.empty()) {
@@ -367,8 +348,7 @@
}
// FIXME: Plumb the combined index into the new pass manager.
if (Conf.UseNewPM || !Conf.OptPipeline.empty()) {
- runNewPMPasses(Conf, Mod, TM, Conf.OptLevel, IsThinLTO, ExportSummary,
- ImportSummary);
+ runNewPMPasses(Conf, Mod, TM, IsThinLTO, ExportSummary, ImportSummary);
} else {
runOldPMPasses(Conf, Mod, TM, IsThinLTO, ExportSummary, ImportSummary);
}
Index: llvm/lib/LTO/LTO.cpp
===================================================================
--- llvm/lib/LTO/LTO.cpp
+++ llvm/lib/LTO/LTO.cpp
@@ -132,7 +132,8 @@
AddUnsigned(-1);
AddUnsigned(Conf.CGOptLevel);
AddUnsigned(Conf.CGFileType);
- AddUnsigned(Conf.OptLevel);
+ AddUnsigned(Conf.OptLevel.getSizeLevel());
+ AddUnsigned(Conf.OptLevel.getSpeedupLevel());
AddUnsigned(Conf.UseNewPM);
AddUnsigned(Conf.Freestanding);
AddString(Conf.OptPipeline);
@@ -1027,7 +1028,8 @@
return It->second;
};
computeDeadSymbolsWithConstProp(ThinLTO.CombinedIndex, GUIDPreservedSymbols,
- isPrevailing, Conf.OptLevel > 0);
+ isPrevailing,
+ Conf.OptLevel.getSpeedupLevel() > 0);
// Setup output file to emit statistics.
auto StatsFileOrErr = setupStatsFile(Conf.StatsFile);
@@ -1469,7 +1471,7 @@
runWholeProgramDevirtOnIndex(ThinLTO.CombinedIndex, ExportedGUIDs,
LocalWPDTargetsMap);
- if (Conf.OptLevel > 0)
+ if (Conf.OptLevel.getSpeedupLevel() > 0)
ComputeCrossModuleImport(ThinLTO.CombinedIndex, ModuleToDefinedGVSummaries,
ImportLists, ExportLists);
Index: llvm/include/llvm/Passes/OptimizationLevel.h
===================================================================
--- llvm/include/llvm/Passes/OptimizationLevel.h
+++ llvm/include/llvm/Passes/OptimizationLevel.h
@@ -15,6 +15,7 @@
#ifndef LLVM_PASSES_OPTIMIZATIONLEVEL_H
#define LLVM_PASSES_OPTIMIZATIONLEVEL_H
+#include "llvm/ADT/Optional.h"
#include <assert.h>
namespace llvm {
@@ -22,6 +23,10 @@
class OptimizationLevel final {
unsigned SpeedLevel = 2;
unsigned SizeLevel = 0;
+
+public:
+ OptimizationLevel() = default;
+
OptimizationLevel(unsigned SpeedLevel, unsigned SizeLevel)
: SpeedLevel(SpeedLevel), SizeLevel(SizeLevel) {
// Check that only valid combinations are passed.
@@ -33,8 +38,25 @@
"Optimize for size should be encoded with speedup level == 2");
}
-public:
- OptimizationLevel() = default;
+ static Optional<OptimizationLevel> forChar(char c) {
+ switch (c) {
+ case '0':
+ return O0;
+ case '1':
+ return O1;
+ case '2':
+ return O2;
+ case '3':
+ return O3;
+ case 's':
+ return Os;
+ case 'z':
+ return Oz;
+ default:
+ return Optional<OptimizationLevel>();
+ }
+ }
+
/// Disable as many optimizations as possible. This doesn't completely
/// disable the optimizer in all cases, for example always_inline functions
/// can be required to be inlined for correctness.
Index: llvm/include/llvm/LTO/legacy/ThinLTOCodeGenerator.h
===================================================================
--- llvm/include/llvm/LTO/legacy/ThinLTOCodeGenerator.h
+++ llvm/include/llvm/LTO/legacy/ThinLTOCodeGenerator.h
@@ -20,6 +20,7 @@
#include "llvm/ADT/Triple.h"
#include "llvm/IR/ModuleSummaryIndex.h"
#include "llvm/LTO/LTO.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Support/CachePruning.h"
#include "llvm/Support/CodeGen.h"
#include "llvm/Support/MemoryBuffer.h"
@@ -222,9 +223,7 @@
}
/// IR optimization level: from 0 to 3.
- void setOptLevel(unsigned NewOptLevel) {
- OptLevel = (NewOptLevel > 3) ? 3 : NewOptLevel;
- }
+ void setOptLevel(OptimizationLevel NewOptLevel) { OptLevel = NewOptLevel; }
/// Enable or disable the new pass manager.
void setUseNewPM(unsigned Enabled) { UseNewPM = Enabled; }
@@ -346,7 +345,7 @@
bool Freestanding = false;
/// IR Optimization Level [0-3].
- unsigned OptLevel = 3;
+ OptimizationLevel OptLevel = OptimizationLevel::O3;
/// Flag to indicate whether the new pass manager should be used for IR
/// optimizations.
Index: llvm/include/llvm/LTO/legacy/LTOCodeGenerator.h
===================================================================
--- llvm/include/llvm/LTO/legacy/LTOCodeGenerator.h
+++ llvm/include/llvm/LTO/legacy/LTOCodeGenerator.h
@@ -43,6 +43,7 @@
#include "llvm/IR/Module.h"
#include "llvm/LTO/Config.h"
#include "llvm/LTO/LTO.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/Error.h"
#include "llvm/Support/ToolOutputFile.h"
@@ -98,7 +99,7 @@
void setCpu(StringRef MCpu) { Config.CPU = std::string(MCpu); }
void setAttrs(std::vector<std::string> MAttrs) { Config.MAttrs = MAttrs; }
- void setOptLevel(unsigned OptLevel);
+ void setOptLevel(OptimizationLevel OptLevel);
void setShouldInternalize(bool Value) { ShouldInternalize = Value; }
void setShouldEmbedUselists(bool Value) { ShouldEmbedUselists = Value; }
Index: llvm/include/llvm/LTO/Config.h
===================================================================
--- llvm/include/llvm/LTO/Config.h
+++ llvm/include/llvm/LTO/Config.h
@@ -20,6 +20,7 @@
#include "llvm/IR/GlobalValue.h"
#include "llvm/IR/LLVMContext.h"
#include "llvm/IR/LegacyPassManager.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Passes/PassBuilder.h"
#include "llvm/Support/CodeGen.h"
#include "llvm/Target/TargetOptions.h"
@@ -54,7 +55,7 @@
Optional<CodeModel::Model> CodeModel = None;
CodeGenOpt::Level CGOptLevel = CodeGenOpt::Default;
CodeGenFileType CGFileType = CGFT_ObjectFile;
- unsigned OptLevel = 2;
+ OptimizationLevel OptLevel = OptimizationLevel::O2;
bool DisableVerify = false;
/// Use the new pass manager
Index: lld/wasm/Driver.cpp
===================================================================
--- lld/wasm/Driver.cpp
+++ lld/wasm/Driver.cpp
@@ -372,7 +372,8 @@
config->sharedMemory = args.hasArg(OPT_shared_memory);
config->importTable = args.hasArg(OPT_import_table);
config->importUndefined = args.hasArg(OPT_import_undefined);
- config->ltoo = args::getInteger(args, OPT_lto_O, 2);
+ config->ltoo =
+ args::getOptLevel(args, OPT_lto_O, llvm::OptimizationLevel::O2);
config->ltoPartitions = args::getInteger(args, OPT_lto_partitions, 1);
config->ltoNewPassManager =
args.hasFlag(OPT_no_lto_legacy_pass_manager, OPT_lto_legacy_pass_manager,
@@ -494,8 +495,6 @@
error("--compress-relocations is incompatible with output debug"
" information. Please pass --strip-debug or --strip-all");
- if (config->ltoo > 3)
- error("invalid optimization level for LTO: " + Twine(config->ltoo));
if (config->ltoPartitions == 0)
error("--lto-partitions: number of threads must be > 0");
if (!get_threadpool_strategy(config->thinLTOJobs))
Index: lld/wasm/Config.h
===================================================================
--- lld/wasm/Config.h
+++ lld/wasm/Config.h
@@ -12,6 +12,7 @@
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/StringSet.h"
#include "llvm/BinaryFormat/Wasm.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Support/CachePruning.h"
namespace lld {
@@ -57,7 +58,7 @@
uint64_t maxMemory;
uint64_t zStackSize;
unsigned ltoPartitions;
- unsigned ltoo;
+ llvm::OptimizationLevel ltoo = llvm::OptimizationLevel::O2;
unsigned optimize;
llvm::StringRef thinLTOJobs;
bool ltoNewPassManager;
Index: lld/test/wasm/lto/opt-level.ll
===================================================================
--- lld/test/wasm/lto/opt-level.ll
+++ lld/test/wasm/lto/opt-level.ll
@@ -3,6 +3,10 @@
; RUN: obj2yaml %t0 | FileCheck --check-prefix=CHECK-O0 %s
; RUN: wasm-ld -o %t2 -e main --lto-O2 %t.o
; RUN: obj2yaml %t2 | FileCheck --check-prefix=CHECK-O2 %s
+; RUN: wasm-ld -o %t2 -e main --lto-Os %t.o
+; RUN: obj2yaml %t2 | FileCheck --check-prefix=CHECK-O2 %s
+; RUN: wasm-ld -o %t2 -e main --lto-Oz %t.o
+; RUN: obj2yaml %t2 | FileCheck --check-prefix=CHECK-O2 %s
; RUN: wasm-ld -o %t2a -e main %t.o
; RUN: obj2yaml %t2a | FileCheck --check-prefix=CHECK-O2 %s
@@ -13,7 +17,7 @@
; RUN: not wasm-ld -o %t3 -e main --lto-O-1 %t.o 2>&1 | \
; RUN: FileCheck --check-prefix=INVALIDNEGATIVE %s
-; INVALIDNEGATIVE: invalid optimization level for LTO: 4294967295
+; INVALIDNEGATIVE: invalid optimization level for LTO: -1
target datalayout = "e-m:e-p:32:32-p10:8:8-p20:8:8-i64:64-n32:64-S128"
target triple = "wasm32-unknown-unknown-wasm"
Index: lld/test/MachO/lto-opt-level.ll
===================================================================
--- lld/test/MachO/lto-opt-level.ll
+++ lld/test/MachO/lto-opt-level.ll
@@ -9,6 +9,12 @@
; RUN: %lld %t/test.o --lto-O2 -o %t/test
; RUN: llvm-nm -pa %t/test | FileCheck %s --check-prefixes=CHECK-O2
+; RUN: %lld %t/test.o --lto-Os -o %t/test
+; RUN: llvm-nm -pa %t/test | FileCheck %s --check-prefixes=CHECK-O2
+
+; RUN: %lld %t/test.o --lto-Oz -o %t/test
+; RUN: llvm-nm -pa %t/test | FileCheck %s --check-prefixes=CHECK-O2
+
; RUN: %lld %t/test.o -o %t/test
; RUN: llvm-nm -pa %t/test | FileCheck %s --check-prefixes=CHECK-O2
Index: lld/test/ELF/lto/opt-level.ll
===================================================================
--- lld/test/ELF/lto/opt-level.ll
+++ lld/test/ELF/lto/opt-level.ll
@@ -10,6 +10,10 @@
; RUN: llvm-nm %t2a | FileCheck --check-prefix=CHECK-O2 %s
; RUN: ld.lld -o %t2 -e main %t.o --plugin-opt O2
; RUN: llvm-nm %t2 | FileCheck --check-prefix=CHECK-O2 %s
+; RUN: ld.lld -o %t2 -e main --lto-Os %t.o
+; RUN: llvm-nm %t2 | FileCheck --check-prefix=CHECK-O2 %s
+; RUN: ld.lld -o %t2 -e main --lto-Oz %t.o
+; RUN: llvm-nm %t2 | FileCheck --check-prefix=CHECK-O2 %s
; Reject invalid optimization levels.
; RUN: not ld.lld -o /dev/null -e main --lto-O6 %t.o 2>&1 | \
@@ -19,14 +23,14 @@
; RUN: FileCheck --check-prefix=INVALID1 %s
; RUN: not ld.lld -o /dev/null -e main --plugin-opt=Ofoo %t.o 2>&1 | \
; RUN: FileCheck --check-prefix=INVALID2 %s
-; INVALID2: --plugin-opt=Ofoo: number expected, but got 'foo'
+; INVALID2: invalid optimization level for LTO: foo
; RUN: not ld.lld -o /dev/null -e main --lto-O-1 %t.o 2>&1 | \
; RUN: FileCheck --check-prefix=INVALIDNEGATIVE1 %s
-; INVALIDNEGATIVE1: invalid optimization level for LTO: 4294967295
+; INVALIDNEGATIVE1: invalid optimization level for LTO: -1
; RUN: not ld.lld -o /dev/null -e main --plugin-opt=O-1 %t.o 2>&1 | \
; RUN: FileCheck --check-prefix=INVALIDNEGATIVE2 %s
-; INVALIDNEGATIVE2: invalid optimization level for LTO: 4294967295
+; INVALIDNEGATIVE2: invalid optimization level for LTO: -1
target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128"
target triple = "x86_64-unknown-linux-gnu"
Index: lld/test/COFF/lto-opt-level.ll
===================================================================
--- lld/test/COFF/lto-opt-level.ll
+++ lld/test/COFF/lto-opt-level.ll
@@ -4,8 +4,17 @@
; RUN: FileCheck --check-prefix=CHECK-O0 %s < %t0.map
; RUN: lld-link /out:%t2.exe /entry:main /subsystem:console /opt:lldlto=2 /lldmap:%t2.map %t.obj
; RUN: FileCheck --check-prefix=CHECK-O2 %s < %t2.map
+; RUN: lld-link /out:%t2.exe /entry:main /subsystem:console /opt:lldlto=s /lldmap:%t2.map %t.obj
+; RUN: FileCheck --check-prefix=CHECK-O2 %s < %t2.map
+; RUN: lld-link /out:%t2.exe /entry:main /subsystem:console /opt:lldlto=z /lldmap:%t2.map %t.obj
+; RUN: FileCheck --check-prefix=CHECK-O2 %s < %t2.map
; RUN: lld-link /out:%t2a.exe /entry:main /subsystem:console /lldmap:%t2a.map %t.obj
; RUN: FileCheck --check-prefix=CHECK-O2 %s < %t2a.map
+; RUN: not lld-link /out:%t2.exe /entry:main /subsystem:console /opt:lldlto=a /lldmap:%t2.map %t.obj 2>&1 | FileCheck %s --check-prefix=CHECK-ERROR-A
+; RUN: not lld-link /out:%t2.exe /entry:main /subsystem:console /opt:lldlto=abc /lldmap:%t2.map %t.obj 2>&1 | FileCheck %s --check-prefix=CHECK-ERROR-ABC
+
+; CHECK-ERROR-A: invalid optimization level: a
+; CHECK-ERROR-ABC: invalid optimization level: abc
target datalayout = "e-m:w-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128"
target triple = "x86_64-pc-windows-msvc"
Index: lld/include/lld/Common/Args.h
===================================================================
--- lld/include/lld/Common/Args.h
+++ lld/include/lld/Common/Args.h
@@ -10,6 +10,7 @@
#define LLD_ARGS_H
#include "lld/Common/LLVM.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Support/CodeGen.h"
#include "llvm/Support/MemoryBuffer.h"
#include <vector>
@@ -23,7 +24,9 @@
namespace lld {
namespace args {
-llvm::CodeGenOpt::Level getCGOptLevel(int optLevelLTO);
+llvm::CodeGenOpt::Level getCGOptLevel(llvm::OptimizationLevel optLevelLTO);
+llvm::OptimizationLevel getOptLevel(llvm::opt::InputArgList &args, unsigned key,
+ llvm::OptimizationLevel Default);
int64_t getInteger(llvm::opt::InputArgList &args, unsigned key,
int64_t Default);
Index: lld/MachO/Driver.cpp
===================================================================
--- lld/MachO/Driver.cpp
+++ lld/MachO/Driver.cpp
@@ -1234,9 +1234,8 @@
config->ltoNewPassManager =
args.hasFlag(OPT_no_lto_legacy_pass_manager, OPT_lto_legacy_pass_manager,
LLVM_ENABLE_NEW_PASS_MANAGER);
- config->ltoo = args::getInteger(args, OPT_lto_O, 2);
- if (config->ltoo > 3)
- error("--lto-O: invalid optimization level: " + Twine(config->ltoo));
+ config->ltoo =
+ args::getOptLevel(args, OPT_lto_O, llvm::OptimizationLevel::O2);
config->thinLTOCacheDir = args.getLastArgValue(OPT_cache_path_lto);
config->thinLTOCachePolicy = getLTOCachePolicy(args);
config->runtimePaths = args::getStrings(args, OPT_rpath);
Index: lld/MachO/Config.h
===================================================================
--- lld/MachO/Config.h
+++ lld/MachO/Config.h
@@ -15,6 +15,7 @@
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/StringSet.h"
#include "llvm/BinaryFormat/MachO.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Support/CachePruning.h"
#include "llvm/Support/GlobPattern.h"
#include "llvm/Support/VersionTuple.h"
@@ -142,7 +143,7 @@
llvm::StringRef ltoObjPath;
llvm::StringRef thinLTOJobs;
llvm::StringRef umbrella;
- uint32_t ltoo = 2;
+ llvm::OptimizationLevel ltoo = llvm::OptimizationLevel::O2;
llvm::CachePruningPolicy thinLTOCachePolicy;
llvm::StringRef thinLTOCacheDir;
bool deadStripDylibs = false;
Index: lld/ELF/LTO.cpp
===================================================================
--- lld/ELF/LTO.cpp
+++ lld/ELF/LTO.cpp
@@ -132,8 +132,8 @@
c.MAttrs = getMAttrs();
c.CGOptLevel = args::getCGOptLevel(config->ltoo);
- c.PTO.LoopVectorization = c.OptLevel > 1;
- c.PTO.SLPVectorization = c.OptLevel > 1;
+ c.PTO.LoopVectorization = c.OptLevel.getSpeedupLevel() > 1;
+ c.PTO.SLPVectorization = c.OptLevel.getSpeedupLevel() > 1;
// Set up a custom pipeline if we've been asked to.
c.OptPipeline = std::string(config->ltoNewPmPasses);
Index: lld/ELF/Driver.cpp
===================================================================
--- lld/ELF/Driver.cpp
+++ lld/ELF/Driver.cpp
@@ -49,6 +49,7 @@
#include "llvm/ADT/StringSwitch.h"
#include "llvm/Config/llvm-config.h"
#include "llvm/LTO/LTO.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Remarks/HotnessThresholdParser.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/Compression.h"
@@ -1069,7 +1070,8 @@
config->ltoWholeProgramVisibility =
args.hasFlag(OPT_lto_whole_program_visibility,
OPT_no_lto_whole_program_visibility, false);
- config->ltoo = args::getInteger(args, OPT_lto_O, 2);
+ config->ltoo =
+ args::getOptLevel(args, OPT_lto_O, llvm::OptimizationLevel::O2);
config->ltoObjPath = args.getLastArgValue(OPT_lto_obj_path_eq);
config->ltoPartitions = args::getInteger(args, OPT_lto_partitions, 1);
config->ltoSampleProfile = args.getLastArgValue(OPT_lto_sample_profile);
@@ -1273,8 +1275,6 @@
if (auto *arg = args.getLastArg(OPT_thinlto_jobs))
config->thinLTOJobs = arg->getValue();
- if (config->ltoo > 3)
- error("invalid optimization level for LTO: " + Twine(config->ltoo));
if (config->ltoPartitions == 0)
error("--lto-partitions: number of threads must be > 0");
if (!get_threadpool_strategy(config->thinLTOJobs))
Index: lld/ELF/Config.h
===================================================================
--- lld/ELF/Config.h
+++ lld/ELF/Config.h
@@ -16,6 +16,7 @@
#include "llvm/ADT/StringRef.h"
#include "llvm/ADT/StringSet.h"
#include "llvm/BinaryFormat/ELF.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Support/CachePruning.h"
#include "llvm/Support/CodeGen.h"
#include "llvm/Support/Endian.h"
@@ -272,7 +273,7 @@
uint64_t mipsGotSize;
uint64_t zStackSize;
unsigned ltoPartitions;
- unsigned ltoo;
+ llvm::OptimizationLevel ltoo;
unsigned optimize;
StringRef thinLTOJobs;
unsigned timeTraceGranularity;
Index: lld/Common/CMakeLists.txt
===================================================================
--- lld/Common/CMakeLists.txt
+++ lld/Common/CMakeLists.txt
@@ -49,6 +49,7 @@
Demangle
MC
Option
+ Passes
Support
Target
Index: lld/Common/Args.cpp
===================================================================
--- lld/Common/Args.cpp
+++ lld/Common/Args.cpp
@@ -12,6 +12,7 @@
#include "llvm/ADT/StringExtras.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/Option/ArgList.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Support/Path.h"
using namespace llvm;
@@ -19,13 +20,27 @@
// TODO(sbc): Remove this once CGOptLevel can be set completely based on bitcode
// function metadata.
-CodeGenOpt::Level lld::args::getCGOptLevel(int optLevelLTO) {
- if (optLevelLTO == 3)
+CodeGenOpt::Level lld::args::getCGOptLevel(OptimizationLevel optLevelLTO) {
+ if (optLevelLTO.getSpeedupLevel() == 3)
return CodeGenOpt::Aggressive;
- assert(optLevelLTO < 3);
return CodeGenOpt::Default;
}
+OptimizationLevel args::getOptLevel(llvm::opt::InputArgList &args,
+ unsigned int key,
+ llvm::OptimizationLevel Default) {
+ Optional<OptimizationLevel> OL;
+ if (opt::Arg *arg = args.getLastArg(key)) {
+ std::string lto = arg->getValue();
+ if (lto.size() == 1)
+ OL = llvm::OptimizationLevel::forChar(lto[0]);
+ if (!OL)
+ error("invalid optimization level for LTO: " + lto);
+ return OL.getValueOr(Default);
+ }
+ return Default;
+}
+
static int64_t getInteger(opt::InputArgList &args, unsigned key,
int64_t Default, unsigned base) {
auto *a = args.getLastArg(key);
Index: lld/COFF/Driver.cpp
===================================================================
--- lld/COFF/Driver.cpp
+++ lld/COFF/Driver.cpp
@@ -36,6 +36,7 @@
#include "llvm/Option/Arg.h"
#include "llvm/Option/ArgList.h"
#include "llvm/Option/Option.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Support/BinaryStreamReader.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/Debug.h"
@@ -1613,7 +1614,12 @@
ltoDebugPM = false;
} else if (s.startswith("lldlto=")) {
StringRef optLevel = s.substr(7);
- if (optLevel.getAsInteger(10, config->ltoo) || config->ltoo > 3)
+ Optional<OptimizationLevel> OL;
+ if (optLevel.size() == 1)
+ OL = OptimizationLevel::forChar(optLevel[0]);
+ if (OL)
+ config->ltoo = *OL;
+ else
error("/opt:lldlto: invalid optimization level: " + optLevel);
} else if (s.startswith("lldltojobs=")) {
StringRef jobs = s.substr(11);
Index: lld/COFF/Config.h
===================================================================
--- lld/COFF/Config.h
+++ lld/COFF/Config.h
@@ -14,6 +14,7 @@
#include "llvm/ADT/StringMap.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/Object/COFF.h"
+#include "llvm/Passes/OptimizationLevel.h"
#include "llvm/Support/CachePruning.h"
#include <cstdint>
#include <map>
@@ -156,7 +157,7 @@
bool noSEH = false;
// Used for /opt:lldlto=N
- unsigned ltoo = 2;
+ llvm::OptimizationLevel ltoo = llvm::OptimizationLevel::O2;
// Used for /opt:lldltojobs=N
std::string thinLTOJobs;
Index: clang/lib/CodeGen/BackendUtil.cpp
===================================================================
--- clang/lib/CodeGen/BackendUtil.cpp
+++ clang/lib/CodeGen/BackendUtil.cpp
@@ -1590,7 +1590,8 @@
Conf.MAttrs = TOpts.Features;
Conf.RelocModel = CGOpts.RelocationModel;
Conf.CGOptLevel = getCGOptLevel(CGOpts);
- Conf.OptLevel = CGOpts.OptimizationLevel;
+ Conf.OptLevel =
+ OptimizationLevel(CGOpts.OptimizationLevel, CGOpts.OptimizeSize);
initTargetOptions(Diags, Conf.Options, CGOpts, TOpts, LOpts, HeaderOpts);
Conf.SampleProfile = std::move(SampleProfile);
Conf.PTO.LoopUnrolling = CGOpts.UnrollLoops;
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits