[llvm] AMDGPU: Use mi_match for more manual selector patterns (PR #216726)
Matt Arsenault via llvm-commits
llvm-commits at lists.llvm.org
Mon Aug 17 06:15:14 PDT 2026
https://github.com/arsenm created https://github.com/llvm/llvm-project/pull/216726
Use mi_match G_SHUFFLE_VECTOR/G_FRAME_INDEX/G_SUB checks. Add new
matchers to check the shufflevector and frame index cases, avoiding
raw getVRegDef uses.
Co-authored-by: Claude (Opus 4.8) <noreply at anthropic.com>
>From 25a2d757610ab2bbc39818dd2e4b401fe6ff1736 Mon Sep 17 00:00:00 2001
From: Matt Arsenault <Matthew.Arsenault at amd.com>
Date: Mon, 17 Aug 2026 15:07:15 +0200
Subject: [PATCH] AMDGPU: Use mi_match for more manual selector patterns
Use mi_match G_SHUFFLE_VECTOR/G_FRAME_INDEX/G_SUB checks. Add new
matchers to check the shufflevector and frame index cases, avoiding
raw getVRegDef uses.
Co-authored-by: Claude (Opus 4.8) <noreply at anthropic.com>
---
.../llvm/CodeGen/GlobalISel/MIPatternMatch.h | 44 +++++++++++++++++++
.../AMDGPU/AMDGPUInstructionSelector.cpp | 35 ++++++---------
2 files changed, 58 insertions(+), 21 deletions(-)
diff --git a/llvm/include/llvm/CodeGen/GlobalISel/MIPatternMatch.h b/llvm/include/llvm/CodeGen/GlobalISel/MIPatternMatch.h
index 91c6275e5ba8d..7c336403159e2 100644
--- a/llvm/include/llvm/CodeGen/GlobalISel/MIPatternMatch.h
+++ b/llvm/include/llvm/CodeGen/GlobalISel/MIPatternMatch.h
@@ -597,6 +597,50 @@ inline GInstrBind<GConcatVectors> m_GConcatVectors(GConcatVectors *&Inst) {
return Inst;
}
+/// Matches a G_SHUFFLE_VECTOR, binding its two source operands and its mask.
+template <typename Src1Ty, typename Src2Ty> struct ShuffleVectorMatch {
+ Src1Ty Src1;
+ Src2Ty Src2;
+ ArrayRef<int> &Mask;
+
+ ShuffleVectorMatch(const Src1Ty &Src1, const Src2Ty &Src2,
+ ArrayRef<int> &Mask)
+ : Src1(Src1), Src2(Src2), Mask(Mask) {}
+ bool match(const MachineRegisterInfo &MRI, Register Reg) {
+ MachineInstr *TmpMI;
+ if (!mi_match(Reg, MRI, m_MInstr(TmpMI)))
+ return false;
+ auto *Shuf = dyn_cast<GShuffleVector>(TmpMI);
+ if (!Shuf || !Src1.match(MRI, Shuf->getSrc1Reg()) ||
+ !Src2.match(MRI, Shuf->getSrc2Reg()))
+ return false;
+ Mask = Shuf->getMask();
+ return true;
+ }
+};
+
+template <typename Src1Ty, typename Src2Ty>
+inline ShuffleVectorMatch<Src1Ty, Src2Ty>
+m_GShuffleVector(const Src1Ty &Src1, const Src2Ty &Src2, ArrayRef<int> &Mask) {
+ return ShuffleVectorMatch<Src1Ty, Src2Ty>(Src1, Src2, Mask);
+}
+
+/// Matches a G_FRAME_INDEX, binding its frame index.
+struct GFrameIndexMatch {
+ int &FI;
+ bool match(const MachineRegisterInfo &MRI, Register Reg) {
+ MachineInstr *TmpMI;
+ if (mi_match(Reg, MRI, m_MInstr(TmpMI)) &&
+ TmpMI->getOpcode() == TargetOpcode::G_FRAME_INDEX) {
+ FI = TmpMI->getOperand(1).getIndex();
+ return true;
+ }
+ return false;
+ }
+};
+
+inline GFrameIndexMatch m_GFrameIndex(int &FI) { return {FI}; }
+
// Helper for matching G_FCONSTANT
inline bind_ty<const ConstantFP *> m_GFCst(const ConstantFP *&C) { return C; }
diff --git a/llvm/lib/Target/AMDGPU/AMDGPUInstructionSelector.cpp b/llvm/lib/Target/AMDGPU/AMDGPUInstructionSelector.cpp
index 0a5dbca02fea2..0c6bbf39508d4 100644
--- a/llvm/lib/Target/AMDGPU/AMDGPUInstructionSelector.cpp
+++ b/llvm/lib/Target/AMDGPU/AMDGPUInstructionSelector.cpp
@@ -2942,18 +2942,16 @@ static bool isExtractHiElt(MachineRegisterInfo &MRI, Register In,
}
}
- MachineInstr *Shuffle = MRI.getVRegDef(Trunc);
- if (Shuffle->getOpcode() != AMDGPU::G_SHUFFLE_VECTOR)
+ ArrayRef<int> Mask;
+ Register Src1;
+ if (!mi_match(Trunc, MRI, m_GShuffleVector(m_Reg(Src1), m_Reg(), Mask)))
return false;
- assert(MRI.getType(Shuffle->getOperand(0).getReg()) ==
- LLT::fixed_vector(2, 16));
-
- ArrayRef<int> Mask = Shuffle->getOperand(3).getShuffleMask();
+ assert(MRI.getType(Src1) == LLT::fixed_vector(2, 16));
assert(Mask.size() == 2);
if (Mask[0] == 1 && Mask[1] <= 1) {
- Out = Shuffle->getOperand(0).getReg();
+ Out = Trunc;
return true;
}
@@ -6499,24 +6497,23 @@ AMDGPUInstructionSelector::selectMUBUFScratchOffen(MachineOperand &Root) const {
std::optional<int> FI;
Register VAddr = Root.getReg();
- const MachineInstr *RootDef = MRI->getVRegDef(Root.getReg());
Register PtrBase;
int64_t ConstOffset;
std::tie(PtrBase, ConstOffset, std::ignore) =
getPtrBaseWithConstantOffset(VAddr, *MRI);
+ int MatchedFI;
if (ConstOffset != 0) {
if (TII.isLegalMUBUFImmOffset(ConstOffset) &&
(!STI.privateMemoryResourceIsRangeChecked() ||
VT->signBitIsZero(PtrBase))) {
- const MachineInstr *PtrBaseDef = MRI->getVRegDef(PtrBase);
- if (PtrBaseDef->getOpcode() == AMDGPU::G_FRAME_INDEX)
- FI = PtrBaseDef->getOperand(1).getIndex();
+ if (mi_match(PtrBase, *MRI, m_GFrameIndex(MatchedFI)))
+ FI = MatchedFI;
else
VAddr = PtrBase;
Offset = ConstOffset;
}
- } else if (RootDef->getOpcode() == AMDGPU::G_FRAME_INDEX) {
- FI = RootDef->getOperand(1).getIndex();
+ } else if (mi_match(Root.getReg(), *MRI, m_GFrameIndex(MatchedFI))) {
+ FI = MatchedFI;
}
return {{[=](MachineInstrBuilder &MIB) { // rsrc
@@ -6736,8 +6733,8 @@ AMDGPUInstructionSelector::selectMUBUFScratchOffset(
}
std::pair<Register, unsigned>
-AMDGPUInstructionSelector::selectDS1Addr1OffsetImpl(MachineOperand &Root) const {
- const MachineInstr *RootDef = MRI->getVRegDef(Root.getReg());
+AMDGPUInstructionSelector::selectDS1Addr1OffsetImpl(
+ MachineOperand &Root) const {
int64_t ConstAddr = 0;
Register PtrBase;
@@ -6750,13 +6747,11 @@ AMDGPUInstructionSelector::selectDS1Addr1OffsetImpl(MachineOperand &Root) const
// (add n0, c0)
return std::pair(PtrBase, Offset);
}
- } else if (RootDef->getOpcode() == AMDGPU::G_SUB) {
+ } else if (mi_match(Root.getReg(), *MRI, m_GSub(m_Reg(), m_Reg()))) {
// TODO
-
} else if (mi_match(Root.getReg(), *MRI, m_ICst(ConstAddr))) {
// TODO
-
}
return std::pair(Root.getReg(), 0);
@@ -6799,7 +6794,6 @@ AMDGPUInstructionSelector::selectDSReadWrite2(MachineOperand &Root,
std::pair<Register, unsigned>
AMDGPUInstructionSelector::selectDSReadWrite2Impl(MachineOperand &Root,
unsigned Size) const {
- const MachineInstr *RootDef = MRI->getVRegDef(Root.getReg());
int64_t ConstAddr = 0;
Register PtrBase;
@@ -6814,12 +6808,11 @@ AMDGPUInstructionSelector::selectDSReadWrite2Impl(MachineOperand &Root,
// (add n0, c0)
return std::pair(PtrBase, OffsetValue0 / Size);
}
- } else if (RootDef->getOpcode() == AMDGPU::G_SUB) {
+ } else if (mi_match(Root.getReg(), *MRI, m_GSub(m_Reg(), m_Reg()))) {
// TODO
} else if (mi_match(Root.getReg(), *MRI, m_ICst(ConstAddr))) {
// TODO
-
}
return std::pair(Root.getReg(), 0);
More information about the llvm-commits
mailing list