MLIR 22.0.0git
Types.h
Go to the documentation of this file.
1//===- Types.h --------------------------------------------------*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#ifndef MLIR_TOOLS_PDLL_AST_TYPES_H_
10#define MLIR_TOOLS_PDLL_AST_TYPES_H_
11
12#include "mlir/Support/LLVM.h"
14#include <optional>
15
16namespace mlir {
17namespace pdll {
18namespace ods {
19class Operation;
20} // namespace ods
21
22namespace ast {
23class Context;
24
25//===----------------------------------------------------------------------===//
26// Type
27//===----------------------------------------------------------------------===//
28
29class Type {
30public:
31 /// This class represents the internal storage of the Type class.
32 struct Storage;
33
34 /// This class provides several utilities when defining derived type classes.
35 template <typename ImplT, typename BaseT = Type>
36 class TypeBase : public BaseT {
37 public:
39 using ImplTy = ImplT;
40 using BaseT::BaseT;
41
42 /// Provide type casting support.
43 static bool classof(Type type) {
44 return type.getTypeID() == TypeID::get<ImplTy>();
45 }
46 };
47
48 Type(Storage *impl = nullptr) : impl(impl) {}
49
50 bool operator==(const Type &other) const { return impl == other.impl; }
51 bool operator!=(const Type &other) const { return !(*this == other); }
52 explicit operator bool() const { return impl; }
53
54 /// Return the internal storage instance of this type.
55 Storage *getImpl() const { return impl; }
56
57 /// Return the TypeID instance of this type.
58 TypeID getTypeID() const;
59
60 /// Print this type to the given stream.
61 void print(raw_ostream &os) const;
62
63 /// Try to refine this type with the one provided. Given two compatible types,
64 /// this will return a merged type contains as much detail from the two types.
65 /// For example, if refining two operation types and one contains a name,
66 /// while the other doesn't, the refined type contains the name. If the two
67 /// types are incompatible, null is returned.
68 Type refineWith(Type other) const;
69
70protected:
71 /// Return the internal storage instance of this type reinterpreted as the
72 /// given derived storage type.
73 template <typename T>
74 const T *getImplAs() const {
75 return static_cast<const T *>(impl);
76 }
77
78private:
79 Storage *impl;
80};
81
82inline llvm::hash_code hash_value(Type type) {
84}
85
87 type.print(os);
88 return os;
89}
90
91//===----------------------------------------------------------------------===//
92// Type::Storage
93//===----------------------------------------------------------------------===//
94
97
98 /// The type identifier for the derived type class.
100};
101
102namespace detail {
103
104/// A utility CRTP base class that defines many of the necessary utilities for
105/// defining a PDLL AST Type.
106template <typename ConcreteT, typename KeyT = void>
108 using KeyTy = KeyT;
111 : Type::Storage(TypeID::get<ConcreteT>()), key(key) {}
112
113 /// Construct an instance with the given storage allocator.
115 const KeyTy &key) {
116 return new (alloc.allocate<ConcreteT>()) ConcreteT(key);
117 }
118
119 /// Utility methods required by the storage allocator.
120 bool operator==(const KeyTy &key) const { return this->key == key; }
121
122 /// Return the key value of this storage class.
123 const KeyTy &getValue() const { return key; }
124
125protected:
127};
128/// A specialization of the storage base for singleton types.
129template <typename ConcreteT>
130struct TypeStorageBase<ConcreteT, void> : public Type::Storage {
133};
134
135//===----------------------------------------------------------------------===//
136// AttributeTypeStorage
137//===----------------------------------------------------------------------===//
138
139struct AttributeTypeStorage : public TypeStorageBase<AttributeTypeStorage> {};
140
141//===----------------------------------------------------------------------===//
142// ConstraintTypeStorage
143//===----------------------------------------------------------------------===//
144
145struct ConstraintTypeStorage : public TypeStorageBase<ConstraintTypeStorage> {};
146
147//===----------------------------------------------------------------------===//
148// OperationTypeStorage
149//===----------------------------------------------------------------------===//
150
152 : public TypeStorageBase<OperationTypeStorage,
153 std::pair<StringRef, const ods::Operation *>> {
154 using Base::Base;
155
156 static OperationTypeStorage *
158 const std::pair<StringRef, const ods::Operation *> &key) {
160 std::make_pair(alloc.copyInto(key.first), key.second));
161 }
162};
163
164//===----------------------------------------------------------------------===//
165// RangeTypeStorage
166//===----------------------------------------------------------------------===//
167
168struct RangeTypeStorage : public TypeStorageBase<RangeTypeStorage, Type> {
169 using Base::Base;
170};
171
172//===----------------------------------------------------------------------===//
173// RewriteTypeStorage
174//===----------------------------------------------------------------------===//
175
176struct RewriteTypeStorage : public TypeStorageBase<RewriteTypeStorage> {};
177
178//===----------------------------------------------------------------------===//
179// TupleTypeStorage
180//===----------------------------------------------------------------------===//
181
183 : public TypeStorageBase<TupleTypeStorage,
184 std::pair<ArrayRef<Type>, ArrayRef<StringRef>>> {
185 using Base::Base;
186
187 static TupleTypeStorage *
190 SmallVector<StringRef> names = llvm::to_vector(llvm::map_range(
191 key.second, [&](StringRef name) { return alloc.copyInto(name); }));
192 return new (alloc.allocate<TupleTypeStorage>())
193 TupleTypeStorage(std::make_pair(alloc.copyInto(key.first),
194 alloc.copyInto(llvm::ArrayRef(names))));
195 }
196};
197
198//===----------------------------------------------------------------------===//
199// TypeTypeStorage
200//===----------------------------------------------------------------------===//
201
202struct TypeTypeStorage : public TypeStorageBase<TypeTypeStorage> {};
203
204//===----------------------------------------------------------------------===//
205// ValueTypeStorage
206//===----------------------------------------------------------------------===//
207
208struct ValueTypeStorage : public TypeStorageBase<ValueTypeStorage> {};
209
210} // namespace detail
211
212//===----------------------------------------------------------------------===//
213// AttributeType
214//===----------------------------------------------------------------------===//
215
216/// This class represents a PDLL type that corresponds to an mlir::Attribute.
217class AttributeType : public Type::TypeBase<detail::AttributeTypeStorage> {
218public:
219 using Base::Base;
220
221 /// Return an instance of the Attribute type.
222 static AttributeType get(Context &context);
223};
224
225//===----------------------------------------------------------------------===//
226// ConstraintType
227//===----------------------------------------------------------------------===//
228
229/// This class represents a PDLL type that corresponds to a constraint. This
230/// type has no MLIR C++ API correspondance.
231class ConstraintType : public Type::TypeBase<detail::ConstraintTypeStorage> {
232public:
233 using Base::Base;
234
235 /// Return an instance of the Constraint type.
236 static ConstraintType get(Context &context);
237};
238
239//===----------------------------------------------------------------------===//
240// OperationType
241//===----------------------------------------------------------------------===//
242
243/// This class represents a PDLL type that corresponds to an mlir::Operation.
244class OperationType : public Type::TypeBase<detail::OperationTypeStorage> {
245public:
246 using Base::Base;
247
248 /// Return an instance of the Operation type with an optional operation name.
249 /// If no name is provided, this type may refer to any operation.
250 static OperationType get(Context &context,
251 std::optional<StringRef> name = std::nullopt,
252 const ods::Operation *odsOp = nullptr);
253
254 /// Return the name of this operation type, or std::nullopt if it doesn't have
255 /// on.
256 std::optional<StringRef> getName() const;
257
258 /// Return the ODS operation that this type refers to, or nullptr if the ODS
259 /// operation is unknown.
260 const ods::Operation *getODSOperation() const;
261};
262
263//===----------------------------------------------------------------------===//
264// RangeType
265//===----------------------------------------------------------------------===//
266
267/// This class represents a PDLL type that corresponds to a range of elements
268/// with a given element type.
269class RangeType : public Type::TypeBase<detail::RangeTypeStorage> {
270public:
271 using Base::Base;
272
273 /// Return an instance of the Range type with the given element type.
274 static RangeType get(Context &context, Type elementType);
275
276 /// Return the element type of this range.
277 Type getElementType() const;
278};
279
280//===----------------------------------------------------------------------===//
281// TypeRangeType
282//===----------------------------------------------------------------------===//
283
284/// This class represents a PDLL type that corresponds to an mlir::TypeRange.
285class TypeRangeType : public RangeType {
286public:
287 using RangeType::RangeType;
288
289 /// Provide type casting support.
290 static bool classof(Type type);
291
292 /// Return an instance of the TypeRange type.
293 static TypeRangeType get(Context &context);
294};
295
296//===----------------------------------------------------------------------===//
297// ValueRangeType
298//===----------------------------------------------------------------------===//
299
300/// This class represents a PDLL type that corresponds to an mlir::ValueRange.
301class ValueRangeType : public RangeType {
302public:
303 using RangeType::RangeType;
304
305 /// Provide type casting support.
306 static bool classof(Type type);
307
308 /// Return an instance of the ValueRange type.
309 static ValueRangeType get(Context &context);
310};
311
312//===----------------------------------------------------------------------===//
313// RewriteType
314//===----------------------------------------------------------------------===//
315
316/// This class represents a PDLL type that corresponds to a rewrite reference.
317/// This type has no MLIR C++ API correspondance.
318class RewriteType : public Type::TypeBase<detail::RewriteTypeStorage> {
319public:
320 using Base::Base;
321
322 /// Return an instance of the Rewrite type.
323 static RewriteType get(Context &context);
324};
325
326//===----------------------------------------------------------------------===//
327// TupleType
328//===----------------------------------------------------------------------===//
329
330/// This class represents a PDLL tuple type, i.e. an ordered set of element
331/// types with optional names.
332class TupleType : public Type::TypeBase<detail::TupleTypeStorage> {
333public:
334 using Base::Base;
335
336 /// Return an instance of the Tuple type.
337 static TupleType get(Context &context, ArrayRef<Type> elementTypes,
338 ArrayRef<StringRef> elementNames);
339 static TupleType get(Context &context, ArrayRef<Type> elementTypes = {});
340
341 /// Return the element types of this tuple.
343
344 /// Return the element names of this tuple.
346
347 /// Return the number of elements within this tuple.
348 size_t size() const { return getElementTypes().size(); }
349
350 /// Return if the tuple has no elements.
351 bool empty() const { return size() == 0; }
352};
353
354//===----------------------------------------------------------------------===//
355// TypeType
356//===----------------------------------------------------------------------===//
357
358/// This class represents a PDLL type that corresponds to an mlir::Type.
359class TypeType : public Type::TypeBase<detail::TypeTypeStorage> {
360public:
361 using Base::Base;
362
363 /// Return an instance of the Type type.
364 static TypeType get(Context &context);
365};
366
367//===----------------------------------------------------------------------===//
368// ValueType
369//===----------------------------------------------------------------------===//
370
371/// This class represents a PDLL type that corresponds to an mlir::Value.
372class ValueType : public Type::TypeBase<detail::ValueTypeStorage> {
373public:
374 using Base::Base;
375
376 /// Return an instance of the Value type.
377 static ValueType get(Context &context);
378};
379
380} // namespace ast
381} // namespace pdll
382} // namespace mlir
383
392
393namespace llvm {
394template <>
395struct DenseMapInfo<mlir::pdll::ast::Type> {
399 static_cast<mlir::pdll::ast::Type::Storage *>(pointer));
400 }
406 static unsigned getHashValue(mlir::pdll::ast::Type val) {
407 return llvm::hash_value(val.getImpl());
408 }
410 return lhs == rhs;
411 }
412};
413
414/// Add support for llvm style casts.
415/// We provide a cast between To and From if From is mlir::pdll::ast::Type or
416/// derives from it
417template <typename To, typename From>
418struct CastInfo<
419 To, From,
420 std::enable_if_t<
421 std::is_same_v<mlir::pdll::ast::Type, std::remove_const_t<From>> ||
422 std::is_base_of_v<mlir::pdll::ast::Type, From>>>
424 DefaultDoCastIfPossible<To, From, CastInfo<To, From>> {
425 static inline bool isPossible(mlir::pdll::ast::Type ty) {
426 /// Return a constant true instead of a dynamic true when casting to self or
427 /// up the hierarchy.
428 if constexpr (std::is_base_of_v<To, From>) {
429 return true;
430 } else {
431 return To::classof(ty);
432 };
433 }
434 static inline To doCast(mlir::pdll::ast::Type ty) { return To(ty.getImpl()); }
435};
436} // namespace llvm
437
438#endif // MLIR_TOOLS_PDLL_AST_TYPES_H_
lhs
#define MLIR_DECLARE_EXPLICIT_TYPE_ID(CLASS_NAME)
Definition TypeID.h:321
This class acts as the base storage that all storage classes must derived from.
This is a utility allocator used to allocate memory for instances of derived types.
ArrayRef< T > copyInto(ArrayRef< T > elements)
Copy the specified array of elements into memory managed by our bump pointer allocator.
T * allocate()
Allocate an instance of the provided type.
This class provides an efficient unique identifier for a specific C++ type.
Definition TypeID.h:107
static TypeID get()
Construct a type info object for the given type T.
Definition TypeID.h:245
This class represents a PDLL type that corresponds to an mlir::Attribute.
Definition Types.h:217
static AttributeType get(Context &context)
Return an instance of the Attribute type.
Definition Types.cpp:56
This class represents a PDLL type that corresponds to a constraint.
Definition Types.h:231
static ConstraintType get(Context &context)
Return an instance of the Constraint type.
Definition Types.cpp:64
This class represents the main context of the PDLL AST.
Definition Context.h:25
This class represents a PDLL type that corresponds to an mlir::Operation.
Definition Types.h:244
const ods::Operation * getODSOperation() const
Return the ODS operation that this type refers to, or nullptr if the ODS operation is unknown.
Definition Types.cpp:86
static OperationType get(Context &context, std::optional< StringRef > name=std::nullopt, const ods::Operation *odsOp=nullptr)
Return an instance of the Operation type with an optional operation name.
Definition Types.cpp:72
std::optional< StringRef > getName() const
Return the name of this operation type, or std::nullopt if it doesn't have on.
Definition Types.cpp:80
This class represents a PDLL type that corresponds to a range of elements with a given element type.
Definition Types.h:269
Type getElementType() const
Return the element type of this range.
Definition Types.cpp:99
static RangeType get(Context &context, Type elementType)
Return an instance of the Range type with the given element type.
Definition Types.cpp:94
This class represents a PDLL type that corresponds to a rewrite reference.
Definition Types.h:318
static RewriteType get(Context &context)
Return an instance of the Rewrite type.
Definition Types.cpp:135
This class represents a PDLL tuple type, i.e.
Definition Types.h:332
size_t size() const
Return the number of elements within this tuple.
Definition Types.h:348
ArrayRef< StringRef > getElementNames() const
Return the element names of this tuple.
Definition Types.cpp:158
bool empty() const
Return if the tuple has no elements.
Definition Types.h:351
ArrayRef< Type > getElementTypes() const
Return the element types of this tuple.
Definition Types.cpp:154
static TupleType get(Context &context, ArrayRef< Type > elementTypes, ArrayRef< StringRef > elementNames)
Return an instance of the Tuple type.
Definition Types.cpp:143
This class represents a PDLL type that corresponds to an mlir::TypeRange.
Definition Types.h:285
static TypeRangeType get(Context &context)
Return an instance of the TypeRange type.
Definition Types.cpp:112
static bool classof(Type type)
Provide type casting support.
Definition Types.cpp:107
This class represents a PDLL type that corresponds to an mlir::Type.
Definition Types.h:359
static TypeType get(Context &context)
Return an instance of the Type type.
Definition Types.cpp:166
This class provides several utilities when defining derived type classes.
Definition Types.h:36
TypeBase< ImplT, BaseT > Base
Definition Types.h:38
static bool classof(Type type)
Provide type casting support.
Definition Types.h:43
TypeID getTypeID() const
Return the TypeID instance of this type.
Definition Types.cpp:30
bool operator!=(const Type &other) const
Definition Types.h:51
Storage * getImpl() const
Return the internal storage instance of this type.
Definition Types.h:55
void print(raw_ostream &os) const
Print this type to the given stream.
Type(Storage *impl=nullptr)
Definition Types.h:48
const T * getImplAs() const
Return the internal storage instance of this type reinterpreted as the given derived storage type.
Definition Types.h:74
Type refineWith(Type other) const
Try to refine this type with the one provided.
Definition Types.cpp:32
bool operator==(const Type &other) const
Definition Types.h:50
This class represents a PDLL type that corresponds to an mlir::ValueRange.
Definition Types.h:301
static bool classof(Type type)
Provide type casting support.
Definition Types.cpp:121
static ValueRangeType get(Context &context)
Return an instance of the ValueRange type.
Definition Types.cpp:126
This class represents a PDLL type that corresponds to an mlir::Value.
Definition Types.h:372
static ValueType get(Context &context)
Return an instance of the Value type.
Definition Types.cpp:174
This class provides an ODS representation of a specific operation.
Definition Operation.h:125
The OpAsmOpInterface, see OpAsmInterface.td for more details.
Definition CallGraph.h:229
llvm::hash_code hash_value(Type type)
Definition Types.h:82
raw_ostream & operator<<(raw_ostream &os, Type type)
Definition Types.h:86
Include the generated interface declarations.
llvm::DenseMapInfo< T, Enable > DenseMapInfo
Definition LLVM.h:122
auto get(MLIRContext *context, Ts &&...params)
Helper method that injects context only if needed, this helps unify some of the attribute constructio...
static bool isEqual(mlir::pdll::ast::Type lhs, mlir::pdll::ast::Type rhs)
Definition Types.h:409
static unsigned getHashValue(mlir::pdll::ast::Type val)
Definition Types.h:406
static mlir::pdll::ast::Type getTombstoneKey()
Definition Types.h:401
static mlir::pdll::ast::Type getEmptyKey()
Definition Types.h:396
Storage(TypeID typeID)
Definition Types.h:96
TypeID typeID
The type identifier for the derived type class.
Definition Types.h:99
static OperationTypeStorage * construct(StorageUniquer::StorageAllocator &alloc, const std::pair< StringRef, const ods::Operation * > &key)
Definition Types.h:157
static TupleTypeStorage * construct(StorageUniquer::StorageAllocator &alloc, std::pair< ArrayRef< Type >, ArrayRef< StringRef > > key)
Definition Types.h:188
A utility CRTP base class that defines many of the necessary utilities for defining a PDLL AST Type.
Definition Types.h:107
bool operator==(const KeyTy &key) const
Utility methods required by the storage allocator.
Definition Types.h:120
const KeyTy & getValue() const
Return the key value of this storage class.
Definition Types.h:123
static ConcreteT * construct(StorageUniquer::StorageAllocator &alloc, const KeyTy &key)
Construct an instance with the given storage allocator.
Definition Types.h:114
TypeStorageBase< ConcreteT, KeyT > Base
Definition Types.h:109