Index: llvm/lib/Target/SystemZ/SystemZAsmPrinter.cpp =================================================================== --- llvm/lib/Target/SystemZ/SystemZAsmPrinter.cpp +++ llvm/lib/Target/SystemZ/SystemZAsmPrinter.cpp @@ -552,18 +552,27 @@ void SystemZAsmPrinter::LowerFENTRY_CALL(const MachineInstr &MI, SystemZMCInstLower &Lower) { + bool RecordMCount = MF->getFunction().hasFnAttribute("mrecord-mcount"); + if (RecordMCount) + OutStreamer->EmitRawText("1:\n"); + MCContext &Ctx = MF->getContext(); if (MF->getFunction().getFnAttribute("mnop-mcount") .getValueAsString() == "true") { EmitNop(Ctx, *OutStreamer, 6, getSubtargetInfo()); - return; + } else { + MCSymbol *fentry = Ctx.getOrCreateSymbol("__fentry__"); + const MCSymbolRefExpr *Op = + MCSymbolRefExpr::create(fentry, MCSymbolRefExpr::VK_PLT, Ctx); + OutStreamer->EmitInstruction(MCInstBuilder(SystemZ::BRASL) + .addReg(SystemZ::R0D).addExpr(Op), getSubtargetInfo()); } - MCSymbol *fentry = Ctx.getOrCreateSymbol("__fentry__"); - const MCSymbolRefExpr *Op = - MCSymbolRefExpr::create(fentry, MCSymbolRefExpr::VK_PLT, Ctx); - OutStreamer->EmitInstruction(MCInstBuilder(SystemZ::BRASL) - .addReg(SystemZ::R0D).addExpr(Op), getSubtargetInfo()); + if (RecordMCount) { + OutStreamer->EmitRawText("\t.section __mcount_loc, \"a\",@progbits\n"); + OutStreamer->EmitRawText("\t.quad 1b\n"); + OutStreamer->EmitRawText("\t.previous"); + } } void SystemZAsmPrinter::LowerSTACKMAP(const MachineInstr &MI) { Index: llvm/lib/Target/SystemZ/SystemZISelDAGToDAG.cpp =================================================================== --- llvm/lib/Target/SystemZ/SystemZISelDAGToDAG.cpp +++ llvm/lib/Target/SystemZ/SystemZISelDAGToDAG.cpp @@ -350,6 +350,9 @@ if (F.getFnAttribute("mnop-mcount").getValueAsString() == "true" && F.getFnAttribute("fentry-call").getValueAsString() != "true") report_fatal_error("mnop-mcount only supported with fentry-call"); + if (F.hasFnAttribute("mrecord-mcount") && + F.getFnAttribute("fentry-call").getValueAsString() != "true") + report_fatal_error("mrecord-mcount only supported with fentry-call"); Subtarget = &MF.getSubtarget(); return SelectionDAGISel::runOnMachineFunction(MF); Index: llvm/test/CodeGen/SystemZ/mrecord-mcount-01.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/SystemZ/mrecord-mcount-01.ll @@ -0,0 +1,32 @@ +; RUN: llc %s -mtriple=s390x-linux-gnu -mcpu=z10 -o - -verify-machineinstrs \ +; RUN: | FileCheck %s + +define void @test1() #0 { +entry: + ret void + +; CHECK-LABEL: @test1 +; CHECK: 1: +; CHECK: brasl %r0, __fentry__ +; CHECK: .section __mcount_loc, "a",@progbits +; CHECK: .quad 1b +; CHECK: .previous +; CHECK: br %r14 +} + +define void @test2() #1 { +entry: + ret void + +; CHECK-LABEL: @test2 +; CHECK: 1: +; CHECK: brcl 0, .Ltmp0 +; CHECK: .section __mcount_loc, "a",@progbits +; CHECK: .quad 1b +; CHECK: .previous +; CHECK: br %r14 +} + +attributes #0 = { "fentry-call"="true" "mrecord-mcount" } +attributes #1 = { "fentry-call"="true" "mnop-mcount"="true" "mrecord-mcount" } + Index: llvm/test/CodeGen/SystemZ/mrecord-mcount-02.ll =================================================================== --- /dev/null +++ llvm/test/CodeGen/SystemZ/mrecord-mcount-02.ll @@ -0,0 +1,11 @@ +; RUN: not llc %s -mtriple=s390x-linux-gnu -o - 2>&1 | FileCheck %s +; +; CHECK: LLVM ERROR: mrecord-mcount only supported with fentry-call + +define void @test1() #0 { +entry: + ret void +} + +attributes #0 = { "instrument-function-entry-inlined"="mcount" "mrecord-mcount" } +