Index: lld/trunk/ELF/Config.h =================================================================== --- lld/trunk/ELF/Config.h +++ lld/trunk/ELF/Config.h @@ -82,6 +82,7 @@ llvm::StringRef LTONewPmPasses; llvm::StringRef MapFile; llvm::StringRef OutputFile; + llvm::StringRef OptRemarksFilename; llvm::StringRef SoName; llvm::StringRef Sysroot; std::string RPath; @@ -117,6 +118,7 @@ bool Nostdlib; bool OFormatBinary; bool OMagic; + bool OptRemarksWithHotness; bool Pic; bool Pie; bool PrintGcSections; Index: lld/trunk/ELF/Driver.cpp =================================================================== --- lld/trunk/ELF/Driver.cpp +++ lld/trunk/ELF/Driver.cpp @@ -533,6 +533,7 @@ Config->NoUndefinedVersion = Args.hasArg(OPT_no_undefined_version); Config->Nostdlib = Args.hasArg(OPT_nostdlib); Config->OMagic = Args.hasArg(OPT_omagic); + Config->OptRemarksWithHotness = Args.hasArg(OPT_opt_remarks_with_hotness); Config->Pie = getArg(Args, OPT_pie, OPT_nopie, false); Config->PrintGcSections = Args.hasArg(OPT_print_gc_sections); Config->Relocatable = Args.hasArg(OPT_relocatable); @@ -555,6 +556,7 @@ Config->LTOAAPipeline = getString(Args, OPT_lto_aa_pipeline); Config->LTONewPmPasses = getString(Args, OPT_lto_newpm_passes); Config->MapFile = getString(Args, OPT_Map); + Config->OptRemarksFilename = getString(Args, OPT_opt_remarks_filename); Config->OutputFile = getString(Args, OPT_o); Config->SoName = getString(Args, OPT_soname); Config->Sysroot = getString(Args, OPT_sysroot); Index: lld/trunk/ELF/LTO.cpp =================================================================== --- lld/trunk/ELF/LTO.cpp +++ lld/trunk/ELF/LTO.cpp @@ -81,6 +81,10 @@ Conf.OptPipeline = Config->LTONewPmPasses; Conf.AAPipeline = Config->LTOAAPipeline; + // Set up optimization remarks if we've been asked to. + Conf.RemarksFilename = Config->OptRemarksFilename; + Conf.RemarksWithHotness = Config->OptRemarksWithHotness; + if (Config->SaveTemps) checkError(Conf.addSaveTemps(std::string(Config->OutputFile) + ".", /*UseInputModulePath*/ true)); Index: lld/trunk/ELF/Options.td =================================================================== --- lld/trunk/ELF/Options.td +++ lld/trunk/ELF/Options.td @@ -385,5 +385,9 @@ HelpText<"Number of LTO codegen partitions">; def disable_verify: F<"disable-verify">; def mllvm: S<"mllvm">; +def opt_remarks_filename: S<"opt-remarks-filename">, + HelpText<"YAML output file for optimization remarks">; +def opt_remarks_with_hotness: F<"opt-remarks-with-hotness">, + HelpText<"Include hotness informations in the optimization remarks file">; def save_temps: F<"save-temps">; def thinlto_jobs: J<"thinlto-jobs=">, HelpText<"Number of ThinLTO jobs">; Index: lld/trunk/test/ELF/lto/opt-remarks.ll =================================================================== --- lld/trunk/test/ELF/lto/opt-remarks.ll +++ lld/trunk/test/ELF/lto/opt-remarks.ll @@ -0,0 +1,68 @@ +; RUN: llvm-as %s -o %t.o + +; RUN: rm -f %t.yaml +; RUN: ld.lld -opt-remarks-filename %t.yaml %t.o -o %t -shared -save-temps +; RUN: llvm-dis %t.0.4.opt.bc -o - | FileCheck %s +; RUN: ld.lld -opt-remarks-with-hotness -opt-remarks-filename %t.hot.yaml \ +; RUN: %t.o -o %t -shared +; RUN: cat %t.yaml | FileCheck %s -check-prefix=YAML +; RUN: cat %t.hot.yaml | FileCheck %s -check-prefix=YAML-HOT + +; Check that @tinkywinky is inlined after optimizations. +; CHECK-LABEL: define i32 @main +; CHECK-NEXT: %a.i = call i32 @patatino() +; CHECK-NEXT: ret i32 %a.i +; CHECK-NEXT: } + +; YAML: --- !Analysis +; YAML-NEXT: Pass: inline +; YAML-NEXT: Name: CanBeInlined +; YAML-NEXT: Function: main +; YAML-NEXT: Args: +; YAML-NEXT: - Callee: tinkywinky +; YAML-NEXT: - String: ' can be inlined into ' +; YAML-NEXT: - Caller: main +; YAML-NEXT: - String: ' with cost=' +; YAML-NEXT: - Cost: '0' +; YAML-NEXT: - String: ' (threshold=' +; YAML-NEXT: - Threshold: '337' +; YAML-NEXT: - String: ')' +; YAML-NEXT: ... +; YAML-NEXT: --- !Passed +; YAML-NEXT: Pass: inline +; YAML-NEXT: Name: Inlined +; YAML-NEXT: Function: main +; YAML-NEXT: Args: +; YAML-NEXT: - Callee: tinkywinky +; YAML-NEXT: - String: ' inlined into ' +; YAML-NEXT: - Caller: main +; YAML-NEXT: ... + +; YAML-HOT: ... +; YAML-HOT: --- !Passed +; YAML-HOT: Pass: inline +; YAML-HOT-NEXT: Name: Inlined +; YAML-HOT-NEXT: Function: main +; YAML-HOT-NEXT: Hotness: 300 +; YAML-HOT-NEXT: Args: +; YAML-HOT-NEXT: - Callee: tinkywinky +; YAML-HOT-NEXT: - String: ' inlined into ' +; YAML-HOT-NEXT: - Caller: main +; YAML-HOT-NEXT: ... + +target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128" +target triple = "x86_64-scei-ps4" + +declare i32 @patatino() + +define i32 @tinkywinky() { + %a = call i32 @patatino() + ret i32 %a +} + +define i32 @main() !prof !0 { + %i = call i32 @tinkywinky() + ret i32 %i +} + +!0 = !{!"function_entry_count", i64 300}