MLIR 22.0.0git
PDLPatternMatch.cpp
Go to the documentation of this file.
1//===- PDLPatternMatch.cpp - Base classes for PDL pattern match
2//------------===//
3//
4// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
5// See https://llvm.org/LICENSE.txt for license information.
6// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7//
8//===----------------------------------------------------------------------===//
9
11#include "llvm/Support/InterleavedRange.h"
12
13using namespace mlir;
14
15//===----------------------------------------------------------------------===//
16// PDLValue
17//===----------------------------------------------------------------------===//
18
19void PDLValue::print(raw_ostream &os) const {
20 if (!value) {
21 os << "<NULL-PDLValue>";
22 return;
23 }
24 switch (kind) {
25 case Kind::Attribute:
26 os << cast<Attribute>();
27 break;
28 case Kind::Operation:
29 os << *cast<Operation *>();
30 break;
31 case Kind::Type:
32 os << cast<Type>();
33 break;
34 case Kind::TypeRange:
35 os << llvm::interleaved(cast<TypeRange>());
36 break;
37 case Kind::Value:
38 os << cast<Value>();
39 break;
40 case Kind::ValueRange:
41 os << llvm::interleaved(cast<ValueRange>());
42 break;
43 }
44}
45
46void PDLValue::print(raw_ostream &os, Kind kind) {
47 switch (kind) {
48 case Kind::Attribute:
49 os << "Attribute";
50 break;
51 case Kind::Operation:
52 os << "Operation";
53 break;
54 case Kind::Type:
55 os << "Type";
56 break;
57 case Kind::TypeRange:
58 os << "TypeRange";
59 break;
60 case Kind::Value:
61 os << "Value";
62 break;
63 case Kind::ValueRange:
64 os << "ValueRange";
65 break;
66 }
67}
68
69//===----------------------------------------------------------------------===//
70// PDLPatternModule
71//===----------------------------------------------------------------------===//
72
73void PDLPatternModule::mergeIn(PDLPatternModule &&other) {
74 // Ignore the other module if it has no patterns.
75 if (!other.pdlModule)
76 return;
77
78 // Steal the functions and config of the other module.
79 for (auto &it : other.constraintFunctions)
80 registerConstraintFunction(it.first(), std::move(it.second));
81 for (auto &it : other.rewriteFunctions)
82 registerRewriteFunction(it.first(), std::move(it.second));
83 for (auto &it : other.configs)
84 configs.emplace_back(std::move(it));
85 for (auto &it : other.configMap)
86 configMap.insert(it);
87
88 // Steal the other state if we have no patterns.
89 if (!pdlModule) {
90 pdlModule = std::move(other.pdlModule);
91 return;
92 }
93
94 // Merge the pattern operations from the other module into this one.
95 Block *block = pdlModule->getBody();
96 block->getOperations().splice(block->end(),
97 other.pdlModule->getBody()->getOperations());
98}
99
100void PDLPatternModule::attachConfigToPatterns(ModuleOp module,
101 PDLPatternConfigSet &configSet) {
102 // Attach the configuration to the symbols within the module. We only add
103 // to symbols to avoid hardcoding any specific operation names here (given
104 // that we don't depend on any PDL dialect). We can't use
105 // cast<SymbolOpInterface> here because patterns may be optional symbols.
106 module->walk([&](Operation *op) {
107 if (op->hasTrait<SymbolOpInterface::Trait>())
108 configMap[op] = &configSet;
109 });
110}
111
112//===----------------------------------------------------------------------===//
113// Function Registry
114//===----------------------------------------------------------------------===//
115
116void PDLPatternModule::registerConstraintFunction(
117 StringRef name, PDLConstraintFunction constraintFn) {
118 // TODO: Is it possible to diagnose when `name` is already registered to
119 // a function that is not equivalent to `constraintFn`?
120 // Allow existing mappings in the case multiple patterns depend on the same
121 // constraint.
122 constraintFunctions.try_emplace(name, std::move(constraintFn));
123}
124
125void PDLPatternModule::registerRewriteFunction(StringRef name,
126 PDLRewriteFunction rewriteFn) {
127 // TODO: Is it possible to diagnose when `name` is already registered to
128 // a function that is not equivalent to `rewriteFn`?
129 // Allow existing mappings in the case multiple patterns depend on the same
130 // rewrite.
131 rewriteFunctions.try_emplace(name, std::move(rewriteFn));
132}
OpListType & getOperations()
Definition Block.h:137
iterator end()
Definition Block.h:144
Include the generated interface declarations.