Index: ELF/Config.h =================================================================== --- ELF/Config.h +++ ELF/Config.h @@ -91,6 +91,7 @@ uint16_t EMachine = llvm::ELF::EM_NONE; uint64_t EntryAddr = -1; unsigned Optimize = 0; + unsigned LTOOptLevel = 2; }; // The only instance of Configuration struct. Index: ELF/Driver.cpp =================================================================== --- ELF/Driver.cpp +++ ELF/Driver.cpp @@ -280,6 +280,12 @@ error("invalid optimization level"); } + if (auto *Arg = Args.getLastArg(OPT_lto_O)) { + StringRef Val = Arg->getValue(); + if (Val.getAsInteger(10, Config->LTOOptLevel)) + error("invalid optimization level"); + } + if (auto *Arg = Args.getLastArg(OPT_hash_style)) { StringRef S = Arg->getValue(); if (S == "gnu") { Index: ELF/LTO.cpp =================================================================== --- ELF/LTO.cpp +++ ELF/LTO.cpp @@ -52,7 +52,7 @@ // Run LTO passes. // Note that the gold plugin has a similar piece of code, so // it is probably better to move this code to a common place. -static void runLTOPasses(Module &M, TargetMachine &TM) { +static void runLTOPasses(Module &M, TargetMachine &TM, unsigned OptLevel) { legacy::PassManager LtoPasses; LtoPasses.add(createTargetTransformInfoWrapperPass(TM.getTargetIRAnalysis())); PassManagerBuilder PMB; @@ -62,7 +62,7 @@ PMB.VerifyOutput = true; PMB.LoopVectorize = true; PMB.SLPVectorize = true; - PMB.OptLevel = 2; // FIXME: This should be an option. + PMB.OptLevel = OptLevel; PMB.populateLTOPassManager(LtoPasses); LtoPasses.run(M); @@ -146,7 +146,7 @@ saveBCFile(Combined, ".lto.bc"); std::unique_ptr TM(getTargetMachine()); - runLTOPasses(Combined, *TM); + runLTOPasses(Combined, *TM, Config->LTOOptLevel); raw_svector_ostream OS(OwningData); legacy::PassManager CodeGenPasses; Index: ELF/Options.td =================================================================== --- ELF/Options.td +++ ELF/Options.td @@ -75,6 +75,9 @@ def l : JoinedOrSeparate<["-"], "l">, MetaVarName<"">, HelpText<"Root name of library to use">; +def lto_O : Joined<["--"], "lto-O">, MetaVarName<"">, + HelpText<"Optimization level for LTO">; + def m : JoinedOrSeparate<["-"], "m">, HelpText<"Set target emulation">; Index: test/ELF/lto/opt-level.ll =================================================================== --- /dev/null +++ test/ELF/lto/opt-level.ll @@ -0,0 +1,21 @@ +; RUN: llvm-as -o %t.o %s +; RUN: ld.lld -o %t0 -m elf_x86_64 -e main --lto-O0 %t.o +; RUN: llvm-nm %t0 | FileCheck --check-prefix=CHECK-O0 %s +; RUN: ld.lld -o %t2 -m elf_x86_64 -e main --lto-O2 %t.o +; RUN: llvm-nm %t2 | FileCheck --check-prefix=CHECK-O2 %s +; RUN: ld.lld -o %t2a -m elf_x86_64 -e main %t.o +; RUN: llvm-nm %t2a | FileCheck --check-prefix=CHECK-O2 %s + +target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +; CHECK-O0: foo +; CHECK-O2-NOT: foo +define internal void @foo() { + ret void +} + +define void @main() { + call void @foo() + ret void +}