LLVM: lib/TableGen/SetTheory.cpp Source File (original) (raw)
1
2
3
4
5
6
7
8
9
10
11
12
13
25#include
26#include
27#include
28#include
29
30using namespace llvm;
31
32
33namespace {
34
37
38
43 }
44};
45
46
51 PrintFatalError(Loc, "Set difference needs at least two arguments: " +
53 RecSet Add, Sub;
57 if (!Sub.count(I))
58 Elts.insert(I);
59 }
60};
61
62
67 PrintFatalError(Loc, "Set intersection requires two arguments: " +
69 RecSet S1, S2;
71 ST.evaluate(Expr->arg_begin()[1], S2, Loc);
73 if (S2.count(I))
74 Elts.insert(I);
75 }
76};
77
78
80 virtual void apply2(SetTheory &ST, const DagInit *Expr, RecSet &Set,
82
86 PrintFatalError(Loc, "Operator requires (Op Set, Int) arguments: " +
88 RecSet Set;
89 ST.evaluate(Expr->arg_begin()[0], Set, Loc);
90 const auto *II = dyn_cast(Expr->arg_begin()[1]);
91 if ()
92 PrintFatalError(Loc, "Second argument must be an integer: " +
94 apply2(ST, Expr, Set, II->getValue(), Elts, Loc);
95 }
96};
97
98
99struct ShlOp : public SetIntBinOp {
100 void apply2(SetTheory &ST, const DagInit *Expr, RecSet &Set, int64_t N,
102 if (N < 0)
105 if (unsigned(N) < Set.size())
106 Elts.insert(Set.begin() + N, Set.end());
107 }
108};
109
110
111struct TruncOp : public SetIntBinOp {
112 void apply2(SetTheory &ST, const DagInit *Expr, RecSet &Set, int64_t N,
114 if (N < 0)
117 if (unsigned(N) > Set.size())
119 Elts.insert(Set.begin(), Set.begin() + N);
120 }
121};
122
123
124struct RotOp : public SetIntBinOp {
126
127 RotOp(bool Rev) : Reverse(Rev) {}
128
129 void apply2(SetTheory &ST, const DagInit *Expr, RecSet &Set, int64_t N,
131 if (Reverse)
133
134 if (Set.empty())
135 return;
136 if (N < 0)
137 N = Set.size() - (-N % Set.size());
138 else
140 Elts.insert(Set.begin() + N, Set.end());
141 Elts.insert(Set.begin(), Set.begin() + N);
142 }
143};
144
145
146struct DecimateOp : public SetIntBinOp {
147 void apply2(SetTheory &ST, const DagInit *Expr, RecSet &Set, int64_t N,
149 if (N <= 0)
152 for (unsigned I = 0; I < Set.size(); I += N)
153 Elts.insert(Set[I]);
154 }
155};
156
157
161
163 unsigned MaxSize = 0;
165 ST.evaluate(Arg, Value, Loc);
166 MaxSize = std::max(MaxSize, unsigned(Value.size()));
167 }
168
169 for (unsigned n = 0; n != MaxSize; ++n)
170 for (const RecSet &Value : Values)
171 if (n < Value.size())
172 Elts.insert(Value[n]);
173 }
174};
175
176
180 int Step = 1;
182 PrintFatalError(Loc, "Bad args to (sequence \"Format\", From, To): " +
185 if (const auto *II = dyn_cast(Expr->arg_begin()[3]))
186 Step = II->getValue();
187 else
190 }
191
193 if (const auto *SI = dyn_cast(Expr->arg_begin()[0]))
194 Format = std::string(SI->getValue());
195 else
197
198 int64_t From, To;
199 if (const auto *II = dyn_cast(Expr->arg_begin()[1]))
201 else
203 if (From < 0 || From >= (1 << 30))
205
206 if (const auto *II = dyn_cast(Expr->arg_begin()[2]))
207 To = II->getValue();
208 else
210 if (To < 0 || To >= (1 << 30))
212
214 cast(Expr->getOperator())->getDef()->getRecords();
215
216 Step *= From <= To ? 1 : -1;
217 while (true) {
218 if (Step > 0 && From > To)
219 break;
220 else if (Step < 0 && From < To)
221 break;
222 std::string Name;
226 if (!Rec)
229
230 if (const RecVec *Result = ST.expand(Rec))
232 else
233 Elts.insert(Rec);
234
235 From += Step;
236 }
237 }
238};
239
240
243
244 FieldExpander(StringRef fn) : FieldName(fn) {}
245
247 ST.evaluate(Def->getValueInit(FieldName), Elts, Def->getLoc());
248 }
249};
250
251}
252
253
254void SetTheory::Operator::anchor() {}
255void SetTheory::Expander::anchor() {}
256
258 addOperator("add", std::make_unique());
259 addOperator("sub", std::make_unique());
260 addOperator("and", std::make_unique());
261 addOperator("shl", std::make_unique());
262 addOperator("trunc", std::make_unique());
263 addOperator("rotl", std::make_unique(false));
264 addOperator("rotr", std::make_unique(true));
265 addOperator("decimate", std::make_unique());
266 addOperator("interleave", std::make_unique());
267 addOperator("sequence", std::make_unique());
268}
269
271 Operators[Name] = std::move(Op);
272}
273
275 Expanders[ClassName] = std::move(E);
276}
277
279 addExpander(ClassName, std::make_unique(FieldName));
280}
281
283
284 if (const auto *Def = dyn_cast(Expr)) {
285 if (const RecVec *Result = expand(Def->getDef()))
286 return Elts.insert(Result->begin(), Result->end());
287 Elts.insert(Def->getDef());
288 return;
289 }
290
291
292 if (const auto *LI = dyn_cast(Expr))
293 return evaluate(LI->begin(), LI->end(), Elts, Loc);
294
295
296 const auto *DagExpr = dyn_cast(Expr);
297 if (!DagExpr)
299 const auto *OpInit = dyn_cast(DagExpr->getOperator());
302 auto I = Operators.find(OpInit->getDef()->getName());
303 if (I == Operators.end())
305 I->second->apply(*this, DagExpr, Elts, Loc);
306}
307
309
310 ExpandMap::iterator I = Expansions.find(Set);
311 if (I != Expansions.end())
312 return &I->second;
313
314
315 for (const auto &[SuperClass, Loc] : Set->getSuperClasses()) {
316
317 if (!isa(SuperClass->getNameInit()))
318 continue;
319 auto I = Expanders.find(SuperClass->getName());
320 if (I == Expanders.end())
321 continue;
322
323 RecVec &EltVec = Expansions[Set];
325 I->second->expand(*this, Set, Elts);
326 EltVec.assign(Elts.begin(), Elts.end());
327 return &EltVec;
328 }
329
330
331 return nullptr;
332}
BlockVerifier::State From
uint64_t IntrinsicInst * II
This file defines the SmallVector class.
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
This class represents an Operation in the Expression.
(v a, b) - Represent a DAG tree value.
unsigned getNumArgs() const
const_arg_iterator arg_begin() const
const_arg_iterator arg_end() const
const Init * getOperator() const
ArrayRef< const Init * > getArgs() const
std::string getAsString() const override
Convert this value to a literal form.
virtual std::string getAsString() const =0
Convert this value to a literal form.
Base class for operators.
Expander - A callback function that can transform a Record representing a set into a fully expanded l...
virtual void expand(SetTheory &, const Record *, RecSet &Elts)=0
Operator - A callback representing a DAG operator.
virtual void apply(SetTheory &, const DagInit *Expr, RecSet &Elts, ArrayRef< SMLoc > Loc)=0
apply - Apply this operator to Expr's arguments and insert the result in Elts.
void addOperator(StringRef Name, std::unique_ptr< Operator >)
addOperator - Add a DAG operator.
SetTheory()
Create a SetTheory instance with only the standard operators.
const RecVec * expand(const Record *Set)
expand - Expand a record into a set of elements if possible.
SmallSetVector< const Record *, 16 > RecSet
void evaluate(const Init *Expr, RecSet &Elts, ArrayRef< SMLoc > Loc)
evaluate - Evaluate Expr and append the resulting set to Elts.
std::vector< const Record * > RecVec
void addFieldExpander(StringRef ClassName, StringRef FieldName)
addFieldExpander - Add an expander for ClassName that simply evaluates FieldName in the Record to get...
void addExpander(StringRef ClassName, std::unique_ptr< Expander >)
addExpander - Add an expander for Records with the named super class.
iterator end()
Get an iterator to the end of the SetVector.
iterator begin()
Get an iterator to the beginning of the SetVector.
bool insert(const value_type &X)
Insert a new element into the SetVector.
A SetVector that performs no allocations if smaller than a certain size.
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
StringRef - Represent a constant reference to a string, i.e.
LLVM Value Representation.
A raw_ostream that writes to an std::string.
llvm::SmallVector< std::shared_ptr< RecordsSlice >, 4 > Records
NodeAddr< DefNode * > Def
This is an optimization pass for GlobalISel generic memory operations.
detail::zippy< detail::zip_shortest, T, U, Args... > zip(T &&t, U &&u, Args &&...args)
zip iterator for two or more iteratable types.
void PrintFatalError(const Twine &Msg)
format_object< Ts... > format(const char *Fmt, const Ts &... Vals)
These are helper functions used to produce formatted output.