diff options
Diffstat (limited to 'include/llvm/IR/PatternMatch.h')
-rw-r--r-- | include/llvm/IR/PatternMatch.h | 56 |
1 files changed, 56 insertions, 0 deletions
diff --git a/include/llvm/IR/PatternMatch.h b/include/llvm/IR/PatternMatch.h index a30fc97e98ef..40f9c21f646b 100644 --- a/include/llvm/IR/PatternMatch.h +++ b/include/llvm/IR/PatternMatch.h @@ -157,6 +157,19 @@ inline match_combine_or<match_zero, match_neg_zero> m_AnyZero() { return m_CombineOr(m_Zero(), m_NegZero()); } +struct match_nan { + template <typename ITy> bool match(ITy *V) { + if (const auto *C = dyn_cast<ConstantFP>(V)) { + const APFloat &APF = C->getValueAPF(); + return APF.isNaN(); + } + return false; + } +}; + +/// Match an arbitrary NaN constant. This includes quiet and signalling nans. +inline match_nan m_NaN() { return match_nan(); } + struct apint_match { const APInt *&Res; apint_match(const APInt *&R) : Res(R) {} @@ -814,6 +827,13 @@ inline CastClass_match<OpTy, Instruction::ZExt> m_ZExt(const OpTy &Op) { return CastClass_match<OpTy, Instruction::ZExt>(Op); } +template <typename OpTy> +inline match_combine_or<CastClass_match<OpTy, Instruction::ZExt>, + CastClass_match<OpTy, Instruction::SExt>> +m_ZExtOrSExt(const OpTy &Op) { + return m_CombineOr(m_ZExt(Op), m_SExt(Op)); +} + /// \brief Matches UIToFP. template <typename OpTy> inline CastClass_match<OpTy, Instruction::UIToFP> m_UIToFP(const OpTy &Op) { @@ -826,6 +846,18 @@ inline CastClass_match<OpTy, Instruction::SIToFP> m_SIToFP(const OpTy &Op) { return CastClass_match<OpTy, Instruction::SIToFP>(Op); } +/// \brief Matches FPTrunc +template <typename OpTy> +inline CastClass_match<OpTy, Instruction::FPTrunc> m_FPTrunc(const OpTy &Op) { + return CastClass_match<OpTy, Instruction::FPTrunc>(Op); +} + +/// \brief Matches FPExt +template <typename OpTy> +inline CastClass_match<OpTy, Instruction::FPExt> m_FPExt(const OpTy &Op) { + return CastClass_match<OpTy, Instruction::FPExt>(Op); +} + //===----------------------------------------------------------------------===// // Matchers for unary operators // @@ -1316,6 +1348,14 @@ template <typename Val_t> inline Signum_match<Val_t> m_Signum(const Val_t &V) { // Matchers for two-operands operators with the operators in either order // +/// \brief Matches a BinaryOperator with LHS and RHS in either order. +template<typename LHS, typename RHS> +inline match_combine_or<AnyBinaryOp_match<LHS, RHS>, + AnyBinaryOp_match<RHS, LHS>> +m_c_BinOp(const LHS &L, const RHS &R) { + return m_CombineOr(m_BinOp(L, R), m_BinOp(R, L)); +} + /// \brief Matches an ICmp with a predicate over LHS and RHS in either order. /// Does not swap the predicate. template<typename LHS, typename RHS> @@ -1325,6 +1365,22 @@ m_c_ICmp(ICmpInst::Predicate &Pred, const LHS &L, const RHS &R) { return m_CombineOr(m_ICmp(Pred, L, R), m_ICmp(Pred, R, L)); } +/// \brief Matches a Add with LHS and RHS in either order. +template<typename LHS, typename RHS> +inline match_combine_or<BinaryOp_match<LHS, RHS, Instruction::Add>, + BinaryOp_match<RHS, LHS, Instruction::Add>> +m_c_Add(const LHS &L, const RHS &R) { + return m_CombineOr(m_Add(L, R), m_Add(R, L)); +} + +/// \brief Matches a Mul with LHS and RHS in either order. +template<typename LHS, typename RHS> +inline match_combine_or<BinaryOp_match<LHS, RHS, Instruction::Mul>, + BinaryOp_match<RHS, LHS, Instruction::Mul>> +m_c_Mul(const LHS &L, const RHS &R) { + return m_CombineOr(m_Mul(L, R), m_Mul(R, L)); +} + /// \brief Matches an And with LHS and RHS in either order. template<typename LHS, typename RHS> inline match_combine_or<BinaryOp_match<LHS, RHS, Instruction::And>, |