Skip to content

Commit 7f73de8

Browse files
admitricpszymich
authored andcommitted
Do not clone debug instruction in code sinking
Move the debug instructions instead of cloning them in CodeSinking and CodeLoopSinking passes. (cherry picked from commit 034a6df)
1 parent aab651c commit 7f73de8

File tree

2 files changed

+86
-6
lines changed

2 files changed

+86
-6
lines changed

IGC/Compiler/CISACodeGen/CodeSinking.cpp

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,7 @@ namespace IGC {
5151
// it is required for correct work of LiveVariables analysis and other
5252
static void ProcessDbgValueInst(BasicBlock& blk, DominatorTree *DT)
5353
{
54+
llvm::DenseMap<Instruction *, Instruction *> PositionMap;
5455
for (auto I = blk.rbegin(), E = blk.rend(); I != E; ++I)
5556
{
5657
Instruction* inst = cast<Instruction>(&*I);
@@ -65,18 +66,15 @@ namespace IGC {
6566
{
6667
if (!DT->dominates(def, inst))
6768
{
68-
auto* instClone = inst->clone();
6969
if (isa<PHINode>(def)) {
7070
// If the instruction is a PHI node, insert the new instruction at the beginning of the block.
71-
instClone->insertBefore(&*def->getParent()->getFirstInsertionPt());
71+
PositionMap[inst] = &*def->getParent()->getFirstInsertionPt();
7272
}
7373
else {
7474
// Otherwise, insert the new instruction after the defining instruction.
75-
instClone->insertAfter(def);
75+
PositionMap[inst] = def->getNextNonDebugInstruction();
76+
IGC_ASSERT(!isa<BranchInst>(def));
7677
}
77-
Value* undef = UndefValue::get(def->getType());
78-
MetadataAsValue* MAV = MetadataAsValue::get(inst->getContext(), ValueAsMetadata::get(undef));
79-
cast<CallInst>(inst)->setArgOperand(0, MAV);
8078
}
8179
}
8280
}
@@ -89,6 +87,9 @@ namespace IGC {
8987
}
9088
}
9189
}
90+
for (auto &[I, Pos] : PositionMap) {
91+
I->moveBefore(Pos);
92+
}
9293
}
9394

9495
// Check the instruction is a 2d block read
Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
;=========================== begin_copyright_notice ============================
2+
;
3+
; Copyright (C) 2025 Intel Corporation
4+
;
5+
; SPDX-License-Identifier: MIT
6+
;
7+
;============================ end_copyright_notice =============================
8+
; REQUIRES: regkeys
9+
; RUN: igc_opt --regkey LoopSinkMinSave=0 --regkey ForceLoopSink=1 --regkey CodeLoopSinkingMinSize=10 --CheckInstrTypes -igc-update-instrtypes-on-run --basic-aa --igc-code-loop-sinking --verify -S %s | FileCheck %s --check-prefix=CHECK-SINK
10+
; RUN: igc_opt --regkey LoopSinkMinSave=0 --regkey ForceLoopSink=1 --regkey LoopSinkForceRollback=1 --regkey CodeLoopSinkingMinSize=10 --CheckInstrTypes -igc-update-instrtypes-on-run --basic-aa --igc-code-loop-sinking --verify -S %s | FileCheck %s --check-prefix=CHECK-ROLLBACK
11+
12+
; CHECK-LABEL: @foo(
13+
14+
; For sink we check there is only one debug value in the loop
15+
16+
; CHECK-SINK: ph:
17+
; CHECK-SINK-NOT: call void @llvm.dbg.value
18+
; CHECK-SINK: loop:
19+
; CHECK-SINK: call void @llvm.dbg.value
20+
; CHECK-SINK-NOT: call void @llvm.dbg.value
21+
22+
23+
; For rollback check the debug value is not duplicated
24+
; Also --verify pass checks that the IR is correct
25+
26+
; CHECK-ROLLBACK: call void @llvm.dbg.value
27+
; CHECK-ROLLBACK-NOT: call void @llvm.dbg.value
28+
29+
30+
define spir_kernel void @foo(i32 %t, i32 %count) {
31+
br label %ph
32+
33+
ph:
34+
%1 = add i32 %t, 1
35+
%2 = add i32 %1, 2
36+
br label %loop
37+
38+
loop: ; preds = %loop, %ph
39+
%index = phi i32 [ 0, %ph ], [ %inc, %loop ]
40+
call void @llvm.dbg.value(metadata i32 %1, metadata !12, metadata !DIExpression(DW_OP_constu, 4, DW_OP_swap, DW_OP_xderef)), !dbg !13
41+
%3 = add i32 %1, 3
42+
%4 = add i32 %2, %3
43+
%inc = add i32 %index, 1
44+
%cmptmp = icmp ult i32 %index, %count
45+
br i1 %cmptmp, label %loop, label %afterloop
46+
47+
afterloop: ; preds = %loop
48+
ret void
49+
}
50+
51+
; Function Attrs: nofree nosync nounwind readnone speculatable willreturn
52+
declare void @llvm.dbg.value(metadata, metadata, metadata) #0
53+
54+
declare i32 @llvm.genx.GenISA.WavePrefix.i32(i32, i8, i1, i1, i32)
55+
56+
attributes #0 = { nofree nosync nounwind readnone speculatable willreturn }
57+
58+
!llvm.module.flags = !{!3, !4, !5}
59+
!llvm.dbg.cu = !{!0}
60+
61+
!0 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus_14, file: !1, producer: "clang", isOptimized: true, runtimeVersion: 0, emissionKind: FullDebug, enums: !2)
62+
!1 = !DIFile(filename: "hi.cpp", directory: "/test/")
63+
!2 = !{}
64+
!3 = !{i32 2, !"Dwarf Version", i32 4}
65+
!4 = !{i32 2, !"Debug Info Version", i32 3}
66+
!5 = !{i32 1, !"wchar_size", i32 4}
67+
!6 = !{!"clang"}
68+
!7 = distinct !DISubprogram(name: "test", scope: !1, file: !1, line: 3, type: !8, isLocal: false, isDefinition: true, scopeLine: 3, flags: DIFlagPrototyped, isOptimized: true, unit: !0, retainedNodes: !11)
69+
!8 = !DISubroutineType(types: !9)
70+
!9 = !{!10, !10}
71+
!10 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed)
72+
!11 = !{!12}
73+
!12 = !DILocalVariable(name: "t", arg: 1, scope: !7, file: !1, line: 3, type: !10)
74+
!13 = !DILocation(line: 3, column: 14, scope: !7)
75+
!14 = !DILocation(line: 4, column: 12, scope: !7)
76+
!15 = distinct !DISubprogram(name: "_start", scope: !1, file: !1, line: 7, type: !16, isLocal: false, isDefinition: true, scopeLine: 7, isOptimized: true, unit: !0, retainedNodes: !2)
77+
!16 = !DISubroutineType(types: !17)
78+
!17 = !{!10}
79+
!18 = !DILocalVariable(name: "a", arg: 1, scope: !7, file: !1, line: 3, type: !10)

0 commit comments

Comments
 (0)