MLIR  16.0.0git
CodegenStrategy.h
Go to the documentation of this file.
1 //===- CodegenStrategy.h - Linalg programmable codegen strategy -*- 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_DIALECT_LINALG_TRANSFORMS_CODEGENSTRATEGY_H_
10 #define MLIR_DIALECT_LINALG_TRANSFORMS_CODEGENSTRATEGY_H_
11 
12 #include <utility>
13 
16 #include "mlir/Pass/PassManager.h"
17 
18 namespace mlir {
19 
20 namespace linalg {
21 
22 /// Abstract Transformation class applied in a sequence that also handles state
23 /// through markers.
26  : filter(std::move(f)) {}
27  virtual ~Transformation() = default;
28  virtual void addToPassPipeline(OpPassManager &pm,
29  LinalgTransformationFilter m) const = 0;
31 };
32 
33 /// Represent one application of LinalgStrategyTileAndFusePass.
34 struct TileAndFuse : public Transformation {
37  : Transformation(std::move(f)), opName(name),
38  options(std::move(options)) {}
39 
41  LinalgTransformationFilter m) const override {
43  }
44 
45 private:
46  std::string opName;
48 };
49 
50 /// Represent one application of LinalgStrategyTilePass.
51 struct Tile : public Transformation {
54  : Transformation(std::move(f)), opName(name),
55  options(std::move(options)) {}
56 
58  LinalgTransformationFilter m) const override {
60  }
61 
62 private:
63  std::string opName;
65 };
66 
67 /// Represent one application of LinalgStrategyPadPass.
68 struct Pad : public Transformation {
71  : Transformation(std::move(f)), opName(name),
72  options(std::move(options)) {}
73 
75  LinalgTransformationFilter m) const override {
77  }
78 
79 private:
80  std::string opName;
82 };
83 
84 /// Represent one application of createLinalgStrategyGeneralizePass.
85 struct Generalize : public Transformation {
86  explicit Generalize(StringRef name,
88  : Transformation(std::move(f)), opName(name) {}
89 
91  LinalgTransformationFilter m) const override {
93  }
94 
95 private:
96  std::string opName;
97 };
98 
99 /// Represent one application of createLinalgStrategyInterchangePass.
100 struct Interchange : public Transformation {
101  explicit Interchange(ArrayRef<int64_t> iteratorInterchange,
103  : Transformation(std::move(f)),
104  iteratorInterchange(iteratorInterchange.begin(),
105  iteratorInterchange.end()) {}
106 
108  LinalgTransformationFilter m) const override {
109  pm.addPass(createLinalgStrategyInterchangePass(iteratorInterchange, m));
110  }
111 
112 private:
113  SmallVector<int64_t> iteratorInterchange;
114 };
115 
116 /// Represent one application of createLinalgStrategyDecomposePass.
117 struct Decompose : public Transformation {
119  : Transformation(std::move(f)) {}
120 
122  LinalgTransformationFilter m) const override {
124  }
125 };
126 
127 /// Represent one application of createLinalgStrategyPeelPass.
128 struct Peel : public Transformation {
131  : Transformation(std::move(f)), options(options) {}
132 
135  : Transformation(std::move(f)), opName(name), options(options) {}
136 
138  LinalgTransformationFilter m) const override {
140  }
141 
142 private:
143  std::string opName;
145 };
146 
147 /// Represent one application of createLinalgStrategyVectorizePass.
148 struct Vectorize : public Transformation {
151  bool padVectorize = false)
152  : Transformation(std::move(f)), options(options),
153  vectorizePadding(padVectorize) {}
154 
157  bool padVectorize = false)
158  : Transformation(std::move(f)), opName(name), options(options),
159  vectorizePadding(padVectorize) {}
160 
162  LinalgTransformationFilter m) const override {
164  vectorizePadding));
165  }
166 
167 private:
168  std::string opName;
170  bool vectorizePadding;
171 };
172 
173 /// Represent one application of createLinalgStrategyLowerVectorsPass.
175  explicit VectorLowering(
178  : Transformation(std::move(f)), options(options) {}
179 
181  LinalgTransformationFilter m) const override {
183  }
184 
185 private:
187 };
188 
189 /// Codegen strategy controls how a Linalg op is progressively lowered.
191  /// Append a pattern to tile the Op `opName` and fuse its producers with
192  /// tiling and fusion `options`.
195  const LinalgTransformationFilter::FilterFunction &f = nullptr) {
196  transformationSequence.emplace_back(
197  std::make_unique<TileAndFuse>(opName, options, f));
198  return *this;
199  }
200  /// Conditionally append a pattern to tile the Op `opName` and fuse its
201  /// producers with tiling and fusion `options`.
205  return b ? tileAndFuse(opName, std::move(options), std::move(f)) : *this;
206  }
207  /// Append a pattern to add a level of tiling for Op `opName` with tiling
208  /// `options`.
210  tile(StringRef opName, const linalg::LinalgTilingOptions &options,
211  const LinalgTransformationFilter::FilterFunction &f = nullptr) {
212  transformationSequence.emplace_back(
213  std::make_unique<Tile>(opName, options, f));
214  return *this;
215  }
216  /// Conditionally append a pattern to add a level of tiling for
217  /// `LinalgOpType` with tiling `options`.
219  tileIf(bool b, StringRef opName, linalg::LinalgTilingOptions options,
221  return b ? tile(opName, std::move(options), std::move(f)) : *this;
222  }
223  /// Append a pattern to pad and hoist the operands of Op `opName` with padding
224  /// `options`.
226  pad(StringRef opName, const linalg::LinalgPaddingOptions &options,
227  const LinalgTransformationFilter::FilterFunction &f = nullptr) {
228  transformationSequence.emplace_back(
229  std::make_unique<Pad>(opName, options, f));
230  return *this;
231  }
232  /// Conditionally append a pattern to pad and hoist the operands of Op
233  /// `opName` with padding `options`.
235  padIf(bool b, StringRef opName, linalg::LinalgPaddingOptions options,
237  return b ? pad(opName, std::move(options), std::move(f)) : *this;
238  }
239  /// Append a pattern to generalize named operations.
241  generalize(StringRef opName,
242  const LinalgTransformationFilter::FilterFunction &f = nullptr) {
243  transformationSequence.emplace_back(
244  std::make_unique<Generalize>(opName, f));
245  return *this;
246  }
247  /// Conditionally append a pattern to generalize named operations.
249  generalizeIf(bool b, StringRef opName,
251  return b ? generalize(opName, std::move(f)) : *this;
252  }
253  /// Append a pattern to interchange iterators.
255  interchange(ArrayRef<int64_t> iteratorInterchange,
256  const LinalgTransformationFilter::FilterFunction &f = nullptr) {
257  transformationSequence.emplace_back(
258  std::make_unique<Interchange>(iteratorInterchange, f));
259  return *this;
260  }
261  /// Conditionally append a pattern to interchange iterators.
263  interchangeIf(bool b, ArrayRef<int64_t> iteratorInterchange,
265  return b ? interchange(iteratorInterchange, std::move(f)) : *this;
266  }
267  /// Append patterns to decompose convolutions.
270  transformationSequence.emplace_back(std::make_unique<Decompose>(f));
271  return *this;
272  }
273  /// Conditionally append patterns to decompose convolutions.
276  return b ? decompose(std::move(f)) : *this;
277  }
278  /// Append a pattern to peel 'LinalgOpType'.
280  peel(StringRef opName, const LinalgPeelOptions &options,
281  const LinalgTransformationFilter::FilterFunction &f = nullptr) {
282  transformationSequence.emplace_back(
283  std::make_unique<Peel>(opName, options, f));
284  return *this;
285  }
286  /// Conditionally append a pattern to peel 'LinalgOpType'.
288  peelIf(bool b, StringRef opName, const LinalgPeelOptions &options,
290  return b ? peel(opName, options, std::move(f)) : *this;
291  }
292  /// Append a pattern to rewrite `LinalgOpType` as a vector operation.
294  vectorize(StringRef opName,
296  bool vectorizePadding = false) {
297  transformationSequence.emplace_back(std::make_unique<Vectorize>(
298  opName, linalg::LinalgVectorizationOptions(), f, vectorizePadding));
299  return *this;
300  }
301  /// Conditionally append a pattern to rewrite `LinalgOpType` as a vector
302  /// operation.
304  vectorizeIf(bool b, StringRef opName,
306  bool vectorizePadding = false) {
307  return b ? vectorize(opName, std::move(f), vectorizePadding) : *this;
308  }
309  /// Append a pattern to lower all vector operations.
311  transformationSequence.emplace_back(
312  std::make_unique<VectorLowering>(options));
313  return *this;
314  }
315  /// Configure the post staged-patterns global enabling passes options.
318  linalgEnablingOptions = options;
319  return *this;
320  }
321 
322  /// Apply the transformation patterns in sequence with cleanup
323  /// transformations interleaved.
324  void configurePassPipeline(OpPassManager &pm, MLIRContext *context,
325  bool addEnablePass = true) const;
326 
327 private:
328  LogicalResult postPatternTransforms(Operation *func) const;
329 
330  LinalgEnablingOptions linalgEnablingOptions;
331  SmallVector<std::unique_ptr<Transformation>, 4> transformationSequence;
332 };
333 
334 } // namespace linalg
335 } // namespace mlir
336 
337 #endif // MLIR_DIALECT_LINALG_TRANSFORMS_CODEGENSTRATEGY_H_
Include the generated interface declarations.
CodegenStrategy & generalizeIf(bool b, StringRef opName, LinalgTransformationFilter::FilterFunction f=nullptr)
Conditionally append a pattern to generalize named operations.
std::unique_ptr< OperationPass< func::FuncOp > > createLinalgStrategyInterchangePass(ArrayRef< int64_t > iteratorInterchange={}, const linalg::LinalgTransformationFilter &filter=linalg::LinalgTransformationFilter())
Create a LinalgStrategyInterchangePass.
Helper class to control application of linalg transformation patterns.
Definition: Transforms.h:348
Pad(StringRef name, linalg::LinalgPaddingOptions options, LinalgTransformationFilter::FilterFunction f=nullptr)
Represent one application of LinalgStrategyTilePass.
VectorLowering(linalg::LinalgVectorLoweringOptions options, LinalgTransformationFilter::FilterFunction f=nullptr)
std::unique_ptr< OperationPass< func::FuncOp > > createLinalgStrategyPeelPass(StringRef opName="", const linalg::LinalgPeelOptions &opt=linalg::LinalgPeelOptions(), const linalg::LinalgTransformationFilter &filter=linalg::LinalgTransformationFilter())
Create a LinalgStrategyPeelPass.
virtual void addToPassPipeline(OpPassManager &pm, LinalgTransformationFilter m) const =0
Operation is a basic unit of execution within MLIR.
Definition: Operation.h:28
void addToPassPipeline(OpPassManager &pm, LinalgTransformationFilter m) const override
CodegenStrategy & generalize(StringRef opName, const LinalgTransformationFilter::FilterFunction &f=nullptr)
Append a pattern to generalize named operations.
void addToPassPipeline(OpPassManager &pm, LinalgTransformationFilter m) const override
std::unique_ptr< OperationPass< func::FuncOp > > createLinalgStrategyVectorizePass(StringRef opName="", linalg::LinalgVectorizationOptions opt=linalg::LinalgVectorizationOptions(), const linalg::LinalgTransformationFilter &filter=linalg::LinalgTransformationFilter(), bool padVectorize=false)
Create a LinalgStrategyVectorizePass.
Options to control the application of enabling transformations.
Definition: Transforms.h:990
Represent one application of LinalgStrategyPadPass.
void addToPassPipeline(OpPassManager &pm, LinalgTransformationFilter m) const override
Vectorize(StringRef name, linalg::LinalgVectorizationOptions options, LinalgTransformationFilter::FilterFunction f=nullptr, bool padVectorize=false)
void addToPassPipeline(OpPassManager &pm, LinalgTransformationFilter m) const override
Interchange(ArrayRef< int64_t > iteratorInterchange, LinalgTransformationFilter::FilterFunction f=nullptr)
std::unique_ptr< OperationPass< func::FuncOp > > createLinalgStrategyGeneralizePass(StringRef opName="", const linalg::LinalgTransformationFilter &filter=linalg::LinalgTransformationFilter())
Create a LinalgStrategyGeneralizePass.
CodegenStrategy & peelIf(bool b, StringRef opName, const LinalgPeelOptions &options, LinalgTransformationFilter::FilterFunction f=nullptr)
Conditionally append a pattern to peel &#39;LinalgOpType&#39;.
Tile(StringRef name, linalg::LinalgTilingOptions options, LinalgTransformationFilter::FilterFunction f=nullptr)
Transformation(LinalgTransformationFilter::FilterFunction f)
CodegenStrategy & peel(StringRef opName, const LinalgPeelOptions &options, const LinalgTransformationFilter::FilterFunction &f=nullptr)
Append a pattern to peel &#39;LinalgOpType&#39;.
CodegenStrategy & decompose(const LinalgTransformationFilter::FilterFunction &f=nullptr)
Append patterns to decompose convolutions.
virtual ~Transformation()=default
Represent one application of createLinalgStrategyGeneralizePass.
Codegen strategy controls how a Linalg op is progressively lowered.
void addToPassPipeline(OpPassManager &pm, LinalgTransformationFilter m) const override
This class represents an efficient way to signal success or failure.
Definition: LogicalResult.h:26
std::unique_ptr< OperationPass< func::FuncOp > > createLinalgStrategyLowerVectorsPass(linalg::LinalgVectorLoweringOptions opt=linalg::LinalgVectorLoweringOptions(), const linalg::LinalgTransformationFilter &filter=linalg::LinalgTransformationFilter())
Create a LinalgStrategyLowerVectorsPass.
Represent one application of createLinalgStrategyInterchangePass.
CodegenStrategy & interchangeIf(bool b, ArrayRef< int64_t > iteratorInterchange, LinalgTransformationFilter::FilterFunction f=nullptr)
Conditionally append a pattern to interchange iterators.
SmallVector< SmallVector< AffineForOp, 8 >, 8 > tile(ArrayRef< AffineForOp > forOps, ArrayRef< uint64_t > sizes, ArrayRef< AffineForOp > targets)
Performs tiling fo imperfectly nested loops (with interchange) by strip-mining the forOps by sizes an...
Definition: LoopUtils.cpp:1701
Vectorize(linalg::LinalgVectorizationOptions options, LinalgTransformationFilter::FilterFunction f=nullptr, bool padVectorize=false)
std::unique_ptr< OperationPass< func::FuncOp > > createLinalgStrategyTileAndFusePass(StringRef opName="", const linalg::LinalgTilingAndFusionOptions &opt={}, const linalg::LinalgTransformationFilter &filter=linalg::LinalgTransformationFilter())
Linalg strategy passes.
void addToPassPipeline(OpPassManager &pm, LinalgTransformationFilter m) const override
CodegenStrategy & tileAndFuseIf(bool b, StringRef opName, LinalgTilingAndFusionOptions options, LinalgTransformationFilter::FilterFunction f=nullptr)
Conditionally append a pattern to tile the Op opName and fuse its producers with tiling and fusion op...
void addToPassPipeline(OpPassManager &pm, LinalgTransformationFilter m) const override
CodegenStrategy & vectorizeIf(bool b, StringRef opName, LinalgTransformationFilter::FilterFunction f=nullptr, bool vectorizePadding=false)
Conditionally append a pattern to rewrite LinalgOpType as a vector operation.
Generalize(StringRef name, LinalgTransformationFilter::FilterFunction f=nullptr)
std::unique_ptr< OperationPass< func::FuncOp > > createLinalgStrategyPadPass(StringRef opName="", const linalg::LinalgPaddingOptions &opt=linalg::LinalgPaddingOptions(), const linalg::LinalgTransformationFilter &filter=linalg::LinalgTransformationFilter())
Create a LinalgStrategyPadPass.
CodegenStrategy & interchange(ArrayRef< int64_t > iteratorInterchange, const LinalgTransformationFilter::FilterFunction &f=nullptr)
Append a pattern to interchange iterators.
CodegenStrategy & setVectorTransferToSCFOptions(LinalgEnablingOptions options)
Configure the post staged-patterns global enabling passes options.
Represent one application of createLinalgStrategyPeelPass.
Represent one application of LinalgStrategyTileAndFusePass.
Decompose(LinalgTransformationFilter::FilterFunction f=nullptr)
static llvm::ManagedStatic< PassManagerOptions > options
void addToPassPipeline(OpPassManager &pm, LinalgTransformationFilter m) const override
std::function< LogicalResult(Operation *)> FilterFunction
Definition: Transforms.h:349
std::unique_ptr< OperationPass< func::FuncOp > > createLinalgStrategyTilePass(StringRef opName="", const linalg::LinalgTilingOptions &opt=linalg::LinalgTilingOptions(), const linalg::LinalgTransformationFilter &filter=linalg::LinalgTransformationFilter())
Create a LinalgStrategyTilePass.
Abstract Transformation class applied in a sequence that also handles state through markers...
Represent one application of createLinalgStrategyVectorizePass.
CodegenStrategy & decomposeIf(bool b, LinalgTransformationFilter::FilterFunction f=nullptr)
Conditionally append patterns to decompose convolutions.
Represent one application of createLinalgStrategyDecomposePass.
CodegenStrategy & tileIf(bool b, StringRef opName, linalg::LinalgTilingOptions options, LinalgTransformationFilter::FilterFunction f=nullptr)
Conditionally append a pattern to add a level of tiling for LinalgOpType with tiling options...
MLIRContext is the top-level object for a collection of MLIR operations.
Definition: MLIRContext.h:55
CodegenStrategy & tileAndFuse(StringRef opName, const LinalgTilingAndFusionOptions &options, const LinalgTransformationFilter::FilterFunction &f=nullptr)
Append a pattern to tile the Op opName and fuse its producers with tiling and fusion options...
CodegenStrategy & vectorize(StringRef opName, const LinalgTransformationFilter::FilterFunction &f=nullptr, bool vectorizePadding=false)
Append a pattern to rewrite LinalgOpType as a vector operation.
CodegenStrategy & tile(StringRef opName, const linalg::LinalgTilingOptions &options, const LinalgTransformationFilter::FilterFunction &f=nullptr)
Append a pattern to add a level of tiling for Op opName with tiling options.
Peel(linalg::LinalgPeelOptions options, LinalgTransformationFilter::FilterFunction f=nullptr)
Vector lowering options control how ops are lowered down to 1-D and scf.for form. ...
Definition: Transforms.h:1014
Peel(StringRef name, linalg::LinalgPeelOptions options, LinalgTransformationFilter::FilterFunction f=nullptr)
LogicalResult vectorize(RewriterBase &builder, LinalgOp linalgOp)
Emit a suitable vector form for a Linalg op with fully static shape.
TileAndFuse(StringRef name, linalg::LinalgTilingAndFusionOptions options, LinalgTransformationFilter::FilterFunction f=nullptr)
void addToPassPipeline(OpPassManager &pm, LinalgTransformationFilter m) const override
Linalg vectorization patterns.
Definition: Transforms.h:945
void addPass(std::unique_ptr< Pass > pass)
Add the given pass to this pass manager.
Definition: Pass.cpp:333
LinalgTransformationFilter::FilterFunction filter
Represent one application of createLinalgStrategyLowerVectorsPass.
static FailureOr< SmallVector< Operation * > > tileAndFuse(Operation *producerOp, Operation *containingOp, RewriterBase &rewriter)
CodegenStrategy & vectorLowering(LinalgVectorLoweringOptions options)
Append a pattern to lower all vector operations.
CodegenStrategy & padIf(bool b, StringRef opName, linalg::LinalgPaddingOptions options, LinalgTransformationFilter::FilterFunction f=nullptr)
Conditionally append a pattern to pad and hoist the operands of Op opName with padding options...
std::unique_ptr< OperationPass< func::FuncOp > > createLinalgStrategyDecomposePass(const linalg::LinalgTransformationFilter &filter=linalg::LinalgTransformationFilter())
Create a LinalgStrategyDecomposePass.
This class represents a pass manager that runs passes on either a specific operation type...
Definition: PassManager.h:52
CodegenStrategy & pad(StringRef opName, const linalg::LinalgPaddingOptions &options, const LinalgTransformationFilter::FilterFunction &f=nullptr)
Append a pattern to pad and hoist the operands of Op opName with padding options. ...