Index: include/llvm/IR/PatternMatch.h =================================================================== --- include/llvm/IR/PatternMatch.h +++ include/llvm/IR/PatternMatch.h @@ -31,6 +31,7 @@ #include "llvm/ADT/APFloat.h" #include "llvm/ADT/APInt.h" +#include "llvm/Analysis/TargetLibraryInfo.h" #include "llvm/IR/CallSite.h" #include "llvm/IR/Constant.h" #include "llvm/IR/Constants.h" @@ -1436,6 +1437,89 @@ return m_Intrinsic(Op0, Op1); } +/// \brief LibFunc matchers. +struct LibFunc_match { + LibFunc F; + TargetLibraryInfo TLI; + + LibFunc_match(LibFunc Func, TargetLibraryInfo TargetLI) + : F(Func), TLI(TargetLI) {} + + template bool match(OpTy *V) { + if (const auto *CI = dyn_cast(V)) + if (const auto *CalledF = CI->getCalledFunction()) + if (TLI.has(F)) + return TLI.getName(F) == CalledF->getName(); + return false; + } +}; + +/// LibFunc matches are combinations of Name matchers, and argument +/// matchers. +template +struct m_LibFunc_Ty; +template struct m_LibFunc_Ty { + using Ty = match_combine_and>; +}; +template struct m_LibFunc_Ty { + using Ty = + match_combine_and::Ty, + Argument_match>; +}; +template +struct m_LibFunc_Ty { + using Ty = + match_combine_and::Ty, + Argument_match>; +}; +template +struct m_LibFunc_Ty { + using Ty = + match_combine_and::Ty, + Argument_match>; +}; + +/// \brief Match LibFunc calls like this: +/// m_LibFunc(m_Value(X)) +template +inline LibFunc_match m_LibFunc(TargetLibraryInfo TLI) { + return LibFunc_match(F, TLI); +} + +template +inline typename m_LibFunc_Ty::Ty +m_LibFunc(const TargetLibraryInfo TLI, const T0 &Op0) { + return m_CombineAnd(m_LibFunc(TLI), m_Argument<0>(Op0)); +} + +template +inline typename m_LibFunc_Ty::Ty +m_LibFunc(const TargetLibraryInfo TLI, const T0 &Op0, const T0 &Op1) { + return m_CombineAnd(m_LibFunc(TLI, Op0), m_Argument<1>(Op1)); +} + +template +inline typename m_LibFunc_Ty::Ty +m_LibFunc(const TargetLibraryInfo TLI, + const T0 &Op0, + const T0 &Op1, + const T0 &Op2) { + return m_CombineAnd(m_LibFunc(TLI, Op0, Op1), m_Argument<2>(Op2)); +} + +template +inline typename m_LibFunc_Ty::Ty +m_LibFunc(const TargetLibraryInfo TLI, + const T0 &Op0, + const T0 &Op1, + const T0 &Op2, + const T0 &Op3) { + return m_CombineAnd(m_LibFunc(TLI, Op0, Op1, Op2), m_Argument<3>(Op3)); +} + template struct Signum_match { Opnd_t Val; Signum_match(const Opnd_t &V) : Val(V) {}