diff --git a/include/llvm/CodeGen/CommandFlags.inc b/include/llvm/CodeGen/CommandFlags.inc index cb69e9f6140..16b7028ce53 100644 --- a/include/llvm/CodeGen/CommandFlags.inc +++ b/include/llvm/CodeGen/CommandFlags.inc @@ -276,6 +276,11 @@ static cl::opt cl::desc("Emit debug info about parameter's entry values"), cl::init(false)); +static cl::opt + ForceDwarfFrameSection("force-dwarf-frame-section", + cl::desc("Always emit a debug frame section."), + cl::init(false)); + // Common utility function tightly tied to the options listed here. Initializes // a TargetOptions object with CodeGen flags and returns it. static TargetOptions InitTargetOptionsFromCodeGenFlags() { @@ -306,6 +311,7 @@ static TargetOptions InitTargetOptionsFromCodeGenFlags() { Options.EmitStackSizeSection = EnableStackSizeSection; Options.EmitAddrsig = EnableAddrsig; Options.EnableDebugEntryValues = EnableDebugEntryValues; + Options.ForceDwarfFrameSection = ForceDwarfFrameSection; Options.MCOptions = InitMCTargetOptionsFromFlags(); diff --git a/include/llvm/CodeGen/MachineFunction.h b/include/llvm/CodeGen/MachineFunction.h index c67fd27278d..c5a6a6eacf0 100644 --- a/include/llvm/CodeGen/MachineFunction.h +++ b/include/llvm/CodeGen/MachineFunction.h @@ -560,6 +560,9 @@ public: } void setHasWinCFI(bool v) { HasWinCFI = v; } + /// True if this function needs frame moves for debug or exceptions. + bool needsFrameMoves() const; + /// Get the function properties const MachineFunctionProperties &getProperties() const { return Properties; } MachineFunctionProperties &getProperties() { return Properties; } diff --git a/include/llvm/Target/TargetOptions.h b/include/llvm/Target/TargetOptions.h index 8cc2a601087..c395e5bcecf 100644 --- a/include/llvm/Target/TargetOptions.h +++ b/include/llvm/Target/TargetOptions.h @@ -119,7 +119,7 @@ namespace llvm { ExplicitEmulatedTLS(false), EnableIPRA(false), EmitStackSizeSection(false), EnableMachineOutliner(false), SupportsDefaultOutlining(false), EmitAddrsig(false), - EnableDebugEntryValues(false) {} + EnableDebugEntryValues(false), ForceDwarfFrameSection(false) {} /// PrintMachineCode - This flag is enabled when the -print-machineinstrs /// option is specified on the command line, and should enable debugging @@ -256,6 +256,9 @@ namespace llvm { /// Emit debug info about parameter's entry values. unsigned EnableDebugEntryValues : 1; + /// Emit DWARF debug frame section. + unsigned ForceDwarfFrameSection : 1; + /// FloatABIType - This setting is set by -float-abi=xxx option is specfied /// on the command line. This setting may either be Default, Soft, or Hard. /// Default selects the target's default behavior. Soft selects the ABI for diff --git a/lib/CodeGen/AsmPrinter/AsmPrinter.cpp b/lib/CodeGen/AsmPrinter/AsmPrinter.cpp index 6bff8de4a9c..4cd30319aab 100644 --- a/lib/CodeGen/AsmPrinter/AsmPrinter.cpp +++ b/lib/CodeGen/AsmPrinter/AsmPrinter.cpp @@ -935,7 +935,7 @@ AsmPrinter::CFIMoveType AsmPrinter::needsCFIMoves() const { MF->getFunction().needsUnwindTableEntry()) return CFI_M_EH; - if (MMI->hasDebugInfo()) + if (MMI->hasDebugInfo() || MF->getTarget().Options.ForceDwarfFrameSection) return CFI_M_Debug; return CFI_M_None; diff --git a/lib/CodeGen/AsmPrinter/DwarfCFIException.cpp b/lib/CodeGen/AsmPrinter/DwarfCFIException.cpp index 207a7284daf..facbf22946e 100644 --- a/lib/CodeGen/AsmPrinter/DwarfCFIException.cpp +++ b/lib/CodeGen/AsmPrinter/DwarfCFIException.cpp @@ -29,6 +29,7 @@ #include "llvm/Support/ErrorHandling.h" #include "llvm/Support/FormattedStream.h" #include "llvm/Target/TargetLoweringObjectFile.h" +#include "llvm/Target/TargetMachine.h" #include "llvm/Target/TargetOptions.h" using namespace llvm; @@ -133,6 +134,8 @@ void DwarfCFIException::beginFragment(const MachineBasicBlock *MBB, if (!hasEmittedCFISections) { if (Asm->needsOnlyDebugCFIMoves()) Asm->OutStreamer->EmitCFISections(false, true); + else if (Asm->TM.Options.ForceDwarfFrameSection) + Asm->OutStreamer->EmitCFISections(true, true); hasEmittedCFISections = true; } diff --git a/lib/CodeGen/CFIInstrInserter.cpp b/lib/CodeGen/CFIInstrInserter.cpp index 1a4d54231cf..3129894c0ac 100644 --- a/lib/CodeGen/CFIInstrInserter.cpp +++ b/lib/CodeGen/CFIInstrInserter.cpp @@ -48,8 +48,7 @@ class CFIInstrInserter : public MachineFunctionPass { } bool runOnMachineFunction(MachineFunction &MF) override { - if (!MF.getMMI().hasDebugInfo() && - !MF.getFunction().needsUnwindTableEntry()) + if (!MF.needsFrameMoves()) return false; MBBVector.resize(MF.getNumBlockIDs()); diff --git a/lib/CodeGen/MachineFunction.cpp b/lib/CodeGen/MachineFunction.cpp index d75e77d4613..115aad3880f 100644 --- a/lib/CodeGen/MachineFunction.cpp +++ b/lib/CodeGen/MachineFunction.cpp @@ -520,6 +520,13 @@ void MachineFunction::print(raw_ostream &OS, const SlotIndexes *Indexes) const { OS << "\n# End machine code for function " << getName() << ".\n\n"; } +/// True if this function needs frame moves for debug or exceptions. +bool MachineFunction::needsFrameMoves() const { + return getMMI().hasDebugInfo() || + getTarget().Options.ForceDwarfFrameSection || + F.needsUnwindTableEntry(); +} + namespace llvm { template<> diff --git a/lib/Target/AArch64/AArch64FrameLowering.cpp b/lib/Target/AArch64/AArch64FrameLowering.cpp index 042d8fdcc51..bbd7c51fde9 100644 --- a/lib/Target/AArch64/AArch64FrameLowering.cpp +++ b/lib/Target/AArch64/AArch64FrameLowering.cpp @@ -844,8 +844,8 @@ void AArch64FrameLowering::emitPrologue(MachineFunction &MF, const TargetInstrInfo *TII = Subtarget.getInstrInfo(); MachineModuleInfo &MMI = MF.getMMI(); AArch64FunctionInfo *AFI = MF.getInfo(); - bool needsFrameMoves = (MMI.hasDebugInfo() || F.needsUnwindTableEntry()) && - !MF.getTarget().getMCAsmInfo()->usesWindowsCFI(); + bool needsFrameMoves = + MF.needsFrameMoves() && !MF.getTarget().getMCAsmInfo()->usesWindowsCFI(); bool HasFP = hasFP(MF); bool NeedsWinCFI = needsWinCFI(MF); bool HasWinCFI = false; diff --git a/lib/Target/ARC/ARCRegisterInfo.cpp b/lib/Target/ARC/ARCRegisterInfo.cpp index a7f89b385ff..490f0893009 100644 --- a/lib/Target/ARC/ARCRegisterInfo.cpp +++ b/lib/Target/ARC/ARCRegisterInfo.cpp @@ -128,7 +128,7 @@ static void ReplaceFrameIndex(MachineBasicBlock::iterator II, ARCRegisterInfo::ARCRegisterInfo() : ARCGenRegisterInfo(ARC::BLINK) {} bool ARCRegisterInfo::needsFrameMoves(const MachineFunction &MF) { - return MF.getMMI().hasDebugInfo() || MF.getFunction().needsUnwindTableEntry(); + return MF.needsFrameMoves(); } const MCPhysReg * diff --git a/lib/Target/Hexagon/HexagonFrameLowering.cpp b/lib/Target/Hexagon/HexagonFrameLowering.cpp index bfa3372d7fa..dc114d07736 100644 --- a/lib/Target/Hexagon/HexagonFrameLowering.cpp +++ b/lib/Target/Hexagon/HexagonFrameLowering.cpp @@ -223,8 +223,7 @@ namespace { bool HexagonCallFrameInformation::runOnMachineFunction(MachineFunction &MF) { auto &HFI = *MF.getSubtarget().getFrameLowering(); - bool NeedCFI = MF.getMMI().hasDebugInfo() || - MF.getFunction().needsUnwindTableEntry(); + bool NeedCFI = MF.needsFrameMoves(); if (!NeedCFI) return false; diff --git a/lib/Target/PowerPC/PPCFrameLowering.cpp b/lib/Target/PowerPC/PPCFrameLowering.cpp index 06a4d183e78..b62c2fea04d 100644 --- a/lib/Target/PowerPC/PPCFrameLowering.cpp +++ b/lib/Target/PowerPC/PPCFrameLowering.cpp @@ -782,8 +782,7 @@ void PPCFrameLowering::emitPrologue(MachineFunction &MF, MachineModuleInfo &MMI = MF.getMMI(); const MCRegisterInfo *MRI = MMI.getContext().getRegisterInfo(); DebugLoc dl; - bool needsCFI = MMI.hasDebugInfo() || - MF.getFunction().needsUnwindTableEntry(); + bool needsCFI = MF.needsFrameMoves(); // Get processor type. bool isPPC64 = Subtarget.isPPC64(); diff --git a/lib/Target/X86/X86FrameLowering.cpp b/lib/Target/X86/X86FrameLowering.cpp index 1b469a814ad..0d4db14a7f1 100644 --- a/lib/Target/X86/X86FrameLowering.cpp +++ b/lib/Target/X86/X86FrameLowering.cpp @@ -993,8 +993,7 @@ void X86FrameLowering::emitPrologue(MachineFunction &MF, bool NeedsWinFPO = !IsFunclet && STI.isTargetWin32() && MMI.getModule()->getCodeViewFlag(); bool NeedsWinCFI = NeedsWin64CFI || NeedsWinFPO; - bool NeedsDwarfCFI = - !IsWin64Prologue && (MMI.hasDebugInfo() || Fn.needsUnwindTableEntry()); + bool NeedsDwarfCFI = !IsWin64Prologue && MF.needsFrameMoves(); Register FramePtr = TRI->getFrameRegister(MF); const Register MachineFramePtr = STI.isTarget64BitILP32() @@ -1614,10 +1613,9 @@ void X86FrameLowering::emitEpilogue(MachineFunction &MF, bool HasFP = hasFP(MF); uint64_t NumBytes = 0; - bool NeedsDwarfCFI = - (!MF.getTarget().getTargetTriple().isOSDarwin() && - !MF.getTarget().getTargetTriple().isOSWindows()) && - (MF.getMMI().hasDebugInfo() || MF.getFunction().needsUnwindTableEntry()); + bool NeedsDwarfCFI = (!MF.getTarget().getTargetTriple().isOSDarwin() && + !MF.getTarget().getTargetTriple().isOSWindows()) && + MF.needsFrameMoves(); if (IsFunclet) { assert(HasFP && "EH funclets without FP not yet implemented"); @@ -2812,11 +2810,9 @@ eliminateCallFramePseudoInstr(MachineFunction &MF, MachineBasicBlock &MBB, unsigned StackAlign = getStackAlignment(); Amount = alignTo(Amount, StackAlign); - MachineModuleInfo &MMI = MF.getMMI(); const Function &F = MF.getFunction(); bool WindowsCFI = MF.getTarget().getMCAsmInfo()->usesWindowsCFI(); - bool DwarfCFI = !WindowsCFI && - (MMI.hasDebugInfo() || F.needsUnwindTableEntry()); + bool DwarfCFI = !WindowsCFI && MF.needsFrameMoves(); // If we have any exception handlers in this function, and we adjust // the SP before calls, we may need to indicate this to the unwinder diff --git a/lib/Target/X86/X86InstrInfo.cpp b/lib/Target/X86/X86InstrInfo.cpp index 8e491c539c3..8fdcf1eec7c 100644 --- a/lib/Target/X86/X86InstrInfo.cpp +++ b/lib/Target/X86/X86InstrInfo.cpp @@ -3963,9 +3963,7 @@ static bool ExpandMOVImmSExti8(MachineInstrBuilder &MIB, MachineFunction &MF = *MBB.getParent(); const X86FrameLowering *TFL = Subtarget.getFrameLowering(); bool IsWin64Prologue = MF.getTarget().getMCAsmInfo()->usesWindowsCFI(); - bool NeedsDwarfCFI = - !IsWin64Prologue && - (MF.getMMI().hasDebugInfo() || MF.getFunction().needsUnwindTableEntry()); + bool NeedsDwarfCFI = !IsWin64Prologue && MF.needsFrameMoves(); bool EmitCFI = !TFL->hasFP(MF) && NeedsDwarfCFI; if (EmitCFI) { TFL->BuildCFI(MBB, I, DL, diff --git a/lib/Target/XCore/XCoreRegisterInfo.cpp b/lib/Target/XCore/XCoreRegisterInfo.cpp index 86ec7f82d4d..56fed26ebd7 100644 --- a/lib/Target/XCore/XCoreRegisterInfo.cpp +++ b/lib/Target/XCore/XCoreRegisterInfo.cpp @@ -203,7 +203,7 @@ static void InsertSPConstInst(MachineBasicBlock::iterator II, } bool XCoreRegisterInfo::needsFrameMoves(const MachineFunction &MF) { - return MF.getMMI().hasDebugInfo() || MF.getFunction().needsUnwindTableEntry(); + return MF.needsFrameMoves(); } const MCPhysReg * diff --git a/test/CodeGen/ARM/dwarf-frame.ll b/test/CodeGen/ARM/dwarf-frame.ll new file mode 100644 index 00000000000..a15c9c50f5a --- /dev/null +++ b/test/CodeGen/ARM/dwarf-frame.ll @@ -0,0 +1,38 @@ +; RUN: llc -mtriple armv7-unknown -frame-pointer=all -filetype=asm -o - %s | FileCheck %s --check-prefix=CHECK-NO-CFI +; RUN: llc -mtriple armv7-unknown -frame-pointer=all -filetype=asm -force-dwarf-frame-section -o - %s | FileCheck %s --check-prefix=CHECK-ALWAYS-CFI + +declare void @dummy_use(i32*, i32) + +define void @test_basic() #0 { + %mem = alloca i32, i32 10 + call void @dummy_use (i32* %mem, i32 10) + ret void +} + +; CHECK-NO-CFI-LABEL: test_basic: +; CHECK-NO-CFI: .fnstart +; CHECK-NO-CFI-NOT: .cfi_sections .debug_frame +; CHECK-NO-CFI-NOT: .cfi_startproc +; CHECK-NO-CFI: @ %bb.0: +; CHECK-NO-CFI: push {r11, lr} +; CHECK-NO-CFI-NOT: .cfi_def_cfa_offset 8 +; CHECK-NO-CFI-NOT: .cfi_offset lr, -4 +; CHECK-NO-CFI-NOT: .cfi_offset r11, -8 +; CHECK-NO-CFI: mov r11, sp +; CHECK-NO-CFI-NOT: .cfi_def_cfa_register r11 +; CHECK-NO-CFI-NOT: .cfi_endproc +; CHECK-NO-CFI: .fnend + +; CHECK-ALWAYS-CFI-LABEL: test_basic: +; CHECK-ALWAYS-CFI: .fnstart +; CHECK-ALWAYS-CFI: .cfi_sections .debug_frame +; CHECK-ALWAYS-CFI: .cfi_startproc +; CHECK-ALWAYS-CFI: @ %bb.0: +; CHECK-ALWAYS-CFI: push {r11, lr} +; CHECK-ALWAYS-CFI: .cfi_def_cfa_offset 8 +; CHECK-ALWAYS-CFI: .cfi_offset lr, -4 +; CHECK-ALWAYS-CFI: .cfi_offset r11, -8 +; CHECK-ALWAYS-CFI: mov r11, sp +; CHECK-ALWAYS-CFI: .cfi_def_cfa_register r11 +; CHECK-ALWAYS-CFI: .cfi_endproc +; CHECK-ALWAYS-CFI: .fnend