tvm
var.h
Go to the documentation of this file.
1 /*
2  * Licensed to the Apache Software Foundation (ASF) under one
3  * or more contributor license agreements. See the NOTICE file
4  * distributed with this work for additional information
5  * regarding copyright ownership. The ASF licenses this file
6  * to you under the Apache License, Version 2.0 (the
7  * "License"); you may not use this file except in compliance
8  * with the License. You may obtain a copy of the License at
9  *
10  * http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing,
13  * software distributed under the License is distributed on an
14  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15  * KIND, either express or implied. See the License for the
16  * specific language governing permissions and limitations
17  * under the License.
18  */
19 
24 #ifndef TVM_TIR_VAR_H_
25 #define TVM_TIR_VAR_H_
26 
27 #include <tvm/ffi/dtype.h>
28 #include <tvm/ir/cow.h>
29 #include <tvm/ir/expr.h>
30 #include <tvm/ir/type.h>
31 
32 #include <functional>
33 #include <string>
34 
35 namespace tvm {
36 namespace tirx {
37 
49 class VarNode : public ExprNode {
50  public:
55  ffi::String name_hint;
56  static void RegisterReflection() {
57  namespace refl = tvm::ffi::reflection;
58  refl::ObjectDef<VarNode>().def_ro("name", &VarNode::name_hint,
59  refl::AttachFieldFlag::SEqHashIgnore());
60  }
61 
62  static constexpr TVMFFISEqHashKind _type_s_eq_hash_kind = kTVMFFISEqHashKindFreeVar;
63  static constexpr const uint32_t _type_child_slots = 1;
65 };
66 
68 class Var : public Expr {
69  public:
70  explicit Var(ffi::UnsafeInit tag) : Expr(tag) {}
71  explicit Var(ffi::ObjectPtr<VarNode> n) : Expr(n) {}
78  TVM_DLL explicit Var(ffi::String name_hint = "v", PrimType dtype = PrimType::Int(32),
79  Span span = Span());
86  TVM_DLL explicit Var(ffi::String name_hint, Type type_annotation, Span span = Span());
92  TVM_DLL Var copy_with_name(const ffi::String& name) const;
98  TVM_DLL Var CopyWithSuffix(const ffi::String& suffix) const;
104  TVM_DLL Var copy_with_dtype(PrimType dtype) const;
105 
110  const VarNode* operator->() const { return get(); }
115  const VarNode* get() const { return static_cast<const VarNode*>(data_.get()); }
118  static constexpr bool _type_container_is_exact = true;
119 };
120 
127 class PrimVar : public PrimExpr {
128  public:
130  explicit PrimVar(ffi::String name_hint, PrimType dtype = PrimType::Int(32), Span span = Span())
131  : PrimExpr(
132  Var(std::move(name_hint), std::move(dtype), std::move(span)).as_or_throw<PrimExpr>()) {}
133 
135  explicit PrimVar(ffi::String name_hint, Type type_annotation, Span span = Span())
136  : PrimExpr(Var(std::move(name_hint), std::move(type_annotation), std::move(span))
137  .as_or_throw<PrimExpr>()) {}
138 
140  operator Var() const { return this->as_or_throw<Var>(); }
141 
142  PrimVar CopyWithSuffix(const ffi::String& suffix) const {
143  return this->as_or_throw<Var>().CopyWithSuffix(suffix).as_or_throw<PrimVar>();
144  }
146  return this->as_or_throw<Var>().copy_with_dtype(dtype).as_or_throw<PrimVar>();
147  }
148 
150  static constexpr bool _type_container_is_exact = true;
151 };
152 
153 using Region = ffi::Array<Range>;
154 
162 enum IterVarType : int {
171  kDataPar = 0,
194  kOrdered = 3,
204  kOpaque = 4,
205  // The following are possible additional
206  // types that are provided during schedule
222  kTensorized = 8
223 };
224 
232  public:
246  ffi::String thread_tag;
251  mutable Span span;
252 
253  PrimExpr ToPrimExpr() const final { return var; }
254 
255  static void RegisterReflection() {
256  namespace refl = tvm::ffi::reflection;
257  refl::ObjectDef<IterVarNode>()
258  .def_ro("dom", &IterVarNode::dom)
259  .def_ro("var", &IterVarNode::var, refl::AttachFieldFlag::SEqHashDefRecursive())
260  .def_ro("iter_type", &IterVarNode::iter_type)
261  .def_ro("thread_tag", &IterVarNode::thread_tag);
262  }
263 
264  static constexpr TVMFFISEqHashKind _type_s_eq_hash_kind = kTVMFFISEqHashKindTreeNode;
266 };
267 
274 class IterVar : public PrimExprConvertible {
275  public:
276  TVM_DLL IterVar(Range dom, PrimVar var, IterVarType iter_type, ffi::String thread_tag = "",
277  Span span = Span());
281  inline operator PrimExpr() const;
282 
285 };
286 
287 // inline implementations
288 inline IterVar::operator PrimExpr() const { return (*this)->var; }
289 
290 inline const char* IterVarType2String(IterVarType t) {
291  switch (t) {
292  case kDataPar:
293  return "DataPar";
294  case kThreadIndex:
295  return "ThreadIndex";
296  case kCommReduce:
297  return "CommReduce";
298  case kOrdered:
299  return "Ordered";
300  case kOpaque:
301  return "Opaque";
302  case kUnrolled:
303  return "Unrolled";
304  case kVectorized:
305  return "Vectorized";
306  case kParallelized:
307  return "Parallelized";
308  case kTensorized:
309  return "Tensorized";
310  }
311  return "Unknown";
312 }
313 } // namespace tirx
314 
315 } // namespace tvm
316 
317 namespace tvm::ffi {
318 
319 template <>
320 inline constexpr bool use_default_type_traits_v<tirx::PrimVar> = false;
321 
322 template <>
323 struct TypeTraits<tirx::PrimVar> : public ObjectRefTypeTraitsBase<tirx::PrimVar> {
324  using Base = ObjectRefTypeTraitsBase<tirx::PrimVar>;
325  using Base::CopyFromAnyViewAfterCheck;
326  using Base::CopyToAnyView;
327  using Base::GetMismatchTypeInfo;
328  using Base::MoveFromAnyAfterCheck;
329  using Base::MoveToAny;
330  using Base::TypeSchema;
331  using Base::TypeStr;
332 
333  TVM_FFI_INLINE static bool CheckAnyStrict(const TVMFFIAny* src) {
334  if (src->type_index == TypeIndex::kTVMFFINone) {
335  return tirx::PrimVar::_type_is_nullable;
336  }
337  if (src->type_index < TypeIndex::kTVMFFIStaticObjectBegin ||
338  !details::IsObjectInstance<tirx::VarNode>(src->type_index)) {
339  return false;
340  }
341  const auto* var = static_cast<const tirx::VarNode*>(
342  details::ObjectUnsafe::ObjectPtrFromUnowned<Object>(src->v_obj).get());
343  return details::AnyUnsafe::CheckAnyStrict<PrimType>(var->ExprNode::ty);
344  }
345 
346  TVM_FFI_INLINE static std::optional<tirx::PrimVar> TryCastFromAnyView(const TVMFFIAny* src) {
347  if (CheckAnyStrict(src)) {
348  if (src->type_index == TypeIndex::kTVMFFINone) {
349  return details::ObjectUnsafe::ObjectRefFromObjectPtr<tirx::PrimVar>(nullptr);
350  }
351  return details::ObjectUnsafe::ObjectRefFromObjectPtr<tirx::PrimVar>(
352  details::ObjectUnsafe::ObjectPtrFromUnowned<tirx::VarNode>(src->v_obj));
353  }
354  return std::nullopt;
355  }
356 };
357 
358 } // namespace tvm::ffi
359 
360 /* \brief Allow tirx.Var as key in STL tables
361  *
362  * For most TIR expressions, it would be ambiguous whether the
363  * expression should follow reference equality or structural equality.
364  * This is not the case for variables, which do not contain nested
365  * internal structure, and are frequently used as keys in lookup
366  * tables.
367  *
368  * Providing `std::hash` and `std::equal_to` specializations for
369  * `tirx::Var` allows it to be used as a key in STL tables. For
370  * `PrimExpr`, the user must specify the type of equality used
371  * (e.g. `std::unordered_set<T, StructuralHash, StructuralEqual>` or
372  * `std::unordered_set<T, ffi::ObjectPtrHash, ffi::ObjectPtrEqual>`).
373  */
374 template <>
375 struct std::hash<tvm::tirx::Var> {
376  std::size_t operator()(const tvm::tirx::Var& var) const { return tvm::ffi::ObjectPtrHash()(var); }
377 };
378 
379 template <>
380 struct std::equal_to<tvm::tirx::Var> {
381  bool operator()(const tvm::tirx::Var& var_a, const tvm::tirx::Var& var_b) const {
382  return tvm::ffi::ObjectPtrEqual()(var_a, var_b);
383  }
384 };
385 
386 #endif // TVM_TIR_VAR_H_
Base type of all the expressions.
Definition: base_expr.h:276
Managed reference to ExprNode.
Definition: base_expr.h:311
Base class for other IR constructs that can be converted to PrimExpr. This is useful for the FFI to c...
Definition: base_expr.h:391
Managed reference to PrimExprConvertibleNode.
Definition: base_expr.h:402
Typed reference/view over any Expr whose ExprNode::ty is PrimType.
Definition: base_expr.h:354
Definition: base_expr.h:113
static PrimType Int(int bits, int lanes=1)
Construct a signed integer type with fixed lanes.
Range container
Definition: expr.h:484
Definition: source_map.h:111
Managed reference to TypeNode.
Definition: base_expr.h:77
An iteration variable representing an iteration over a one dimensional interval.
Definition: var.h:231
Range dom
the domain of iteration, if known, can be None For the intermediate schedule node,...
Definition: var.h:237
ffi::String thread_tag
additional tag on the iteration variable, set this if this is bound already to a known thread tag.
Definition: var.h:246
IterVarType iter_type
The type of the IterVar.
Definition: var.h:241
static void RegisterReflection()
Definition: var.h:255
PrimVar var
The looping variable.
Definition: var.h:239
PrimExpr ToPrimExpr() const final
Definition: var.h:253
Span span
Span that points to the original source code. Reserved debug information.
Definition: var.h:251
static constexpr TVMFFISEqHashKind _type_s_eq_hash_kind
Definition: var.h:264
TVM_FFI_DECLARE_OBJECT_INFO_FINAL("tirx.IterVar", IterVarNode, PrimExprConvertibleNode)
Iteration Variable, represents an iteration over an integer interval.
Definition: var.h:274
IterVar(Range dom, PrimVar var, IterVarType iter_type, ffi::String thread_tag="", Span span=Span())
TVM_FFI_DEFINE_OBJECT_REF_METHODS_NULLABLE(IterVar, PrimExprConvertible, IterVarNode)
TVM_DEFINE_OBJECT_REF_COW_METHOD(IterVarNode)
Checked scalar view over a VarNode.
Definition: var.h:127
TVM_FFI_DEFINE_OBJECT_REF_METHODS_NULLABLE(PrimVar, PrimExpr, VarNode)
PrimVar(ffi::String name_hint, PrimType dtype=PrimType::Int(32), Span span=Span())
Construct a scalar variable directly from a primitive type.
Definition: var.h:130
static constexpr bool _type_container_is_exact
Definition: var.h:150
PrimVar CopyWithSuffix(const ffi::String &suffix) const
Definition: var.h:142
PrimVar(ffi::String name_hint, Type type_annotation, Span span=Span())
Construct a scalar variable directly from a checked type annotation.
Definition: var.h:135
PrimVar copy_with_dtype(PrimType dtype) const
Definition: var.h:145
A variable node in the IR.
Definition: var.h:49
ffi::String name_hint
The hint to the variable name.
Definition: var.h:55
static void RegisterReflection()
Definition: var.h:56
static constexpr TVMFFISEqHashKind _type_s_eq_hash_kind
Definition: var.h:62
TVM_FFI_DECLARE_OBJECT_INFO("tirx.Var", VarNode, ExprNode)
static constexpr const uint32_t _type_child_slots
Definition: var.h:63
a named variable in TIR
Definition: var.h:68
Var(ffi::String name_hint="v", PrimType dtype=PrimType::Int(32), Span span=Span())
Constructor.
static constexpr bool _type_container_is_exact
Definition: var.h:118
const VarNode * operator->() const
Get pointer to the internal value.
Definition: var.h:110
Var(ffi::String name_hint, Type type_annotation, Span span=Span())
Constructor which provides a more detailed type annotation.
Var copy_with_dtype(PrimType dtype) const
Make a new copy of the variable with specified dtype.
Var CopyWithSuffix(const ffi::String &suffix) const
Make a new copy of var with same type, append suffix.
Var(ffi::UnsafeInit tag)
Definition: var.h:70
Var(ffi::ObjectPtr< VarNode > n)
Definition: var.h:71
Var copy_with_name(const ffi::String &name) const
Make a new copy of var with same type, but a different nam.
const VarNode * get() const
Get pointer to the internal value.
Definition: var.h:115
Copy-on-write helper macro for IR ffi::ObjectRef types.
Base expr nodes in TVM.
IR/AST nodes for TVM types shared across IR variants.
Definition: iter_affine_map.h:231
PrimVar var(std::string name_hint, PrimType t=PrimType::Int(32))
Construct a new Var expression.
IterVarType
Type of iteration variable. Each IterVar have a specific type.
Definition: var.h:162
@ kThreadIndex
The IterVar itself is a thread-index of a fixed thread launching group. Note that this is already ass...
Definition: var.h:179
@ kUnrolled
The execution is unrolled.
Definition: var.h:210
@ kCommReduce
Communicative reduction. Cannot be directly parallelized.
Definition: var.h:186
@ kTensorized
Marks boundary of tensorization intrinsic.
Definition: var.h:222
@ kVectorized
The loop is vectorized.
Definition: var.h:214
@ kDataPar
Data parallel iteration. This normally corresponds to axis of Tensor. Allow all IterVar manipulations...
Definition: var.h:171
@ kParallelized
The loop is parallelized.
Definition: var.h:218
@ kOpaque
IterVar is opaque,.
Definition: var.h:204
@ kOrdered
Serial loops with loop carry dependency, the iteration must execute in order. Cannot be re-ordered.
Definition: var.h:194
ffi::Array< Range > Region
Definition: var.h:153
const char * IterVarType2String(IterVarType t)
Definition: var.h:290
An object that builds and maintains block scope and StmtSref mapping for Dependence analysis.
Definition: analyzer.h:40
ObjectRefTypeTraitsBase< tirx::PrimVar > Base
Definition: var.h:324
static TVM_FFI_INLINE bool CheckAnyStrict(const TVMFFIAny *src)
Definition: var.h:333
static TVM_FFI_INLINE std::optional< tirx::PrimVar > TryCastFromAnyView(const TVMFFIAny *src)
Definition: var.h:346