Skip to content

Commit 4361da6

Browse files
authored
Merge pull request #38942 from mshockwave/dev-dbg-var-artificial
[DebugInfo] Prevent salvaged debug vars from being marked artificial
2 parents c517b45 + da5ef90 commit 4361da6

File tree

4 files changed

+44
-2
lines changed

4 files changed

+44
-2
lines changed

lib/IRGen/IRGenDebugInfo.cpp

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2543,6 +2543,23 @@ void IRGenDebugInfoImpl::emitDbgIntrinsic(
25432543
!llvm::FindDbgDeclareUses(Storage).empty())
25442544
return;
25452545

2546+
// Fragment DIExpression cannot cover the whole variable
2547+
// or going out-of-bound.
2548+
if (auto Fragment = Expr->getFragmentInfo())
2549+
if (auto VarSize = Var->getSizeInBits()) {
2550+
unsigned FragSize = Fragment->SizeInBits;
2551+
unsigned FragOffset = Fragment->OffsetInBits;
2552+
if (FragOffset + FragSize > *VarSize ||
2553+
FragSize == *VarSize) {
2554+
// Drop the fragment part
2555+
assert(Expr->isValid());
2556+
// Since this expression is valid, DW_OP_LLVM_fragment
2557+
// and its arguments must be the last 3 elements.
2558+
auto OrigElements = Expr->getElements();
2559+
Expr = DBuilder.createExpression(OrigElements.drop_back(3));
2560+
}
2561+
}
2562+
25462563
// A dbg.declare is only meaningful if there is a single alloca for
25472564
// the variable that is live throughout the function.
25482565
if (auto *Alloca = dyn_cast<llvm::AllocaInst>(Storage)) {

lib/SILOptimizer/Utils/InstOptUtils.cpp

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2119,8 +2119,7 @@ void swift::salvageDebugInfo(SILInstruction *I) {
21192119
DestVal.getDefiningInstruction())) {
21202120
if (auto VarInfo = ASI->getVarInfo())
21212121
SILBuilder(SI, ASI->getDebugScope())
2122-
.createDebugValue(RegularLocation::getAutoGeneratedLocation(),
2123-
SI->getSrc(), *VarInfo);
2122+
.createDebugValue(SI->getLoc(), SI->getSrc(), *VarInfo);
21242123
}
21252124
}
21262125
}

test/DebugInfo/debug_info_expression.sil

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,10 @@ struct MyStruct {
88
var y: Builtin.Int64
99
}
1010

11+
struct SmallStruct {
12+
var z : Builtin.Int64
13+
}
14+
1115
sil_scope 1 { loc "file.swift":7:6 parent @test_fragment : $@convention(thin) () -> () }
1216

1317
// Testing op_fragment w/ debug_value_addr
@@ -16,6 +20,8 @@ bb0:
1620
%2 = alloc_stack $MyStruct, var, name "my_struct", loc "file.swift":8:9, scope 1
1721
// CHECK: %[[MY_STRUCT:.+]] = alloca %{{.*}}MyStruct
1822
// CHECK: llvm.dbg.declare(metadata {{.*}}* %[[MY_STRUCT]], metadata ![[VAR_DECL_MD:[0-9]+]]
23+
// CHECK: %[[SMALL_STRUCT:.+]] = alloca %{{.*}}SmallStruct
24+
// CHECK: llvm.dbg.declare(metadata {{.*}}* %[[SMALL_STRUCT]], metadata ![[SMALL_VAR_DECL_MD:[0-9]+]]
1925
%3 = struct_element_addr %2 : $*MyStruct, #MyStruct.x, loc "file.swift":9:17, scope 1
2026
// CHECK: %[[FIELD_X:.*]] = getelementptr {{.*}} %[[MY_STRUCT]]
2127
// CHECK-SIL: debug_value_addr %{{[0-9]+}} : $*Builtin.Int64
@@ -25,6 +31,17 @@ bb0:
2531
// CHECK: llvm.dbg.value(metadata {{.*}}* %[[FIELD_X]], metadata ![[VAR_DECL_MD]]
2632
// CHECK-SAME: !DIExpression(DW_OP_deref, DW_OP_LLVM_fragment, 0, 64)
2733
// CHECK-NOT: ), !dbg ![[VAR_DECL_MD]]
34+
35+
%4 = alloc_stack $SmallStruct, var, name "small_struct", loc "file.swift":10:11, scope 1
36+
%5 = struct_element_addr %4 : $*SmallStruct, #SmallStruct.z, loc "file.swift":11:13, scope 1
37+
// CHECK: %[[FIELD_Z:.*]] = getelementptr {{.*}} %[[SMALL_STRUCT]]
38+
// If the fragment covers the whole struct, we're not generating the
39+
// DW_OP_LLVM_fragment part.
40+
// CHECK: llvm.dbg.value(metadata {{.*}}* %[[FIELD_Z]], metadata ![[SMALL_VAR_DECL_MD]]
41+
// CHECK-SAME: !DIExpression(DW_OP_deref)
42+
debug_value_addr %5 : $*Builtin.Int64, var, (name "small_struct", loc "file.swift":10:11, scope 1), type $SmallStruct, expr op_fragment:#SmallStruct.z, loc "file.swift":11:13, scope 1
43+
dealloc_stack %4 : $*SmallStruct
44+
2845
dealloc_stack %2 : $*MyStruct
2946
%r = tuple()
3047
return %r : $()

test/DebugInfo/sroa_mem2reg.sil

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@
22
// RUN: %target-sil-opt -enable-sil-verify-all -sil-print-debuginfo -sroa -mem2reg %s -o %t.sil
33
// RUN: %FileCheck --check-prefix=CHECK-MEM2REG %s --input-file=%t.sil
44
// RUN: %target-swiftc_driver -Xfrontend -disable-debugger-shadow-copies -g -emit-ir %t.sil | %FileCheck --check-prefix=CHECK-IR %s
5+
// RUN: %target-swiftc_driver -Xfrontend -disable-debugger-shadow-copies -g -c %t.sil -o %t.o
6+
// RUN: %llvm-dwarfdump --debug-info %t.o | %FileCheck --check-prefix=CHECK-DWARF %s
57
sil_stage canonical
68

79
import Builtin
@@ -78,3 +80,10 @@ bb0(%0 : $Int64, %1 : $Int64):
7880
// CHECK-IR-SAME: line: 7
7981
// CHECK-IR: ![[ARG2_MD]] = !DILocalVariable(name: "in_y", arg: 2
8082
// CHECK-IR-SAME: line: 7
83+
84+
// CHECK-DWARF-LABEL: DW_AT_name ("foo")
85+
// CHECK-DWARF: DW_TAG_variable
86+
// CHECK-DWARF: DW_AT_name ("my_struct")
87+
// Shouldn't be marked artificial
88+
// CHECK-DWARF-NOT: DW_AT_artificial (true)
89+
// CHECK-DWARF: DW_TAG_{{.*}}

0 commit comments

Comments
 (0)