[llvm-branch-commits] [llvm] [KeyInstr] Merge atoms in DILocation::getMergedLocation (PR #133480)

Orlando Cazalet-Hyams via llvm-branch-commits llvm-branch-commits at lists.llvm.org
Thu May 1 08:01:02 PDT 2025


https://github.com/OCHyams updated https://github.com/llvm/llvm-project/pull/133480

>From 2c538d7ba71f82c49800331d996316a96696aee2 Mon Sep 17 00:00:00 2001
From: Orlando Cazalet-Hyams <orlando.hyams at sony.com>
Date: Fri, 21 Mar 2025 11:52:30 +0000
Subject: [PATCH 1/4] [KeyInstr] Merge atoms in DILocation::getMergedLocation

NFC for builds with LLVM_EXPERIMENTAL_KEY_INSTRUCTIONS=OFF (default).

In an ideal world we would be able to track that the merged location is used in
multiple source atoms. We can't do this though, so instead we arbitrarily but
deterministically pick one.

In cases where the InlinedAt field is unchanged we keep the atom with the
lowest non-zero rank (highest precedence). If the ranks are equal we choose
the smaller non-zero group number (arbitrary choice).

In cases where the InlinedAt field is adjusted we generate a new atom group.
Keeping the group wouldn't make sense (a source atom is identified by the
group number and InlinedAt pair) but discarding the atom info could result
in missed is_stmts.

Add unittest in MetadataTest.cpp.
---
 llvm/lib/IR/DebugInfoMetadata.cpp  |  54 ++++++++++--
 llvm/unittests/IR/MetadataTest.cpp | 134 +++++++++++++++++++++++++++++
 2 files changed, 182 insertions(+), 6 deletions(-)

