[llvm] 45af938 - [Coroutines] Walk inlinedAt recursively to create legal DILabels (#157099)

via llvm-commits llvm-commits at lists.llvm.org
Fri Sep 5 07:07:33 PDT 2025


Author: Christian Ulmann
Date: 2025-09-05T16:07:29+02:00
New Revision: 45af938ecf1b97ae84b4c43220038a84e6c4ef42

URL: https://github.com/llvm/llvm-project/commit/45af938ecf1b97ae84b4c43220038a84e6c4ef42
DIFF: https://github.com/llvm/llvm-project/commit/45af938ecf1b97ae84b4c43220038a84e6c4ef42.diff

LOG: [Coroutines] Walk inlinedAt recursively to create legal DILabels (#157099)

This commit resolves a defect in the creation of DILabels for suspend
points. While a previous change introduced support for inlined
locations, it did not consider that a location might originate from
multiple inlinings. Therefore, we extend this to walk iteratively
through all `inlinedAt` locations to get to the root.

Added: 
    

Modified: 
    llvm/lib/Transforms/Coroutines/CoroSplit.cpp
    llvm/test/Transforms/Coroutines/coro-split-dbg-labels-inlined.ll

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Transforms/Coroutines/CoroSplit.cpp b/llvm/lib/Transforms/Coroutines/CoroSplit.cpp
index 88b2bd9aa2046..02c38d02cff64 100644
--- a/llvm/lib/Transforms/Coroutines/CoroSplit.cpp
+++ b/llvm/lib/Transforms/Coroutines/CoroSplit.cpp
@@ -1568,13 +1568,15 @@ struct SwitchCoroutineSplitter {
         if (DebugLoc SuspendLoc = S->getDebugLoc()) {
           std::string LabelName =
               ("__coro_resume_" + Twine(SuspendIndex)).str();
-          // Take the "inlined at" location, if present. This is mandatory as
-          // the DILabel insertion checks that the scopes of label and the
-          // attached location match. This is not the case when the suspend
-          // location has been inlined due to pointing to the original scope.
-          DILocation *DILoc = SuspendLoc->getInlinedAt();
-          if (!DILoc)
-            DILoc = SuspendLoc;
+          // Take the "inlined at" location recursively, if present. This is
+          // mandatory as the DILabel insertion checks that the scopes of label
+          // and the attached location match. This is not the case when the
+          // suspend location has been inlined due to pointing to the original
+          // scope.
+          DILocation *DILoc = SuspendLoc;
+          while (DILocation *InlinedAt = DILoc->getInlinedAt())
+            DILoc = InlinedAt;
+
           DILabel *ResumeLabel =
               DBuilder.createLabel(DIS, LabelName, DILoc->getFile(),
                                    SuspendLoc.getLine(), SuspendLoc.getCol(),

diff  --git a/llvm/test/Transforms/Coroutines/coro-split-dbg-labels-inlined.ll b/llvm/test/Transforms/Coroutines/coro-split-dbg-labels-inlined.ll
index 0905f5981502c..e9737b62b0b8f 100644
--- a/llvm/test/Transforms/Coroutines/coro-split-dbg-labels-inlined.ll
+++ b/llvm/test/Transforms/Coroutines/coro-split-dbg-labels-inlined.ll
@@ -1,5 +1,8 @@
 ; RUN: opt %s -passes='cgscc(coro-split)' -S | FileCheck %s
 
+; Verifies that suspend points with inlined locations are handled properly,
+; i.e., that their debug labels point to the correct subprogram.
+
 source_filename = "coro.c"
 
 ; Function Attrs: nounwind uwtable
@@ -96,4 +99,7 @@ attributes #4 = { argmemonly nounwind readonly }
 !41 = !DILocation(line: 17, column: 1, scope: !16)
 
 !100 = distinct !DISubprogram(name: "callee", scope: !1, file: !1, line: 8, type: !17, scopeLine: 4, isOptimized: true, unit: !0, retainedNodes: !2)
-!101 = !DILocation(line: 12, column: 6, scope: !16)
+!101 = !DILocation(line: 42, column: 6, scope: !102, inlinedAt: !103)
+
+!102 = distinct !DISubprogram(name: "callee_recursive", scope: !1, file: !1, line: 8, type: !17, scopeLine: 4, isOptimized: true, unit: !0, retainedNodes: !2)
+!103 = !DILocation(line: 12, column: 6, scope: !16)


        


More information about the llvm-commits mailing list