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