diff --git a/llvm/lib/IR/DebugInfoMetadata.cpp b/llvm/lib/IR/DebugInfoMetadata.cpp
index e3b105a6ac109..30ad9c11b2614 100644
--- a/llvm/lib/IR/DebugInfoMetadata.cpp
+++ b/llvm/lib/IR/DebugInfoMetadata.cpp
@@ -302,11 +302,15 @@ DILocation *DILocation::getMergedLocation(DILocation *LocA, DILocation *LocB) {
 
   // Merge the two locations if possible, using the supplied
   // inlined-at location for the created location.
-  auto MergeLocPair = [&C](const DILocation *L1, const DILocation *L2,
-                           DILocation *InlinedAt) -> DILocation * {
+  auto *LocAIA = LocA->getInlinedAt();
+  auto *LocBIA = LocB->getInlinedAt();
+  auto MergeLocPair = [&C, LocAIA,
+                       LocBIA](const DILocation *L1, const DILocation *L2,
+                               DILocation *InlinedAt) -> DILocation * {
     if (L1 == L2)
       return DILocation::get(C, L1->getLine(), L1->getColumn(), L1->getScope(),
-                             InlinedAt);
+                             InlinedAt, L1->isImplicitCode(),
+                             L1->getAtomGroup(), L1->getAtomRank());
 
     // If the locations originate from different subprograms we can't produce
     // a common location.
@@ -342,8 +346,44 @@ DILocation *DILocation::getMergedLocation(DILocation *LocA, DILocation *LocB) {
     bool SameCol = L1->getColumn() == L2->getColumn();
     unsigned Line = SameLine ? L1->getLine() : 0;
     unsigned Col = SameLine && SameCol ? L1->getColumn() : 0;
-
-    return DILocation::get(C, Line, Col, Scope, InlinedAt);
+    bool IsImplicitCode = L1->isImplicitCode() && L2->isImplicitCode();
+    uint64_t Group = 0;
+    uint64_t Rank = 0;
+    if (SameLine) {
+      if (L1->getAtomGroup() || L2->getAtomGroup()) {
+        // If we're preserving the same matching inlined-at field we can
+        // preserve the atom.
+        if (LocBIA == LocAIA && InlinedAt == LocBIA) {
+          // Deterministically keep the lowest non-zero ranking atom group
+          // number.
+          // FIXME: It would be nice if we could track that an instruction
+          // belongs to two source atoms.
+          bool UseL1Atom = [L1, L2]() {
+            if (L1->getAtomRank() == L2->getAtomRank()) {
+              // Arbitrarily choose the lowest non-zero group number.
+              if (!L1->getAtomGroup() || !L2->getAtomGroup())
+                return !L2->getAtomGroup();
+              return L1->getAtomGroup() < L2->getAtomGroup();
+            }
+            // Choose the lowest non-zero rank.
+            if (!L1->getAtomRank() || !L2->getAtomRank())
+              return !L2->getAtomRank();
+            return L1->getAtomRank() < L2->getAtomRank();
+          }();
+          Group = UseL1Atom ? L1->getAtomGroup() : L2->getAtomGroup();
+          Rank = UseL1Atom ? L1->getAtomRank() : L2->getAtomRank();
+        } else {
+          // If either instruction is part of a source atom, reassign it a new
+          // atom group. This essentially regresses to non-key-instructions
+          // behaviour (now that it's the only instruction in its group it'll
+          // probably get is_stmt applied).
+          Group = C.incNextAtomGroup();
+          Rank = 1;
+        }
+      }
+    }
+    return DILocation::get(C, Line, Col, Scope, InlinedAt, IsImplicitCode,
+                           Group, Rank);
   };
 
   DILocation *Result = ARIt != ALocs.rend() ? (*ARIt)->getInlinedAt() : nullptr;
@@ -370,7 +410,9 @@ DILocation *DILocation::getMergedLocation(DILocation *LocA, DILocation *LocB) {
   // historically picked A's scope, and a nullptr inlined-at location, so that
   // behavior is mimicked here but I am not sure if this is always the correct
   // way to handle this.
-  return DILocation::get(C, 0, 0, LocA->getScope(), nullptr);
+  // Key Instructions: it's fine to drop atom group and rank here, as line 0
+  // is a nonsensical is_stmt location.
+  return DILocation::get(C, 0, 0, LocA->getScope(), nullptr, false, 0, 0);
 }
 
 std::optional<unsigned>
diff --git a/llvm/unittests/IR/MetadataTest.cpp b/llvm/unittests/IR/MetadataTest.cpp
index b1a7d9966ffc4..17abef23d1842 100644
--- a/llvm/unittests/IR/MetadataTest.cpp
+++ b/llvm/unittests/IR/MetadataTest.cpp
@@ -1445,6 +1445,140 @@ TEST_F(DILocationTest, Merge) {
     auto *M2 = DILocation::getMergedLocation(A2, B);
     EXPECT_EQ(M1, M2);
   }
+
+#ifdef EXPERIMENTAL_KEY_INSTRUCTIONS
+#define EXPECT_ATOM(Loc, Group, Rank)                                          \
+  EXPECT_EQ(Group, M->getAtomGroup());                                         \
+  EXPECT_EQ(Rank, M->getAtomRank());
+#else
+#define EXPECT_ATOM(Loc, Group, Rank)                                          \
+  EXPECT_EQ(0u, M->getAtomGroup());                                            \
+  EXPECT_EQ(0u, M->getAtomRank());                                             \
+  (void)Group;                                                                 \
+  (void)Rank;
+#endif
+  // Identical, including source atom numbers.
+  {
+    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 1);
+    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 1);
+    auto *M = DILocation::getMergedLocation(A, B);
+    EXPECT_ATOM(M, 1u, 1u);
+    // DILocations are uniqued, so we can check equality by ptr.
+    EXPECT_EQ(M, DILocation::getMergedLocation(A, B));
+  }
+
+  // Identical but different atom ranks (same atom) - choose the lowest nonzero
+  // rank.
+  {
+    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 1);
+    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 2);
+    auto *M = DILocation::getMergedLocation(A, B);
+    EXPECT_ATOM(M, 1u, 1u);
+    EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
+
+    A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 0);
+    B = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 2);
+    M = DILocation::getMergedLocation(A, B);
+    EXPECT_ATOM(M, 1u, 2u);
+    EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
+  }
+
+  // Identical but different atom ranks (different atom) - choose the lowest
+  // nonzero rank.
+  {
+    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 1);
+    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, 2, 2);
+    auto *M = DILocation::getMergedLocation(A, B);
+    EXPECT_ATOM(M, 1u, 1u);
+    EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
+
+    A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 0);
+    B = DILocation::get(Context, 2, 7, N, nullptr, false, 2, 2);
+    M = DILocation::getMergedLocation(A, B);
+    EXPECT_ATOM(M, 2u, 2u);
+    EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
+  }
+
+  // Identical but equal atom rank (different atom) - choose the lowest non-zero
+  // group (arbitrary choice for deterministic behaviour).
+  {
+    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 1);
+    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, 2, 1);
+    auto *M = DILocation::getMergedLocation(A, B);
+    EXPECT_ATOM(M, 1u, 1u);
+    EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
+
+    A = DILocation::get(Context, 2, 7, N, nullptr, false, 0, 1);
+    B = DILocation::get(Context, 2, 7, N, nullptr, false, 2, 1);
+    M = DILocation::getMergedLocation(A, B);
+    EXPECT_ATOM(M, 2u, 1u);
+    EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
+  }
+
+  // Completely different except same atom numbers. Zero out the atoms.
+  {
+    auto *I = DILocation::get(Context, 2, 7, N);
+    auto *A = DILocation::get(Context, 1, 6, S, I, false, 1, 1);
+    auto *B =
+        DILocation::get(Context, 2, 7, getSubprogram(), nullptr, false, 1, 1);
+    auto *M = DILocation::getMergedLocation(A, B);
+    EXPECT_EQ(0u, M->getLine());
+    EXPECT_EQ(0u, M->getColumn());
+    EXPECT_TRUE(isa<DILocalScope>(M->getScope()));
+    EXPECT_EQ(S, M->getScope());
+    EXPECT_EQ(nullptr, M->getInlinedAt());
+  }
+
+  // Same inlined-at chain but different atoms. Choose the lowest
+  // non-zero group (arbitrary choice for deterministic behaviour).
+  {
+    auto *I = DILocation::get(Context, 1, 7, N);
+    auto *F = getSubprogram();
+    auto *A = DILocation::get(Context, 1, 1, F, I, false, 1, 2);
+    auto *B = DILocation::get(Context, 1, 1, F, I, false, 2, 1);
+    auto *M = DILocation::getMergedLocation(A, B);
+    EXPECT_ATOM(M, 2u, 1u);
+    EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
+
+    A = DILocation::get(Context, 1, 1, F, I, false, 1, 2);
+    B = DILocation::get(Context, 1, 1, F, I, false, 2, 0);
+    M = DILocation::getMergedLocation(A, B);
+    EXPECT_ATOM(M, 1u, 2u);
+    EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
+  }
+
+  // Partially equal inlined-at chain but different atoms. Generate a new atom
+  // group (if either have a group number). This configuration seems unlikely
+  // to occur as line numbers must match, but isn't impossible.
+  {
+    // Reset global counter to ensure EXPECT numbers line up.
+    Context.pImpl->NextAtomGroup = 1;
+    // x1 -> y2 -> z4
+    //       y3 -> z4
+    auto *FX = getSubprogram();
+    auto *FY = getSubprogram();
+    auto *FZ = getSubprogram();
+    auto *Z4 = DILocation::get(Context, 1, 4, FZ);
+    auto *Y3IntoZ4 = DILocation::get(Context, 1, 3, FY, Z4, false, 1, 1);
+    auto *Y2IntoZ4 = DILocation::get(Context, 1, 2, FY, Z4);
+    auto *X1IntoY2 = DILocation::get(Context, 1, 1, FX, Y2IntoZ4);
+    auto *M = DILocation::getMergedLocation(X1IntoY2, Y3IntoZ4);
+    EXPECT_EQ(M->getScope(), FY);
+    EXPECT_EQ(M->getInlinedAt()->getScope(), FZ);
+    EXPECT_ATOM(M, 2u, 1u);
+
+    // This swapped merge will produce a new atom group too.
+    M = DILocation::getMergedLocation(Y3IntoZ4, X1IntoY2);
+
+    // Same again, even if the atom numbers match.
+    auto *X1IntoY2SameAtom =
+        DILocation::get(Context, 1, 1, FX, Y2IntoZ4, false, 1, 1);
+    M = DILocation::getMergedLocation(X1IntoY2SameAtom, Y3IntoZ4);
+    EXPECT_ATOM(M, 4u, 1u);
+    M = DILocation::getMergedLocation(Y3IntoZ4, X1IntoY2SameAtom);
+    EXPECT_ATOM(M, 5u, 1u);
+  }
+#undef EXPECT_ATOM
 }
 
 TEST_F(DILocationTest, getDistinct) {

>From 9a42448ebc317df4fba1a6fc707bcd60648ddf5f Mon Sep 17 00:00:00 2001
From: Orlando Cazalet-Hyams <orlando.hyams at sony.com>
Date: Thu, 1 May 2025 15:37:59 +0100
Subject: [PATCH 2/4] param-comments and simplify lambda with early exits

---
 llvm/lib/IR/DebugInfoMetadata.cpp  | 68 ++++++++++++-----------
 llvm/unittests/IR/MetadataTest.cpp | 88 ++++++++++++++++++------------
 2 files changed, 90 insertions(+), 66 deletions(-)

diff --git a/llvm/lib/IR/DebugInfoMetadata.cpp b/llvm/lib/IR/DebugInfoMetadata.cpp
index 30ad9c11b2614..18a14eb8bf535 100644
--- a/llvm/lib/IR/DebugInfoMetadata.cpp
+++ b/llvm/lib/IR/DebugInfoMetadata.cpp
@@ -347,40 +347,43 @@ DILocation *DILocation::getMergedLocation(DILocation *LocA, DILocation *LocB) {
     unsigned Line = SameLine ? L1->getLine() : 0;
     unsigned Col = SameLine && SameCol ? L1->getColumn() : 0;
     bool IsImplicitCode = L1->isImplicitCode() && L2->isImplicitCode();
+
+    // Discard source location atom if the line becomes 0. And there's nothing
+    // further to do if neither location has an atom number.
+    if (!SameLine || !(L1->getAtomGroup() || L2->getAtomGroup()))
+      return DILocation::get(C, Line, Col, Scope, InlinedAt, IsImplicitCode,
+                             /*AtomGroup*/ 0, /*AtomRank*/ 0);
+
     uint64_t Group = 0;
     uint64_t Rank = 0;
-    if (SameLine) {
-      if (L1->getAtomGroup() || L2->getAtomGroup()) {
-        // If we're preserving the same matching inlined-at field we can
-        // preserve the atom.
-        if (LocBIA == LocAIA && InlinedAt == LocBIA) {
-          // Deterministically keep the lowest non-zero ranking atom group
-          // number.
-          // FIXME: It would be nice if we could track that an instruction
-          // belongs to two source atoms.
-          bool UseL1Atom = [L1, L2]() {
-            if (L1->getAtomRank() == L2->getAtomRank()) {
-              // Arbitrarily choose the lowest non-zero group number.
-              if (!L1->getAtomGroup() || !L2->getAtomGroup())
-                return !L2->getAtomGroup();
-              return L1->getAtomGroup() < L2->getAtomGroup();
-            }
-            // Choose the lowest non-zero rank.
-            if (!L1->getAtomRank() || !L2->getAtomRank())
-              return !L2->getAtomRank();
-            return L1->getAtomRank() < L2->getAtomRank();
-          }();
-          Group = UseL1Atom ? L1->getAtomGroup() : L2->getAtomGroup();
-          Rank = UseL1Atom ? L1->getAtomRank() : L2->getAtomRank();
-        } else {
-          // If either instruction is part of a source atom, reassign it a new
-          // atom group. This essentially regresses to non-key-instructions
-          // behaviour (now that it's the only instruction in its group it'll
-          // probably get is_stmt applied).
-          Group = C.incNextAtomGroup();
-          Rank = 1;
+    // If we're preserving the same matching inlined-at field we can
+    // preserve the atom.
+    if (LocBIA == LocAIA && InlinedAt == LocBIA) {
+      // Deterministically keep the lowest non-zero ranking atom group
+      // number.
+      // FIXME: It would be nice if we could track that an instruction
+      // belongs to two source atoms.
+      bool UseL1Atom = [L1, L2]() {
+        if (L1->getAtomRank() == L2->getAtomRank()) {
+          // Arbitrarily choose the lowest non-zero group number.
+          if (!L1->getAtomGroup() || !L2->getAtomGroup())
+            return !L2->getAtomGroup();
+          return L1->getAtomGroup() < L2->getAtomGroup();
         }
-      }
+        // Choose the lowest non-zero rank.
+        if (!L1->getAtomRank() || !L2->getAtomRank())
+          return !L2->getAtomRank();
+        return L1->getAtomRank() < L2->getAtomRank();
+      }();
+      Group = UseL1Atom ? L1->getAtomGroup() : L2->getAtomGroup();
+      Rank = UseL1Atom ? L1->getAtomRank() : L2->getAtomRank();
+    } else {
+      // If either instruction is part of a source atom, reassign it a new
+      // atom group. This essentially regresses to non-key-instructions
+      // behaviour (now that it's the only instruction in its group it'll
+      // probably get is_stmt applied).
+      Group = C.incNextDILocationAtomGroup();
+      Rank = 1;
     }
     return DILocation::get(C, Line, Col, Scope, InlinedAt, IsImplicitCode,
                            Group, Rank);
@@ -412,7 +415,8 @@ DILocation *DILocation::getMergedLocation(DILocation *LocA, DILocation *LocB) {
   // way to handle this.
   // Key Instructions: it's fine to drop atom group and rank here, as line 0
   // is a nonsensical is_stmt location.
-  return DILocation::get(C, 0, 0, LocA->getScope(), nullptr, false, 0, 0);
+  return DILocation::get(C, 0, 0, LocA->getScope(), nullptr, false,
+                         /*AtomGroup*/ 0, /*AtomRank*/ 0);
 }
 
 std::optional<unsigned>
diff --git a/llvm/unittests/IR/MetadataTest.cpp b/llvm/unittests/IR/MetadataTest.cpp
index 17abef23d1842..f9b2658568c89 100644
--- a/llvm/unittests/IR/MetadataTest.cpp
+++ b/llvm/unittests/IR/MetadataTest.cpp
@@ -1459,10 +1459,12 @@ TEST_F(DILocationTest, Merge) {
 #endif
   // Identical, including source atom numbers.
   {
-    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 1);
-    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 1);
+    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 1,
+                              /*AtomRank*/ 1);
+    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 1,
+                              /*AtomRank*/ 1);
     auto *M = DILocation::getMergedLocation(A, B);
-    EXPECT_ATOM(M, 1u, 1u);
+    EXPECT_ATOM(M, /*AtomGroup*/ 1u, 1u);
     // DILocations are uniqued, so we can check equality by ptr.
     EXPECT_EQ(M, DILocation::getMergedLocation(A, B));
   }
@@ -1470,57 +1472,70 @@ TEST_F(DILocationTest, Merge) {
   // Identical but different atom ranks (same atom) - choose the lowest nonzero
   // rank.
   {
-    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 1);
-    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 2);
+    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 1,
+                              /*AtomRank*/ 1);
+    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 1,
+                              /*AtomRank*/ 2);
     auto *M = DILocation::getMergedLocation(A, B);
