[llvm] [RISCV][GISel] Support select G_INSERT_SUBVECTOR (PR #171092)

Jianjian Guan via llvm-commits llvm-commits at lists.llvm.org
Tue Dec 9 23:21:36 PST 2025


================
@@ -1007,6 +1007,66 @@ bool RISCVInstructionSelector::selectExtractSubvector(
   return true;
 }
 
+bool RISCVInstructionSelector::selectInsertSubVector(
+    MachineInstr &MI, MachineIRBuilder &MIB) const {
+  assert(MI.getOpcode() == TargetOpcode::G_INSERT_SUBVECTOR);
+
+  Register DstReg = MI.getOperand(0).getReg();
+  Register VecReg = MI.getOperand(1).getReg();
+  Register SubVecReg = MI.getOperand(2).getReg();
+
+  LLT VecTy = MRI->getType(VecReg);
+  LLT SubVecTy = MRI->getType(SubVecReg);
+
+  MVT VecMVT = getMVTForLLT(VecTy);
+  MVT SubVecMVT = getMVTForLLT(SubVecTy);
+
+  unsigned Idx = static_cast<unsigned>(MI.getOperand(3).getImm());
+
+  unsigned SubRegIdx;
+  std::tie(SubRegIdx, Idx) =
+      RISCVTargetLowering::decomposeSubvectorInsertExtractToSubRegs(
+          VecMVT, SubVecMVT, Idx, &TRI);
+
+  // If the Idx hasn't been completely eliminated then this is a subvector
+  // insert which doesn't naturally align to a vector register. These must
+  // be handled using instructions to manipulate the vector registers.
+  if (Idx != 0)
+    return false;
+
+  RISCVVType::VLMUL SubVecLMUL = RISCVTargetLowering::getLMUL(SubVecMVT);
+  [[maybe_unused]] bool IsSubVecPartReg =
+      SubVecLMUL == RISCVVType::VLMUL::LMUL_F2 ||
+      SubVecLMUL == RISCVVType::VLMUL::LMUL_F4 ||
+      SubVecLMUL == RISCVVType::VLMUL::LMUL_F8;
+
+  // Constrain dst
+  unsigned DstRegClassID = RISCVTargetLowering::getRegClassIDForVecVT(VecMVT);
+  const TargetRegisterClass *DstRC = TRI.getRegClass(DstRegClassID);
+  if (!RBI.constrainGenericRegister(DstReg, *DstRC, *MRI))
+    return false;
+
+  // If we haven't set a SubRegIdx, then we must be going between
+  // equally-sized LMUL groups (e.g. VR -> VR). This can be done as a copy.
+  if (SubRegIdx == RISCV::NoSubRegister) {
+    assert(RISCVTargetLowering::getRegClassIDForVecVT(SubVecMVT) ==
+               DstRegClassID &&
+           "Unexpected subvector insert");
+    MIB.buildInstr(TargetOpcode::COPY, {DstReg}, {}).addReg(SubVecReg);
----------------
jacquesguan wrote:

Seems that we only use `MachineInstrBuilder` in `RISCVInstructionSelector.cpp`, I think maybe refactor them all in a new pr.

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


More information about the llvm-commits mailing list