[llvm] r295164 - [LLVM][XRAY][MIPS] Support xray on mips/mipsel/mips64/mips64el
Sagar Thakur via llvm-commits
llvm-commits at lists.llvm.org
Wed Feb 15 02:48:11 PST 2017
Author: slthakur
Date: Wed Feb 15 04:48:11 2017
New Revision: 295164
URL: http://llvm.org/viewvc/llvm-project?rev=295164&view=rev
Log:
[LLVM][XRAY][MIPS] Support xray on mips/mipsel/mips64/mips64el
Summary: Adds support for xray instrumentation on mips for both 32-bit and 64-bit.
Reviewed by sdardis, dberris
Differential: D27697
Added:
llvm/trunk/test/CodeGen/Mips/xray-mips-attribute-instrumentation.ll
llvm/trunk/test/CodeGen/Mips/xray-section-group.ll
Modified:
llvm/trunk/lib/CodeGen/XRayInstrumentation.cpp
llvm/trunk/lib/Target/Mips/MipsAsmPrinter.cpp
llvm/trunk/lib/Target/Mips/MipsAsmPrinter.h
llvm/trunk/lib/Target/Mips/MipsSubtarget.h
Modified: llvm/trunk/lib/CodeGen/XRayInstrumentation.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/XRayInstrumentation.cpp?rev=295164&r1=295163&r2=295164&view=diff
==============================================================================
--- llvm/trunk/lib/CodeGen/XRayInstrumentation.cpp (original)
+++ llvm/trunk/lib/CodeGen/XRayInstrumentation.cpp Wed Feb 15 04:48:11 2017
@@ -158,6 +158,10 @@ bool XRayInstrumentation::runOnMachineFu
case Triple::ArchType::thumb:
case Triple::ArchType::aarch64:
case Triple::ArchType::ppc64le:
+ case Triple::ArchType::mips:
+ case Triple::ArchType::mipsel:
+ case Triple::ArchType::mips64:
+ case Triple::ArchType::mips64el:
// For the architectures which don't have a single return instruction
prependRetWithPatchableExit(MF, TII);
break;
Modified: llvm/trunk/lib/Target/Mips/MipsAsmPrinter.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/MipsAsmPrinter.cpp?rev=295164&r1=295163&r2=295164&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/MipsAsmPrinter.cpp (original)
+++ llvm/trunk/lib/Target/Mips/MipsAsmPrinter.cpp Wed Feb 15 04:48:11 2017
@@ -39,6 +39,7 @@
#include "llvm/MC/MCELFStreamer.h"
#include "llvm/MC/MCExpr.h"
#include "llvm/MC/MCInst.h"
+#include "llvm/MC/MCInstBuilder.h"
#include "llvm/MC/MCSection.h"
#include "llvm/MC/MCSectionELF.h"
#include "llvm/MC/MCSymbolELF.h"
@@ -79,6 +80,9 @@ bool MipsAsmPrinter::runOnMachineFunctio
NaClAlignIndirectJumpTargets(MF);
AsmPrinter::runOnMachineFunction(MF);
+
+ EmitXRayTable();
+
return true;
}
@@ -132,6 +136,7 @@ void MipsAsmPrinter::emitPseudoIndirectB
void MipsAsmPrinter::EmitInstruction(const MachineInstr *MI) {
MipsTargetStreamer &TS = getTargetStreamer();
+ unsigned Opc = MI->getOpcode();
TS.forbidModuleDirective();
if (MI->isDebugValue()) {
@@ -143,20 +148,20 @@ void MipsAsmPrinter::EmitInstruction(con
}
// If we just ended a constant pool, mark it as such.
- if (InConstantPool && MI->getOpcode() != Mips::CONSTPOOL_ENTRY) {
+ if (InConstantPool && Opc != Mips::CONSTPOOL_ENTRY) {
OutStreamer->EmitDataRegion(MCDR_DataRegionEnd);
InConstantPool = false;
}
- if (MI->getOpcode() == Mips::CONSTPOOL_ENTRY) {
+ if (Opc == Mips::CONSTPOOL_ENTRY) {
// CONSTPOOL_ENTRY - This instruction represents a floating
- //constant pool in the function. The first operand is the ID#
+ // constant pool in the function. The first operand is the ID#
// for this instruction, the second is the index into the
// MachineConstantPool that this is, the third is the size in
// bytes of this constant pool entry.
// The required alignment is specified on the basic block holding this MI.
//
unsigned LabelId = (unsigned)MI->getOperand(0).getImm();
- unsigned CPIdx = (unsigned)MI->getOperand(1).getIndex();
+ unsigned CPIdx = (unsigned)MI->getOperand(1).getIndex();
// If this is the first entry of the pool, mark it.
if (!InConstantPool) {
@@ -174,6 +179,17 @@ void MipsAsmPrinter::EmitInstruction(con
return;
}
+ switch (Opc) {
+ case Mips::PATCHABLE_FUNCTION_ENTER:
+ LowerPATCHABLE_FUNCTION_ENTER(*MI);
+ return;
+ case Mips::PATCHABLE_FUNCTION_EXIT:
+ LowerPATCHABLE_FUNCTION_EXIT(*MI);
+ return;
+ case Mips::PATCHABLE_TAIL_CALL:
+ LowerPATCHABLE_TAIL_CALL(*MI);
+ return;
+ }
MachineBasicBlock::const_instr_iterator I = MI->getIterator();
MachineBasicBlock::const_instr_iterator E = MI->getParent()->instr_end();
@@ -1034,6 +1050,149 @@ void MipsAsmPrinter::EmitEndOfAsmFile(Mo
OutStreamer->SwitchSection(OutContext.getObjectFileInfo()->getTextSection());
}
+void MipsAsmPrinter::EmitSled(const MachineInstr &MI, SledKind Kind) {
+ const uint8_t NoopsInSledCount = Subtarget->isGP64bit() ? 15 : 11;
+ // For mips32 we want to emit the following pattern:
+ //
+ // .Lxray_sled_N:
+ // ALIGN
+ // B .tmpN
+ // 11 NOP instructions (44 bytes)
+ // ADDIU T9, T9, 52
+ // .tmpN
+ //
+ // We need the 44 bytes (11 instructions) because at runtime, we'd
+ // be patching over the full 48 bytes (12 instructions) with the following
+ // pattern:
+ //
+ // ADDIU SP, SP, -8
+ // NOP
+ // SW RA, 4(SP)
+ // SW T9, 0(SP)
+ // LUI T9, %hi(__xray_FunctionEntry/Exit)
+ // ORI T9, T9, %lo(__xray_FunctionEntry/Exit)
+ // LUI T0, %hi(function_id)
+ // JALR T9
+ // ORI T0, T0, %lo(function_id)
+ // LW T9, 0(SP)
+ // LW RA, 4(SP)
+ // ADDIU SP, SP, 8
+ //
+ // We add 52 bytes to t9 because we want to adjust the function pointer to
+ // the actual start of function i.e. the address just after the noop sled.
+ // We do this because gp displacement relocation is emitted at the start of
+ // of the function i.e after the nop sled and to correctly calculate the
+ // global offset table address, t9 must hold the address of the instruction
+ // containing the gp displacement relocation.
+ // FIXME: Is this correct for the static relocation model?
+ //
+ // For mips64 we want to emit the following pattern:
+ //
+ // .Lxray_sled_N:
+ // ALIGN
+ // B .tmpN
+ // 15 NOP instructions (60 bytes)
+ // .tmpN
+ //
+ // We need the 60 bytes (15 instructions) because at runtime, we'd
+ // be patching over the full 64 bytes (16 instructions) with the following
+ // pattern:
+ //
+ // DADDIU SP, SP, -16
+ // NOP
+ // SD RA, 8(SP)
+ // SD T9, 0(SP)
+ // LUI T9, %highest(__xray_FunctionEntry/Exit)
+ // ORI T9, T9, %higher(__xray_FunctionEntry/Exit)
+ // DSLL T9, T9, 16
+ // ORI T9, T9, %hi(__xray_FunctionEntry/Exit)
+ // DSLL T9, T9, 16
+ // ORI T9, T9, %lo(__xray_FunctionEntry/Exit)
+ // LUI T0, %hi(function_id)
+ // JALR T9
+ // ADDIU T0, T0, %lo(function_id)
+ // LD T9, 0(SP)
+ // LD RA, 8(SP)
+ // DADDIU SP, SP, 16
+ //
+ OutStreamer->EmitCodeAlignment(4);
+ auto CurSled = OutContext.createTempSymbol("xray_sled_", true);
+ OutStreamer->EmitLabel(CurSled);
+ auto Target = OutContext.createTempSymbol();
+
+ // Emit "B .tmpN" instruction, which jumps over the nop sled to the actual
+ // start of function
+ const MCExpr *TargetExpr = MCSymbolRefExpr::create(
+ Target, MCSymbolRefExpr::VariantKind::VK_None, OutContext);
+ EmitToStreamer(*OutStreamer, MCInstBuilder(Mips::BEQ)
+ .addReg(Mips::ZERO)
+ .addReg(Mips::ZERO)
+ .addExpr(TargetExpr));
+
+ for (int8_t I = 0; I < NoopsInSledCount; I++)
+ EmitToStreamer(*OutStreamer, MCInstBuilder(Mips::SLL)
+ .addReg(Mips::ZERO)
+ .addReg(Mips::ZERO)
+ .addImm(0));
+
+ OutStreamer->EmitLabel(Target);
+
+ if (!Subtarget->isGP64bit()) {
+ EmitToStreamer(*OutStreamer,
+ MCInstBuilder(Mips::ADDiu)
+ .addReg(Mips::T9)
+ .addReg(Mips::T9)
+ .addImm(0x34));
+ }
+
+ recordSled(CurSled, MI, Kind);
+}
+
+void MipsAsmPrinter::EmitXRayTable() {
+ if (Sleds.empty())
+ return;
+ if (Subtarget->isTargetELF()) {
+ auto PrevSection = OutStreamer->getCurrentSectionOnly();
+ auto Fn = MF->getFunction();
+ MCSection *Section;
+
+ if (Fn->hasComdat())
+ Section = OutContext.getELFSection("xray_instr_map", ELF::SHT_PROGBITS,
+ ELF::SHF_ALLOC | ELF::SHF_GROUP, 0,
+ Fn->getComdat()->getName());
+ else
+ Section =
+ OutContext.getELFSection("xray_instr_map", ELF::SHT_PROGBITS,
+ ELF::SHF_ALLOC, 0, CurrentFnSym->getName());
+
+ OutStreamer->SwitchSection(Section);
+ for (const auto &Sled : Sleds) {
+ OutStreamer->EmitSymbolValue(Sled.Sled, Subtarget->isGP64bit() ? 8 : 4);
+ OutStreamer->EmitSymbolValue(CurrentFnSym, Subtarget->isGP64bit() ? 8 : 4);
+ auto Kind = static_cast<uint8_t>(Sled.Kind);
+ OutStreamer->EmitBytes(
+ StringRef(reinterpret_cast<const char *>(&Kind), 1));
+ OutStreamer->EmitBytes(
+ StringRef(reinterpret_cast<const char *>(&Sled.AlwaysInstrument), 1));
+ OutStreamer->EmitZeros(Subtarget->isGP64bit() ? 14 : 6);
+ }
+ OutStreamer->SwitchSection(PrevSection);
+ }
+ Sleds.clear();
+}
+
+void MipsAsmPrinter::LowerPATCHABLE_FUNCTION_ENTER(const MachineInstr &MI) {
+ EmitSled(MI, SledKind::FUNCTION_ENTER);
+}
+
+void MipsAsmPrinter::LowerPATCHABLE_FUNCTION_EXIT(const MachineInstr &MI) {
+ EmitSled(MI, SledKind::FUNCTION_EXIT);
+}
+
+void MipsAsmPrinter::LowerPATCHABLE_TAIL_CALL(const MachineInstr &MI) {
+ EmitSled(MI, SledKind::TAIL_CALL);
+}
+
void MipsAsmPrinter::PrintDebugValueComment(const MachineInstr *MI,
raw_ostream &OS) {
// TODO: implement
Modified: llvm/trunk/lib/Target/Mips/MipsAsmPrinter.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/MipsAsmPrinter.h?rev=295164&r1=295163&r2=295164&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/MipsAsmPrinter.h (original)
+++ llvm/trunk/lib/Target/Mips/MipsAsmPrinter.h Wed Feb 15 04:48:11 2017
@@ -35,7 +35,21 @@ class LLVM_LIBRARY_VISIBILITY MipsAsmPri
void EmitInstrWithMacroNoAT(const MachineInstr *MI);
+ //===------------------------------------------------------------------===//
+ // XRay implementation
+ //===------------------------------------------------------------------===//
+public:
+ // XRay-specific lowering for Mips.
+ void LowerPATCHABLE_FUNCTION_ENTER(const MachineInstr &MI);
+ void LowerPATCHABLE_FUNCTION_EXIT(const MachineInstr &MI);
+ void LowerPATCHABLE_TAIL_CALL(const MachineInstr &MI);
+ // Helper function that emits the XRay sleds we've collected for a particular
+ // function.
+ void EmitXRayTable();
+
private:
+ void EmitSled(const MachineInstr &MI, SledKind Kind);
+
// tblgen'erated function.
bool emitPseudoExpansionLowering(MCStreamer &OutStreamer,
const MachineInstr *MI);
Modified: llvm/trunk/lib/Target/Mips/MipsSubtarget.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/MipsSubtarget.h?rev=295164&r1=295163&r2=295164&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/MipsSubtarget.h (original)
+++ llvm/trunk/lib/Target/Mips/MipsSubtarget.h Wed Feb 15 04:48:11 2017
@@ -236,6 +236,7 @@ public:
return (HasSym32 && isABI_N64()) || isABI_N32() || isABI_O32();
}
bool isSingleFloat() const { return IsSingleFloat; }
+ bool isTargetELF() const { return TargetTriple.isOSBinFormatELF(); }
bool hasVFPU() const { return HasVFPU; }
bool inMips16Mode() const { return InMips16Mode; }
bool inMips16ModeDefault() const {
@@ -277,6 +278,8 @@ public:
bool isTargetNaCl() const { return TargetTriple.isOSNaCl(); }
+ bool isXRaySupported() const override { return true; }
+
// for now constant islands are on for the whole compilation unit but we only
// really use them if in addition we are in mips16 mode
static bool useConstantIslands();
Added: llvm/trunk/test/CodeGen/Mips/xray-mips-attribute-instrumentation.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/Mips/xray-mips-attribute-instrumentation.ll?rev=295164&view=auto
==============================================================================
--- llvm/trunk/test/CodeGen/Mips/xray-mips-attribute-instrumentation.ll (added)
+++ llvm/trunk/test/CodeGen/Mips/xray-mips-attribute-instrumentation.ll Wed Feb 15 04:48:11 2017
@@ -0,0 +1,147 @@
+; RUN: llc -filetype=asm -o - -mtriple=mips-unknown-linux-gnu < %s | FileCheck --check-prefix=CHECK --check-prefix=CHECK-MIPS32 %s
+; RUN: llc -filetype=asm -o - -mtriple=mipsel-unknown-linux-gnu < %s | FileCheck --check-prefix=CHECK --check-prefix=CHECK-MIPS32 %s
+; RUN: llc -filetype=asm -o - -mtriple=mips64-unknown-linux-gnu < %s | FileCheck --check-prefix=CHECK --check-prefix=CHECK-MIPS64 %s
+; RUN: llc -filetype=asm -o - -mtriple=mips64el-unknown-linux-gnu < %s | FileCheck --check-prefix=CHECK --check-prefix=CHECK-MIPS64 %s
+
+define i32 @foo() nounwind noinline uwtable "function-instrument"="xray-always" {
+; CHECK: .p2align 2
+; CHECK-MIPS64-LABEL: .Lxray_sled_0:
+; CHECK-MIPS32-LABEL: $xray_sled_0:
+; CHECK-MIPS64: b .Ltmp0
+; CHECK-MIPS32: b $tmp0
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64-LABEL: .Ltmp0:
+; CHECK-MIPS32-LABEL: $tmp0:
+; CHECK-MIPS32: addiu $25, $25, 52
+ ret i32 0
+; CHECK: .p2align 2
+; CHECK-MIPS64-LABEL: .Lxray_sled_1:
+; CHECK-MIPS32-LABEL: $xray_sled_1:
+; CHECK-MIPS64: b .Ltmp1
+; CHECK-MIPS32: b $tmp1
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64-LABEL: .Ltmp1:
+; CHECK-MIPS32-LABEL: $tmp1:
+; CHECK-MIPS32: addiu $25, $25, 52
+}
+; CHECK: .section xray_instr_map,{{.*}}
+; CHECK-MIPS64: .8byte .Lxray_sled_0
+; CHECK-MIPS64: .8byte .Lxray_sled_1
+; CHECK-MIPS32: .4byte ($xray_sled_0)
+; CHECK-MIPS32: .4byte ($xray_sled_1)
+
+; We test multiple returns in a single function to make sure we're getting all
+; of them with XRay instrumentation.
+define i32 @bar(i32 %i) nounwind noinline uwtable "function-instrument"="xray-always" {
+; CHECK: .p2align 2
+; CHECK-MIPS64-LABEL: .Lxray_sled_2:
+; CHECK-MIPS32-LABEL: $xray_sled_2:
+; CHECK-MIPS64: b .Ltmp2
+; CHECK-MIPS32: b $tmp2
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64-LABEL: .Ltmp2:
+; CHECK-MIPS32-LABEL: $tmp2:
+; CHECK-MIPS32: addiu $25, $25, 52
+Test:
+ %cond = icmp eq i32 %i, 0
+ br i1 %cond, label %IsEqual, label %NotEqual
+IsEqual:
+ ret i32 0
+; CHECK: .p2align 2
+; CHECK-MIPS64-LABEL: .Lxray_sled_3:
+; CHECK-MIPS32-LABEL: $xray_sled_3:
+; CHECK-MIPS64: b .Ltmp3
+; CHECK-MIPS32: b $tmp3
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64-LABEL: .Ltmp3:
+; CHECK-MIPS32-LABEL: $tmp3:
+; CHECK-MIPS32: addiu $25, $25, 52
+NotEqual:
+ ret i32 1
+; CHECK: .p2align 2
+; CHECK-MIPS64-LABEL: .Lxray_sled_4:
+; CHECK-MIPS32-LABEL: $xray_sled_4:
+; CHECK-MIPS64: b .Ltmp4
+; CHECK-MIPS32: b $tmp4
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-NEXT: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64: nop
+; CHECK-MIPS64-LABEL: .Ltmp4:
+; CHECK-MIPS32-LABEL: $tmp4:
+; CHECK-MIPS32: addiu $25, $25, 52
+}
+; CHECK: .section xray_instr_map,{{.*}}
+; CHECK-MIPS64: .8byte .Lxray_sled_2
+; CHECK-MIPS64: .8byte .Lxray_sled_3
+; CHECK-MIPS64: .8byte .Lxray_sled_4
+; CHECK-MIPS32: .4byte ($xray_sled_2)
+; CHECK-MIPS32: .4byte ($xray_sled_3)
+; CHECK-MIPS32: .4byte ($xray_sled_4)
Added: llvm/trunk/test/CodeGen/Mips/xray-section-group.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/Mips/xray-section-group.ll?rev=295164&view=auto
==============================================================================
--- llvm/trunk/test/CodeGen/Mips/xray-section-group.ll (added)
+++ llvm/trunk/test/CodeGen/Mips/xray-section-group.ll Wed Feb 15 04:48:11 2017
@@ -0,0 +1,31 @@
+; RUN: llc -filetype=asm -o - -mtriple=mips-unknown-linux-gnu -function-sections < %s | FileCheck %s
+; RUN: llc -filetype=asm -o - -mtriple=mipsel-unknown-linux-gnu -function-sections < %s | FileCheck %s
+; RUN: llc -filetype=obj -o %t -mtriple=mips-unknown-linux-gnu -function-sections < %s
+; RUN: llvm-readobj -sections %t | FileCheck %s --check-prefix=CHECK-OBJ
+; RUN: llc -filetype=obj -o %t -mtriple=mipsel-unknown-linux-gnu -function-sections < %s
+; RUN: llvm-readobj -sections %t | FileCheck %s --check-prefix=CHECK-OBJ
+; RUN: llc -filetype=asm -o - -mtriple=mips64-unknown-linux-gnu -function-sections < %s | FileCheck %s
+; RUN: llc -filetype=asm -o - -mtriple=mips64el-unknown-linux-gnu -function-sections < %s | FileCheck %s
+; RUN: llc -filetype=obj -o %t -mtriple=mips64-unknown-linux-gnu -function-sections < %s
+; RUN: llvm-readobj -sections %t | FileCheck %s --check-prefix=CHECK-OBJ
+; RUN: llc -filetype=obj -o %t -mtriple=mips64el-unknown-linux-gnu -function-sections < %s
+; RUN: llvm-readobj -sections %t | FileCheck %s --check-prefix=CHECK-OBJ
+
+define i32 @foo() nounwind noinline uwtable "function-instrument"="xray-always" {
+; CHECK: .section .text.foo,"ax", at progbits
+ ret i32 0
+; CHECK: .section xray_instr_map,"a", at progbits
+}
+
+; CHECK-OBJ: Section {
+; CHECK-OBJ: Name: xray_instr_map
+
+$bar = comdat any
+define i32 @bar() nounwind noinline uwtable "function-instrument"="xray-always" comdat($bar) {
+; CHECK: .section .text.bar,"axG", at progbits,bar,comdat
+ ret i32 1
+; CHECK: .section xray_instr_map,"aG", at progbits,bar,comdat
+}
+
+; CHECK-OBJ: Section {
+; CHECK-OBJ: Name: xray_instr_map
More information about the llvm-commits
mailing list