-    EXPECT_ATOM(M, 1u, 1u);
+    EXPECT_ATOM(M, /*AtomGroup*/ 1u, /*AtomRank*/ 1u);
     EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
 
-    A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 0);
-    B = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 2);
+    A = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 1,
+                        /*AtomRank*/ 0);
+    B = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 1,
+                        /*AtomRank*/ 2);
     M = DILocation::getMergedLocation(A, B);
-    EXPECT_ATOM(M, 1u, 2u);
+    EXPECT_ATOM(M, /*AtomGroup*/ 1u, /*AtomRank*/ 2u);
     EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
   }
 
   // Identical but different atom ranks (different atom) - choose the lowest
   // nonzero rank.
   {
-    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 1);
-    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, 2, 2);
+    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 1,
+                              /*AtomRank*/ 1);
+    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 2,
+                              /*AtomRank*/ 2);
     auto *M = DILocation::getMergedLocation(A, B);
     EXPECT_ATOM(M, 1u, 1u);
     EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
 
-    A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 0);
-    B = DILocation::get(Context, 2, 7, N, nullptr, false, 2, 2);
+    A = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 1,
+                        /*AtomRank*/ 0);
+    B = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 2,
+                        /*AtomRank*/ 2);
     M = DILocation::getMergedLocation(A, B);
