/*
 * Copyright 2020 WebAssembly Community Group participants
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

//
// match.h - Provides an easily extensible layered API for matching expression
// patterns and extracting their components. The low-level API provides modular
// building blocks for creating matchers for any data type and the high-level
// API provides a succinct and flexible interface for matching expressions and
// extracting useful information from them.

#ifndef wasm_ir_match_h
#define wasm_ir_match_h

#include "ir/abstract.h"
#include "wasm.h"

namespace wasm::Match {

// The available matchers are:
//
//  i32, i64, f32, f64
//
//    Match constants of the corresponding type. Takes zero or one argument. The
//    argument can be a specific value to match or it can be a pointer to a
//    value, Literal, or Const* at which to store the matched entity.
//
//  bval, ival, fval
//
//    Match any boolean, any integer or any floating point constant. Takes
//    neither, either, or both of two possible arguments: first, a pointer to a
//    value, Literal, or Const* at which to store the matched entity and second,
//    a specific value to match.
//
//  constant
//
//    Matches any numeric Const expression. Takes neither, either, or both of
//    two possible arguments: first, a pointer to either Literal or Const* at
//    which to store the matched entity and second, a specific value (given as
//    an int32_t) to match..
//
//  any
//
//    Matches any Expression. Optionally takes as an argument a pointer to
//    Expression* at which to store the matched Expression*.
//
//  unary
//
//    Matches Unary expressions. Takes an optional pointer to Unary* at which to
//    store the matched Unary*, followed by either a UnaryOp or an Abstract::Op
//    describing which unary expressions to match, followed by a matcher to
//    apply to the unary expression's operand.
//
//  binary
//
//    Matches Binary expressions. Takes an optional pointer to Binary* at which
//    to store the matched Binary*, followed by either a BinaryOp or an
//    Abstract::Op describing which binary expresions to match, followed by
//    matchers to apply to the binary expression's left and right operands.
//
//  select
//
//    Matches Select expressions. Takes an optional pointer to Select* at which
//    to store the matched Select*, followed by matchers to apply to the ifTrue,
//    ifFalse, and condition operands.
//
//
// How to create new matchers:
//
//  Lets add a matcher for an expression type that is declared in wasm.h:
//
//    class Frozzle : public SpecificExpression<Expression::FrozzleId> {
//    public:
//      Expression* foo;
//      Expression* bar;
//      Expression* baz;
//    };
//
//  This expression is very simple; in order to match it, all we need to do is
//  apply other matchers to its subexpressions. The matcher infrastructure will
//  handle this automatically once we tell it how to access the subexpressions.
//  To tell the matcher infrastructure how many subexpressions there are we need
//  to specialize `NumComponents`.
//
//    template<> struct NumComponents<Frozzle*> {
//      static constexpr size_t value = 3;
//    };
//
//  And to tell the matcher infrastructure how to access those three
//  subexpressions, we need to specialize `GetComponent` three times.
//
//    template<> struct GetComponent<Frozzle*, 0> {
//      Expression* operator()(Frozzle* curr) { return curr->foo; }
//    };
//    template<> struct GetComponent<Frozzle*, 1> {
//      Expression* operator()(Frozzle* curr) { return curr->bar; }
//    };
//    template<> struct GetComponent<Frozzle*, 2> {
//      Expression* operator()(Frozzle* curr) { return curr->baz; }
//    };
//
//  For simple expressions, that's all we need to do to get a fully functional
//  matcher that we can construct and use like this, where S1, S2, and S3 are
//  the types of the submatchers to use and s1, s2, and s3 are instances of
//  those types:
//
//    Frozzle* extracted;
//    auto matcher = Matcher<Frozzle*, S1, S2, S3>(&extracted, {}, s1, s2, s3);
//    if (matches(expr, matcher)) {
//      // `extracted` set to `expr` here
//    }
//
//  It's annoying to have to write out the types S1, S2, and S3 and we don't get
//  class template argument deduction (CTAD) until C++17, so it's useful to
//  create a wrapper function so can take advantage of function template
//  argument deduction. We can also take this opportunity to make the interface
//  more compact.
//
//    template<class S1, class S2, class S3>
//    inline decltype(auto) frozzle(Frozzle** binder,
//                                  S1&& s1, S2&& s2, S3&& s3) {
//      return Matcher<Frozzle*, S1, S2, S3>(binder, {}, s1, s2, s3);
//    }
//    template<class S1, class S2, class S3>
//    inline decltype(auto) frozzle(S1&& s1, S2&& s2, S3&& s3) {
//      return Matcher<Frozzle*, S1, S2, S3>(nullptr, {}, s1, s2, s3);
//    }
//
//  Notice that we make the interface more compact by providing overloads with
//  and without the binder. Here is the final matcher usage:
//
//    Frozzle* extracted;
//    if (matches(expr, frozzle(&extracted, s1, s2, s3))) {
//      // `extracted` set to `expr` here
//    }
//
//  Some matchers are more complicated, though, because they need to do
//  something besides just applying submatchers to the components of an
//  expression. These matchers require slightly more work.
//
//
// Complex matchers:
//
//  Lets add a matcher that will match calls to functions whose names start with
//  certain prefixes. Since this is not a normal matcher for Call expressions,
//  we can't identify it by the Call* type. Instead, we have to create a new
//  identifier type, called a "Kind" for it.
//
//    struct PrefixCallKind {};
//
//  Next, since we're not in the common case of using a specific expression
//  pointer as our kind, we have to tell the matcher infrastructure what type of
//  thing this matcher matches. Since we want this matcher to be able to match
//  any given prefix, we also need the matcher to contain the given prefix as
//  state, and we need to tell the matcher infrastructure what type that state
//  is as well. To specify these types, we need to specialize
//  `KindTypeRegistry` for `PrefixCallKind`.
//
//    template<> struct KindTypeRegistry<PrefixCallKind> {
//      using matched_t = Call*;
//      using data_t = Name;
//    };
//
//  Note that because `matched_t` is set to a specific expression pointer, this
//  matcher will automatically be able to be applied to any `Expression*`, not
//  just `Call*`. If `matched_t` were not a specific expression pointer, this
//  matcher would only be able to be applied to types compatible with
//  `matched_t`. Also note that if a matcher does not need to store any state,
//  its `data_t` should be set to `unused_t`.
//
//  Now we need to tell the matcher infrastructure what custom logic to apply
//  for this matcher. We do this by specializing `MatchSelf`.
//
//    template<> struct MatchSelf<PrefixCallKind> {
//      bool operator()(Call* curr, Name prefix) {
//        return curr->name.startsWith(prefix);
//      }
//    };
//
//  Note that the first parameter to `MatchSelf<Kind>::operator()` will be that
//  kind's `matched_t` and the second parameter will be that kind's `data_t`,
//  which may be `unused_t`. (TODO: detect if `data_t` is `unused_t` and don't
//  expose it in the Matcher interface if so.)
//
//  After this, everything is the same as in the simple matcher case. This
//  particular matcher doesn't need to recurse into any subcomponents, so we can
//  skip straight to creating the wrapper function.
//
//    decltype(auto) prefixCall(Call** binder, Name prefix) {
//      return Matcher<PrefixCallKind>(binder, prefix);
//    }
//
//  Now we can use the new matcher:
//
//    Call* call;
//    if (matches(expr, prefixCall(&call, "__foo"))) {
//      // `call` set to `expr` here
//    }
//

// The main entrypoint for matching. If the match succeeds, all variables bound
// in the matcher will be set to their corresponding matched values. Otherwise,
// the value of the bound variables is unspecified and may have changed.
template<class Matcher> inline bool matches(Expression* expr, Matcher matcher) {
  return matcher.matches(expr);
}

namespace Internal {

struct unused_t {};

// Each matcher has a `Kind`, which controls how candidate values are
// destructured and inspected. For most matchers, `Kind` is a pointer to the
// matched subtype of Expression, but when there are multiple matchers for the
// same kind of expression, they are disambiguated by having different `Kind`s.
// In this case, or if the matcher matches something besides a pointer to a
// subtype of Expression, or if the matcher requires additional state, the
// matched type and the type of additional state must be associated with the
// `Kind` via a specialization of `KindTypeRegistry`.
template<class Kind> struct KindTypeRegistry {
  // The matched type
  using matched_t = void;
  // The type of additional state needed to perform a match. Can be set to
  // `unused_t` if it's not needed.
  using data_t = unused_t;
};

// Given a `Kind`, produce the type `matched_t` that is matched by that Kind and
// the type `candidate_t` that is the type of the parameter of the `matches`
// method. These types are only different if `matched_t` is a pointer to a
// subtype of Expression, in which case `candidate_t` is Expression*.
template<class Kind> struct MatchTypes {
  using matched_t = typename std::conditional_t<
    std::is_base_of<Expression, std::remove_pointer_t<Kind>>::value,
    Kind,
    typename KindTypeRegistry<Kind>::matched_t>;

  static constexpr bool isExpr =
    std::is_base_of<Expression, std::remove_pointer_t<matched_t>>::value;

  using candidate_t =
    typename std::conditional_t<isExpr, Expression*, matched_t>;
};

template<class Kind> using matched_t = typename MatchTypes<Kind>::matched_t;
template<class Kind> using candidate_t = typename MatchTypes<Kind>::candidate_t;
template<class Kind> using data_t = typename KindTypeRegistry<Kind>::data_t;

// Defined if the matched type is a specific expression pointer, so can be
// `dynCast`ed to from Expression*.
template<class Kind>
using enable_if_castable_t = typename std::enable_if<
  std::is_base_of<Expression, std::remove_pointer_t<matched_t<Kind>>>::value &&
    !std::is_same<Expression*, matched_t<Kind>>::value,
  int>::type;

// Opposite of above
template<class Kind>
using enable_if_not_castable_t = typename std::enable_if<
  !std::is_base_of<Expression, std::remove_pointer_t<matched_t<Kind>>>::value ||
    std::is_same<Expression*, matched_t<Kind>>::value,
  int>::type;

// Do a normal dynCast from Expression* to the subtype, storing the result in
// `out` and returning `true` iff the cast succeeded.
template<class Kind, enable_if_castable_t<Kind> = 0>
inline bool dynCastCandidate(candidate_t<Kind> candidate,
                             matched_t<Kind>& out) {
  out = candidate->template dynCast<std::remove_pointer_t<matched_t<Kind>>>();
  return out != nullptr;
}

// Otherwise we are not matching an Expression, so this is infallible.
template<class Kind, enable_if_not_castable_t<Kind> = 0>
inline bool dynCastCandidate(candidate_t<Kind> candidate,
                             matched_t<Kind>& out) {
  out = candidate;
  return true;
}

// Matchers can optionally specialize this to perform custom matching logic
// before recursing into submatchers, potentially short-circuiting the match.
// Uses a struct because partial specialization of functions is not allowed.
template<class Kind> struct MatchSelf {
  bool operator()(matched_t<Kind>, data_t<Kind>) { return true; }
};

// Used to statically ensure that each matcher has the correct number of
// submatchers. This needs to be specialized for each kind of matcher that has
// submatchers.
template<class Kind> struct NumComponents {
  static constexpr size_t value = 0;
};

// Every kind of matcher needs to partially specialize this for each of its
// components. Each specialization should define
//
//   T operator()(matched_t<Kind>)
//
// where T is the component's type. Components will be matched from first to
// last. Uses a struct instead of a function because partial specialization of
// functions is not allowed.
template<class Kind, int pos> struct GetComponent;

// A type-level linked list to hold an arbitrary number of matchers.
template<class...> struct SubMatchers {};
template<class CurrMatcher, class... NextMatchers>
struct SubMatchers<CurrMatcher, NextMatchers...> {
  CurrMatcher curr;
  SubMatchers<NextMatchers...> next;
  SubMatchers(CurrMatcher curr, NextMatchers... next)
    : curr(curr), next(next...) {};
};

// Iterates through the components of the candidate, applying a submatcher to
// each component. Uses a struct instead of a function because partial
// specialization of functions is not allowed.
template<class Kind, int pos, class CurrMatcher = void, class... NextMatchers>
struct Components {
  static inline bool
  match(matched_t<Kind> candidate,
        SubMatchers<CurrMatcher, NextMatchers...>& matchers) {
    return matchers.curr.matches(GetComponent<Kind, pos>{}(candidate)) &&
           Components<Kind, pos + 1, NextMatchers...>::match(candidate,
                                                             matchers.next);
  }
};
template<class Kind, int pos> struct Components<Kind, pos> {
  static_assert(pos == NumComponents<Kind>::value,
                "Unexpected number of submatchers");
  static inline bool match(matched_t<Kind>, SubMatchers<>) {
    // Base case when there are no components left; trivially true.
    return true;
  }
};

template<class Kind, class... Matchers> struct Matcher {
  matched_t<Kind>* binder;
  data_t<Kind> data;
  SubMatchers<Matchers...> submatchers;

  Matcher(matched_t<Kind>* binder, data_t<Kind> data, Matchers... submatchers)
    : binder(binder), data(data), submatchers(submatchers...) {}

  inline bool matches(candidate_t<Kind> candidate) {
    matched_t<Kind> casted;
    if (dynCastCandidate<Kind>(candidate, casted)) {
      if (binder != nullptr) {
        *binder = casted;
      }
      return MatchSelf<Kind>{}(casted, data) &&
             Components<Kind, 0, Matchers...>::match(casted, submatchers);
    }
    return false;
  }
};

// Concrete low-level matcher implementations. Not intended for direct external
// use.

// Any<T>: matches any value of the expected type
template<class T> struct AnyKind {};
template<class T> struct KindTypeRegistry<AnyKind<T>> {
  using matched_t = T;
  using data_t = unused_t;
};
template<class T> inline decltype(auto) Any(T* binder) {
  return Matcher<AnyKind<T>>(binder, {});
}

// Exact<T>: matches exact values of the expected type
template<class T> struct ExactKind {};
template<class T> struct KindTypeRegistry<ExactKind<T>> {
  using matched_t = T;
  using data_t = T;
};
template<class T> struct MatchSelf<ExactKind<T>> {
  bool operator()(T self, T expected) { return self == expected; }
};
template<class T> inline decltype(auto) Exact(T* binder, T data) {
  return Matcher<ExactKind<T>>(binder, data);
}

// {Bool,I32,I64,Int,F32,F64,Float,Number}Lit:
// match `Literal` of the expected `Type`
struct BoolLK {
  static bool matchType(Literal lit) {
    return lit.type == Type::i32 && (uint32_t)lit.geti32() <= 1U;
  }
  static int32_t getVal(Literal lit) { return lit.geti32(); }
};
struct I32LK {
  static bool matchType(Literal lit) { return lit.type == Type::i32; }
  static int32_t getVal(Literal lit) { return lit.geti32(); }
};
struct I64LK {
  static bool matchType(Literal lit) { return lit.type == Type::i64; }
  static int64_t getVal(Literal lit) { return lit.geti64(); }
};
struct IntLK {
  static bool matchType(Literal lit) { return lit.type.isInteger(); }
  static int64_t getVal(Literal lit) { return lit.getInteger(); }
};
struct F32LK {
  static bool matchType(Literal lit) { return lit.type == Type::f32; }
  static float getVal(Literal lit) { return lit.getf32(); }
};
struct F64LK {
  static bool matchType(Literal lit) { return lit.type == Type::f64; }
  static double getVal(Literal lit) { return lit.getf64(); }
};
struct FloatLK {
  static bool matchType(Literal lit) { return lit.type.isFloat(); }
  static double getVal(Literal lit) { return lit.getFloat(); }
};
template<class T> struct LitKind {};
template<class T> struct KindTypeRegistry<LitKind<T>> {
  using matched_t = Literal;
  using data_t = unused_t;
};
template<class T> struct MatchSelf<LitKind<T>> {
  bool operator()(Literal lit, unused_t) { return T::matchType(lit); }
};
template<class T> struct NumComponents<LitKind<T>> {
  static constexpr size_t value = 1;
};
template<class T> struct GetComponent<LitKind<T>, 0> {
  decltype(auto) operator()(Literal lit) { return T::getVal(lit); }
};
template<class S> inline decltype(auto) BoolLit(Literal* binder, S&& s) {
  return Matcher<LitKind<BoolLK>, S>(binder, {}, s);
}
template<class S> inline decltype(auto) I32Lit(Literal* binder, S&& s) {
  return Matcher<LitKind<I32LK>, S>(binder, {}, s);
}
template<class S> inline decltype(auto) I64Lit(Literal* binder, S&& s) {
  return Matcher<LitKind<I64LK>, S>(binder, {}, s);
}
template<class S> inline decltype(auto) IntLit(Literal* binder, S&& s) {
  return Matcher<LitKind<IntLK>, S>(binder, {}, s);
}
template<class S> inline decltype(auto) F32Lit(Literal* binder, S&& s) {
  return Matcher<LitKind<F32LK>, S>(binder, {}, s);
}
template<class S> inline decltype(auto) F64Lit(Literal* binder, S&& s) {
  return Matcher<LitKind<F64LK>, S>(binder, {}, s);
}
template<class S> inline decltype(auto) FloatLit(Literal* binder, S&& s) {
  return Matcher<LitKind<FloatLK>, S>(binder, {}, s);
}
struct NumberLitKind {};
template<> struct KindTypeRegistry<NumberLitKind> {
  using matched_t = Literal;
  using data_t = int32_t;
};
template<> struct MatchSelf<NumberLitKind> {
  bool operator()(Literal lit, int32_t expected) {
    return lit.type.isNumber() &&
           Literal::makeFromInt32(expected, lit.type) == lit;
  }
};
inline decltype(auto) NumberLit(Literal* binder, int32_t expected) {
  return Matcher<NumberLitKind>(binder, expected);
}

// Const
template<> struct NumComponents<Const*> {
  static constexpr size_t value = 1;
};
template<> struct GetComponent<Const*, 0> {
  Literal operator()(Const* c) { return c->value; }
};
template<class S> inline decltype(auto) ConstMatcher(Const** binder, S&& s) {
  return Matcher<Const*, S>(binder, {}, s);
}

// Unary, UnaryOp and AbstractUnaryOp
template<> struct NumComponents<Unary*> {
  static constexpr size_t value = 2;
};
template<> struct GetComponent<Unary*, 0> {
  UnaryOp operator()(Unary* curr) { return curr->op; }
};
template<> struct GetComponent<Unary*, 1> {
  Expression* operator()(Unary* curr) { return curr->value; }
};
struct UnaryOpK {
  using Op = UnaryOp;
  static UnaryOp getOp(Type, Op op) { return op; }
};
struct AbstractUnaryOpK {
  using Op = Abstract::Op;
  static UnaryOp getOp(Type type, Abstract::Op op) {
    return Abstract::getUnary(type, op);
  }
};
template<class T> struct UnaryOpKind {};
template<class T> struct KindTypeRegistry<UnaryOpKind<T>> {
  using matched_t = Unary*;
  using data_t = typename T::Op;
};
template<class T> struct MatchSelf<UnaryOpKind<T>> {
  bool operator()(Unary* curr, typename T::Op op) {
    return curr->op == T::getOp(curr->value->type, op);
  }
};
template<class T> struct NumComponents<UnaryOpKind<T>> {
  static constexpr size_t value = 1;
};
template<class T> struct GetComponent<UnaryOpKind<T>, 0> {
  Expression* operator()(Unary* curr) { return curr->value; }
};
template<class S1, class S2>
inline decltype(auto) UnaryMatcher(Unary** binder, S1&& s1, S2&& s2) {
  return Matcher<Unary*, S1, S2>(binder, {}, s1, s2);
}
template<class S>
inline decltype(auto) UnaryOpMatcher(Unary** binder, UnaryOp op, S&& s) {
  return Matcher<UnaryOpKind<UnaryOpK>, S>(binder, op, s);
}
template<class S>
inline decltype(auto)
AbstractUnaryOpMatcher(Unary** binder, Abstract::Op op, S&& s) {
  return Matcher<UnaryOpKind<AbstractUnaryOpK>, S>(binder, op, s);
}

// Binary, BinaryOp and AbstractBinaryOp
template<> struct NumComponents<Binary*> {
  static constexpr size_t value = 3;
};
template<> struct GetComponent<Binary*, 0> {
  BinaryOp operator()(Binary* curr) { return curr->op; }
};
template<> struct GetComponent<Binary*, 1> {
  Expression* operator()(Binary* curr) { return curr->left; }
};
template<> struct GetComponent<Binary*, 2> {
  Expression* operator()(Binary* curr) { return curr->right; }
};
struct BinaryOpK {
  using Op = BinaryOp;
  static BinaryOp getOp(Type, Op op) { return op; }
};
struct AbstractBinaryOpK {
  using Op = Abstract::Op;
  static BinaryOp getOp(Type type, Abstract::Op op) {
    return Abstract::getBinary(type, op);
  }
};
template<class T> struct BinaryOpKind {};
template<class T> struct KindTypeRegistry<BinaryOpKind<T>> {
  using matched_t = Binary*;
  using data_t = typename T::Op;
};
template<class T> struct MatchSelf<BinaryOpKind<T>> {
  bool operator()(Binary* curr, typename T::Op op) {
    return curr->op == T::getOp(curr->left->type, op);
  }
};
template<class T> struct NumComponents<BinaryOpKind<T>> {
  static constexpr size_t value = 2;
};
template<class T> struct GetComponent<BinaryOpKind<T>, 0> {
  Expression* operator()(Binary* curr) { return curr->left; }
};
template<class T> struct GetComponent<BinaryOpKind<T>, 1> {
  Expression* operator()(Binary* curr) { return curr->right; }
};
template<class S1, class S2, class S3>
inline decltype(auto)
BinaryMatcher(Binary** binder, S1&& s1, S2&& s2, S3&& s3) {
  return Matcher<Binary*, S1, S2, S3>(binder, {}, s1, s2, s3);
}
template<class S1, class S2>
inline decltype(auto)
BinaryOpMatcher(Binary** binder, BinaryOp op, S1&& s1, S2&& s2) {
  return Matcher<BinaryOpKind<BinaryOpK>, S1, S2>(binder, op, s1, s2);
}
template<class S1, class S2>
inline decltype(auto)
AbstractBinaryOpMatcher(Binary** binder, Abstract::Op op, S1&& s1, S2&& s2) {
  return Matcher<BinaryOpKind<AbstractBinaryOpK>, S1, S2>(binder, op, s1, s2);
}

// Select
template<> struct NumComponents<Select*> {
  static constexpr size_t value = 3;
};
template<> struct GetComponent<Select*, 0> {
  Expression* operator()(Select* curr) { return curr->ifTrue; }
};
template<> struct GetComponent<Select*, 1> {
  Expression* operator()(Select* curr) { return curr->ifFalse; }
};
template<> struct GetComponent<Select*, 2> {
  Expression* operator()(Select* curr) { return curr->condition; }
};
template<class S1, class S2, class S3>
inline decltype(auto)
SelectMatcher(Select** binder, S1&& s1, S2&& s2, S3&& s3) {
  return Matcher<Select*, S1, S2, S3>(binder, {}, s1, s2, s3);
}

} // namespace Internal

// Public matching API

inline decltype(auto) bval() {
  return Internal::ConstMatcher(
    nullptr, Internal::BoolLit(nullptr, Internal::Any<bool>(nullptr)));
}
inline decltype(auto) bval(bool x) {
  return Internal::ConstMatcher(
    nullptr, Internal::BoolLit(nullptr, Internal::Exact<bool>(nullptr, x)));
}
inline decltype(auto) bval(bool* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::BoolLit(nullptr, Internal::Any(binder)));
}
inline decltype(auto) bval(Literal* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::BoolLit(binder, Internal::Any<bool>(nullptr)));
}
inline decltype(auto) bval(Const** binder) {
  return Internal::ConstMatcher(
    binder, Internal::BoolLit(nullptr, Internal::Any<bool>(nullptr)));
}

inline decltype(auto) i32() {
  return Internal::ConstMatcher(
    nullptr, Internal::I32Lit(nullptr, Internal::Any<int32_t>(nullptr)));
}
// Use int rather than int32_t to disambiguate literal 0, which otherwise could
// be resolved to either the int32_t overload or any of the pointer overloads.
inline decltype(auto) i32(int x) {
  return Internal::ConstMatcher(
    nullptr, Internal::I32Lit(nullptr, Internal::Exact<int32_t>(nullptr, x)));
}
inline decltype(auto) i32(int32_t* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::I32Lit(nullptr, Internal::Any(binder)));
}
inline decltype(auto) i32(Literal* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::I32Lit(binder, Internal::Any<int32_t>(nullptr)));
}
inline decltype(auto) i32(Const** binder) {
  return Internal::ConstMatcher(
    binder, Internal::I32Lit(nullptr, Internal::Any<int32_t>(nullptr)));
}

inline decltype(auto) i64() {
  return Internal::ConstMatcher(
    nullptr, Internal::I64Lit(nullptr, Internal::Any<int64_t>(nullptr)));
}
inline decltype(auto) i64(int64_t x) {
  return Internal::ConstMatcher(
    nullptr, Internal::I64Lit(nullptr, Internal::Exact<int64_t>(nullptr, x)));
}
// Disambiguate literal 0, which could otherwise be interpreted as a pointer
inline decltype(auto) i64(int x) { return i64(int64_t(x)); }
inline decltype(auto) i64(int64_t* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::I64Lit(nullptr, Internal::Any(binder)));
}
inline decltype(auto) i64(Literal* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::I64Lit(binder, Internal::Any<int64_t>(nullptr)));
}
inline decltype(auto) i64(Const** binder) {
  return Internal::ConstMatcher(
    binder, Internal::I64Lit(nullptr, Internal::Any<int64_t>(nullptr)));
}

inline decltype(auto) f32() {
  return Internal::ConstMatcher(
    nullptr, Internal::F32Lit(nullptr, Internal::Any<float>(nullptr)));
}
inline decltype(auto) f32(float x) {
  return Internal::ConstMatcher(
    nullptr, Internal::F32Lit(nullptr, Internal::Exact<float>(nullptr, x)));
}
// Disambiguate literal 0, which could otherwise be interpreted as a pointer
inline decltype(auto) f32(int x) { return f32(float(x)); }
inline decltype(auto) f32(float* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::F32Lit(nullptr, Internal::Any(binder)));
}
inline decltype(auto) f32(Literal* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::F32Lit(binder, Internal::Any<float>(nullptr)));
}
inline decltype(auto) f32(Const** binder) {
  return Internal::ConstMatcher(
    binder, Internal::F32Lit(nullptr, Internal::Any<float>(nullptr)));
}

inline decltype(auto) f64() {
  return Internal::ConstMatcher(
    nullptr, Internal::F64Lit(nullptr, Internal::Any<double>(nullptr)));
}
inline decltype(auto) f64(double x) {
  return Internal::ConstMatcher(
    nullptr, Internal::F64Lit(nullptr, Internal::Exact<double>(nullptr, x)));
}
// Disambiguate literal 0, which could otherwise be interpreted as a pointer
inline decltype(auto) f64(int x) { return f64(double(x)); }
inline decltype(auto) f64(double* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::F64Lit(nullptr, Internal::Any(binder)));
}
inline decltype(auto) f64(Literal* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::F64Lit(binder, Internal::Any<double>(nullptr)));
}
inline decltype(auto) f64(Const** binder) {
  return Internal::ConstMatcher(
    binder, Internal::F64Lit(nullptr, Internal::Any<double>(nullptr)));
}

inline decltype(auto) ival() {
  return Internal::ConstMatcher(
    nullptr, Internal::IntLit(nullptr, Internal::Any<int64_t>(nullptr)));
}
inline decltype(auto) ival(int64_t x) {
  return Internal::ConstMatcher(
    nullptr, Internal::IntLit(nullptr, Internal::Exact<int64_t>(nullptr, x)));
}
// Disambiguate literal 0, which could otherwise be interpreted as a pointer
inline decltype(auto) ival(int x) { return ival(int64_t(x)); }
inline decltype(auto) ival(int64_t* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::IntLit(nullptr, Internal::Any(binder)));
}
inline decltype(auto) ival(Literal* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::IntLit(binder, Internal::Any<int64_t>(nullptr)));
}
inline decltype(auto) ival(Const** binder) {
  return Internal::ConstMatcher(
    binder, Internal::IntLit(nullptr, Internal::Any<int64_t>(nullptr)));
}
inline decltype(auto) ival(Literal* binder, int64_t x) {
  return Internal::ConstMatcher(
    nullptr, Internal::IntLit(binder, Internal::Exact<int64_t>(nullptr, x)));
}
inline decltype(auto) ival(Const** binder, int64_t x) {
  return Internal::ConstMatcher(
    binder, Internal::IntLit(nullptr, Internal::Exact<int64_t>(nullptr, x)));
}

inline decltype(auto) fval() {
  return Internal::ConstMatcher(
    nullptr, Internal::FloatLit(nullptr, Internal::Any<double>(nullptr)));
}
inline decltype(auto) fval(double x) {
  return Internal::ConstMatcher(
    nullptr, Internal::FloatLit(nullptr, Internal::Exact<double>(nullptr, x)));
}
// Disambiguate literal 0, which could otherwise be interpreted as a pointer
inline decltype(auto) fval(int x) { return fval(double(x)); }
inline decltype(auto) fval(double* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::FloatLit(nullptr, Internal::Any(binder)));
}
inline decltype(auto) fval(Literal* binder) {
  return Internal::ConstMatcher(
    nullptr, Internal::FloatLit(binder, Internal::Any<double>(nullptr)));
}
inline decltype(auto) fval(Const** binder) {
  return Internal::ConstMatcher(
    binder, Internal::FloatLit(nullptr, Internal::Any<double>(nullptr)));
}
inline decltype(auto) fval(Literal* binder, double x) {
  return Internal::ConstMatcher(
    nullptr, Internal::FloatLit(binder, Internal::Exact<double>(nullptr, x)));
}
inline decltype(auto) fval(Const** binder, double x) {
  return Internal::ConstMatcher(
    binder, Internal::FloatLit(nullptr, Internal::Exact<double>(nullptr, x)));
}

inline decltype(auto) constant() {
  return Internal::ConstMatcher(nullptr, Internal::Any<Literal>(nullptr));
}
inline decltype(auto) constant(int x) {
  return Internal::ConstMatcher(nullptr, Internal::NumberLit(nullptr, x));
}
inline decltype(auto) constant(Literal* binder) {
  return Internal::ConstMatcher(nullptr, Internal::Any(binder));
}
inline decltype(auto) constant(Const** binder) {
  return Internal::ConstMatcher(binder, Internal::Any<Literal>(nullptr));
}
inline decltype(auto) constant(Literal* binder, int32_t x) {
  return Internal::ConstMatcher(nullptr, Internal::NumberLit(binder, x));
}
inline decltype(auto) constant(Const** binder, int32_t x) {
  return Internal::ConstMatcher(binder, Internal::NumberLit(nullptr, x));
}

inline decltype(auto) any() { return Internal::Any<Expression*>(nullptr); }
inline decltype(auto) any(Expression** binder) { return Internal::Any(binder); }

template<class S> inline decltype(auto) unary(S&& s) {
  return Internal::UnaryMatcher(nullptr, Internal::Any<UnaryOp>(nullptr), s);
}
template<class S> inline decltype(auto) unary(Unary** binder, S&& s) {
  return Internal::UnaryMatcher(binder, Internal::Any<UnaryOp>(nullptr), s);
}
template<class S> inline decltype(auto) unary(UnaryOp* binder, S&& s) {
  return Internal::UnaryMatcher(nullptr, Internal::Any<UnaryOp>(binder), s);
}
template<class S> inline decltype(auto) unary(UnaryOp op, S&& s) {
  return Internal::UnaryOpMatcher(nullptr, op, s);
}
template<class S> inline decltype(auto) unary(Abstract::Op op, S&& s) {
  return Internal::AbstractUnaryOpMatcher(nullptr, op, s);
}
template<class S>
inline decltype(auto) unary(Unary** binder, UnaryOp op, S&& s) {
  return Internal::UnaryOpMatcher(binder, op, s);
}
template<class S>
inline decltype(auto) unary(Unary** binder, Abstract::Op op, S&& s) {
  return Internal::AbstractUnaryOpMatcher(binder, op, s);
}
template<class S1, class S2> inline decltype(auto) binary(S1&& s1, S2&& s2) {
  return Internal::BinaryMatcher(
    nullptr, Internal::Any<BinaryOp>(nullptr), s1, s2);
}
template<class S1, class S2>
inline decltype(auto) binary(Binary** binder, S1&& s1, S2&& s2) {
  return Internal::BinaryMatcher(
    binder, Internal::Any<BinaryOp>(nullptr), s1, s2);
}
template<class S1, class S2>
inline decltype(auto) binary(BinaryOp* binder, S1&& s1, S2&& s2) {
  return Internal::BinaryMatcher(
    nullptr, Internal::Any<BinaryOp>(binder), s1, s2);
}
template<class S1, class S2>
inline decltype(auto) binary(BinaryOp op, S1&& s1, S2&& s2) {
  return Internal::BinaryOpMatcher(nullptr, op, s1, s2);
}
template<class S1, class S2>
inline decltype(auto) binary(Abstract::Op op, S1&& s1, S2&& s2) {
  return Internal::AbstractBinaryOpMatcher(nullptr, op, s1, s2);
}
template<class S1, class S2>
inline decltype(auto) binary(Binary** binder, BinaryOp op, S1&& s1, S2&& s2) {
  return Internal::BinaryOpMatcher(binder, op, s1, s2);
}
template<class S1, class S2>
inline decltype(auto)
binary(Binary** binder, Abstract::Op op, S1&& s1, S2&& s2) {
  return Internal::AbstractBinaryOpMatcher(binder, op, s1, s2);
}

template<class S1, class S2, class S3>
inline decltype(auto) select(S1&& s1, S2&& s2, S3&& s3) {
  return Internal::SelectMatcher(nullptr, s1, s2, s3);
}
template<class S1, class S2, class S3>
inline decltype(auto) select(Select** binder, S1&& s1, S2&& s2, S3&& s3) {
  return Internal::SelectMatcher(binder, s1, s2, s3);
}

} // namespace wasm::Match

#endif // wasm_ir_match_h
