diff --git a/clang/include/clang/Basic/CodeGenOptions.def b/clang/include/clang/Basic/CodeGenOptions.def --- a/clang/include/clang/Basic/CodeGenOptions.def +++ b/clang/include/clang/Basic/CodeGenOptions.def @@ -106,6 +106,10 @@ ///< Set when -fxray-always-emit-typedevents is enabled. CODEGENOPT(XRayAlwaysEmitTypedEvents , 1, 0) +///< Set when -fxray-ignore-loops is enabled. +CODEGENOPT(XRayIgnoreLoops , 1, 0) + + ///< Set the minimum number of instructions in a function to determine selective ///< XRay instrumentation. VALUE_CODEGENOPT(XRayInstructionThreshold , 32, 200) diff --git a/clang/include/clang/Driver/Options.td b/clang/include/clang/Driver/Options.td --- a/clang/include/clang/Driver/Options.td +++ b/clang/include/clang/Driver/Options.td @@ -1292,6 +1292,13 @@ def fnoxray_always_emit_typedevents : Flag<["-"], "fno-xray-always-emit-typedevents">, Group, Flags<[CC1Option]>; +def fxray_ignore_loops : Flag<["-"], "fxray-ignore-loops">, Group, + Flags<[CC1Option]>, + HelpText<"Don't instrument functions with loops unless they also meet the minimum function size">; +def fno_xray_ignore_loops : Flag<["-"], "fno-xray-ignore-loops">, Group, + Flags<[CC1Option]>; + + def fxray_link_deps : Flag<["-"], "fxray-link-deps">, Group, Flags<[CC1Option]>, HelpText<"Tells clang to add the link dependencies for XRay.">; diff --git a/clang/lib/CodeGen/CodeGenFunction.cpp b/clang/lib/CodeGen/CodeGenFunction.cpp --- a/clang/lib/CodeGen/CodeGenFunction.cpp +++ b/clang/lib/CodeGen/CodeGenFunction.cpp @@ -818,6 +818,9 @@ Fn->addFnAttr( "xray-instruction-threshold", llvm::itostr(CGM.getCodeGenOpts().XRayInstructionThreshold)); + if (CGM.getCodeGenOpts().XRayIgnoreLoops) { + Fn->addFnAttr("xray-ignore-loops"); + } } if (const auto *Attr = D->getAttr()) { diff --git a/clang/lib/Frontend/CompilerInvocation.cpp b/clang/lib/Frontend/CompilerInvocation.cpp --- a/clang/lib/Frontend/CompilerInvocation.cpp +++ b/clang/lib/Frontend/CompilerInvocation.cpp @@ -1091,6 +1091,8 @@ Args.hasArg(OPT_fxray_always_emit_typedevents); Opts.XRayInstructionThreshold = getLastArgIntValue(Args, OPT_fxray_instruction_threshold_EQ, 200, Diags); + Opts.XRayIgnoreLoops = + Args.hasArg(OPT_fxray_ignore_loops, OPT_fno_xray_ignore_loops, false); auto XRayInstrBundles = Args.getAllArgValues(OPT_fxray_instrumentation_bundle); diff --git a/clang/test/CodeGen/xray-ignore-loops.cpp b/clang/test/CodeGen/xray-ignore-loops.cpp new file mode 100644 --- /dev/null +++ b/clang/test/CodeGen/xray-ignore-loops.cpp @@ -0,0 +1,8 @@ +// RUN: %clang_cc1 -fxray-instrument -fxray-ignore-loops -x c++ -std=c++11 -emit-llvm -o - %s -triple x86_64-unknown-linux-gnu | FileCheck %s + +int foo() { + return 1; +} + +// CHECK: define i32 @_Z3foov() #[[ATTRS:[0-9]+]] { +// CHECK-DAG: attributes #[[ATTRS]] = {{.*}} "xray-ignore-loops" {{.*}}