With this patch we're now accounting for two more cases which should be considered 'valid throughout': First, where RangeEnd is ScopeEnd. Second, where RangeEnd comes before ScopeEnd when including meta instructions, but are both preceded by the same non-meta instruction. CTMark shows a geomean binary size reduction of 1.5% for RelWithDebInfo builds. `llvm-locstats` (using D85636) shows a very small variable location coverage change in 2 of 10 binaries, but it is in the order of 10s of bytes which lines up with my expectations. I've added a test which checks both of these new cases. The first check in the test isn't strictly necessary for this patch. But I'm not sure that it is explicitly tested anywhere else, and is useful for the final patch in the series. Reviewed By: aprantl Differential Revision: https://reviews.llvm.org/D86151
93 lines
3.9 KiB
YAML
93 lines
3.9 KiB
YAML
# RUN: llc %s --start-after=livedebugvalues -filetype=obj -o - \
|
|
# RUN: | llvm-dwarfdump - -name local* -regex \
|
|
# RUN: | FileCheck %s
|
|
#
|
|
## This tests certain single location detection functionality. The Test MIR
|
|
## is hand written. Test directives and comments inline.
|
|
|
|
--- |
|
|
target triple = "x86_64-unknown-linux-gnu"
|
|
define dso_local i32 @fun() local_unnamed_addr !dbg !7 {
|
|
entry:
|
|
ret i32 0
|
|
}
|
|
|
|
!llvm.dbg.cu = !{!0}
|
|
!llvm.module.flags = !{!3, !4, !5}
|
|
!llvm.ident = !{!6}
|
|
|
|
!0 = distinct !DICompileUnit(language: DW_LANG_C99, file: !1, producer: "clang version 11.0.0", isOptimized: true, runtimeVersion: 0, emissionKind: FullDebug, splitDebugInlining: false, nameTableKind: None)
|
|
!1 = !DIFile(filename: "example.c", directory: "/")
|
|
!3 = !{i32 7, !"Dwarf Version", i32 4}
|
|
!4 = !{i32 2, !"Debug Info Version", i32 3}
|
|
!5 = !{i32 1, !"wchar_size", i32 4}
|
|
!6 = !{!"clang version 11.0.0"}
|
|
!8 = !DISubroutineType(types: !9)
|
|
!9 = !{!10}
|
|
!10 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
|
|
!22 = !DISubroutineType(types: !23)
|
|
!23 = !{!10, !10}
|
|
; --- Important metadata ---
|
|
!7 = distinct !DISubprogram(name: "fun", scope: !1, file: !1, line: 2, type: !8, scopeLine: 2, flags: DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0)
|
|
!24 = distinct !DILexicalBlock(scope: !7, file: !1, line: 9, column: 3)
|
|
!14 = distinct !DILexicalBlock(scope: !7, file: !1, line: 4, column: 3)
|
|
!12 = !DILocalVariable(name: "locala", scope: !7, file: !1, line: 1, type: !10)
|
|
!13 = !DILocalVariable(name: "localb", scope: !14, file: !1, line: 2, type: !10)
|
|
!25 = !DILocalVariable(name: "localc", scope: !24, file: !1, line: 3, type: !10)
|
|
!27 = !DILocalVariable(name: "tmp", scope: !14, file: !1, line: 2, type: !10)
|
|
!15 = !DILocation(line: 1, column: 0, scope: !7)
|
|
!18 = !DILocation(line: 2, column: 1, scope: !14)
|
|
!26 = !DILocation(line: 3, column: 1, scope: !24)
|
|
...
|
|
---
|
|
name: fun
|
|
body: |
|
|
bb.0.entry:
|
|
;; This is the scope and variable structure:
|
|
;; int fun() { // scope fun !7
|
|
;; int locala; // scope fun !7, var locala !12, debug-location !15
|
|
;; { int localb; // scope fun:block !14, var localb !13, debug-location !18
|
|
;; int tmp; } // scope fun:block !14, var localb !27, debug-location !18
|
|
;; { int localc; } // scope fun:block !24, var localc !25, debug-location !26
|
|
;; }
|
|
;;
|
|
;; (1) Check that frame-setup instructions are not counted against
|
|
;; locations being valid throughout the function call.
|
|
;
|
|
; CHECK: DW_TAG_variable
|
|
; CHECK-NEXT: DW_AT_location (DW_OP_reg5 RDI)
|
|
; CHECK-NEXT: DW_AT_name ("locala")
|
|
$rbp = frame-setup MOV64rr $rsp
|
|
DBG_VALUE $edi, $noreg, !12, !DIExpression(), debug-location !15
|
|
$eax = MOV32ri 0, debug-location !15
|
|
|
|
;; (2) The scope block ends with a meta instruction. A location range ends
|
|
;; with the final non-meta instruction in the scope. Check that
|
|
;; location is considered valid throughout.
|
|
;
|
|
; CHECK: DW_TAG_variable
|
|
; CHECK-NEXT: DW_AT_location (DW_OP_reg2 RCX)
|
|
; CHECK-NEXT: DW_AT_name ("localb")
|
|
;
|
|
;; start scope, start location range
|
|
DBG_VALUE $ecx, $noreg, !13, !DIExpression(), debug-location !18
|
|
;; end location range
|
|
$ecx = MOV32ri 1, debug-location !18
|
|
;; end scope
|
|
DBG_VALUE $noreg, $noreg, !27, !DIExpression(), debug-location !18
|
|
|
|
;; (3) The final instruction in the scope closes a location range. Check
|
|
;; that location is considered valid throughout.
|
|
;
|
|
; CHECK: DW_TAG_variable
|
|
; CHECK-NEXT: DW_AT_location (DW_OP_reg4 RSI)
|
|
; CHECK-NEXT: DW_AT_name ("localc")
|
|
;
|
|
;; start scope, start location range
|
|
DBG_VALUE $esi, $noreg, !25, !DIExpression(), debug-location !26
|
|
;; end scope, end location range
|
|
$esi = MOV32ri 2, debug-location !26
|
|
|
|
RETQ debug-location !15
|
|
...
|