MLIR 24.0.0git
AffineOps.h
Go to the documentation of this file.
1//===- AffineOps.h - MLIR Affine Operations -------------------------------===//
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// This file defines convenience types for working with Affine operations
10// in the MLIR operation set.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef MLIR_DIALECT_AFFINE_IR_AFFINEOPS_H
15#define MLIR_DIALECT_AFFINE_IR_AFFINEOPS_H
16
20#include "mlir/IR/AffineMap.h"
21#include "mlir/IR/Builders.h"
25namespace mlir {
26namespace affine {
27
28class AffineApplyOp;
29class AffineBound;
30class AffineMaxOp;
31class AffineMinOp;
32class AffineValueMap;
33
34/// A utility function to check if a value is defined at the top level of an
35/// op with trait `AffineScope` or is a region argument for such an op. A value
36/// of index type defined at the top level is always a valid symbol for all its
37/// uses.
38bool isTopLevelValue(Value value);
39
40/// A utility function to check if a value is defined at the top level of
41/// `region` or is an argument of `region`. A value of index type defined at the
42/// top level of a `AffineScope` region is always a valid symbol for all
43/// uses in that region.
44bool isTopLevelValue(Value value, Region *region);
45
46/// Returns the closest region enclosing `op` that is held by an operation with
47/// trait `AffineScope`; `nullptr` if there is no such region.
48Region *getAffineScope(Operation *op);
49
50/// Returns the closest region enclosing `op` that is held by a non-affine
51/// operation; `nullptr` if there is no such region. This method is meant to
52/// be used by affine analysis methods (e.g. dependence analysis) which are
53/// only meaningful when performed among/between operations from the same
54/// analysis scope.
55Region *getAffineAnalysisScope(Operation *op);
56
57/// Return the product of `terms`, creating an `affine.apply` if any of them are
58/// non-constant values. If any of `terms` is `nullptr`, return `nullptr`.
61
62/// Returns true if the given Value can be used as a dimension id in the region
63/// of the closest surrounding op that has the trait `AffineScope`.
64bool isValidDim(Value value);
65
66/// Returns true if the given Value can be used as a dimension id in `region`,
67/// i.e., for all its uses in `region`.
68bool isValidDim(Value value, Region *region);
69
70/// Returns true if the given value can be used as a symbol in the region of the
71/// closest surrounding op that has the trait `AffineScope`.
72bool isValidSymbol(Value value);
73
74/// Returns true if the given Value can be used as a symbol for `region`, i.e.,
75/// for all its uses in `region`.
76bool isValidSymbol(Value value, Region *region);
77
78/// Parses dimension and symbol list. `numDims` is set to the number of
79/// dimensions in the list parsed.
80ParseResult parseDimAndSymbolList(OpAsmParser &parser,
81 SmallVectorImpl<Value> &operands,
82 unsigned &numDims);
83
84/// Modifies both `map` and `operands` in-place so as to:
85/// 1. drop duplicate operands
86/// 2. drop unused dims and symbols from map
87/// 3. promote valid symbols to symbolic operands in case they appeared as
88/// dimensional operands
89/// 4. propagate constant operands and drop them
91 SmallVectorImpl<Value> *operands);
92
93/// Canonicalizes an integer set the same way canonicalizeMapAndOperands does
94/// for affine maps.
96 SmallVectorImpl<Value> *operands);
97
98/// Returns a composed AffineApplyOp by composing `map` and `operands` with
99/// other AffineApplyOps supplying those operands. The operands of the resulting
100/// AffineApplyOp do not change the length of AffineApplyOp chains.
101AffineApplyOp makeComposedAffineApply(OpBuilder &b, Location loc, AffineMap map,
102 ArrayRef<OpFoldResult> operands,
103 bool composeAffineMin = false);
105 ArrayRef<OpFoldResult> operands,
106 bool composeAffineMin = false);
107
108/// Constructs an AffineApplyOp that applies `map` to `operands` after composing
109/// the map with the maps of any other AffineApplyOp supplying the operands,
110/// then immediately attempts to fold it. If folding results in a constant
111/// value, no ops are actually created. The `map` must be a single-result affine
112/// map.
114 AffineMap map,
115 ArrayRef<OpFoldResult> operands,
116 bool composeAffineMin = false);
117/// Variant of `makeComposedFoldedAffineApply` that applies to an expression.
119 AffineExpr expr,
120 ArrayRef<OpFoldResult> operands,
121 bool composeAffineMin = false);
122/// Variant of `makeComposedFoldedAffineApply` suitable for multi-result maps.
123/// Note that this may create as many affine.apply operations as the map has
124/// results given that affine.apply must be single-result.
127 bool composeAffineMin = false);
128
129/// Returns an AffineMinOp obtained by composing `map` and `operands` with
130/// AffineApplyOps supplying those operands.
131AffineMinOp makeComposedAffineMin(OpBuilder &b, Location loc, AffineMap map,
132 ArrayRef<OpFoldResult> operands);
133
134/// Constructs an AffineMinOp that computes a minimum across the results of
135/// applying `map` to `operands`, then immediately attempts to fold it. If
136/// folding results in a constant value, no ops are actually created.
138 AffineMap map,
139 ArrayRef<OpFoldResult> operands);
140
141/// Constructs an AffineMinOp that computes a maximum across the results of
142/// applying `map` to `operands`, then immediately attempts to fold it. If
143/// folding results in a constant value, no ops are actually created.
145 AffineMap map,
146 ArrayRef<OpFoldResult> operands);
147
148/// Given an affine map `map` and its input `operands`, this method composes
149/// into `map`, maps of AffineApplyOps whose results are the values in
150/// `operands`, iteratively until no more of `operands` are the result of an
151/// AffineApplyOp. When this function returns, `map` becomes the composed affine
152/// map, and each Value in `operands` is guaranteed to be either a loop IV or a
153/// terminal symbol, i.e., a symbol defined at the top level or a block/function
154/// argument.
156 SmallVectorImpl<Value> *operands,
157 bool composeAffineMin = false);
158
159} // namespace affine
160} // namespace mlir
161
162#include "mlir/Dialect/Affine/IR/AffineOpsDialect.h.inc"
163
164#define GET_OP_CLASSES
165#include "mlir/Dialect/Affine/IR/AffineOps.h.inc"
166
167namespace mlir {
168namespace affine {
169
170/// Returns true if the provided value is the induction variable of an
171/// AffineForOp.
172bool isAffineForInductionVar(Value val);
173
174/// Returns true if `val` is the induction variable of an AffineParallelOp.
175bool isAffineParallelInductionVar(Value val);
176
177/// Returns true if the provided value is the induction variable of an
178/// AffineForOp or AffineParallelOp.
179bool isAffineInductionVar(Value val);
180
181/// Returns the loop parent of an induction variable. If the provided value is
182/// not an induction variable, then return nullptr.
183AffineForOp getForInductionVarOwner(Value val);
184
185/// Returns true if the provided value is among the induction variables of an
186/// AffineParallelOp.
187AffineParallelOp getAffineParallelInductionVarOwner(Value val);
188
189/// Extracts the induction variables from a list of AffineForOps and places them
190/// in the output argument `ivs`.
191void extractForInductionVars(ArrayRef<AffineForOp> forInsts,
192 SmallVectorImpl<Value> *ivs);
193
194/// Extracts the induction variables from a list of either AffineForOp or
195/// AffineParallelOp and places them in the output argument `ivs`.
196void extractInductionVars(ArrayRef<Operation *> affineOps,
197 SmallVectorImpl<Value> &ivs);
198
199/// Builds a perfect nest of affine.for loops, i.e., each loop except the
200/// innermost one contains only another loop and a terminator. The loops iterate
201/// from "lbs" to "ubs" with "steps". The body of the innermost loop is
202/// populated by calling "bodyBuilderFn" and providing it with an OpBuilder, a
203/// Location and a list of loop induction variables.
204void buildAffineLoopNest(OpBuilder &builder, Location loc,
205 ArrayRef<int64_t> lbs, ArrayRef<int64_t> ubs,
206 ArrayRef<int64_t> steps,
207 function_ref<void(OpBuilder &, Location, ValueRange)>
208 bodyBuilderFn = nullptr);
209void buildAffineLoopNest(OpBuilder &builder, Location loc, ValueRange lbs,
210 ValueRange ubs, ArrayRef<int64_t> steps,
211 function_ref<void(OpBuilder &, Location, ValueRange)>
212 bodyBuilderFn = nullptr);
213
214/// AffineBound represents a lower or upper bound in the for operation.
215/// This class does not own the underlying operands. Instead, it refers
216/// to the operands stored in the AffineForOp. Its life span should not exceed
217/// that of the for operation it refers to.
218class AffineBound {
219public:
221 AffineMap getMap() { return map; }
222
223 unsigned getNumOperands() { return operands.size(); }
224 Value getOperand(unsigned idx) {
225 return op.getOperand(operands.getBeginOperandIndex() + idx);
226 }
227
228 using operand_iterator = AffineForOp::operand_iterator;
229 using operand_range = AffineForOp::operand_range;
230
231 operand_iterator operandBegin() { return operands.begin(); }
232 operand_iterator operandEnd() { return operands.end(); }
234
235private:
236 // 'affine.for' operation that contains this bound.
237 AffineForOp op;
238 // Operands of the affine map.
239 OperandRange operands;
240 // Affine map for this bound.
241 AffineMap map;
242
243 AffineBound(AffineForOp op, OperandRange operands, AffineMap map)
244 : op(op), operands(operands), map(map) {}
245
246 friend class AffineForOp;
247};
248
249} // namespace affine
250} // namespace mlir
251
252#endif
b
Return true if permutation is a valid permutation of the outer_dims_perm (case OuterOrInnerPerm::Oute...
Base type for affine expression.
Definition AffineExpr.h:68
A multi-dimensional affine map Affine map's are immutable like Type's, and they are uniqued.
Definition AffineMap.h:46
An integer set representing a conjunction of one or more affine equalities and inequalities.
Definition IntegerSet.h:44
This class defines the main interface for locations in MLIR and acts as a non-nullable wrapper around...
Definition Location.h:76
The OpAsmParser has methods for interacting with the asm parser: parsing things from it,...
This class helps build Operations.
Definition Builders.h:210
This class represents a single result from folding an operation.
This class implements the operand iterators for the Operation class.
Definition ValueRange.h:44
This class contains a list of basic blocks and a link to the parent operation it is attached to.
Definition Region.h:26
This class represents an instance of an SSA value in the MLIR system, representing a computable value...
Definition Value.h:96
AffineBound represents a lower or upper bound in the for operation.
Definition AffineOps.h:218
Value getOperand(unsigned idx)
Definition AffineOps.h:224
operand_iterator operandBegin()
Definition AffineOps.h:231
AffineForOp::operand_iterator operand_iterator
Definition AffineOps.h:228
AffineForOp::operand_range operand_range
Definition AffineOps.h:229
AffineForOp getAffineForOp()
Definition AffineOps.h:220
operand_range getOperands()
Definition AffineOps.h:233
operand_iterator operandEnd()
Definition AffineOps.h:232
An AffineValueMap is an affine map plus its ML value operands and results for analysis purposes.
void buildAffineLoopNest(OpBuilder &builder, Location loc, ArrayRef< int64_t > lbs, ArrayRef< int64_t > ubs, ArrayRef< int64_t > steps, function_ref< void(OpBuilder &, Location, ValueRange)> bodyBuilderFn=nullptr)
Builds a perfect nest of affine.for loops, i.e., each loop except the innermost one contains only ano...
AffineApplyOp makeComposedAffineApply(OpBuilder &b, Location loc, AffineMap map, ArrayRef< OpFoldResult > operands, bool composeAffineMin=false)
Returns a composed AffineApplyOp by composing map and operands with other AffineApplyOps supplying th...
void extractForInductionVars(ArrayRef< AffineForOp > forInsts, SmallVectorImpl< Value > *ivs)
Extracts the induction variables from a list of AffineForOps and places them in the output argument i...
bool isValidDim(Value value)
Returns true if the given Value can be used as a dimension id in the region of the closest surroundin...
bool isAffineInductionVar(Value val)
Returns true if the provided value is the induction variable of an AffineForOp or AffineParallelOp.
SmallVector< OpFoldResult > makeComposedFoldedMultiResultAffineApply(OpBuilder &b, Location loc, AffineMap map, ArrayRef< OpFoldResult > operands, bool composeAffineMin=false)
Variant of makeComposedFoldedAffineApply suitable for multi-result maps.
OpFoldResult computeProduct(Location loc, OpBuilder &builder, ArrayRef< OpFoldResult > terms)
Return the product of terms, creating an affine.apply if any of them are non-constant values.
AffineForOp getForInductionVarOwner(Value val)
Returns the loop parent of an induction variable.
void canonicalizeMapAndOperands(AffineMap *map, SmallVectorImpl< Value > *operands)
Modifies both map and operands in-place so as to:
OpFoldResult makeComposedFoldedAffineMax(OpBuilder &b, Location loc, AffineMap map, ArrayRef< OpFoldResult > operands)
Constructs an AffineMinOp that computes a maximum across the results of applying map to operands,...
bool isAffineForInductionVar(Value val)
Returns true if the provided value is the induction variable of an AffineForOp.
OpFoldResult makeComposedFoldedAffineApply(OpBuilder &b, Location loc, AffineMap map, ArrayRef< OpFoldResult > operands, bool composeAffineMin=false)
Constructs an AffineApplyOp that applies map to operands after composing the map with the maps of any...
OpFoldResult makeComposedFoldedAffineMin(OpBuilder &b, Location loc, AffineMap map, ArrayRef< OpFoldResult > operands)
Constructs an AffineMinOp that computes a minimum across the results of applying map to operands,...
bool isTopLevelValue(Value value)
A utility function to check if a value is defined at the top level of an op with trait AffineScope or...
Region * getAffineAnalysisScope(Operation *op)
Returns the closest region enclosing op that is held by a non-affine operation; nullptr if there is n...
void fullyComposeAffineMapAndOperands(AffineMap *map, SmallVectorImpl< Value > *operands, bool composeAffineMin=false)
Given an affine map map and its input operands, this method composes into map, maps of AffineApplyOps...
void canonicalizeSetAndOperands(IntegerSet *set, SmallVectorImpl< Value > *operands)
Canonicalizes an integer set the same way canonicalizeMapAndOperands does for affine maps.
void extractInductionVars(ArrayRef< Operation * > affineOps, SmallVectorImpl< Value > &ivs)
Extracts the induction variables from a list of either AffineForOp or AffineParallelOp and places the...
bool isValidSymbol(Value value)
Returns true if the given value can be used as a symbol in the region of the closest surrounding op t...
AffineParallelOp getAffineParallelInductionVarOwner(Value val)
Returns true if the provided value is among the induction variables of an AffineParallelOp.
Region * getAffineScope(Operation *op)
Returns the closest region enclosing op that is held by an operation with trait AffineScope; nullptr ...
ParseResult parseDimAndSymbolList(OpAsmParser &parser, SmallVectorImpl< Value > &operands, unsigned &numDims)
Parses dimension and symbol list.
bool isAffineParallelInductionVar(Value val)
Returns true if val is the induction variable of an AffineParallelOp.
AffineMinOp makeComposedAffineMin(OpBuilder &b, Location loc, AffineMap map, ArrayRef< OpFoldResult > operands)
Returns an AffineMinOp obtained by composing map and operands with AffineApplyOps supplying those ope...
Include the generated interface declarations.
llvm::function_ref< Fn > function_ref
Definition LLVM.h:147