[llvm] [DebugInfo][SimpleLoopUnswitch] Fix missing debug location updates (PR #97662)

Shan Huang via llvm-commits llvm-commits at lists.llvm.org
Mon Jul 8 08:59:30 PDT 2024


================
@@ -0,0 +1,75 @@
+; RUN: opt -passes='simple-loop-unswitch<nontrivial>' -S < %s | FileCheck %s
+
+define i32 @basic(i32 %N, i1 %cond, i32 %select_input) !dbg !5 {
+; CHECK-LABEL: define i32 @basic(
+
+; Check that SimpleLoopUnswitch's unswitchNontrivialInvariants() drops the
+; debug location of the hoisted terminator and doesn't give any debug location
+; to the new freeze, since it's inserted in a hoist block.
+; Also check that in unswitchNontrivialInvariants(), the new br instruction
+; inherits the debug location of the old terminator in the same block.
+
+; CHECK:       entry:
+; CHECK-NEXT:    [[COND_FR:%.*]] = freeze i1 [[COND:%.*]]{{$}}
+; CHECK-NEXT:    br i1 [[COND_FR]], label %[[ENTRY_SPLIT_US:.*]], label %[[ENTRY_SPLIT:.*]]{{$}}
+; CHECK:       for.body.us:
+; CHECK-NEXT:    br label %0, !dbg [[DBG13:![0-9]+]]
----------------
Apochens wrote:

This debug location comes from the debug location update:

```cpp
  Instruction *BI = BranchInst::Create(ClonedSuccBB, ClonedParentBB);
  BI->setDebugLoc(ClonedTerminator->getDebugLoc());
  ClonedTerminator->eraseFromParent();
```

In the update, `BI` points the new br instruction. So, the debug location of `select` is propagated from `ClonedTerminator` to `BI`. To illustrate the instruction that `ClonedTerminator` points to, I paste the IR program before the remove of `ClonedTerminator` in the above code:

```LLVM IR
define i32 @basic(i32 %N, i1 %cond, i32 %select_input) !dbg !5 {
entry:
  br label %entry.split, !dbg !8

entry.split.us:                                   ; No predecessors!
  br label %for.cond.us, !dbg !8

for.cond.us:                                      ; preds = %1, %entry.split.us
  %res.us = phi i32 [ 0, %entry.split.us ], [ %add.us, %1 ], !dbg !9
  %i.us = phi i32 [ 0, %entry.split.us ], [ %inc.us, %1 ], !dbg !10
  %cmp.us = icmp slt i32 %i.us, %N, !dbg !11
  br i1 %cmp.us, label %for.body.us, label %for.cond.cleanup.split.us, !dbg !12

for.body.us:                                      ; preds = %for.cond.us
->br i1 %cond, label %0, label %1, !dbg !13    (ClonedTerminator)
  br label %0, !dbg !13.                                       (BI)

0:                                                ; preds = %for.body.us, %for.body.us
  br label %1, !dbg !13

1:                                                ; preds = %0, %for.body.us
  %unswitched.select.us = phi i32 [ %select_input, %0 ], !dbg !13
  %add.us = add nuw nsw i32 %unswitched.select.us, %res.us, !dbg !14
  %inc.us = add nuw nsw i32 %i.us, 1, !dbg !15
  br label %for.cond.us, !dbg !16

for.cond.cleanup.split.us:                        ; preds = %for.cond.us
  ...
}
```

I just propagate the debug location of the instruction pointed by `ClonedTerminator` to `BI`, and the reason why `ClonedTerminator` has the debug location of the `select` could be resulted by spliting the cloned for body (as the contents of block `%1` is actually the contents of `%for.body`).

https://github.com/llvm/llvm-project/pull/97662


More information about the llvm-commits mailing list