diff --git a/llvm/lib/MC/MCObjectFileInfo.cpp b/llvm/lib/MC/MCObjectFileInfo.cpp index 5afe00eee2242..f2917179e1fc1 100644 --- a/llvm/lib/MC/MCObjectFileInfo.cpp +++ b/llvm/lib/MC/MCObjectFileInfo.cpp @@ -10,6 +10,7 @@ #include "llvm/ADT/StringExtras.h" #include "llvm/BinaryFormat/COFF.h" #include "llvm/BinaryFormat/ELF.h" +#include "llvm/BinaryFormat/GOFF.h" #include "llvm/BinaryFormat/SFrame.h" #include "llvm/BinaryFormat/Wasm.h" #include "llvm/MC/MCAsmInfo.h" @@ -24,6 +25,7 @@ #include "llvm/MC/MCSectionSPIRV.h" #include "llvm/MC/MCSectionWasm.h" #include "llvm/MC/MCSectionXCOFF.h" +#include "llvm/MC/MCSymbolGOFF.h" #include "llvm/TargetParser/Triple.h" using namespace llvm; @@ -608,6 +610,65 @@ void MCObjectFileInfo::initGOFFMCObjectFileInfo(const Triple &T) { GOFF::ESD_LB_NoLoad, GOFF::ESD_RQ_0, GOFF::ESD_ALIGN_Doubleword, 0}, RootSDSection); + + // Debug Info Sections. The ED name is the same used by the XL compiler. + auto InitDebugSection = [this, + RootSDSection](StringRef EDName, + StringRef LDName) -> MCSectionGOFF * { + MCSectionGOFF *ED = Ctx->getGOFFSection( + SectionKind::getMetadata(), EDName, + GOFF::EDAttr{false, GOFF::ESD_RMODE_64, GOFF::ESD_NS_Parts, + GOFF::ESD_TS_ByteOriented, GOFF::ESD_BA_Concatenate, + GOFF::ESD_LB_NoLoad, GOFF::ESD_RQ_0, + GOFF::ESD_ALIGN_Doubleword, 0}, + RootSDSection); + // At least for llc, this function is called twice! (See function + // compileModule() in llc.cpp). Since the context is not cleared, the + // already allocated section is returned above. We only add the begin symbol + // if it is not yet set to avoid an assertion. + MCSymbolGOFF *LD = static_cast(ED->getBeginSymbol()); + if (!LD) { + LD = static_cast(getContext().getOrCreateSymbol(LDName)); + LD->setCodeData(GOFF::ESD_EXE_DATA); + LD->setWeak(false); + LD->setLinkage(GOFF::ESD_LT_XPLink); + LD->setExternal(false); + ED->setBeginSymbol(LD); + } else + assert(LD->getName() == LDName && "Wrong label name"); + return ED; + }; + DwarfAbbrevSection = InitDebugSection("D_ABREV", ".debug_abbrev"); + DwarfInfoSection = InitDebugSection("D_INFO", ".debug_info"); + DwarfLineSection = InitDebugSection("D_LINE", ".debug_line"); + DwarfFrameSection = InitDebugSection("D_FRAME", ".debug_frame"); + DwarfPubNamesSection = InitDebugSection("D_PBNMS", ".debug_pubnames"); + DwarfPubTypesSection = InitDebugSection("D_PTYPES", ".debug_pubtypes"); + DwarfStrSection = InitDebugSection("D_STR", ".debug_str"); + DwarfLocSection = InitDebugSection("D_LOC", ".debug_loc"); + DwarfARangesSection = InitDebugSection("D_ARNGE", ".debug_aranges"); + DwarfRangesSection = InitDebugSection("D_RNGES", ".debug_ranges"); + DwarfMacinfoSection = InitDebugSection("D_MACIN", ".debug_macinfo"); + + // DWARF 5 sections. + DwarfDebugNamesSection = InitDebugSection("D_NAMES", ".debug_names"); + DwarfStrOffSection = InitDebugSection("D_STROFFS", ".debug_str_offsets"); + DwarfAddrSection = InitDebugSection("D_ADDR", ".debug_addr"); + DwarfRnglistsSection = InitDebugSection("D_RNGLISTS", ".debug_rnglists"); + DwarfLoclistsSection = InitDebugSection("D_LOCLISTS", ".debug_loclists"); + DwarfLineStrSection = InitDebugSection("D_LINESTR", ".debug_line_str"); + + // Special GNU sections. + DwarfGnuPubNamesSection = InitDebugSection("D_GPBNMS", ".debug_gnu_pubnames"); + DwarfGnuPubTypesSection = + InitDebugSection("D_GPTYPES", ".debug_gnu_pubtypes"); + + // Accelerator Tables. + DwarfAccelNamesSection = InitDebugSection("D_APPLNMS", ".apple_names"); + DwarfAccelNamespaceSection = + InitDebugSection("D_APPLNMSP", ".apple_namespaces"); + DwarfAccelTypesSection = InitDebugSection("D_APPLTYPS", ".apple_types"); + DwarfAccelObjCSection = InitDebugSection("D_APPLOBJC", ".apple_objc"); } void MCObjectFileInfo::initCOFFMCObjectFileInfo(const Triple &T) { diff --git a/llvm/test/CodeGen/SystemZ/zos-dwarf.ll b/llvm/test/CodeGen/SystemZ/zos-dwarf.ll new file mode 100644 index 0000000000000..919602c799f7a --- /dev/null +++ b/llvm/test/CodeGen/SystemZ/zos-dwarf.ll @@ -0,0 +1,31 @@ +; RUN: llc < %s -mtriple=s390x-ibm-zos -emit-gnuas-syntax-on-zos=0 | FileCheck %s + +@fortytwo = hidden global i32 42, align 4, !dbg !0 + +define hidden signext i32 @getFortyTwo() !dbg !8 { +entry: + %0 = load i32, ptr @fortytwo, align 4, !dbg !11 + ret i32 %0, !dbg !12 +} + +!llvm.dbg.cu = !{!2} +!llvm.module.flags = !{!6, !7} + +!0 = !DIGlobalVariableExpression(var: !1, expr: !DIExpression()) +!1 = distinct !DIGlobalVariable(name: "fortytwo", scope: !2, file: !3, line: 2, type: !5, isLocal: false, isDefinition: true) +!2 = distinct !DICompileUnit(language: DW_LANG_C11, file: !3, producer: "clang version 22.0.0git", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug, globals: !4, splitDebugInlining: false, nameTableKind: None) +!3 = !DIFile(filename: "fortytwo.c", directory: "") +!4 = !{!0} +!5 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed) +!6 = !{i32 7, !"Dwarf Version", i32 4} +!7 = !{i32 2, !"Debug Info Version", i32 3} +!8 = distinct !DISubprogram(name: "getFortyTwo", scope: !3, file: !3, line: 4, type: !9, scopeLine: 4, spFlags: DISPFlagDefinition, unit: !2) +!9 = !DISubroutineType(types: !10) +!10 = !{!5} +!11 = !DILocation(line: 4, column: 28, scope: !8) +!12 = !DILocation(line: 4, column: 21, scope: !8) + +; Check the emitted section definition +; CHECK: D_ABREV CATTR ALIGN(3),FILL(0),NOLOAD,RMODE(64) +; CHECK: D_INFO CATTR ALIGN(3),FILL(0),NOLOAD,RMODE(64) +; CHECK: D_STR CATTR ALIGN(3),FILL(0),NOLOAD,RMODE(64)