-    EXPECT_ATOM(M, 2u, 2u);
+    EXPECT_ATOM(M, /*AtomGroup*/ 2u, /*AtomRank*/ 2u);
     EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
   }
 
   // Identical but equal atom rank (different atom) - choose the lowest non-zero
   // group (arbitrary choice for deterministic behaviour).
   {
-    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, 1, 1);
-    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, 2, 1);
+    auto *A = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 1,
+                              /*AtomRank*/ 1);
+    auto *B = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 2,
+                              /*AtomRank*/ 1);
     auto *M = DILocation::getMergedLocation(A, B);
     EXPECT_ATOM(M, 1u, 1u);
     EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
 
-    A = DILocation::get(Context, 2, 7, N, nullptr, false, 0, 1);
-    B = DILocation::get(Context, 2, 7, N, nullptr, false, 2, 1);
+    A = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 0,
+                        /*AtomRank*/ 1);
+    B = DILocation::get(Context, 2, 7, N, nullptr, false, /*AtomGroup*/ 2,
+                        /*AtomRank*/ 1);
     M = DILocation::getMergedLocation(A, B);
-    EXPECT_ATOM(M, 2u, 1u);
+    EXPECT_ATOM(M, /*AtomGroup*/ 2u, /*AtomRank*/ 1u);
     EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
   }
 
   // Completely different except same atom numbers. Zero out the atoms.
   {
     auto *I = DILocation::get(Context, 2, 7, N);
-    auto *A = DILocation::get(Context, 1, 6, S, I, false, 1, 1);
-    auto *B =
-        DILocation::get(Context, 2, 7, getSubprogram(), nullptr, false, 1, 1);
+    auto *A = DILocation::get(Context, 1, 6, S, I, false, /*AtomGroup*/ 1,
+                              /*AtomRank*/ 1);
+    auto *B = DILocation::get(Context, 2, 7, getSubprogram(), nullptr, false,
+                              /*AtomGroup*/ 1, /*AtomRank*/ 1);
     auto *M = DILocation::getMergedLocation(A, B);
     EXPECT_EQ(0u, M->getLine());
     EXPECT_EQ(0u, M->getColumn());
@@ -1534,16 +1549,20 @@ TEST_F(DILocationTest, Merge) {
   {
     auto *I = DILocation::get(Context, 1, 7, N);
     auto *F = getSubprogram();
-    auto *A = DILocation::get(Context, 1, 1, F, I, false, 1, 2);
-    auto *B = DILocation::get(Context, 1, 1, F, I, false, 2, 1);
+    auto *A = DILocation::get(Context, 1, 1, F, I, false, /*AtomGroup*/ 1,
+                              /*AtomRank*/ 2);
+    auto *B = DILocation::get(Context, 1, 1, F, I, false, /*AtomGroup*/ 2,
+                              /*AtomRank*/ 1);
     auto *M = DILocation::getMergedLocation(A, B);
-    EXPECT_ATOM(M, 2u, 1u);
+    EXPECT_ATOM(M, 2u, /*AtomRank*/ 1u);
     EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
 
-    A = DILocation::get(Context, 1, 1, F, I, false, 1, 2);
-    B = DILocation::get(Context, 1, 1, F, I, false, 2, 0);
+    A = DILocation::get(Context, 1, 1, F, I, false, /*AtomGroup*/ 1,
+                        /*AtomRank*/ 2);
+    B = DILocation::get(Context, 1, 1, F, I, false, /*AtomGroup*/ 2,
+                        /*AtomRank*/ 0);
     M = DILocation::getMergedLocation(A, B);
-    EXPECT_ATOM(M, 1u, 2u);
+    EXPECT_ATOM(M, /*AtomGroup*/ 1u, /*AtomRank*/ 2u);
     EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
   }
 
@@ -1559,24 +1578,25 @@ TEST_F(DILocationTest, Merge) {
     auto *FY = getSubprogram();
     auto *FZ = getSubprogram();
     auto *Z4 = DILocation::get(Context, 1, 4, FZ);
-    auto *Y3IntoZ4 = DILocation::get(Context, 1, 3, FY, Z4, false, 1, 1);
+    auto *Y3IntoZ4 = DILocation::get(Context, 1, 3, FY, Z4, false,
+                                     /*AtomGroup*/ 1, /*AtomRank*/ 1);
     auto *Y2IntoZ4 = DILocation::get(Context, 1, 2, FY, Z4);
     auto *X1IntoY2 = DILocation::get(Context, 1, 1, FX, Y2IntoZ4);
     auto *M = DILocation::getMergedLocation(X1IntoY2, Y3IntoZ4);
     EXPECT_EQ(M->getScope(), FY);
     EXPECT_EQ(M->getInlinedAt()->getScope(), FZ);
-    EXPECT_ATOM(M, 2u, 1u);
+    EXPECT_ATOM(M, /*AtomGroup*/ 2u, /*AtomRank*/ 1u);
 
     // This swapped merge will produce a new atom group too.
     M = DILocation::getMergedLocation(Y3IntoZ4, X1IntoY2);
 
     // Same again, even if the atom numbers match.
-    auto *X1IntoY2SameAtom =
-        DILocation::get(Context, 1, 1, FX, Y2IntoZ4, false, 1, 1);
+    auto *X1IntoY2SameAtom = DILocation::get(Context, 1, 1, FX, Y2IntoZ4, false,
+                                             /*AtomGroup*/ 1, /*AtomRank*/ 1);
     M = DILocation::getMergedLocation(X1IntoY2SameAtom, Y3IntoZ4);
-    EXPECT_ATOM(M, 4u, 1u);
+    EXPECT_ATOM(M, /*AtomGroup*/ 4u, /*AtomRank*/ 1u);
     M = DILocation::getMergedLocation(Y3IntoZ4, X1IntoY2SameAtom);
-    EXPECT_ATOM(M, 5u, 1u);
+    EXPECT_ATOM(M, /*AtomGroup*/ 5u, /*AtomRank*/ 1u);
   }
 #undef EXPECT_ATOM
 }

>From efbffe41911de304ed81c629b11c2c159a618fb0 Mon Sep 17 00:00:00 2001
From: Orlando Cazalet-Hyams <orlando.hyams at sony.com>
Date: Thu, 1 May 2025 15:42:16 +0100
Subject: [PATCH 3/4] use new function names

---
 llvm/lib/Transforms/Utils/CloneFunction.cpp | 2 +-
 llvm/unittests/IR/MetadataTest.cpp          | 6 +++---
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/llvm/lib/Transforms/Utils/CloneFunction.cpp b/llvm/lib/Transforms/Utils/CloneFunction.cpp
index 139c689126d94..7b3e0729f5a74 100644
--- a/llvm/lib/Transforms/Utils/CloneFunction.cpp
+++ b/llvm/lib/Transforms/Utils/CloneFunction.cpp
@@ -55,7 +55,7 @@ void llvm::mapAtomInstance(const DebugLoc &DL, ValueToValueMapTy &VMap) {
     return;
 
   // Map entry to a new atom group.
-  uint64_t NewGroup = DL->getContext().incNextAtomGroup();
+  uint64_t NewGroup = DL->getContext().incNextDILocationAtomGroup();
   assert(NewGroup > CurGroup && "Next should always be greater than current");
   It->second = NewGroup;
 
diff --git a/llvm/unittests/IR/MetadataTest.cpp b/llvm/unittests/IR/MetadataTest.cpp
index f9b2658568c89..a17a07074b621 100644
--- a/llvm/unittests/IR/MetadataTest.cpp
+++ b/llvm/unittests/IR/MetadataTest.cpp
@@ -1753,12 +1753,12 @@ TEST_F(DILocationTest, KeyInstructions) {
   EXPECT_EQ(Context.pImpl->NextAtomGroup, 6u);
 
   // Check the waterline gets incremented by 1.
-  EXPECT_EQ(Context.incNextAtomGroup(), 6u);
+  EXPECT_EQ(Context.incNextDILocationAtomGroup(), 6u);
   EXPECT_EQ(Context.pImpl->NextAtomGroup, 7u);
 
-  Context.updateAtomGroupWaterline(8);
+  Context.updateDILocationAtomGroupWaterline(8);
   EXPECT_EQ(Context.pImpl->NextAtomGroup, 8u);
-  Context.updateAtomGroupWaterline(7);
+  Context.updateDILocationAtomGroupWaterline(7);
   EXPECT_EQ(Context.pImpl->NextAtomGroup, 8u);
 }
 

>From 1353653a82713b49630f9f257b670b74422cd3b1 Mon Sep 17 00:00:00 2001
From: Orlando Cazalet-Hyams <orlando.hyams at sony.com>
Date: Thu, 1 May 2025 15:59:54 +0100
Subject: [PATCH 4/4] fix unittest

---
 llvm/unittests/IR/MetadataTest.cpp | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/llvm/unittests/IR/MetadataTest.cpp b/llvm/unittests/IR/MetadataTest.cpp
index a17a07074b621..f9f2e6f47cf7a 100644
--- a/llvm/unittests/IR/MetadataTest.cpp
+++ b/llvm/unittests/IR/MetadataTest.cpp
@@ -1552,9 +1552,9 @@ TEST_F(DILocationTest, Merge) {
     auto *A = DILocation::get(Context, 1, 1, F, I, false, /*AtomGroup*/ 1,
                               /*AtomRank*/ 2);
     auto *B = DILocation::get(Context, 1, 1, F, I, false, /*AtomGroup*/ 2,
-                              /*AtomRank*/ 1);
+                              /*AtomRank*/ 2);
     auto *M = DILocation::getMergedLocation(A, B);
-    EXPECT_ATOM(M, 2u, /*AtomRank*/ 1u);
+    EXPECT_ATOM(M, /*AtomGroup*/ 1u, /*AtomRank*/ 2u);
     EXPECT_EQ(M, DILocation::getMergedLocation(B, A));
 
     A = DILocation::get(Context, 1, 1, F, I, false, /*AtomGroup*/ 1,



More information about the llvm-branch-commits mailing list