26#ifndef TVM_TIRX_STMT_FUNCTOR_H_
27#define TVM_TIRX_STMT_FUNCTOR_H_
35#include <unordered_map>
50template <
typename FType>
53template <
typename R,
typename... Args>
67 return Dispatch(node, std::forward<Args>(args)...);
70 TVM_FFI_INLINE
virtual R
Dispatch(
const Stmt& node, Args... args) {
71 TVM_FFI_ICHECK(node.defined()) <<
"Cannot dispatch a null statement";
72 return (*vtable_)(node,
this, std::forward<Args>(args)...);
76 return DispatchDefault_(node, std::forward<Args>(args)...);
79 return DispatchDefault_(node, std::forward<Args>(args)...);
82 return DispatchDefault_(node, std::forward<Args>(args)...);
85 return DispatchDefault_(node, std::forward<Args>(args)...);
88 return DispatchDefault_(node, std::forward<Args>(args)...);
91 return DispatchDefault_(node, std::forward<Args>(args)...);
94 return DispatchDefault_(node, std::forward<Args>(args)...);
97 return DispatchDefault_(node, std::forward<Args>(args)...);
100 return DispatchDefault_(node, std::forward<Args>(args)...);
103 return DispatchDefault_(node, std::forward<Args>(args)...);
106 return DispatchDefault_(node, std::forward<Args>(args)...);
109 return DispatchDefault_(node, std::forward<Args>(args)...);
113 TVM_FFI_THROW(InternalError) <<
"Do not have a default for " << node->GetTypeKey();
114 TVM_FFI_UNREACHABLE();
124 vtable->template SetDispatch<StmtNode>(
125 [](
const ffi::ObjectRef& node,
TSelf* self, Args... args) -> R {
126 return self->DispatchDefault_(node.get(), std::forward<Args>(args)...);
128 SetDispatch<TSelf, BindNode>(vtable);
129 SetDispatch<TSelf, RegionStmtNode>(vtable);
130 SetDispatch<TSelf, IfNode>(vtable);
131 SetDispatch<TSelf, ForNode>(vtable);
132 SetDispatch<TSelf, WhileNode>(vtable);
133 SetDispatch<TSelf, ReturnNode>(vtable);
134 SetDispatch<TSelf, BreakNode>(vtable);
135 SetDispatch<TSelf, ContinueNode>(vtable);
136 SetDispatch<TSelf, TensorStoreNode>(vtable);
137 SetDispatch<TSelf, AssertStmtNode>(vtable);
138 SetDispatch<TSelf, SeqStmtNode>(vtable);
139 SetDispatch<TSelf, EvaluateNode>(vtable);
142 template <
typename Self,
typename Node>
144 vtable->template SetDispatch<Node>(
145 [](
const ffi::ObjectRef& node,
TSelf* self, Args... args) -> R {
146 return static_cast<Self*>(self)->Dispatch_(static_cast<const Node*>(node.get()),
147 std::forward<Args>(args)...);
152 static const VTable* GlobalVTable() {
153 static const VTable table = [] {
161 const VTable* vtable_;
235 InplaceMode inplace_mode = InplaceMode::kDisallow) {
236 return ffi::details::UnchangedOrUnsafe::MoveFromTVMFFIAny<Stmt>(
237 ffi::details::UnchangedOrUnsafe::MoveToTVMFFIAny(Mutate(ffi::AnyView(stmt), inplace_mode)));
242 InplaceMode inplace_mode = InplaceMode::kDisallow) {
243 auto result = Mutate(
static_cast<const Stmt&
>(stmt), inplace_mode);
244 if (result.UnchangedOrSameAs(stmt))
return ffi::Unchanged();
245 return SeqStmt(std::move(result).ValueUnchecked());
248 TVM_FFI_INLINE UnchangedOr<ffi::Optional<SeqStmt>>
Mutate(
249 const ffi::Optional<SeqStmt>& stmt, InplaceMode inplace_mode = InplaceMode::kDisallow) {
250 if (!stmt.has_value())
return ffi::Unchanged();
251 auto result = Mutate(stmt.value(), inplace_mode);
252 if (result.IsUnchanged())
return ffi::Unchanged();
253 return ffi::Optional<SeqStmt>(std::move(result).ValueUnchecked());
257 TVM_FFI_INLINE UnchangedOr<ffi::Optional<Stmt>>
Mutate(
258 const ffi::Optional<Stmt>& stmt, InplaceMode inplace_mode = InplaceMode::kDisallow) {
259 if (!stmt.has_value())
return ffi::Unchanged();
260 auto result = Mutate(stmt.value(), inplace_mode);
261 if (result.IsUnchanged())
return ffi::Unchanged();
262 return ffi::Optional<Stmt>(std::move(result).ValueUnchecked());
267 virtual UnchangedOr<Stmt>
Mutate_(
const IfNode* op, InplaceMode inplace_mode);
297 Stmt stmt, std::function<ffi::Optional<PrimExpr>(
const Var&)> vmap);
309 PrimExpr expr, std::function<ffi::Optional<PrimExpr>(
const Var&)> vmap);
321template <
typename Node,
typename = std::enable_if_t<std::is_base_of_v<StmtNode, Node>>>
325 ffi::Optional<VisitInterrupt> Visit(ffi::AnyView value)
final {
326 if (contains_node || value.as<
ExprNode>()) {
329 if (value.as<Node>()) {
330 contains_node =
true;
333 return StmtExprVisitor::Visit(value);
336 bool contains_node{
false};
339 auto visitor = ffi::make_object<Visitor>();
340 visitor->Visit(stmt);
341 return visitor->contains_node;
Assert condition, if an error occurs, return the error message.
Definition stmt.h:260
Bind a variable to a value in the enclosing scope.
Definition stmt.h:135
A Break in control flow.
Definition stmt.h:605
Call corresponds to callable invocation.
Definition expr.h:935
A Continue in control flow.
Definition stmt.h:632
Evaluates an expression. This is mostly used for putting a Call node into Stmt.
Definition stmt.h:352
Structural Expr mutator with native overrides for core expressions and structural fallback for other ...
Definition expr_functor.h:431
virtual UnchangedOr< Expr > Mutate_(const OpaqueExprNode *node, InplaceMode inplace_mode)
TVM_FFI_INLINE UnchangedOr< PrimExpr > Mutate(const PrimExpr &expr, InplaceMode inplace_mode=InplaceMode::kDisallow)
Mutate a primitive expression, preserving its expression category.
Definition expr_functor.h:446
Base type of all the expressions.
Definition base_expr.h:324
Structural Expr visitor with native overrides for core expressions.
Definition expr_functor.h:336
virtual ffi::Optional< VisitInterrupt > Visit_(const OpaqueExprNode *node)
virtual ffi::Optional< VisitInterrupt > Visit(ffi::AnyView value)
Construct a visitor with the core expression hooks.
Definition object_functor.h:242
A for loop, with possible type annotations.
Definition stmt.h:457
If statement.
Definition stmt.h:387
A dynamically dispatched functor on the type of the first argument.
Definition object_functor.h:85
Base node for opaque construction-time expressions.
Definition base_expr.h:394
Typed reference/view over any Expr whose ExprNode::ty is PrimType.
Definition base_expr.h:447
A single-body statement whose semantics are defined by an operator. Operands are evaluated in the enc...
Definition stmt.h:189
A return from the current function.
Definition stmt.h:571
The container of seq statement. Represent a sequence of statements.
Definition stmt.h:75
Sequence statement.
Definition stmt.h:92
Container of all statements.
Definition stmt.h:62
Load a value from an indexed expression source.
Definition expr.h:443
Store a primitive value to an indexed destination expression.
Definition stmt.h:308
Get the index-th field out of a tuple.
Definition expr.h:405
Tuple container.
Definition expr.h:363
A local variable in the IR.
Definition expr.h:694
Managed reference to VarNode.
Definition expr.h:714
A While loop.
Definition stmt.h:533
Create a vector where all the elements are value.
Definition vector_expr.h:79
Let binding. Bind var to value then evaluate body.
Definition expr.h:727
Construct a vector with lanes elements where its i-th element equals base + i * stride....
Definition vector_expr.h:42
Shuffle instruction. vec = concat(vectors) result = (vec[indices[0]], vec[indices[1]] ....
Definition vector_expr.h:117
Mutator that recursively mutates stmts and exprs on them.
Definition stmt_functor.h:221
virtual UnchangedOr< Stmt > Mutate_(const ReturnNode *op, InplaceMode inplace_mode)
TVM_FFI_INLINE UnchangedOr< Stmt > Mutate(const Stmt &stmt, InplaceMode inplace_mode=InplaceMode::kDisallow)
Mutate a borrowed statement through the virtual generic entry.
Definition stmt_functor.h:234
static void InitVTable(VTable *vtable)
virtual UnchangedOr< Stmt > Mutate_(const ForNode *op, InplaceMode inplace_mode)
TVM_FFI_INLINE UnchangedOr< ffi::Optional< SeqStmt > > Mutate(const ffi::Optional< SeqStmt > &stmt, InplaceMode inplace_mode=InplaceMode::kDisallow)
Definition stmt_functor.h:248
StmtExprMutator(const VTable *vtable)
Definition stmt_functor.h:279
virtual UnchangedOr< Stmt > Mutate_(const RegionStmtNode *op, InplaceMode inplace_mode)
virtual UnchangedOr< Stmt > Mutate_(const EvaluateNode *op, InplaceMode inplace_mode)
virtual UnchangedOr< Stmt > Mutate_(const ContinueNode *op, InplaceMode inplace_mode)
virtual UnchangedOr< Stmt > Mutate_(const WhileNode *op, InplaceMode inplace_mode)
virtual UnchangedOr< Stmt > Mutate_(const IfNode *op, InplaceMode inplace_mode)
TVM_FFI_INLINE UnchangedOr< ffi::Optional< Stmt > > Mutate(const ffi::Optional< Stmt > &stmt, InplaceMode inplace_mode=InplaceMode::kDisallow)
Mutate an optional statement, preserving an absent function body.
Definition stmt_functor.h:257
virtual UnchangedOr< Stmt > Mutate_(const BreakNode *op, InplaceMode inplace_mode)
virtual UnchangedOr< Stmt > Mutate_(const BindNode *op, InplaceMode inplace_mode)
virtual UnchangedOr< Stmt > Mutate_(const TensorStoreNode *op, InplaceMode inplace_mode)
virtual UnchangedOr< Stmt > Mutate_(const AssertStmtNode *op, InplaceMode inplace_mode)
TVM_FFI_INLINE UnchangedOr< SeqStmt > Mutate(const SeqStmt &stmt, InplaceMode inplace_mode=InplaceMode::kDisallow)
Mutate a scope body without collapsing its sequence container.
Definition stmt_functor.h:241
virtual UnchangedOr< Stmt > Mutate_(const SeqStmtNode *op, InplaceMode inplace_mode)
Native visitor for TIRx statements and their expression operands.
Definition stmt_functor.h:176
ffi::Optional< VisitInterrupt > Visit_(const prim::LetNode *op) override
static void InitVTable(VTable *vtable)
virtual ffi::Optional< VisitInterrupt > Visit_(const AssertStmtNode *op)
virtual ffi::Optional< VisitInterrupt > Visit_(const ReturnNode *op)
virtual ffi::Optional< VisitInterrupt > Visit_(const WhileNode *op)
ffi::Optional< VisitInterrupt > Visit_(const prim::ShuffleNode *op) override
virtual ffi::Optional< VisitInterrupt > Visit_(const BindNode *op)
virtual ffi::Optional< VisitInterrupt > Visit_(const TensorStoreNode *op)
virtual ffi::Optional< VisitInterrupt > Visit_(const ForNode *op)
virtual ffi::Optional< VisitInterrupt > Visit_(const ContinueNode *op)
ffi::Optional< VisitInterrupt > Visit_(const VarNode *op) override
ffi::Optional< VisitInterrupt > Visit_(const OpaqueExprNode *op) override
ffi::Optional< VisitInterrupt > Visit_(const TensorLoadNode *op) override
virtual ffi::Optional< VisitInterrupt > Visit_(const BreakNode *op)
virtual ffi::Optional< VisitInterrupt > Visit_(const SeqStmtNode *op)
virtual ffi::Optional< VisitInterrupt > Visit_(const IfNode *op)
virtual ffi::Optional< VisitInterrupt > Visit_(const RegionStmtNode *op)
ffi::Optional< VisitInterrupt > Visit_(const TupleNode *op) override
ffi::Optional< VisitInterrupt > Visit_(const TupleGetItemNode *op) override
ffi::Optional< VisitInterrupt > Visit_(const CallNode *op) override
ffi::Optional< VisitInterrupt > Visit_(const prim::RampNode *op) override
ffi::Optional< VisitInterrupt > Visit_(const prim::BroadcastNode *op) override
virtual ffi::Optional< VisitInterrupt > Visit_(const EvaluateNode *op)
StmtExprVisitor(const VTable *vtable)
Definition stmt_functor.h:209
Definition stmt_functor.h:54
virtual R Dispatch_(const AssertStmtNode *node, Args... args)
Definition stmt_functor.h:102
virtual R Dispatch_(const ContinueNode *node, Args... args)
Definition stmt_functor.h:96
virtual ~StmtFunctor()=default
Destroy through the statement functor base.
virtual R Dispatch_(const IfNode *node, Args... args)
Definition stmt_functor.h:81
virtual R Dispatch_(const BindNode *node, Args... args)
Definition stmt_functor.h:75
virtual R Dispatch_(const SeqStmtNode *node, Args... args)
Definition stmt_functor.h:105
virtual R Dispatch_(const BreakNode *node, Args... args)
Definition stmt_functor.h:93
R result_type
The result type of this functor.
Definition stmt_functor.h:60
virtual R Dispatch_(const TensorStoreNode *node, Args... args)
Definition stmt_functor.h:99
virtual R Dispatch_(const ReturnNode *node, Args... args)
Definition stmt_functor.h:90
virtual R Dispatch_(const WhileNode *node, Args... args)
Definition stmt_functor.h:87
virtual R Dispatch_(const RegionStmtNode *node, Args... args)
Definition stmt_functor.h:78
static void SetDispatch(VTable *vtable)
Register an additional node hook implemented by Self.
Definition stmt_functor.h:143
StmtFunctor(const VTable *vtable)
Construct with a finalized table that outlives the functor.
Definition stmt_functor.h:121
virtual R DispatchDefault_(const ffi::Object *node, Args...)
Default behavior for statement hooks not overridden by a subclass.
Definition stmt_functor.h:112
TVM_FFI_INLINE R operator()(const Stmt &node, Args... args)
Dispatch a statement, forwarding additional arguments to its hook.
Definition stmt_functor.h:66
static void InitVTable(VTable *vtable)
Register statement hooks in a fresh mutable table.
Definition stmt_functor.h:123
virtual R Dispatch_(const ForNode *node, Args... args)
Definition stmt_functor.h:84
virtual R Dispatch_(const EvaluateNode *node, Args... args)
Definition stmt_functor.h:108
virtual TVM_FFI_INLINE R Dispatch(const Stmt &node, Args... args)
Dispatch to a node hook, including registered ancestor hooks.
Definition stmt_functor.h:70
StmtFunctor()
Construct a functor with the TIRx statement hooks.
Definition stmt_functor.h:62
Type-dispatched statement functor with a caller-selected signature.
Definition stmt_functor.h:51
Native visiting and mutation of core IR expressions.
TVM_TIRX_DLL Stmt SubstituteWithDataTypeLegalization(Stmt stmt, std::function< ffi::Optional< PrimExpr >(const Var &)> vmap)
Substitute the var specified by vmap and legalize data types after substitution.
bool ContainsNode(const Stmt &stmt)
Check if the statement contains the specified node type.
Definition stmt_functor.h:322
An object that builds and maintains block scope and StmtSref mapping for Dependence analysis.
Definition attr.h:23
Native object dispatch, visiting and mutation with structural fallback.
#define TVM_DEFINE_OBJECT_FUNCTOR_DEFAULT_CONSTRUCTOR(Class, Parent)
Define a default constructor backed by one initialized native dispatch table.
Definition object_functor.h:529
#define TVM_TIRX_DLL
Definition base.h:83
TIRx statements and shared statement entry header.