Skip to content

Commit 770e55a

Browse files
committed
VPlan Pattern match for Instruction::Select
1 parent f44a950 commit 770e55a

File tree

1 file changed

+57
-0
lines changed

1 file changed

+57
-0
lines changed

llvm/lib/Transforms/Vectorize/VPlanPatternMatch.h

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,17 @@ template <typename Class> struct bind_ty {
5050
}
5151
};
5252

53+
/// Match a specified VPValue.
54+
struct specificval_ty {
55+
const VPValue *Val;
56+
57+
specificval_ty(const VPValue *V) : Val(V) {} //std::move?
58+
59+
bool match(VPValue *VPV) { return VPV == Val; }
60+
};
61+
62+
inline specificval_ty m_Specific(const VPValue *VPV) { return VPV; }
63+
5364
/// Match a specified integer value or vector of all elements of that
5465
/// value. \p BitWidth optionally specifies the bitwidth the matched constant
5566
/// must have. If it is 0, the matched constant can have any bitwidth.
@@ -197,6 +208,39 @@ using AllBinaryRecipe_match =
197208
BinaryRecipe_match<Op0_t, Op1_t, Opcode, Commutative, VPWidenRecipe,
198209
VPReplicateRecipe, VPWidenCastRecipe, VPInstruction>;
199210

211+
template <typename Op0_t, typename Op1_t, typename Op2_t, unsigned Opcode,
212+
typename... RecipeTys>
213+
struct TernaryRecipe_match {
214+
Op0_t Op0;
215+
Op1_t Op1;
216+
Op2_t Op2;
217+
218+
TernaryRecipe_match(Op0_t Op0, Op1_t Op1, Op2_t Op2)
219+
: Op0(Op0), Op1(Op1), Op2(Op2) {}
220+
221+
bool match(const VPValue *V) {
222+
auto *DefR = V->getDefiningRecipe();
223+
return DefR && match(DefR);
224+
}
225+
226+
bool match(const VPSingleDefRecipe *R) {
227+
return match(static_cast<const VPRecipeBase *>(R));
228+
}
229+
230+
bool match(const VPRecipeBase *R) {
231+
if (!detail::MatchRecipeAndOpcode<Opcode, RecipeTys...>::match(R))
232+
return false;
233+
assert(R->getNumOperands() == 3 &&
234+
"recipe with matched opcode does not have 3 operands");
235+
return Op0.match(R->getOperand(0)) && Op1.match(R->getOperand(1)) &&
236+
Op2.match(R->getOperand(2));
237+
}
238+
};
239+
240+
template <typename Op0_t, typename Op1_t, typename Op2_t, unsigned Opcode>
241+
using TernaryVPInstruction_match =
242+
TernaryRecipe_match<Op0_t, Op1_t, Op2_t, Opcode, VPInstruction>;
243+
200244
template <unsigned Opcode, typename Op0_t>
201245
inline UnaryVPInstruction_match<Op0_t, Opcode>
202246
m_VPInstruction(const Op0_t &Op0) {
@@ -209,6 +253,12 @@ m_VPInstruction(const Op0_t &Op0, const Op1_t &Op1) {
209253
return BinaryVPInstruction_match<Op0_t, Op1_t, Opcode>(Op0, Op1);
210254
}
211255

256+
template <unsigned Opcode, typename Op0_t, typename Op1_t, typename Op2_t>
257+
inline TernaryVPInstruction_match<Op0_t, Op1_t, Op2_t, Opcode>
258+
m_VPInstruction(const Op0_t &Op0, const Op1_t &Op1, const Op2_t &Op2) {
259+
return TernaryVPInstruction_match<Op0_t, Op1_t, Op2_t, Opcode>(Op0, Op1, Op2);
260+
}
261+
212262
template <typename Op0_t>
213263
inline UnaryVPInstruction_match<Op0_t, VPInstruction::Not>
214264
m_Not(const Op0_t &Op0) {
@@ -304,6 +354,13 @@ m_LogicalAnd(const Op0_t &Op0, const Op1_t &Op1) {
304354
return m_VPInstruction<VPInstruction::LogicalAnd, Op0_t, Op1_t>(Op0, Op1);
305355
}
306356

357+
template <typename Op0_t, typename Op1_t, typename Op2_t>
358+
inline TernaryVPInstruction_match<Op0_t, Op1_t, Op2_t, Instruction::Select>
359+
m_Select(const Op0_t &Cond, const Op1_t &LHS, const Op2_t &RHS) {
360+
return m_VPInstruction<Instruction::Select, Op0_t, Op1_t, Op2_t>(Cond, LHS,
361+
RHS);
362+
}
363+
307364
struct VPCanonicalIVPHI_match {
308365
bool match(const VPValue *V) {
309366
auto *DefR = V->getDefiningRecipe();

0 commit comments

Comments
 (0)