[llvm] [RISCV][GISel] Move G_BRJT expansion to legalization (PR #73711)

Craig Topper via llvm-commits llvm-commits at lists.llvm.org
Tue Nov 19 23:50:21 PST 2024


================
@@ -317,6 +318,62 @@ bool RISCVLegalizerInfo::legalizeShlAshrLshr(
   return true;
 }
 
+bool RISCVLegalizerInfo::legalizeBRJT(MachineInstr &MI,
+                                      MachineIRBuilder &MIRBuilder) const {
+  MachineRegisterInfo &MRI = *MIRBuilder.getMRI();
+  auto &MF = *MI.getParent()->getParent();
+  const MachineJumpTableInfo *MJTI = MF.getJumpTableInfo();
+  unsigned EntrySize = MJTI->getEntrySize(MF.getDataLayout());
+
+  Register PtrReg = MI.getOperand(0).getReg();
+  LLT PtrTy = MRI.getType(PtrReg);
+  Register IndexReg = MI.getOperand(2).getReg();
+  LLT IndexTy = MRI.getType(IndexReg);
+
+  MachineInstrBuilder Index;
+  if (isPowerOf2_32(EntrySize)) {
+    auto ShiftAmt = MIRBuilder.buildConstant(IndexTy, Log2_32(EntrySize));
+    Index = MIRBuilder.buildShl(IndexTy, IndexReg, ShiftAmt);
+  } else
+    return false;
+
+  auto Addr = MIRBuilder.buildPtrAdd(PtrTy, PtrReg, Index);
+
+  MachineMemOperand *MMO = MF.getMachineMemOperand(
+      MachinePointerInfo::getJumpTable(MF), MachineMemOperand::MOLoad,
+      EntrySize, Align(MJTI->getEntryAlignment(MF.getDataLayout())));
+
+  Register TargetReg;
+  switch (MJTI->getEntryKind()) {
+  default:
+    llvm_unreachable("Unexpected jumptable entry kind");
+  case MachineJumpTableInfo::EK_LabelDifference32: {
+    // For PIC, the sequence is:
+    // BRIND(load(Jumptable + index) + RelocBase)
+    // RelocBase can be JumpTable, GOT or some sort of global base.
+    auto Load = MIRBuilder.buildLoadInstr(
+        TargetOpcode::G_LOAD, LLT::scalar(EntrySize * 8), Addr, *MMO);
+    Load = MIRBuilder.buildSExtOrTrunc(IndexTy, Load);
+    TargetReg = MIRBuilder.buildPtrAdd(PtrTy, PtrReg, Load).getReg(0);
+    break;
+  }
+  case MachineJumpTableInfo::EK_Custom32: {
+    auto Load = MIRBuilder.buildLoadInstr(TargetOpcode::G_SEXTLOAD, IndexTy,
+                                          Addr, *MMO);
+    TargetReg = MIRBuilder.buildIntToPtr(PtrTy, Load).getReg(0);
+    break;
+  }
+  case MachineJumpTableInfo::EK_BlockAddress:
+    TargetReg = MIRBuilder.buildLoad(PtrTy, Addr, *MMO).getReg(0);
+    break;
+  }
+
+  MIRBuilder.buildBrIndirect(TargetReg);
+
+  MI.eraseFromParent();
----------------
topperc wrote:

eraseInstr removes the instruction from the InstList in Legalizer.cpp. Since we're visiting the instruction, it was just popped from the InstList. So there's no need for the observer to remove from InstList.

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


More information about the llvm-commits mailing list