[llvm] [CGData][MachineOutliner] Global Outlining (PR #90074)

Ellis Hoag via llvm-commits llvm-commits at lists.llvm.org
Thu Sep 5 12:05:34 PDT 2024


================
@@ -585,6 +644,107 @@ void MachineOutliner::emitOutlinedFunctionRemark(OutlinedFunction &OF) {
   MORE.emit(R);
 }
 
+struct MatchedEntry {
+  size_t StartIdx;
+  size_t Length;
+  size_t Count;
+};
+
+static const HashNode *followHashNode(stable_hash StableHash,
+                                      const HashNode *Current) {
+  auto I = Current->Successors.find(StableHash);
+  return (I == Current->Successors.end()) ? nullptr : I->second.get();
+}
+
+// Find all matches in the global outlined hash tree.
+// It's quadratic complexity in theory, but it's nearly linear in practice
+// since the length of outlined sequences are small within a block.
+static std::vector<MatchedEntry> getMatchedEntries(InstructionMapper &Mapper) {
+  auto &InstrList = Mapper.InstrList;
+  auto &UnsignedVec = Mapper.UnsignedVec;
+
+  std::vector<MatchedEntry> MatchedEntries;
+  auto Size = UnsignedVec.size();
+
+  // Get the global outlined hash tree built from the previous run.
+  assert(cgdata::hasOutlinedHashTree());
+  const auto *RootNode = cgdata::getOutlinedHashTree()->getRoot();
+  for (size_t I = 0; I < Size; ++I) {
+    // Skip the invalid mapping.
+    if (UnsignedVec[I] >= Mapper.LegalInstrNumber)
+      continue;
+    const MachineInstr &MI = *InstrList[I];
+    // Skip debug instructions as we did for the outlined function.
+    if (MI.isDebugInstr())
+      continue;
+    // Skip the empty hash value.
+    stable_hash StableHashI = stableHashValue(MI);
+    if (!StableHashI)
+      continue;
+
+    const HashNode *LastNode = followHashNode(StableHashI, RootNode);
+    if (!LastNode)
+      continue;
+
+    size_t J = I + 1;
+    for (; J < Size; ++J) {
+      // Break on the invalid mapping.
+      if (UnsignedVec[J] >= Mapper.LegalInstrNumber)
+        break;
+      // Skip debug instructions as we did for the outlined function.
+      const MachineInstr &MJ = *InstrList[J];
+      if (MJ.isDebugInstr())
+        continue;
+      // Break on the empty hash value.
+      stable_hash StableHashJ = stableHashValue(MJ);
+      if (!StableHashJ)
+        break;
+      LastNode = followHashNode(StableHashJ, LastNode);
+      if (!LastNode)
+        break;
----------------
ellishg wrote:

This code seems to be nearly identical to the code above. Should we factor this out into a helper function that returns `LastNode`?

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


More information about the llvm-commits mailing list