From: Paul Robinson Date: Tue, 11 Aug 2015 21:36:45 +0000 (+0000) Subject: Make DW_AT_[MIPS_]linkage_name optional, and off by default for SCE. X-Git-Url: http://demsky.eecs.uci.edu/git/?a=commitdiff_plain;h=bbf32bd275fb1ab0a18824924437de5966f73832;p=oota-llvm.git Make DW_AT_[MIPS_]linkage_name optional, and off by default for SCE. Mangled "linkage" names can be huge, and if the debugger (or other tools) have no use for them, the size savings can be very impressive (on the order of 40%). Add one test for controlling behavior, and modify a number of tests to either stop using linkage names, or make llc emit them (so these tests will still run when the default triple is for PS4). Differential Revision: http://reviews.llvm.org/D11374 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@244678 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/CodeGen/AsmPrinter/DwarfDebug.cpp b/lib/CodeGen/AsmPrinter/DwarfDebug.cpp index e09a90fbd0b..4a673d49ced 100644 --- a/lib/CodeGen/AsmPrinter/DwarfDebug.cpp +++ b/lib/CodeGen/AsmPrinter/DwarfDebug.cpp @@ -116,6 +116,14 @@ DwarfPubSections("generate-dwarf-pub-sections", cl::Hidden, clEnumVal(Disable, "Disabled"), clEnumValEnd), cl::init(Default)); +static cl::opt +DwarfLinkageNames("dwarf-linkage-names", cl::Hidden, + cl::desc("Emit DWARF linkage-name attributes."), + cl::values(clEnumVal(Default, "Default for platform"), + clEnumVal(Enable, "Enabled"), + clEnumVal(Disable, "Disabled"), clEnumValEnd), + cl::init(Default)); + static const char *const DWARFGroupName = "DWARF Emission"; static const char *const DbgTimerName = "DWARF Debug Writer"; @@ -250,6 +258,12 @@ DwarfDebug::DwarfDebug(AsmPrinter *A, Module *M) else HasDwarfPubSections = DwarfPubSections == Enable; + // SCE does not use linkage names. + if (DwarfLinkageNames == Default) + UseLinkageNames = !tuneForSCE(); + else + UseLinkageNames = DwarfLinkageNames == Enable; + unsigned DwarfVersionNumber = Asm->TM.Options.MCOptions.DwarfVersion; DwarfVersion = DwarfVersionNumber ? DwarfVersionNumber : MMI->getModule()->getDwarfVersion(); diff --git a/lib/CodeGen/AsmPrinter/DwarfDebug.h b/lib/CodeGen/AsmPrinter/DwarfDebug.h index d17589cba9e..977f3406441 100644 --- a/lib/CodeGen/AsmPrinter/DwarfDebug.h +++ b/lib/CodeGen/AsmPrinter/DwarfDebug.h @@ -333,6 +333,9 @@ class DwarfDebug : public AsmPrinterHandler { /// Whether to use the GNU TLS opcode (instead of the standard opcode). bool UseGNUTLSOpcode; + /// Whether to emit DW_AT_[MIPS_]linkage_name. + bool UseLinkageNames; + /// Version of dwarf we're emitting. unsigned DwarfVersion; @@ -588,6 +591,9 @@ public: SymSize[Sym] = Size; } + /// Returns whether to emit DW_AT_[MIPS_]linkage_name. + bool useLinkageNames() const { return UseLinkageNames; } + /// Returns whether to use DW_OP_GNU_push_tls_address, instead of the /// standard DW_OP_form_tls_address opcode bool useGNUTLSOpcode() const { return UseGNUTLSOpcode; } diff --git a/lib/CodeGen/AsmPrinter/DwarfUnit.cpp b/lib/CodeGen/AsmPrinter/DwarfUnit.cpp index 72b9fe7fd8f..d5ed0cd0945 100644 --- a/lib/CodeGen/AsmPrinter/DwarfUnit.cpp +++ b/lib/CodeGen/AsmPrinter/DwarfUnit.cpp @@ -667,7 +667,7 @@ void DwarfUnit::addConstantValue(DIE &Die, const APInt &Val, bool Unsigned) { } void DwarfUnit::addLinkageName(DIE &Die, StringRef LinkageName) { - if (!LinkageName.empty()) + if (!LinkageName.empty() && DD->useLinkageNames()) addString(Die, DD->getDwarfVersion() >= 4 ? dwarf::DW_AT_linkage_name : dwarf::DW_AT_MIPS_linkage_name, diff --git a/test/DebugInfo/2010-04-06-NestedFnDbgInfo.ll b/test/DebugInfo/2010-04-06-NestedFnDbgInfo.ll index b22a48f5516..9f78440fd91 100644 --- a/test/DebugInfo/2010-04-06-NestedFnDbgInfo.ll +++ b/test/DebugInfo/2010-04-06-NestedFnDbgInfo.ll @@ -13,7 +13,7 @@ ; CHECK-NOT: DW_TAG ; CHECK: DW_AT_low_pc ; CHECK-NOT: DW_TAG -; CHECK: DW_AT_linkage_name {{.*}} "_ZZN1B2fnEvEN1A3fooEv" +; CHECK: DW_AT_name {{.*}} "foo" ; And just double check that there's no out of line definition that references ; this subprogram. ; CHECK-NOT: DW_AT_specification {{.*}} {[[FOO_INL]]} diff --git a/test/DebugInfo/PR20038.ll b/test/DebugInfo/PR20038.ll index 7560130e6d0..884331d7ea6 100644 --- a/test/DebugInfo/PR20038.ll +++ b/test/DebugInfo/PR20038.ll @@ -3,7 +3,7 @@ ; For some reason, the output when targetting sparc is not quite as expected. ; XFAIL: sparc -; RUN: %llc_dwarf -O0 -filetype=obj < %s | llvm-dwarfdump -debug-dump=info - | FileCheck %s +; RUN: %llc_dwarf -O0 -filetype=obj -dwarf-linkage-names=Enable < %s | llvm-dwarfdump -debug-dump=info - | FileCheck %s ; IR generated from clang -O0 with: ; struct C { diff --git a/test/DebugInfo/X86/dwarf-linkage-names.ll b/test/DebugInfo/X86/dwarf-linkage-names.ll new file mode 100644 index 00000000000..203ad212b46 --- /dev/null +++ b/test/DebugInfo/X86/dwarf-linkage-names.ll @@ -0,0 +1,71 @@ +; DWARF linkage name attributes are optional; verify they are missing for +; PS4 triple or when tuning for SCE. + +; RUN: llc -O0 -mtriple=x86_64-unknown-unknown < %s | FileCheck %s -check-prefix LINKAGE1 +; RUN: llc -O0 -mtriple=x86_64-unknown-unknown < %s | FileCheck %s -check-prefix LINKAGE2 +; RUN: llc -O0 -mtriple=x86_64-scei-ps4 < %s | FileCheck %s -check-prefix NOLINKAGE +; RUN: llc -O0 -mtriple=x86_64-unknown-unknown -debugger-tune=sce < %s | FileCheck %s -check-prefix NOLINKAGE + +; $ clang++ -emit-llvm -S -g dwarf-linkage-names.cpp +; namespace test { +; int global_var; +; int bar() { return global_var; } +;}; + +; With linkage names, we get an attribute for the declaration (first) entry +; for the global variable, and one for the function. + +; This assumes the variable will appear before the function. +; LINKAGE1: .section .debug_info +; LINKAGE1: DW_TAG_variable +; LINKAGE1-NOT: DW_TAG +; LINKAGE1: {{DW_AT_(MIPS_)*linkage_name}} +; LINKAGE1: DW_TAG_subprogram +; LINKAGE1-NOT: DW_TAG +; LINKAGE1: {{DW_AT_(MIPS_)*linkage_name}} +; LINKAGE1: .section + +; Also verify we see the mangled names. We do this as a separate pass to +; avoid depending on the order of .debug_info and .debug_str sections. + +; LINKAGE2-DAG: .asciz "_ZN4test10global_varE" +; LINKAGE2-DAG: .asciz "_ZN4test3barEv" + +; Without linkage names, verify there aren't any linkage-name attributes, +; and no mangled names. + +; NOLINKAGE-NOT: {{DW_AT_(MIPS_)*linkage_name}} +; NOLINKAGE-NOT: .asciz "_ZN4test10global_varE" +; NOLINKAGE-NOT: .asciz "_ZN4test3barEv" + +@_ZN4test10global_varE = global i32 0, align 4 + +; Function Attrs: nounwind uwtable +define i32 @_ZN4test3barEv() #0 { +entry: + %0 = load i32, i32* @_ZN4test10global_varE, align 4, !dbg !14 + ret i32 %0, !dbg !15 +} + +attributes #0 = { nounwind uwtable "disable-tail-calls"="false" "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "stack-protector-buffer-size"="8" "target-cpu"="x86-64" "target-features"="+sse,+sse2" "unsafe-fp-math"="false" "use-soft-float"="false" } + +!llvm.dbg.cu = !{!0} +!llvm.module.flags = !{!11, !12} +!llvm.ident = !{!13} + +!0 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !1, producer: "clang version 3.8.0 (trunk 244662)", isOptimized: false, runtimeVersion: 0, emissionKind: 1, enums: !2, subprograms: !3, globals: !9) +!1 = !DIFile(filename: "dwarf-linkage-names.cpp", directory: "/home/probinson/projects/scratch") +!2 = !{} +!3 = !{!4} +!4 = !DISubprogram(name: "bar", linkageName: "_ZN4test3barEv", scope: !5, file: !1, line: 3, type: !6, isLocal: false, isDefinition: true, scopeLine: 3, flags: DIFlagPrototyped, isOptimized: false, function: i32 ()* @_ZN4test3barEv, variables: !2) +!5 = !DINamespace(name: "test", scope: null, file: !1, line: 1) +!6 = !DISubroutineType(types: !7) +!7 = !{!8} +!8 = !DIBasicType(name: "int", size: 32, align: 32, encoding: DW_ATE_signed) +!9 = !{!10} +!10 = !DIGlobalVariable(name: "global_var", linkageName: "_ZN4test10global_varE", scope: !5, file: !1, line: 2, type: !8, isLocal: false, isDefinition: true, variable: i32* @_ZN4test10global_varE) +!11 = !{i32 2, !"Dwarf Version", i32 4} +!12 = !{i32 2, !"Debug Info Version", i32 3} +!13 = !{!"clang version 3.8.0 (trunk 244662)"} +!14 = !DILocation(line: 3, column: 21, scope: !4) +!15 = !DILocation(line: 3, column: 14, scope: !4) diff --git a/test/DebugInfo/X86/recursive_inlining.ll b/test/DebugInfo/X86/recursive_inlining.ll index 62c04052008..fff5471bb68 100644 --- a/test/DebugInfo/X86/recursive_inlining.ll +++ b/test/DebugInfo/X86/recursive_inlining.ll @@ -38,16 +38,16 @@ ; CHECK-NOT: {{DW_TAG|NULL}} ; CHECK: DW_TAG_member ; CHECK-NOT: {{DW_TAG|NULL}} -; CHECK: DW_TAG_subprogram +; CHECK: [[M_FN2_DECL:.*]]: DW_TAG_subprogram ; CHECK-NOT: DW_TAG ; CHECK: DW_AT_name {{.*}} "m_fn2" ; CHECK-NOT: {{DW_TAG|NULL}} -; CHECK: [[M_FN2_THIS_DECL:.*]]: DW_TAG_formal_parameter +; CHECK: DW_TAG_formal_parameter ; The abstract definition of C::m_fn2 ; CHECK: [[M_FN2_ABS_DEF:.*]]: DW_TAG_subprogram ; CHECK-NOT: DW_TAG -; CHECK: DW_AT_specification {{.*}} "_ZN1C5m_fn2Ev" +; CHECK: DW_AT_specification {{.*}} {[[M_FN2_DECL]]} ; CHECK-NOT: DW_TAG ; CHECK: DW_AT_inline ; CHECK-NOT: {{DW_TAG|NULL}} @@ -63,7 +63,7 @@ ; The concrete definition of C::m_fn2 ; CHECK: DW_TAG_subprogram ; CHECK-NOT: DW_TAG -; CHECK: DW_AT_abstract_origin {{.*}} {[[M_FN2_ABS_DEF]]} "_ZN1C5m_fn2Ev" +; CHECK: DW_AT_abstract_origin {{.*}} {[[M_FN2_ABS_DEF]]} ; CHECK-NOT: {{DW_TAG|NULL}} ; CHECK: DW_TAG_formal_parameter ; CHECK-NOT: DW_TAG @@ -78,7 +78,7 @@ ; Inlined C::m_fn2: ; CHECK: DW_TAG_inlined_subroutine ; CHECK-NOT: DW_TAG -; CHECK: DW_AT_abstract_origin {{.*}} {[[M_FN2_ABS_DEF]]} "_ZN1C5m_fn2Ev" +; CHECK: DW_AT_abstract_origin {{.*}} {[[M_FN2_ABS_DEF]]} ; CHECK-NOT: {{DW_TAG|NULL}} ; CHECK: DW_TAG_formal_parameter ; CHECK-NOT: DW_TAG diff --git a/test/DebugInfo/cross-cu-inlining.ll b/test/DebugInfo/cross-cu-inlining.ll index 7929d5a39e5..3750eab8363 100644 --- a/test/DebugInfo/cross-cu-inlining.ll +++ b/test/DebugInfo/cross-cu-inlining.ll @@ -1,7 +1,7 @@ ; REQUIRES: object-emission -; RUN: %llc_dwarf -O0 -filetype=obj < %s | llvm-dwarfdump -debug-dump=info - | FileCheck -implicit-check-not=DW_TAG %s -; RUN: %llc_dwarf -dwarf-accel-tables=Enable -O0 -filetype=obj < %s | llvm-dwarfdump - | FileCheck --check-prefix=CHECK-ACCEL --check-prefix=CHECK %s +; RUN: %llc_dwarf -O0 -filetype=obj -dwarf-linkage-names=Enable < %s | llvm-dwarfdump -debug-dump=info - | FileCheck -implicit-check-not=DW_TAG %s +; RUN: %llc_dwarf -dwarf-accel-tables=Enable -dwarf-linkage-names=Enable -O0 -filetype=obj < %s | llvm-dwarfdump - | FileCheck --check-prefix=CHECK-ACCEL --check-prefix=CHECK %s ; Build from source: ; $ clang++ a.cpp b.cpp -g -c -emit-llvm diff --git a/test/DebugInfo/enum-types.ll b/test/DebugInfo/enum-types.ll index 418d7f30cba..048475ef3bb 100644 --- a/test/DebugInfo/enum-types.ll +++ b/test/DebugInfo/enum-types.ll @@ -1,6 +1,6 @@ ; REQUIRES: object-emission ; -; RUN: %llc_dwarf -filetype=obj -O0 < %s | llvm-dwarfdump -debug-dump=info - | FileCheck %s +; RUN: %llc_dwarf -filetype=obj -O0 -dwarf-linkage-names=Enable < %s | llvm-dwarfdump -debug-dump=info - | FileCheck %s ; Make sure we can handle enums with the same identifier but in enum types of ; different compile units. diff --git a/test/DebugInfo/incorrect-variable-debugloc.ll b/test/DebugInfo/incorrect-variable-debugloc.ll index 86f16ca8779..cff254ee3c6 100644 --- a/test/DebugInfo/incorrect-variable-debugloc.ll +++ b/test/DebugInfo/incorrect-variable-debugloc.ll @@ -38,11 +38,11 @@ ; CHECK: DW_TAG_structure_type ; CHECK-NEXT: DW_AT_name {{.*}} "C" -; CHECK: DW_TAG_subprogram -; CHECK-NOT: DW_TAG +; CHECK: [[M_FN3_DECL:.*]]: DW_TAG_subprogram +; CHECK-NOT: {{DW_TAG|NULL}} ; CHECK: DW_AT_name {{.*}} "m_fn3" -; CHECK: DW_AT_specification {{.*}} "_ZN1C5m_fn3Ev" +; CHECK: DW_AT_specification {{.*}} {[[M_FN3_DECL]]} ; CHECK-NOT: DW_TAG ; CHECK: DW_TAG_formal_parameter ; CHECK-NOT: DW_TAG diff --git a/test/DebugInfo/missing-abstract-variable.ll b/test/DebugInfo/missing-abstract-variable.ll index 88b32aad6d5..6273e171483 100644 --- a/test/DebugInfo/missing-abstract-variable.ll +++ b/test/DebugInfo/missing-abstract-variable.ll @@ -37,7 +37,7 @@ ; x(u); ; } -; CHECK: DW_TAG_subprogram +; CHECK: [[X_DECL:.*]]: DW_TAG_subprogram ; CHECK-NOT: DW_TAG ; CHECK: DW_AT_name {{.*}} "x" ; CHECK-NOT: {{DW_TAG|NULL}} @@ -57,7 +57,7 @@ ; CHECK-NOT: {{DW_TAG|NULL}} ; CHECK: DW_TAG_inlined_subroutine ; CHECK-NOT: DW_TAG -; CHECK: DW_AT_abstract_origin {{.*}} "_Z1xb" +; CHECK: DW_AT_abstract_origin {{.*}} {[[X_DECL]]} ; CHECK-NOT: {{DW_TAG|NULL}} ; CHECK: DW_TAG_formal_parameter ; CHECK-NOT: DW_TAG @@ -78,7 +78,7 @@ ; CHECK-NOT: {{DW_TAG|NULL}} ; CHECK: DW_TAG_inlined_subroutine ; CHECK-NOT: DW_TAG -; CHECK: DW_AT_abstract_origin {{.*}} "_Z1xb" +; CHECK: DW_AT_abstract_origin {{.*}} {[[X_DECL]]} ; CHECK-NOT: {{DW_TAG|NULL}} ; FIXME: This formal parameter goes missing at least at -O2 (& on ; mips/powerpc), maybe before that. Perhaps SelectionDAG is to blame (and diff --git a/test/DebugInfo/namespace.ll b/test/DebugInfo/namespace.ll index 792981b0087..c43de6b16fa 100644 --- a/test/DebugInfo/namespace.ll +++ b/test/DebugInfo/namespace.ll @@ -1,7 +1,6 @@ ; REQUIRES: object-emission -; RUN: %llc_dwarf -O0 -filetype=obj < %s > %t -; RUN: llvm-dwarfdump %t | FileCheck %s +; RUN: %llc_dwarf -O0 -filetype=obj -dwarf-linkage-names=Enable < %s | llvm-dwarfdump - | FileCheck %s ; CHECK: debug_info contents ; CHECK: [[NS1:0x[0-9a-f]*]]:{{ *}}DW_TAG_namespace ; CHECK-NEXT: DW_AT_name{{.*}} = "A" diff --git a/test/DebugInfo/namespace_function_definition.ll b/test/DebugInfo/namespace_function_definition.ll index 5f87cfc90c2..6983a687aba 100644 --- a/test/DebugInfo/namespace_function_definition.ll +++ b/test/DebugInfo/namespace_function_definition.ll @@ -1,6 +1,6 @@ ; REQUIRES: object-emission -; RUN: %llc_dwarf -O0 -filetype=obj < %s | llvm-dwarfdump -debug-dump=info - | FileCheck %s +; RUN: %llc_dwarf -O0 -filetype=obj -dwarf-linkage-names=Enable < %s | llvm-dwarfdump -debug-dump=info - | FileCheck %s ; Generated from clang with the following source: ; namespace ns { diff --git a/test/DebugInfo/namespace_inline_function_definition.ll b/test/DebugInfo/namespace_inline_function_definition.ll index 99b09c9545a..abbe9c34e96 100644 --- a/test/DebugInfo/namespace_inline_function_definition.ll +++ b/test/DebugInfo/namespace_inline_function_definition.ll @@ -1,6 +1,6 @@ ; REQUIRES: object-emission -; RUN: %llc_dwarf -O0 -filetype=obj < %s | llvm-dwarfdump -debug-dump=info - | FileCheck %s +; RUN: %llc_dwarf -O0 -filetype=obj -dwarf-linkage-names=Enable < %s | llvm-dwarfdump -debug-dump=info - | FileCheck %s ; Generate from clang with the following source. Note that the definition of ; the inline function follows its use to workaround another bug that should be diff --git a/test/Linker/type-unique-odr-a.ll b/test/Linker/type-unique-odr-a.ll index 2ce264b0f9c..6f3ee71fe7f 100644 --- a/test/Linker/type-unique-odr-a.ll +++ b/test/Linker/type-unique-odr-a.ll @@ -1,6 +1,6 @@ ; REQUIRES: object-emission, native ; -; RUN: llvm-link %s %p/type-unique-odr-b.ll -S -o - | %llc_dwarf -filetype=obj -O0 | llvm-dwarfdump -debug-dump=info - | FileCheck %s +; RUN: llvm-link %s %p/type-unique-odr-b.ll -S -o - | %llc_dwarf -dwarf-linkage-names=Enable -filetype=obj -O0 | llvm-dwarfdump -debug-dump=info - | FileCheck %s ; ; Test ODR-based type uniquing for C++ class members. ; rdar://problem/15851313. diff --git a/test/Linker/type-unique-simple2-a.ll b/test/Linker/type-unique-simple2-a.ll index 0297717ba21..56682c4babb 100644 --- a/test/Linker/type-unique-simple2-a.ll +++ b/test/Linker/type-unique-simple2-a.ll @@ -18,7 +18,8 @@ ; return A().getFoo(); ; } ; -; CHECK: _ZN1A6setFooEv +; CHECK: DW_AT_name {{.*}} "setFoo" +; CHECK-NOT: DW_TAG ; CHECK: DW_AT_accessibility [DW_FORM_data1] (DW_ACCESS_public) ; CHECK-NOT: DW_AT_accessibility ; CHECK: DW_TAG diff --git a/test/Linker/type-unique-type-array-a.ll b/test/Linker/type-unique-type-array-a.ll index d9387e54020..ca6c2524bb8 100644 --- a/test/Linker/type-unique-type-array-a.ll +++ b/test/Linker/type-unique-type-array-a.ll @@ -23,7 +23,7 @@ ; CHECK: DW_TAG_class_type ; CHECK-NEXT: DW_AT_name {{.*}} "A" ; CHECK: DW_TAG_subprogram -; CHECK: DW_AT_MIPS_linkage_name {{.*}} "_ZN1A5testAE2SA" +; CHECK: DW_AT_name {{.*}} "testA" ; CHECK: DW_TAG_formal_parameter ; CHECK: DW_TAG_formal_parameter ; CHECK-NEXT: DW_AT_type [DW_FORM_ref4] (cu + 0x{{.*}} => {0x[[STRUCT:.*]]}) @@ -34,7 +34,7 @@ ; CHECK: DW_TAG_class_type ; CHECK-NEXT: DW_AT_name {{.*}} "B" ; CHECK: DW_TAG_subprogram -; CHECK: DW_AT_MIPS_linkage_name {{.*}} "_ZN1B5testBE2SA" +; CHECK: DW_AT_name {{.*}} "testB" ; CHECK: DW_TAG_formal_parameter ; CHECK: DW_TAG_formal_parameter ; CHECK-NEXT: DW_AT_type [DW_FORM_ref_addr] {{.*}}[[STRUCT]]