Index: clang/include/clang/Driver/Options.td =================================================================== --- clang/include/clang/Driver/Options.td +++ clang/include/clang/Driver/Options.td @@ -1013,6 +1013,8 @@ def fthinlto_index_EQ : Joined<["-"], "fthinlto-index=">, Flags<[CC1Option]>, Group, HelpText<"Perform ThinLTO importing using provided function summary index">; +def femit_summary_index : Flag<["-"], "femit-summary-index">, Group, + Flags<[CC1Option]>, HelpText<"Emit a module summary (default for ThinLTO)">; def fmacro_backtrace_limit_EQ : Joined<["-"], "fmacro-backtrace-limit=">, Group, Flags<[DriverOption, CoreOption]>; def fmerge_all_constants : Flag<["-"], "fmerge-all-constants">, Group; Index: clang/include/clang/Frontend/CodeGenOptions.def =================================================================== --- clang/include/clang/Frontend/CodeGenOptions.def +++ clang/include/clang/Frontend/CodeGenOptions.def @@ -88,8 +88,10 @@ ///< be generated. CODEGENOPT(PrepareForLTO , 1, 0) ///< Set when -flto is enabled on the ///< compile step. -CODEGENOPT(EmitSummaryIndex, 1, 0) ///< Set when -flto=thin is enabled on the +CODEGENOPT(PrepareForThinLTO , 1, 0) ///< Set when -flto=thin is enabled on the ///< compile step. +CODEGENOPT(EmitSummaryIndex , 1, 0) ///< Emit a module summary. This is enabled + ///< by default for ThinLTO. CODEGENOPT(LTOUnit, 1, 0) ///< Emit IR to support LTO unit features (CFI, whole ///< program vtable opt). CODEGENOPT(IncrementalLinkerCompatible, 1, 0) ///< Emit an object file which can Index: clang/lib/CodeGen/BackendUtil.cpp =================================================================== --- clang/lib/CodeGen/BackendUtil.cpp +++ clang/lib/CodeGen/BackendUtil.cpp @@ -486,7 +486,7 @@ PMBuilder.Inliner = createFunctionInliningPass( CodeGenOpts.OptimizationLevel, CodeGenOpts.OptimizeSize, (!CodeGenOpts.SampleProfileFile.empty() && - CodeGenOpts.EmitSummaryIndex)); + CodeGenOpts.PrepareForThinLTO)); } PMBuilder.OptLevel = CodeGenOpts.OptimizationLevel; @@ -497,7 +497,7 @@ PMBuilder.DisableUnrollLoops = !CodeGenOpts.UnrollLoops; PMBuilder.MergeFunctions = CodeGenOpts.MergeFunctions; - PMBuilder.PrepareForThinLTO = CodeGenOpts.EmitSummaryIndex; + PMBuilder.PrepareForThinLTO = CodeGenOpts.PrepareForThinLTO; PMBuilder.PrepareForLTO = CodeGenOpts.PrepareForLTO; PMBuilder.RerollLoops = CodeGenOpts.RerollLoops; @@ -738,7 +738,7 @@ break; case Backend_EmitBC: - if (CodeGenOpts.EmitSummaryIndex) { + if (CodeGenOpts.PrepareForThinLTO) { if (!CodeGenOpts.ThinLinkBitcodeFile.empty()) { std::error_code EC; ThinLinkOS.reset(new llvm::raw_fd_ostream( @@ -752,10 +752,13 @@ } PerModulePasses.add( createWriteThinLTOBitcodePass(*OS, ThinLinkOS.get())); - } - else + } else { + if (CodeGenOpts.EmitSummaryIndex) + TheModule->addModuleFlag(Module::Error, "ThinLTO", uint32_t(0)); PerModulePasses.add( - createBitcodeWriterPass(*OS, CodeGenOpts.EmitLLVMUseLists)); + createBitcodeWriterPass(*OS, CodeGenOpts.EmitLLVMUseLists, + CodeGenOpts.EmitSummaryIndex)); + } break; case Backend_EmitLL: @@ -907,7 +910,7 @@ break; case Backend_EmitBC: - if (CodeGenOpts.EmitSummaryIndex) { + if (CodeGenOpts.PrepareForThinLTO) { if (!CodeGenOpts.ThinLinkBitcodeFile.empty()) { std::error_code EC; ThinLinkOS.emplace(CodeGenOpts.ThinLinkBitcodeFile, EC, @@ -921,8 +924,9 @@ MPM.addPass( ThinLTOBitcodeWriterPass(*OS, ThinLinkOS ? &*ThinLinkOS : nullptr)); } else { + if (CodeGenOpts.EmitSummaryIndex) + TheModule->addModuleFlag(Module::Error, "ThinLTO", uint32_t(0)); MPM.addPass(BitcodeWriterPass(*OS, CodeGenOpts.EmitLLVMUseLists, - CodeGenOpts.EmitSummaryIndex, CodeGenOpts.EmitSummaryIndex)); } break; Index: clang/lib/Driver/ToolChains/Clang.cpp =================================================================== --- clang/lib/Driver/ToolChains/Clang.cpp +++ clang/lib/Driver/ToolChains/Clang.cpp @@ -2057,6 +2057,8 @@ if (JA.getType() == types::TY_LLVM_BC) CmdArgs.push_back("-emit-llvm-uselists"); + Args.AddLastArg(CmdArgs, options::OPT_femit_summary_index); + if (D.isUsingLTO()) { Args.AddLastArg(CmdArgs, options::OPT_flto, options::OPT_flto_EQ); Index: clang/lib/Frontend/CompilerInvocation.cpp =================================================================== --- clang/lib/Frontend/CompilerInvocation.cpp +++ clang/lib/Frontend/CompilerInvocation.cpp @@ -649,8 +649,10 @@ Opts.NoUseJumpTables = Args.hasArg(OPT_fno_jump_tables); Opts.PrepareForLTO = Args.hasArg(OPT_flto, OPT_flto_EQ); + Opts.EmitSummaryIndex = Args.hasArg(OPT_femit_summary_index); const Arg *A = Args.getLastArg(OPT_flto, OPT_flto_EQ); - Opts.EmitSummaryIndex = A && A->containsValue("thin"); + if (A && A->containsValue("thin")) + Opts.PrepareForThinLTO = Opts.EmitSummaryIndex = true; Opts.LTOUnit = Args.hasFlag(OPT_flto_unit, OPT_fno_lto_unit, false); if (Arg *A = Args.getLastArg(OPT_fthinlto_index_EQ)) { if (IK.getLanguage() != InputKind::LLVM_IR) Index: clang/test/CodeGen/emit-summary-index.c =================================================================== --- /dev/null +++ clang/test/CodeGen/emit-summary-index.c @@ -0,0 +1,14 @@ +// RUN: %clang_cc1 -flto=thin -emit-llvm-bc < %s | llvm-bcanalyzer -dump | FileCheck %s +// ; Check that the -flto=thin option emits a ThinLTO summary +// CHECK: