[llvm] [Hexagon] Add Hexagon Copy Hoisting pass (PR #89313)

Perry MacMurray via llvm-commits llvm-commits at lists.llvm.org
Mon Apr 22 15:03:54 PDT 2024


https://github.com/quic-pmacmurr updated https://github.com/llvm/llvm-project/pull/89313

>From cb4721804738b89f2d1fc0b771d7747626b59c60 Mon Sep 17 00:00:00 2001
From: Perry MacMurray <pmacmurr at quicinc.com>
Date: Thu, 4 Apr 2024 19:27:46 -0700
Subject: [PATCH 1/5] [Hexagon] Add Hexagon Copy Hoisting pass

The purpose of this pass is to move the common copy instructions that
are present in all the successor of a basic block (BB) to the end of BB.

Co-authored-by: Jyotsna Verma <jverma at quicinc.com>
---
 llvm/lib/Target/Hexagon/CMakeLists.txt        |   1 +
 .../Target/Hexagon/HexagonCopyHoisting.cpp    | 294 ++++++++++++++++++
 .../Target/Hexagon/HexagonTargetMachine.cpp   |  10 +
 .../CodeGen/Hexagon/hexagon-copy-hoisting.mir |  53 ++++
 4 files changed, 358 insertions(+)
 create mode 100644 llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
 create mode 100644 llvm/test/CodeGen/Hexagon/hexagon-copy-hoisting.mir

diff --git a/llvm/lib/Target/Hexagon/CMakeLists.txt b/llvm/lib/Target/Hexagon/CMakeLists.txt
index cdc062eee72b1e..9e4ca08aea40da 100644
--- a/llvm/lib/Target/Hexagon/CMakeLists.txt
+++ b/llvm/lib/Target/Hexagon/CMakeLists.txt
@@ -26,6 +26,7 @@ add_llvm_target(HexagonCodeGen
   HexagonCommonGEP.cpp
   HexagonConstExtenders.cpp
   HexagonConstPropagation.cpp
+  HexagonCopyHoisting.cpp
   HexagonCopyToCombine.cpp
   HexagonEarlyIfConv.cpp
   HexagonExpandCondsets.cpp
diff --git a/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp b/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
new file mode 100644
index 00000000000000..0b25b9259f082e
--- /dev/null
+++ b/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
@@ -0,0 +1,294 @@
+//===--------- HexagonCopyHoisting.cpp - Hexagon Copy Hoisting  ----------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+// The purpose of this pass is to move the copy instructions that are
+// present in all the successor of a basic block (BB) to the end of BB.
+//===----------------------------------------------------------------------===//
+
+#include "llvm/ADT/PostOrderIterator.h"
+#include "llvm/ADT/PostOrderIterator.h"
+#include "llvm/ADT/StringMap.h"
+#include "llvm/ADT/StringRef.h"
+#include "llvm/ADT/SmallString.h"
+#include "llvm/ADT/Twine.h"
+#include "llvm/CodeGen/LiveInterval.h"
+#include "llvm/CodeGen/LiveIntervals.h"
+#include "llvm/CodeGen/MachineInstrBuilder.h"
+#include "llvm/CodeGen/MachineDominators.h"
+#include "llvm/CodeGen/MachineRegisterInfo.h"
+#include "llvm/Support/Debug.h"
+#include "llvm/Support/CommandLine.h"
+#include "HexagonTargetMachine.h"
+
+#define DEBUG_TYPE "CopyHoist"
+
+using namespace llvm;
+
+static cl::opt<std::string> CPHoistFn("cphoistfn", cl::Hidden, cl::desc(""),
+                                      cl::init(""));
+
+namespace llvm {
+  void initializeHexagonCopyHoistingPass(PassRegistry& Registry);
+  FunctionPass *createHexagonCopyHoisting();
+}
+
+namespace {
+
+class HexagonCopyHoisting : public MachineFunctionPass {
+
+public:
+  static char ID;
+  HexagonCopyHoisting()
+      : MachineFunctionPass(ID), MFN(0), MRI(0) {
+    initializeHexagonCopyHoistingPass(*PassRegistry::getPassRegistry());
+  }
+
+  StringRef getPassName() const override {
+    return "Hexagon Copy Hoisting";
+  }
+
+  void getAnalysisUsage(AnalysisUsage &AU) const override {
+    AU.addRequired<SlotIndexes>();
+    AU.addRequired<LiveIntervals>();
+    AU.addPreserved<SlotIndexes>();
+    AU.addPreserved<LiveIntervals>();
+    AU.addRequired<MachineDominatorTree>();
+    AU.addPreserved<MachineDominatorTree>();
+    MachineFunctionPass::getAnalysisUsage(AU);
+  }
+
+  bool runOnMachineFunction(MachineFunction &Fn) override;
+  void collectCopyInst();
+  void addMItoCopyList(MachineInstr *MI);
+  bool analyzeCopy(MachineBasicBlock *BB);
+  bool isSafetoMove(MachineInstr *CandMI);
+  void moveCopyInstr(MachineBasicBlock *DestBB, StringRef key,
+                     MachineInstr *MI);
+
+  MachineFunction *MFN;
+  MachineRegisterInfo *MRI;
+  StringMap<MachineInstr*> CopyMI;
+  std::vector<StringMap<MachineInstr*> > CopyMIList;
+};
+
+}
+
+char HexagonCopyHoisting::ID = 0;
+
+namespace llvm {
+  char &HexagonCopyHoistingID = HexagonCopyHoisting::ID;
+}
+
+bool HexagonCopyHoisting::runOnMachineFunction(MachineFunction &Fn) {
+
+  if ((CPHoistFn != "") && (CPHoistFn != Fn.getFunction().getName()))
+    return false;
+
+  MFN = &Fn;
+  MRI = &Fn.getRegInfo();
+
+  LLVM_DEBUG(dbgs() << "\nCopy Hoisting:"
+                    << "\'" << Fn.getName() << "\'\n");
+
+  CopyMIList.clear();
+  CopyMIList.resize(Fn.getNumBlockIDs());
+
+  // Traverse through all basic blocks and collect copy instructions.
+  collectCopyInst();
+
+  // Traverse through the basic blocks again and move the COPY instructions
+  // that are present in all the successors of BB to BB.
+  bool changed = false;
+  for (auto I = po_begin(&Fn), E = po_end(&Fn); I != E; ++I) {
+    MachineBasicBlock &BB = **I;
+    if (!BB.empty()) {
+      if (BB.pred_size() != 1)//
+        continue;
+      auto &BBCopyInst = CopyMIList[BB.getNumber()];
+      if (BBCopyInst.size() > 0)
+        changed |= analyzeCopy(*BB.pred_begin());
+    }
+  }
+  // Re-compute liveness
+  if (changed) {
+    LiveIntervals &LIS = getAnalysis<LiveIntervals>();
+    SlotIndexes *SI = LIS.getSlotIndexes();
+    SI->releaseMemory();
+    SI->runOnMachineFunction(Fn);
+    LIS.releaseMemory();
+    LIS.runOnMachineFunction(Fn);
+  }
+  return changed;
+}
+
+//===----------------------------------------------------------------------===//
+// Save all COPY instructions for each basic block in CopyMIList vector.
+//===----------------------------------------------------------------------===//
+void HexagonCopyHoisting::collectCopyInst() {
+  for (auto BI = MFN->begin(), BE = MFN->end(); BI != BE; ++BI) {
+    MachineBasicBlock *BB = &*BI;
+#ifndef NDEBUG
+    auto &BBCopyInst = CopyMIList[BB->getNumber()];
+    LLVM_DEBUG(dbgs() << "Visiting BB#" << BB->getNumber() << ":\n");
+#endif
+
+    for (auto MII = BB->begin(), MIE = BB->end(); MII != MIE; ++MII) {
+      MachineInstr *MI = &*MII;
+      if (MI->getOpcode() == TargetOpcode::COPY )
+        addMItoCopyList(MI);
+    }
+    LLVM_DEBUG(dbgs() << "\tNumber of copies: " << BBCopyInst.size() << "\n");
+  }
+}
+
+void HexagonCopyHoisting::addMItoCopyList(MachineInstr *MI) {
+  unsigned BBNum = MI->getParent()->getNumber();
+  auto &BBCopyInst = CopyMIList[BBNum];
+  unsigned DstReg = MI->getOperand(0).getReg();
+  unsigned SrcReg = MI->getOperand(1).getReg();
+
+  if (!Register::isVirtualRegister(DstReg) ||
+      !Register::isVirtualRegister(SrcReg) ||
+      MRI->getRegClass(DstReg) != &Hexagon::IntRegsRegClass ||
+      MRI->getRegClass(SrcReg) != &Hexagon::IntRegsRegClass)
+    return;
+
+  StringRef key;
+  SmallString<256> TmpData("");
+  (void)Twine(Register::virtReg2Index(DstReg)).toStringRef(TmpData);
+  TmpData+='=';
+  key = Twine(Register::virtReg2Index(SrcReg)).toStringRef(TmpData);
+  BBCopyInst[key]=MI;
+#ifndef NDEBUG
+  LLVM_DEBUG(dbgs() << "\tAdding Copy Instr to the list: " << MI << "\n");
+  for (auto II = BBCopyInst.begin(), IE = BBCopyInst.end(); II != IE; ++II) {
+    MachineInstr *TempMI = (*II).getValue();
+    LLVM_DEBUG(dbgs() << "\tIn the list: " << TempMI << "\n");
+  }
+#endif
+}
+
+//===----------------------------------------------------------------------===//
+// Look at the COPY instructions of all the successors of BB. If the same
+// instruction is present in every successor and can be safely moved,
+// pull it into BB.
+//===----------------------------------------------------------------------===//
+bool HexagonCopyHoisting::analyzeCopy(MachineBasicBlock *BB) {
+
+  bool changed = false;
+  if (BB->succ_size() < 2 )
+    return false;
+
+  for (auto I = BB->succ_begin(), E = BB->succ_end(); I != E; ++I) {
+    MachineBasicBlock *SB = *I;
+    if (SB->pred_size() != 1 || SB->isEHPad() || SB->hasAddressTaken())
+      return false;
+  }
+
+  auto SuccI = BB->succ_begin(), SuccE = BB->succ_end();
+
+  MachineBasicBlock *SBB1 = *SuccI;
+  ++SuccI;
+  auto &BBCopyInst1 = CopyMIList[SBB1->getNumber()];
+
+  for ( auto II = BBCopyInst1.begin(), IE = BBCopyInst1.end(); II != IE; ++II) {
+    StringRef key = (*II).getKeyData();
+    MachineInstr *MI = (*II).getValue();
+    bool IsSafetoMove = true;
+    for (SuccI = BB->succ_begin(); SuccI != SuccE; ++SuccI) {
+      MachineBasicBlock *SuccBB = *SuccI;
+      auto &SuccBBCopyInst = CopyMIList[SuccBB->getNumber()];
+      if (!SuccBBCopyInst.count(key)) {
+        // Same copy not present in this successor
+        IsSafetoMove = false;
+        break;
+      }
+      // If present, make sure that it's safe to pull this copy instruction
+      // into the predecessor.
+      MachineInstr *SuccMI = SuccBBCopyInst[key];
+      if (!isSafetoMove(SuccMI)) {
+        IsSafetoMove = false;
+        break;
+      }
+    }
+    // If we have come this far, this copy instruction can be safely
+    // moved to the predecessor basic block.
+    if (IsSafetoMove) {
+      LLVM_DEBUG(dbgs() << "\t\t Moving instr to BB#" << BB->getNumber() << ": "
+                        << MI << "\n");
+      moveCopyInstr(BB, key, MI);
+      // Add my into BB copyMI list.
+      changed = true;
+    }
+  }
+
+#ifndef NDEBUG
+  auto &BBCopyInst = CopyMIList[BB->getNumber()];
+  for ( auto II = BBCopyInst.begin(), IE = BBCopyInst.end(); II != IE; ++II) {
+    MachineInstr *TempMI = (*II).getValue();
+    LLVM_DEBUG(dbgs() << "\tIn the list: " << TempMI << "\n");
+  }
+#endif
+  return changed;
+}
+
+bool HexagonCopyHoisting::isSafetoMove(MachineInstr *CandMI) {
+// Make sure that it's safe to move this 'copy' instruction to the predecessor
+// basic block.
+  assert(CandMI->getOperand(0).isReg() && CandMI->getOperand(1).isReg());
+  unsigned DefR = CandMI->getOperand(0).getReg();
+  unsigned UseR = CandMI->getOperand(1).getReg();
+
+  MachineBasicBlock *BB = CandMI->getParent();
+  // There should not be a def/use of DefR between the start of BB and CandMI.
+  MachineBasicBlock::iterator MII, MIE;
+  for (MII = BB->begin(), MIE = CandMI; MII != MIE;  ++MII) {
+    MachineInstr *otherMI =  &*MII;
+    for (MachineInstr::mop_iterator Mo = otherMI->operands_begin(),
+           E = otherMI->operands_end(); Mo != E; ++Mo)
+      if (Mo->isReg() && Mo->getReg() == DefR)
+        return false;
+  }
+  // There should not be a def of UseR between the start of BB and CandMI.
+  for (MII = BB->begin(), MIE = CandMI; MII != MIE;  ++MII) {
+    MachineInstr *otherMI = &*MII;
+    for (MachineInstr::mop_iterator Mo = otherMI->operands_begin(),
+           E = otherMI->operands_end(); Mo != E; ++Mo)
+      if (Mo->isReg() && Mo->isDef() && Mo->getReg() == UseR)
+        return false;
+  }
+  return true;
+}
+
+void HexagonCopyHoisting::moveCopyInstr(MachineBasicBlock *DestBB,
+                                       StringRef key, MachineInstr *MI) {
+  MachineBasicBlock::iterator FirstTI = DestBB->getFirstTerminator();
+  assert(FirstTI != DestBB->end());
+
+  DestBB->splice(FirstTI, MI->getParent(), MI);
+
+  addMItoCopyList(MI);
+  auto I = ++(DestBB->succ_begin()), E = DestBB->succ_end();
+  for (; I != E; ++I) {
+    MachineBasicBlock *SuccBB = *I;
+    auto &BBCopyInst = CopyMIList[SuccBB->getNumber()];
+    MachineInstr *SuccMI = BBCopyInst[key];
+    SuccMI->eraseFromParent();
+    BBCopyInst.erase(key);
+  }
+}
+
+//===----------------------------------------------------------------------===//
+//                         Public Constructor Functions
+//===----------------------------------------------------------------------===//
+
+INITIALIZE_PASS(HexagonCopyHoisting, "hexagon-move-phicopy",
+    "Hexagon move phi copy", false, false)
+
+FunctionPass* llvm::createHexagonCopyHoisting() {
+  return new HexagonCopyHoisting();
+}
diff --git a/llvm/lib/Target/Hexagon/HexagonTargetMachine.cpp b/llvm/lib/Target/Hexagon/HexagonTargetMachine.cpp
index e64d7e52a9aa9b..8e5fe6dd61b834 100644
--- a/llvm/lib/Target/Hexagon/HexagonTargetMachine.cpp
+++ b/llvm/lib/Target/Hexagon/HexagonTargetMachine.cpp
@@ -72,6 +72,10 @@ static cl::opt<bool> EnableTfrCleanup("hexagon-tfr-cleanup", cl::init(true),
 static cl::opt<bool> EnableEarlyIf("hexagon-eif", cl::init(true), cl::Hidden,
                                    cl::desc("Enable early if-conversion"));
 
+static cl::opt<bool> EnableCopyHoist("hexagon-copy-hoist", cl::init(true),
+                                     cl::Hidden, cl::ZeroOrMore,
+                                     cl::desc("Enable Hexagon copy hoisting"));
+
 static cl::opt<bool> EnableGenInsert("hexagon-insert", cl::init(true),
   cl::Hidden, cl::desc("Generate \"insert\" instructions"));
 
@@ -152,9 +156,11 @@ SchedCustomRegistry("hexagon", "Run Hexagon's custom scheduler",
                     createVLIWMachineSched);
 
 namespace llvm {
+  extern char &HexagonCopyHoistingID;
   extern char &HexagonExpandCondsetsID;
   extern char &HexagonTfrCleanupID;
   void initializeHexagonBitSimplifyPass(PassRegistry&);
+  void initializeHexagonCopyHoistingPass(PassRegistry&);
   void initializeHexagonConstExtendersPass(PassRegistry&);
   void initializeHexagonConstPropagationPass(PassRegistry&);
   void initializeHexagonCopyToCombinePass(PassRegistry&);
@@ -184,6 +190,7 @@ namespace llvm {
   FunctionPass *createHexagonCommonGEP();
   FunctionPass *createHexagonConstExtenders();
   FunctionPass *createHexagonConstPropagationPass();
+  FunctionPass *createHexagonCopyHoisting();
   FunctionPass *createHexagonCopyToCombine();
   FunctionPass *createHexagonEarlyIfConversion();
   FunctionPass *createHexagonFixupHwLoops();
@@ -260,6 +267,7 @@ HexagonTargetMachine::HexagonTargetMachine(const Target &T, const Triple &TT,
           (HexagonNoOpt ? CodeGenOptLevel::None : OL)),
       TLOF(std::make_unique<HexagonTargetObjectFile>()),
       Subtarget(Triple(TT), CPU, FS, *this) {
+  initializeHexagonCopyHoistingPass(*PassRegistry::getPassRegistry());
   initializeHexagonExpandCondsetsPass(*PassRegistry::getPassRegistry());
   initializeHexagonLoopAlignPass(*PassRegistry::getPassRegistry());
   initializeHexagonTfrCleanupPass(*PassRegistry::getPassRegistry());
@@ -433,6 +441,8 @@ void HexagonPassConfig::addPreRegAlloc() {
       addPass(createHexagonConstExtenders());
     if (EnableExpandCondsets)
       insertPass(&RegisterCoalescerID, &HexagonExpandCondsetsID);
+    if (EnableCopyHoist)
+      insertPass(&RegisterCoalescerID, &HexagonCopyHoistingID);
     if (EnableTfrCleanup)
       insertPass(&VirtRegRewriterID, &HexagonTfrCleanupID);
     if (!DisableStoreWidening)
diff --git a/llvm/test/CodeGen/Hexagon/hexagon-copy-hoisting.mir b/llvm/test/CodeGen/Hexagon/hexagon-copy-hoisting.mir
new file mode 100644
index 00000000000000..0836cac7f9134f
--- /dev/null
+++ b/llvm/test/CodeGen/Hexagon/hexagon-copy-hoisting.mir
@@ -0,0 +1,53 @@
+# RUN: llc -march=hexagon -run-pass hexagon-move-phicopy -o - %s | FileCheck %s
+
+# CHECK-COUNT-1: %4:intregs = COPY %1
+
+# CHECK: bb.1
+# CHECK-NOT: %4:intregs = COPY %1
+
+# CHECK: bb.2
+# CHECK-NOT: %4:intregs = COPY %1
+# CHECK: %5:intregs = COPY %0
+
+---
+name:            f0
+tracksRegLiveness: true
+registers:
+  - { id: 0, class: intregs, preferred-register: '' }
+  - { id: 1, class: intregs, preferred-register: '' }
+  - { id: 2, class: predregs, preferred-register: '' }
+  - { id: 3, class: predregs, preferred-register: '' }
+  - { id: 4, class: intregs, preferred-register: '' }
+  - { id: 5, class: intregs, preferred-register: '' }
+liveins:
+  - { reg: '$r0', virtual-reg: '%0' }
+  - { reg: '$r1', virtual-reg: '%1' }
+stack:
+  - { id: 0, offset: 0, size: 4, alignment: 8 }
+body: |
+  bb.0:
+    successors: %bb.1, %bb.2
+    liveins: $r0, $r1
+
+    %1:intregs = COPY $r1
+    %0:intregs = COPY $r0
+    %2:predregs = C2_cmpgt %0, %1
+    %3:predregs = C2_not %2
+    J2_jumpt %3, %bb.2, implicit-def dead $pc
+    J2_jump %bb.1, implicit-def dead $pc
+
+  bb.1:
+    successors: %bb.0
+
+    %4:intregs = COPY %1
+    $r1 = COPY %4
+    J2_jump %bb.0, implicit-def dead $pc
+
+  bb.2:
+    successors: %bb.0
+
+    %4:intregs = COPY %1
+    %5:intregs = COPY %0
+    $r1 = COPY %4
+    J2_jump %bb.0, implicit-def dead $pc
+...

>From d287ada1ac288948e08cd83f77291bab9cc1c56a Mon Sep 17 00:00:00 2001
From: Perry MacMurray <pmacmurr at quicinc.com>
Date: Thu, 18 Apr 2024 22:00:25 -0700
Subject: [PATCH 2/5] Apply clang-format

---
 .../Target/Hexagon/HexagonCopyHoisting.cpp    |  66 +++----
 .../Target/Hexagon/HexagonTargetMachine.cpp   | 183 +++++++++---------
 2 files changed, 127 insertions(+), 122 deletions(-)

diff --git a/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp b/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
index 0b25b9259f082e..631ae4379387e9 100644
--- a/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
+++ b/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
@@ -9,20 +9,19 @@
 // present in all the successor of a basic block (BB) to the end of BB.
 //===----------------------------------------------------------------------===//
 
+#include "HexagonTargetMachine.h"
 #include "llvm/ADT/PostOrderIterator.h"
-#include "llvm/ADT/PostOrderIterator.h"
+#include "llvm/ADT/SmallString.h"
 #include "llvm/ADT/StringMap.h"
 #include "llvm/ADT/StringRef.h"
-#include "llvm/ADT/SmallString.h"
 #include "llvm/ADT/Twine.h"
 #include "llvm/CodeGen/LiveInterval.h"
 #include "llvm/CodeGen/LiveIntervals.h"
-#include "llvm/CodeGen/MachineInstrBuilder.h"
 #include "llvm/CodeGen/MachineDominators.h"
+#include "llvm/CodeGen/MachineInstrBuilder.h"
 #include "llvm/CodeGen/MachineRegisterInfo.h"
-#include "llvm/Support/Debug.h"
 #include "llvm/Support/CommandLine.h"
-#include "HexagonTargetMachine.h"
+#include "llvm/Support/Debug.h"
 
 #define DEBUG_TYPE "CopyHoist"
 
@@ -32,9 +31,9 @@ static cl::opt<std::string> CPHoistFn("cphoistfn", cl::Hidden, cl::desc(""),
                                       cl::init(""));
 
 namespace llvm {
-  void initializeHexagonCopyHoistingPass(PassRegistry& Registry);
-  FunctionPass *createHexagonCopyHoisting();
-}
+void initializeHexagonCopyHoistingPass(PassRegistry &Registry);
+FunctionPass *createHexagonCopyHoisting();
+} // namespace llvm
 
 namespace {
 
@@ -42,14 +41,11 @@ class HexagonCopyHoisting : public MachineFunctionPass {
 
 public:
   static char ID;
-  HexagonCopyHoisting()
-      : MachineFunctionPass(ID), MFN(0), MRI(0) {
+  HexagonCopyHoisting() : MachineFunctionPass(ID), MFN(0), MRI(0) {
     initializeHexagonCopyHoistingPass(*PassRegistry::getPassRegistry());
   }
 
-  StringRef getPassName() const override {
-    return "Hexagon Copy Hoisting";
-  }
+  StringRef getPassName() const override { return "Hexagon Copy Hoisting"; }
 
   void getAnalysisUsage(AnalysisUsage &AU) const override {
     AU.addRequired<SlotIndexes>();
@@ -71,16 +67,16 @@ class HexagonCopyHoisting : public MachineFunctionPass {
 
   MachineFunction *MFN;
   MachineRegisterInfo *MRI;
-  StringMap<MachineInstr*> CopyMI;
-  std::vector<StringMap<MachineInstr*> > CopyMIList;
+  StringMap<MachineInstr *> CopyMI;
+  std::vector<StringMap<MachineInstr *>> CopyMIList;
 };
 
-}
+} // namespace
 
 char HexagonCopyHoisting::ID = 0;
 
 namespace llvm {
-  char &HexagonCopyHoistingID = HexagonCopyHoisting::ID;
+char &HexagonCopyHoistingID = HexagonCopyHoisting::ID;
 }
 
 bool HexagonCopyHoisting::runOnMachineFunction(MachineFunction &Fn) {
@@ -106,7 +102,7 @@ bool HexagonCopyHoisting::runOnMachineFunction(MachineFunction &Fn) {
   for (auto I = po_begin(&Fn), E = po_end(&Fn); I != E; ++I) {
     MachineBasicBlock &BB = **I;
     if (!BB.empty()) {
-      if (BB.pred_size() != 1)//
+      if (BB.pred_size() != 1) //
         continue;
       auto &BBCopyInst = CopyMIList[BB.getNumber()];
       if (BBCopyInst.size() > 0)
@@ -138,7 +134,7 @@ void HexagonCopyHoisting::collectCopyInst() {
 
     for (auto MII = BB->begin(), MIE = BB->end(); MII != MIE; ++MII) {
       MachineInstr *MI = &*MII;
-      if (MI->getOpcode() == TargetOpcode::COPY )
+      if (MI->getOpcode() == TargetOpcode::COPY)
         addMItoCopyList(MI);
     }
     LLVM_DEBUG(dbgs() << "\tNumber of copies: " << BBCopyInst.size() << "\n");
@@ -160,9 +156,9 @@ void HexagonCopyHoisting::addMItoCopyList(MachineInstr *MI) {
   StringRef key;
   SmallString<256> TmpData("");
   (void)Twine(Register::virtReg2Index(DstReg)).toStringRef(TmpData);
-  TmpData+='=';
+  TmpData += '=';
   key = Twine(Register::virtReg2Index(SrcReg)).toStringRef(TmpData);
-  BBCopyInst[key]=MI;
+  BBCopyInst[key] = MI;
 #ifndef NDEBUG
   LLVM_DEBUG(dbgs() << "\tAdding Copy Instr to the list: " << MI << "\n");
   for (auto II = BBCopyInst.begin(), IE = BBCopyInst.end(); II != IE; ++II) {
@@ -180,7 +176,7 @@ void HexagonCopyHoisting::addMItoCopyList(MachineInstr *MI) {
 bool HexagonCopyHoisting::analyzeCopy(MachineBasicBlock *BB) {
 
   bool changed = false;
-  if (BB->succ_size() < 2 )
+  if (BB->succ_size() < 2)
     return false;
 
   for (auto I = BB->succ_begin(), E = BB->succ_end(); I != E; ++I) {
@@ -195,7 +191,7 @@ bool HexagonCopyHoisting::analyzeCopy(MachineBasicBlock *BB) {
   ++SuccI;
   auto &BBCopyInst1 = CopyMIList[SBB1->getNumber()];
 
-  for ( auto II = BBCopyInst1.begin(), IE = BBCopyInst1.end(); II != IE; ++II) {
+  for (auto II = BBCopyInst1.begin(), IE = BBCopyInst1.end(); II != IE; ++II) {
     StringRef key = (*II).getKeyData();
     MachineInstr *MI = (*II).getValue();
     bool IsSafetoMove = true;
@@ -228,7 +224,7 @@ bool HexagonCopyHoisting::analyzeCopy(MachineBasicBlock *BB) {
 
 #ifndef NDEBUG
   auto &BBCopyInst = CopyMIList[BB->getNumber()];
-  for ( auto II = BBCopyInst.begin(), IE = BBCopyInst.end(); II != IE; ++II) {
+  for (auto II = BBCopyInst.begin(), IE = BBCopyInst.end(); II != IE; ++II) {
     MachineInstr *TempMI = (*II).getValue();
     LLVM_DEBUG(dbgs() << "\tIn the list: " << TempMI << "\n");
   }
@@ -237,8 +233,8 @@ bool HexagonCopyHoisting::analyzeCopy(MachineBasicBlock *BB) {
 }
 
 bool HexagonCopyHoisting::isSafetoMove(MachineInstr *CandMI) {
-// Make sure that it's safe to move this 'copy' instruction to the predecessor
-// basic block.
+  // Make sure that it's safe to move this 'copy' instruction to the predecessor
+  // basic block.
   assert(CandMI->getOperand(0).isReg() && CandMI->getOperand(1).isReg());
   unsigned DefR = CandMI->getOperand(0).getReg();
   unsigned UseR = CandMI->getOperand(1).getReg();
@@ -246,18 +242,20 @@ bool HexagonCopyHoisting::isSafetoMove(MachineInstr *CandMI) {
   MachineBasicBlock *BB = CandMI->getParent();
   // There should not be a def/use of DefR between the start of BB and CandMI.
   MachineBasicBlock::iterator MII, MIE;
-  for (MII = BB->begin(), MIE = CandMI; MII != MIE;  ++MII) {
-    MachineInstr *otherMI =  &*MII;
+  for (MII = BB->begin(), MIE = CandMI; MII != MIE; ++MII) {
+    MachineInstr *otherMI = &*MII;
     for (MachineInstr::mop_iterator Mo = otherMI->operands_begin(),
-           E = otherMI->operands_end(); Mo != E; ++Mo)
+                                    E = otherMI->operands_end();
+         Mo != E; ++Mo)
       if (Mo->isReg() && Mo->getReg() == DefR)
         return false;
   }
   // There should not be a def of UseR between the start of BB and CandMI.
-  for (MII = BB->begin(), MIE = CandMI; MII != MIE;  ++MII) {
+  for (MII = BB->begin(), MIE = CandMI; MII != MIE; ++MII) {
     MachineInstr *otherMI = &*MII;
     for (MachineInstr::mop_iterator Mo = otherMI->operands_begin(),
-           E = otherMI->operands_end(); Mo != E; ++Mo)
+                                    E = otherMI->operands_end();
+         Mo != E; ++Mo)
       if (Mo->isReg() && Mo->isDef() && Mo->getReg() == UseR)
         return false;
   }
@@ -265,7 +263,7 @@ bool HexagonCopyHoisting::isSafetoMove(MachineInstr *CandMI) {
 }
 
 void HexagonCopyHoisting::moveCopyInstr(MachineBasicBlock *DestBB,
-                                       StringRef key, MachineInstr *MI) {
+                                        StringRef key, MachineInstr *MI) {
   MachineBasicBlock::iterator FirstTI = DestBB->getFirstTerminator();
   assert(FirstTI != DestBB->end());
 
@@ -287,8 +285,8 @@ void HexagonCopyHoisting::moveCopyInstr(MachineBasicBlock *DestBB,
 //===----------------------------------------------------------------------===//
 
 INITIALIZE_PASS(HexagonCopyHoisting, "hexagon-move-phicopy",
-    "Hexagon move phi copy", false, false)
+                "Hexagon move phi copy", false, false)
 
-FunctionPass* llvm::createHexagonCopyHoisting() {
+FunctionPass *llvm::createHexagonCopyHoisting() {
   return new HexagonCopyHoisting();
 }
diff --git a/llvm/lib/Target/Hexagon/HexagonTargetMachine.cpp b/llvm/lib/Target/Hexagon/HexagonTargetMachine.cpp
index 8e5fe6dd61b834..3a792ecfd03d5c 100644
--- a/llvm/lib/Target/Hexagon/HexagonTargetMachine.cpp
+++ b/llvm/lib/Target/Hexagon/HexagonTargetMachine.cpp
@@ -43,8 +43,9 @@ cl::opt<unsigned> RDFFuncBlockLimit(
     "rdf-bb-limit", cl::Hidden, cl::init(1000),
     cl::desc("Basic block limit for a function for RDF optimizations"));
 
-static cl::opt<bool> DisableHardwareLoops("disable-hexagon-hwloops",
-  cl::Hidden, cl::desc("Disable Hardware Loops for Hexagon target"));
+static cl::opt<bool>
+    DisableHardwareLoops("disable-hexagon-hwloops", cl::Hidden,
+                         cl::desc("Disable Hardware Loops for Hexagon target"));
 
 static cl::opt<bool>
     DisableAModeOpt("disable-hexagon-amodeopt", cl::Hidden,
@@ -58,8 +59,9 @@ static cl::opt<bool>
     DisableHCP("disable-hcp", cl::Hidden,
                cl::desc("Disable Hexagon constant propagation"));
 
-static cl::opt<bool> DisableStoreWidening("disable-store-widen",
-  cl::Hidden, cl::init(false), cl::desc("Disable store widening"));
+static cl::opt<bool> DisableStoreWidening("disable-store-widen", cl::Hidden,
+                                          cl::init(false),
+                                          cl::desc("Disable store widening"));
 
 static cl::opt<bool> EnableExpandCondsets("hexagon-expand-condsets",
                                           cl::init(true), cl::Hidden,
@@ -76,42 +78,49 @@ static cl::opt<bool> EnableCopyHoist("hexagon-copy-hoist", cl::init(true),
                                      cl::Hidden, cl::ZeroOrMore,
                                      cl::desc("Enable Hexagon copy hoisting"));
 
-static cl::opt<bool> EnableGenInsert("hexagon-insert", cl::init(true),
-  cl::Hidden, cl::desc("Generate \"insert\" instructions"));
+static cl::opt<bool>
+    EnableGenInsert("hexagon-insert", cl::init(true), cl::Hidden,
+                    cl::desc("Generate \"insert\" instructions"));
 
 static cl::opt<bool>
     EnableCommGEP("hexagon-commgep", cl::init(true), cl::Hidden,
                   cl::desc("Enable commoning of GEP instructions"));
 
-static cl::opt<bool> EnableGenExtract("hexagon-extract", cl::init(true),
-  cl::Hidden, cl::desc("Generate \"extract\" instructions"));
+static cl::opt<bool>
+    EnableGenExtract("hexagon-extract", cl::init(true), cl::Hidden,
+                     cl::desc("Generate \"extract\" instructions"));
 
-static cl::opt<bool> EnableGenMux("hexagon-mux", cl::init(true), cl::Hidden,
-  cl::desc("Enable converting conditional transfers into MUX instructions"));
+static cl::opt<bool> EnableGenMux(
+    "hexagon-mux", cl::init(true), cl::Hidden,
+    cl::desc("Enable converting conditional transfers into MUX instructions"));
 
-static cl::opt<bool> EnableGenPred("hexagon-gen-pred", cl::init(true),
-  cl::Hidden, cl::desc("Enable conversion of arithmetic operations to "
-  "predicate instructions"));
+static cl::opt<bool>
+    EnableGenPred("hexagon-gen-pred", cl::init(true), cl::Hidden,
+                  cl::desc("Enable conversion of arithmetic operations to "
+                           "predicate instructions"));
 
 static cl::opt<bool>
     EnableLoopPrefetch("hexagon-loop-prefetch", cl::Hidden,
                        cl::desc("Enable loop data prefetch on Hexagon"));
 
-static cl::opt<bool> DisableHSDR("disable-hsdr", cl::init(false), cl::Hidden,
-  cl::desc("Disable splitting double registers"));
+static cl::opt<bool>
+    DisableHSDR("disable-hsdr", cl::init(false), cl::Hidden,
+                cl::desc("Disable splitting double registers"));
 
 static cl::opt<bool>
     EnableGenMemAbs("hexagon-mem-abs", cl::init(true), cl::Hidden,
                     cl::desc("Generate absolute set instructions"));
 
 static cl::opt<bool> EnableBitSimplify("hexagon-bit", cl::init(true),
-  cl::Hidden, cl::desc("Bit simplification"));
+                                       cl::Hidden,
+                                       cl::desc("Bit simplification"));
 
 static cl::opt<bool> EnableLoopResched("hexagon-loop-resched", cl::init(true),
-  cl::Hidden, cl::desc("Loop rescheduling"));
+                                       cl::Hidden,
+                                       cl::desc("Loop rescheduling"));
 
-static cl::opt<bool> HexagonNoOpt("hexagon-noopt", cl::init(false),
-  cl::Hidden, cl::desc("Disable backend optimizations"));
+static cl::opt<bool> HexagonNoOpt("hexagon-noopt", cl::init(false), cl::Hidden,
+                                  cl::desc("Disable backend optimizations"));
 
 static cl::opt<bool>
     EnableVectorPrint("enable-hexagon-vector-print", cl::Hidden,
@@ -152,72 +161,72 @@ static ScheduleDAGInstrs *createVLIWMachineSched(MachineSchedContext *C) {
 }
 
 static MachineSchedRegistry
-SchedCustomRegistry("hexagon", "Run Hexagon's custom scheduler",
-                    createVLIWMachineSched);
+    SchedCustomRegistry("hexagon", "Run Hexagon's custom scheduler",
+                        createVLIWMachineSched);
 
 namespace llvm {
-  extern char &HexagonCopyHoistingID;
-  extern char &HexagonExpandCondsetsID;
-  extern char &HexagonTfrCleanupID;
-  void initializeHexagonBitSimplifyPass(PassRegistry&);
-  void initializeHexagonCopyHoistingPass(PassRegistry&);
-  void initializeHexagonConstExtendersPass(PassRegistry&);
-  void initializeHexagonConstPropagationPass(PassRegistry&);
-  void initializeHexagonCopyToCombinePass(PassRegistry&);
-  void initializeHexagonEarlyIfConversionPass(PassRegistry&);
-  void initializeHexagonExpandCondsetsPass(PassRegistry&);
-  void initializeHexagonGenMemAbsolutePass(PassRegistry &);
-  void initializeHexagonGenMuxPass(PassRegistry&);
-  void initializeHexagonHardwareLoopsPass(PassRegistry&);
-  void initializeHexagonLoopIdiomRecognizeLegacyPassPass(PassRegistry &);
-  void initializeHexagonLoopAlignPass(PassRegistry &);
-  void initializeHexagonNewValueJumpPass(PassRegistry&);
-  void initializeHexagonOptAddrModePass(PassRegistry&);
-  void initializeHexagonPacketizerPass(PassRegistry&);
-  void initializeHexagonRDFOptPass(PassRegistry&);
-  void initializeHexagonSplitDoubleRegsPass(PassRegistry&);
-  void initializeHexagonTfrCleanupPass(PassRegistry &);
-  void initializeHexagonVExtractPass(PassRegistry &);
-  void initializeHexagonVectorCombineLegacyPass(PassRegistry&);
-  void initializeHexagonVectorLoopCarriedReuseLegacyPassPass(PassRegistry &);
-  Pass *createHexagonLoopIdiomPass();
-  Pass *createHexagonVectorLoopCarriedReuseLegacyPass();
-
-  FunctionPass *createHexagonBitSimplify();
-  FunctionPass *createHexagonBranchRelaxation();
-  FunctionPass *createHexagonCallFrameInformation();
-  FunctionPass *createHexagonCFGOptimizer();
-  FunctionPass *createHexagonCommonGEP();
-  FunctionPass *createHexagonConstExtenders();
-  FunctionPass *createHexagonConstPropagationPass();
-  FunctionPass *createHexagonCopyHoisting();
-  FunctionPass *createHexagonCopyToCombine();
-  FunctionPass *createHexagonEarlyIfConversion();
-  FunctionPass *createHexagonFixupHwLoops();
-  FunctionPass *createHexagonGenExtract();
-  FunctionPass *createHexagonGenInsert();
-  FunctionPass *createHexagonGenMemAbsolute();
-  FunctionPass *createHexagonGenMux();
-  FunctionPass *createHexagonGenPredicate();
-  FunctionPass *createHexagonHardwareLoops();
-  FunctionPass *createHexagonISelDag(HexagonTargetMachine &TM,
-                                     CodeGenOptLevel OptLevel);
-  FunctionPass *createHexagonLoopAlign();
-  FunctionPass *createHexagonLoopRescheduling();
-  FunctionPass *createHexagonNewValueJump();
-  FunctionPass *createHexagonOptAddrMode();
-  FunctionPass *createHexagonOptimizeSZextends();
-  FunctionPass *createHexagonPacketizer(bool Minimal);
-  FunctionPass *createHexagonPeephole();
-  FunctionPass *createHexagonRDFOpt();
-  FunctionPass *createHexagonSplitConst32AndConst64();
-  FunctionPass *createHexagonSplitDoubleRegs();
-  FunctionPass *createHexagonStoreWidening();
-  FunctionPass *createHexagonTfrCleanup();
-  FunctionPass *createHexagonVectorCombineLegacyPass();
-  FunctionPass *createHexagonVectorPrint();
-  FunctionPass *createHexagonVExtract();
-} // end namespace llvm;
+extern char &HexagonCopyHoistingID;
+extern char &HexagonExpandCondsetsID;
+extern char &HexagonTfrCleanupID;
+void initializeHexagonBitSimplifyPass(PassRegistry &);
+void initializeHexagonCopyHoistingPass(PassRegistry &);
+void initializeHexagonConstExtendersPass(PassRegistry &);
+void initializeHexagonConstPropagationPass(PassRegistry &);
+void initializeHexagonCopyToCombinePass(PassRegistry &);
+void initializeHexagonEarlyIfConversionPass(PassRegistry &);
+void initializeHexagonExpandCondsetsPass(PassRegistry &);
+void initializeHexagonGenMemAbsolutePass(PassRegistry &);
+void initializeHexagonGenMuxPass(PassRegistry &);
+void initializeHexagonHardwareLoopsPass(PassRegistry &);
+void initializeHexagonLoopIdiomRecognizeLegacyPassPass(PassRegistry &);
+void initializeHexagonLoopAlignPass(PassRegistry &);
+void initializeHexagonNewValueJumpPass(PassRegistry &);
+void initializeHexagonOptAddrModePass(PassRegistry &);
+void initializeHexagonPacketizerPass(PassRegistry &);
+void initializeHexagonRDFOptPass(PassRegistry &);
+void initializeHexagonSplitDoubleRegsPass(PassRegistry &);
+void initializeHexagonTfrCleanupPass(PassRegistry &);
+void initializeHexagonVExtractPass(PassRegistry &);
+void initializeHexagonVectorCombineLegacyPass(PassRegistry &);
+void initializeHexagonVectorLoopCarriedReuseLegacyPassPass(PassRegistry &);
+Pass *createHexagonLoopIdiomPass();
+Pass *createHexagonVectorLoopCarriedReuseLegacyPass();
+
+FunctionPass *createHexagonBitSimplify();
+FunctionPass *createHexagonBranchRelaxation();
+FunctionPass *createHexagonCallFrameInformation();
+FunctionPass *createHexagonCFGOptimizer();
+FunctionPass *createHexagonCommonGEP();
+FunctionPass *createHexagonConstExtenders();
+FunctionPass *createHexagonConstPropagationPass();
+FunctionPass *createHexagonCopyHoisting();
+FunctionPass *createHexagonCopyToCombine();
+FunctionPass *createHexagonEarlyIfConversion();
+FunctionPass *createHexagonFixupHwLoops();
+FunctionPass *createHexagonGenExtract();
+FunctionPass *createHexagonGenInsert();
+FunctionPass *createHexagonGenMemAbsolute();
+FunctionPass *createHexagonGenMux();
+FunctionPass *createHexagonGenPredicate();
+FunctionPass *createHexagonHardwareLoops();
+FunctionPass *createHexagonISelDag(HexagonTargetMachine &TM,
+                                   CodeGenOptLevel OptLevel);
+FunctionPass *createHexagonLoopAlign();
+FunctionPass *createHexagonLoopRescheduling();
+FunctionPass *createHexagonNewValueJump();
+FunctionPass *createHexagonOptAddrMode();
+FunctionPass *createHexagonOptimizeSZextends();
+FunctionPass *createHexagonPacketizer(bool Minimal);
+FunctionPass *createHexagonPeephole();
+FunctionPass *createHexagonRDFOpt();
+FunctionPass *createHexagonSplitConst32AndConst64();
+FunctionPass *createHexagonSplitDoubleRegs();
+FunctionPass *createHexagonStoreWidening();
+FunctionPass *createHexagonTfrCleanup();
+FunctionPass *createHexagonVectorCombineLegacyPass();
+FunctionPass *createHexagonVectorPrint();
+FunctionPass *createHexagonVExtract();
+} // namespace llvm
 
 static Reloc::Model getEffectiveRelocModel(std::optional<Reloc::Model> RM) {
   return RM.value_or(Reloc::Static);
@@ -277,10 +286,8 @@ HexagonTargetMachine::HexagonTargetMachine(const Target &T, const Triple &TT,
 const HexagonSubtarget *
 HexagonTargetMachine::getSubtargetImpl(const Function &F) const {
   AttributeList FnAttrs = F.getAttributes();
-  Attribute CPUAttr =
-      FnAttrs.getFnAttr("target-cpu");
-  Attribute FSAttr =
-      FnAttrs.getFnAttr("target-features");
+  Attribute CPUAttr = FnAttrs.getFnAttr("target-cpu");
+  Attribute FSAttr = FnAttrs.getFnAttr("target-features");
 
   std::string CPU =
       CPUAttr.isValid() ? CPUAttr.getValueAsString().str() : TargetCPU;
@@ -339,7 +346,7 @@ namespace {
 class HexagonPassConfig : public TargetPassConfig {
 public:
   HexagonPassConfig(HexagonTargetMachine &TM, PassManagerBase &PM)
-    : TargetPassConfig(TM, PM) {}
+      : TargetPassConfig(TM, PM) {}
 
   HexagonTargetMachine &getHexagonTargetMachine() const {
     return getTM<HexagonTargetMachine>();

>From c7db6f19f405830f886c4d921055e62556f5d457 Mon Sep 17 00:00:00 2001
From: Perry MacMurray <pmacmurr at quicinc.com>
Date: Fri, 19 Apr 2024 10:01:24 -0700
Subject: [PATCH 3/5] Fix clang-format

I was running an outdated version
---
 llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp b/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
index 631ae4379387e9..8a4672f5fa05c1 100644
--- a/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
+++ b/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
@@ -87,8 +87,7 @@ bool HexagonCopyHoisting::runOnMachineFunction(MachineFunction &Fn) {
   MFN = &Fn;
   MRI = &Fn.getRegInfo();
 
-  LLVM_DEBUG(dbgs() << "\nCopy Hoisting:"
-                    << "\'" << Fn.getName() << "\'\n");
+  LLVM_DEBUG(dbgs() << "\nCopy Hoisting:" << "\'" << Fn.getName() << "\'\n");
 
   CopyMIList.clear();
   CopyMIList.resize(Fn.getNumBlockIDs());

>From 11039a77c568278b9e05dc474cac793abf7705aa Mon Sep 17 00:00:00 2001
From: Perry MacMurray <pmacmurr at quicinc.com>
Date: Fri, 19 Apr 2024 14:09:15 -0700
Subject: [PATCH 4/5] Code review changes

---
 .../Target/Hexagon/HexagonCopyHoisting.cpp    | 119 ++++++++----------
 1 file changed, 54 insertions(+), 65 deletions(-)

diff --git a/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp b/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
index 8a4672f5fa05c1..de21c2e7dd68d5 100644
--- a/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
+++ b/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
@@ -41,7 +41,7 @@ class HexagonCopyHoisting : public MachineFunctionPass {
 
 public:
   static char ID;
-  HexagonCopyHoisting() : MachineFunctionPass(ID), MFN(0), MRI(0) {
+  HexagonCopyHoisting() : MachineFunctionPass(ID), MFN(nullptr), MRI(nullptr) {
     initializeHexagonCopyHoistingPass(*PassRegistry::getPassRegistry());
   }
 
@@ -62,13 +62,14 @@ class HexagonCopyHoisting : public MachineFunctionPass {
   void addMItoCopyList(MachineInstr *MI);
   bool analyzeCopy(MachineBasicBlock *BB);
   bool isSafetoMove(MachineInstr *CandMI);
-  void moveCopyInstr(MachineBasicBlock *DestBB, StringRef key,
-                     MachineInstr *MI);
+  void moveCopyInstr(MachineBasicBlock *DestBB,
+                     std::pair<Register, Register> Key, MachineInstr *MI);
 
   MachineFunction *MFN;
   MachineRegisterInfo *MRI;
   StringMap<MachineInstr *> CopyMI;
-  std::vector<StringMap<MachineInstr *>> CopyMIList;
+  std::vector<DenseMap<std::pair<Register, Register>, MachineInstr *>>
+      CopyMIList;
 };
 
 } // namespace
@@ -77,7 +78,7 @@ char HexagonCopyHoisting::ID = 0;
 
 namespace llvm {
 char &HexagonCopyHoistingID = HexagonCopyHoisting::ID;
-}
+} // namespace llvm
 
 bool HexagonCopyHoisting::runOnMachineFunction(MachineFunction &Fn) {
 
@@ -97,19 +98,18 @@ bool HexagonCopyHoisting::runOnMachineFunction(MachineFunction &Fn) {
 
   // Traverse through the basic blocks again and move the COPY instructions
   // that are present in all the successors of BB to BB.
-  bool changed = false;
-  for (auto I = po_begin(&Fn), E = po_end(&Fn); I != E; ++I) {
-    MachineBasicBlock &BB = **I;
-    if (!BB.empty()) {
-      if (BB.pred_size() != 1) //
+  bool Changed = false;
+  for (MachineBasicBlock *BB : post_order(&Fn)) {
+    if (!BB->empty()) {
+      if (BB->pred_size() != 1)
         continue;
-      auto &BBCopyInst = CopyMIList[BB.getNumber()];
+      auto &BBCopyInst = CopyMIList[BB->getNumber()];
       if (BBCopyInst.size() > 0)
-        changed |= analyzeCopy(*BB.pred_begin());
+        Changed |= analyzeCopy(*BB->pred_begin());
     }
   }
   // Re-compute liveness
-  if (changed) {
+  if (Changed) {
     LiveIntervals &LIS = getAnalysis<LiveIntervals>();
     SlotIndexes *SI = LIS.getSlotIndexes();
     SI->releaseMemory();
@@ -117,24 +117,22 @@ bool HexagonCopyHoisting::runOnMachineFunction(MachineFunction &Fn) {
     LIS.releaseMemory();
     LIS.runOnMachineFunction(Fn);
   }
-  return changed;
+  return Changed;
 }
 
 //===----------------------------------------------------------------------===//
 // Save all COPY instructions for each basic block in CopyMIList vector.
 //===----------------------------------------------------------------------===//
 void HexagonCopyHoisting::collectCopyInst() {
-  for (auto BI = MFN->begin(), BE = MFN->end(); BI != BE; ++BI) {
-    MachineBasicBlock *BB = &*BI;
+  for (MachineBasicBlock &BB : *MFN) {
 #ifndef NDEBUG
-    auto &BBCopyInst = CopyMIList[BB->getNumber()];
-    LLVM_DEBUG(dbgs() << "Visiting BB#" << BB->getNumber() << ":\n");
+    auto &BBCopyInst = CopyMIList[BB.getNumber()];
+    LLVM_DEBUG(dbgs() << "Visiting BB#" << BB.getNumber() << ":\n");
 #endif
 
-    for (auto MII = BB->begin(), MIE = BB->end(); MII != MIE; ++MII) {
-      MachineInstr *MI = &*MII;
-      if (MI->getOpcode() == TargetOpcode::COPY)
-        addMItoCopyList(MI);
+    for (MachineInstr &MI : BB) {
+      if (MI.getOpcode() == TargetOpcode::COPY)
+        addMItoCopyList(&MI);
     }
     LLVM_DEBUG(dbgs() << "\tNumber of copies: " << BBCopyInst.size() << "\n");
   }
@@ -143,8 +141,8 @@ void HexagonCopyHoisting::collectCopyInst() {
 void HexagonCopyHoisting::addMItoCopyList(MachineInstr *MI) {
   unsigned BBNum = MI->getParent()->getNumber();
   auto &BBCopyInst = CopyMIList[BBNum];
-  unsigned DstReg = MI->getOperand(0).getReg();
-  unsigned SrcReg = MI->getOperand(1).getReg();
+  Register DstReg = MI->getOperand(0).getReg();
+  Register SrcReg = MI->getOperand(1).getReg();
 
   if (!Register::isVirtualRegister(DstReg) ||
       !Register::isVirtualRegister(SrcReg) ||
@@ -152,16 +150,16 @@ void HexagonCopyHoisting::addMItoCopyList(MachineInstr *MI) {
       MRI->getRegClass(SrcReg) != &Hexagon::IntRegsRegClass)
     return;
 
-  StringRef key;
+  StringRef Key;
   SmallString<256> TmpData("");
   (void)Twine(Register::virtReg2Index(DstReg)).toStringRef(TmpData);
   TmpData += '=';
-  key = Twine(Register::virtReg2Index(SrcReg)).toStringRef(TmpData);
-  BBCopyInst[key] = MI;
+  Key = Twine(Register::virtReg2Index(SrcReg)).toStringRef(TmpData);
+  BBCopyInst.insert(std::pair(std::pair(SrcReg, DstReg), MI));
 #ifndef NDEBUG
   LLVM_DEBUG(dbgs() << "\tAdding Copy Instr to the list: " << MI << "\n");
-  for (auto II = BBCopyInst.begin(), IE = BBCopyInst.end(); II != IE; ++II) {
-    MachineInstr *TempMI = (*II).getValue();
+  for (auto II : BBCopyInst) {
+    MachineInstr *TempMI = II.getSecond();
     LLVM_DEBUG(dbgs() << "\tIn the list: " << TempMI << "\n");
   }
 #endif
@@ -174,37 +172,32 @@ void HexagonCopyHoisting::addMItoCopyList(MachineInstr *MI) {
 //===----------------------------------------------------------------------===//
 bool HexagonCopyHoisting::analyzeCopy(MachineBasicBlock *BB) {
 
-  bool changed = false;
+  bool Changed = false;
   if (BB->succ_size() < 2)
     return false;
 
-  for (auto I = BB->succ_begin(), E = BB->succ_end(); I != E; ++I) {
-    MachineBasicBlock *SB = *I;
+  for (MachineBasicBlock *SB : BB->successors()) {
     if (SB->pred_size() != 1 || SB->isEHPad() || SB->hasAddressTaken())
       return false;
   }
 
-  auto SuccI = BB->succ_begin(), SuccE = BB->succ_end();
-
-  MachineBasicBlock *SBB1 = *SuccI;
-  ++SuccI;
+  MachineBasicBlock *SBB1 = *BB->succ_begin();
   auto &BBCopyInst1 = CopyMIList[SBB1->getNumber()];
 
-  for (auto II = BBCopyInst1.begin(), IE = BBCopyInst1.end(); II != IE; ++II) {
-    StringRef key = (*II).getKeyData();
-    MachineInstr *MI = (*II).getValue();
+  for (auto II : BBCopyInst1) {
+    std::pair<Register, Register> Key = II.getFirst();
+    MachineInstr *MI = II.getSecond();
     bool IsSafetoMove = true;
-    for (SuccI = BB->succ_begin(); SuccI != SuccE; ++SuccI) {
-      MachineBasicBlock *SuccBB = *SuccI;
+    for (MachineBasicBlock *SuccBB : BB->successors()) {
       auto &SuccBBCopyInst = CopyMIList[SuccBB->getNumber()];
-      if (!SuccBBCopyInst.count(key)) {
+      if (!SuccBBCopyInst.count(Key)) {
         // Same copy not present in this successor
         IsSafetoMove = false;
         break;
       }
       // If present, make sure that it's safe to pull this copy instruction
       // into the predecessor.
-      MachineInstr *SuccMI = SuccBBCopyInst[key];
+      MachineInstr *SuccMI = SuccBBCopyInst[Key];
       if (!isSafetoMove(SuccMI)) {
         IsSafetoMove = false;
         break;
@@ -215,67 +208,63 @@ bool HexagonCopyHoisting::analyzeCopy(MachineBasicBlock *BB) {
     if (IsSafetoMove) {
       LLVM_DEBUG(dbgs() << "\t\t Moving instr to BB#" << BB->getNumber() << ": "
                         << MI << "\n");
-      moveCopyInstr(BB, key, MI);
+      moveCopyInstr(BB, Key, MI);
       // Add my into BB copyMI list.
-      changed = true;
+      Changed = true;
     }
   }
 
 #ifndef NDEBUG
   auto &BBCopyInst = CopyMIList[BB->getNumber()];
-  for (auto II = BBCopyInst.begin(), IE = BBCopyInst.end(); II != IE; ++II) {
-    MachineInstr *TempMI = (*II).getValue();
+  for (auto II : BBCopyInst) {
+    MachineInstr *TempMI = II.getSecond();
     LLVM_DEBUG(dbgs() << "\tIn the list: " << TempMI << "\n");
   }
 #endif
-  return changed;
+  return Changed;
 }
 
 bool HexagonCopyHoisting::isSafetoMove(MachineInstr *CandMI) {
   // Make sure that it's safe to move this 'copy' instruction to the predecessor
   // basic block.
   assert(CandMI->getOperand(0).isReg() && CandMI->getOperand(1).isReg());
-  unsigned DefR = CandMI->getOperand(0).getReg();
-  unsigned UseR = CandMI->getOperand(1).getReg();
+  Register DefR = CandMI->getOperand(0).getReg();
+  Register UseR = CandMI->getOperand(1).getReg();
 
   MachineBasicBlock *BB = CandMI->getParent();
   // There should not be a def/use of DefR between the start of BB and CandMI.
   MachineBasicBlock::iterator MII, MIE;
   for (MII = BB->begin(), MIE = CandMI; MII != MIE; ++MII) {
-    MachineInstr *otherMI = &*MII;
-    for (MachineInstr::mop_iterator Mo = otherMI->operands_begin(),
-                                    E = otherMI->operands_end();
-         Mo != E; ++Mo)
-      if (Mo->isReg() && Mo->getReg() == DefR)
+    MachineInstr *OtherMI = &*MII;
+    for (const MachineOperand &Mo : OtherMI->operands())
+      if (Mo.isReg() && Mo.getReg() == DefR)
         return false;
   }
   // There should not be a def of UseR between the start of BB and CandMI.
   for (MII = BB->begin(), MIE = CandMI; MII != MIE; ++MII) {
-    MachineInstr *otherMI = &*MII;
-    for (MachineInstr::mop_iterator Mo = otherMI->operands_begin(),
-                                    E = otherMI->operands_end();
-         Mo != E; ++Mo)
-      if (Mo->isReg() && Mo->isDef() && Mo->getReg() == UseR)
+    MachineInstr *OtherMI = &*MII;
+    for (const MachineOperand &Mo : OtherMI->operands())
+      if (Mo.isReg() && Mo.isDef() && Mo.getReg() == UseR)
         return false;
   }
   return true;
 }
 
 void HexagonCopyHoisting::moveCopyInstr(MachineBasicBlock *DestBB,
-                                        StringRef key, MachineInstr *MI) {
+                                        std::pair<Register, Register> Key,
+                                        MachineInstr *MI) {
   MachineBasicBlock::iterator FirstTI = DestBB->getFirstTerminator();
   assert(FirstTI != DestBB->end());
 
   DestBB->splice(FirstTI, MI->getParent(), MI);
 
   addMItoCopyList(MI);
-  auto I = ++(DestBB->succ_begin()), E = DestBB->succ_end();
-  for (; I != E; ++I) {
+  for (auto I = ++(DestBB->succ_begin()), E = DestBB->succ_end(); I != E; ++I) {
     MachineBasicBlock *SuccBB = *I;
     auto &BBCopyInst = CopyMIList[SuccBB->getNumber()];
-    MachineInstr *SuccMI = BBCopyInst[key];
+    MachineInstr *SuccMI = BBCopyInst[Key];
     SuccMI->eraseFromParent();
-    BBCopyInst.erase(key);
+    BBCopyInst.erase(Key);
   }
 }
 

>From 25de806df705307f26b9e87560e7ac77394f7989 Mon Sep 17 00:00:00 2001
From: Perry MacMurray <pmacmurr at quicinc.com>
Date: Mon, 22 Apr 2024 14:54:35 -0700
Subject: [PATCH 5/5] A few more code review changes

---
 llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp | 10 +---------
 1 file changed, 1 insertion(+), 9 deletions(-)

diff --git a/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp b/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
index de21c2e7dd68d5..97917270601bc8 100644
--- a/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
+++ b/llvm/lib/Target/Hexagon/HexagonCopyHoisting.cpp
@@ -10,15 +10,13 @@
 //===----------------------------------------------------------------------===//
 
 #include "HexagonTargetMachine.h"
+#include "llvm/ADT/DenseMap.h"
 #include "llvm/ADT/PostOrderIterator.h"
-#include "llvm/ADT/SmallString.h"
-#include "llvm/ADT/StringMap.h"
 #include "llvm/ADT/StringRef.h"
 #include "llvm/ADT/Twine.h"
 #include "llvm/CodeGen/LiveInterval.h"
 #include "llvm/CodeGen/LiveIntervals.h"
 #include "llvm/CodeGen/MachineDominators.h"
-#include "llvm/CodeGen/MachineInstrBuilder.h"
 #include "llvm/CodeGen/MachineRegisterInfo.h"
 #include "llvm/Support/CommandLine.h"
 #include "llvm/Support/Debug.h"
@@ -67,7 +65,6 @@ class HexagonCopyHoisting : public MachineFunctionPass {
 
   MachineFunction *MFN;
   MachineRegisterInfo *MRI;
-  StringMap<MachineInstr *> CopyMI;
   std::vector<DenseMap<std::pair<Register, Register>, MachineInstr *>>
       CopyMIList;
 };
@@ -150,11 +147,6 @@ void HexagonCopyHoisting::addMItoCopyList(MachineInstr *MI) {
       MRI->getRegClass(SrcReg) != &Hexagon::IntRegsRegClass)
     return;
 
-  StringRef Key;
-  SmallString<256> TmpData("");
-  (void)Twine(Register::virtReg2Index(DstReg)).toStringRef(TmpData);
-  TmpData += '=';
-  Key = Twine(Register::virtReg2Index(SrcReg)).toStringRef(TmpData);
   BBCopyInst.insert(std::pair(std::pair(SrcReg, DstReg), MI));
 #ifndef NDEBUG
   LLVM_DEBUG(dbgs() << "\tAdding Copy Instr to the list: " << MI << "\n");



More information about the llvm-commits mailing list