File: | build/source/llvm/utils/TableGen/DAGISelMatcherEmitter.cpp |
Warning: | line 1136, column 12 Value stored to 'TotalSize' during its initialization is never read |
Press '?' to see keyboard shortcuts
Keyboard shortcuts:
1 | //===- DAGISelMatcherEmitter.cpp - Matcher Emitter ------------------------===// |
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 contains code to generate C++ code for a matcher. |
10 | // |
11 | //===----------------------------------------------------------------------===// |
12 | |
13 | #include "CodeGenDAGPatterns.h" |
14 | #include "CodeGenInstruction.h" |
15 | #include "CodeGenRegisters.h" |
16 | #include "CodeGenTarget.h" |
17 | #include "DAGISelMatcher.h" |
18 | #include "SDNodeProperties.h" |
19 | #include "llvm/ADT/DenseMap.h" |
20 | #include "llvm/ADT/MapVector.h" |
21 | #include "llvm/ADT/StringMap.h" |
22 | #include "llvm/ADT/TinyPtrVector.h" |
23 | #include "llvm/Support/CommandLine.h" |
24 | #include "llvm/Support/Format.h" |
25 | #include "llvm/Support/SourceMgr.h" |
26 | #include "llvm/TableGen/Error.h" |
27 | #include "llvm/TableGen/Record.h" |
28 | |
29 | using namespace llvm; |
30 | |
31 | enum { |
32 | IndexWidth = 6, |
33 | FullIndexWidth = IndexWidth + 4, |
34 | HistOpcWidth = 40, |
35 | }; |
36 | |
37 | cl::OptionCategory DAGISelCat("Options for -gen-dag-isel"); |
38 | |
39 | // To reduce generated source code size. |
40 | static cl::opt<bool> OmitComments("omit-comments", |
41 | cl::desc("Do not generate comments"), |
42 | cl::init(false), cl::cat(DAGISelCat)); |
43 | |
44 | static cl::opt<bool> InstrumentCoverage( |
45 | "instrument-coverage", |
46 | cl::desc("Generates tables to help identify patterns matched"), |
47 | cl::init(false), cl::cat(DAGISelCat)); |
48 | |
49 | namespace { |
50 | class MatcherTableEmitter { |
51 | const CodeGenDAGPatterns &CGP; |
52 | |
53 | SmallVector<unsigned, Matcher::HighestKind+1> OpcodeCounts; |
54 | |
55 | DenseMap<TreePattern *, unsigned> NodePredicateMap; |
56 | std::vector<TreePredicateFn> NodePredicates; |
57 | std::vector<TreePredicateFn> NodePredicatesWithOperands; |
58 | |
59 | // We de-duplicate the predicates by code string, and use this map to track |
60 | // all the patterns with "identical" predicates. |
61 | StringMap<TinyPtrVector<TreePattern *>> NodePredicatesByCodeToRun; |
62 | |
63 | StringMap<unsigned> PatternPredicateMap; |
64 | std::vector<std::string> PatternPredicates; |
65 | |
66 | DenseMap<const ComplexPattern*, unsigned> ComplexPatternMap; |
67 | std::vector<const ComplexPattern*> ComplexPatterns; |
68 | |
69 | |
70 | DenseMap<Record*, unsigned> NodeXFormMap; |
71 | std::vector<Record*> NodeXForms; |
72 | |
73 | std::vector<std::string> VecIncludeStrings; |
74 | MapVector<std::string, unsigned, StringMap<unsigned> > VecPatterns; |
75 | |
76 | unsigned getPatternIdxFromTable(std::string &&P, std::string &&include_loc) { |
77 | const auto It = VecPatterns.find(P); |
78 | if (It == VecPatterns.end()) { |
79 | VecPatterns.insert(make_pair(std::move(P), VecPatterns.size())); |
80 | VecIncludeStrings.push_back(std::move(include_loc)); |
81 | return VecIncludeStrings.size() - 1; |
82 | } |
83 | return It->second; |
84 | } |
85 | |
86 | public: |
87 | MatcherTableEmitter(const CodeGenDAGPatterns &cgp) |
88 | : CGP(cgp), OpcodeCounts(Matcher::HighestKind + 1, 0) {} |
89 | |
90 | unsigned EmitMatcherList(const Matcher *N, const unsigned Indent, |
91 | unsigned StartIdx, raw_ostream &OS); |
92 | |
93 | unsigned SizeMatcherList(Matcher *N, raw_ostream &OS); |
94 | |
95 | void EmitPredicateFunctions(raw_ostream &OS); |
96 | |
97 | void EmitHistogram(const Matcher *N, raw_ostream &OS); |
98 | |
99 | void EmitPatternMatchTable(raw_ostream &OS); |
100 | |
101 | private: |
102 | void EmitNodePredicatesFunction(const std::vector<TreePredicateFn> &Preds, |
103 | StringRef Decl, raw_ostream &OS); |
104 | |
105 | unsigned SizeMatcher(Matcher *N, raw_ostream &OS); |
106 | |
107 | unsigned EmitMatcher(const Matcher *N, const unsigned Indent, unsigned CurrentIdx, |
108 | raw_ostream &OS); |
109 | |
110 | unsigned getNodePredicate(TreePredicateFn Pred) { |
111 | TreePattern *TP = Pred.getOrigPatFragRecord(); |
112 | unsigned &Entry = NodePredicateMap[TP]; |
113 | if (Entry == 0) { |
114 | TinyPtrVector<TreePattern *> &SameCodePreds = |
115 | NodePredicatesByCodeToRun[Pred.getCodeToRunOnSDNode()]; |
116 | if (SameCodePreds.empty()) { |
117 | // We've never seen a predicate with the same code: allocate an entry. |
118 | if (Pred.usesOperands()) { |
119 | NodePredicatesWithOperands.push_back(Pred); |
120 | Entry = NodePredicatesWithOperands.size(); |
121 | } else { |
122 | NodePredicates.push_back(Pred); |
123 | Entry = NodePredicates.size(); |
124 | } |
125 | } else { |
126 | // We did see an identical predicate: re-use it. |
127 | Entry = NodePredicateMap[SameCodePreds.front()]; |
128 | assert(Entry != 0)(static_cast <bool> (Entry != 0) ? void (0) : __assert_fail ("Entry != 0", "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp" , 128, __extension__ __PRETTY_FUNCTION__)); |
129 | assert(TreePredicateFn(SameCodePreds.front()).usesOperands() ==(static_cast <bool> (TreePredicateFn(SameCodePreds.front ()).usesOperands() == Pred.usesOperands() && "PatFrags with some code must have same usesOperands setting" ) ? void (0) : __assert_fail ("TreePredicateFn(SameCodePreds.front()).usesOperands() == Pred.usesOperands() && \"PatFrags with some code must have same usesOperands setting\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 131, __extension__ __PRETTY_FUNCTION__)) |
130 | Pred.usesOperands() &&(static_cast <bool> (TreePredicateFn(SameCodePreds.front ()).usesOperands() == Pred.usesOperands() && "PatFrags with some code must have same usesOperands setting" ) ? void (0) : __assert_fail ("TreePredicateFn(SameCodePreds.front()).usesOperands() == Pred.usesOperands() && \"PatFrags with some code must have same usesOperands setting\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 131, __extension__ __PRETTY_FUNCTION__)) |
131 | "PatFrags with some code must have same usesOperands setting")(static_cast <bool> (TreePredicateFn(SameCodePreds.front ()).usesOperands() == Pred.usesOperands() && "PatFrags with some code must have same usesOperands setting" ) ? void (0) : __assert_fail ("TreePredicateFn(SameCodePreds.front()).usesOperands() == Pred.usesOperands() && \"PatFrags with some code must have same usesOperands setting\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 131, __extension__ __PRETTY_FUNCTION__)); |
132 | } |
133 | // In both cases, we've never seen this particular predicate before, so |
134 | // mark it in the list of predicates sharing the same code. |
135 | SameCodePreds.push_back(TP); |
136 | } |
137 | return Entry-1; |
138 | } |
139 | |
140 | unsigned getPatternPredicate(StringRef PredName) { |
141 | unsigned &Entry = PatternPredicateMap[PredName]; |
142 | if (Entry == 0) { |
143 | PatternPredicates.push_back(PredName.str()); |
144 | Entry = PatternPredicates.size(); |
145 | } |
146 | return Entry-1; |
147 | } |
148 | unsigned getComplexPat(const ComplexPattern &P) { |
149 | unsigned &Entry = ComplexPatternMap[&P]; |
150 | if (Entry == 0) { |
151 | ComplexPatterns.push_back(&P); |
152 | Entry = ComplexPatterns.size(); |
153 | } |
154 | return Entry-1; |
155 | } |
156 | |
157 | unsigned getNodeXFormID(Record *Rec) { |
158 | unsigned &Entry = NodeXFormMap[Rec]; |
159 | if (Entry == 0) { |
160 | NodeXForms.push_back(Rec); |
161 | Entry = NodeXForms.size(); |
162 | } |
163 | return Entry-1; |
164 | } |
165 | |
166 | }; |
167 | } // end anonymous namespace. |
168 | |
169 | static std::string GetPatFromTreePatternNode(const TreePatternNode *N) { |
170 | std::string str; |
171 | raw_string_ostream Stream(str); |
172 | Stream << *N; |
173 | return str; |
174 | } |
175 | |
176 | static unsigned GetVBRSize(unsigned Val) { |
177 | if (Val <= 127) return 1; |
178 | |
179 | unsigned NumBytes = 0; |
180 | while (Val >= 128) { |
181 | Val >>= 7; |
182 | ++NumBytes; |
183 | } |
184 | return NumBytes+1; |
185 | } |
186 | |
187 | /// EmitVBRValue - Emit the specified value as a VBR, returning the number of |
188 | /// bytes emitted. |
189 | static unsigned EmitVBRValue(uint64_t Val, raw_ostream &OS) { |
190 | if (Val <= 127) { |
191 | OS << Val << ", "; |
192 | return 1; |
193 | } |
194 | |
195 | uint64_t InVal = Val; |
196 | unsigned NumBytes = 0; |
197 | while (Val >= 128) { |
198 | OS << (Val&127) << "|128,"; |
199 | Val >>= 7; |
200 | ++NumBytes; |
201 | } |
202 | OS << Val; |
203 | if (!OmitComments) |
204 | OS << "/*" << InVal << "*/"; |
205 | OS << ", "; |
206 | return NumBytes+1; |
207 | } |
208 | |
209 | /// Emit the specified signed value as a VBR. To improve compression we encode |
210 | /// positive numbers shifted left by 1 and negative numbers negated and shifted |
211 | /// left by 1 with bit 0 set. |
212 | static unsigned EmitSignedVBRValue(uint64_t Val, raw_ostream &OS) { |
213 | if ((int64_t)Val >= 0) |
214 | Val = Val << 1; |
215 | else |
216 | Val = (-Val << 1) | 1; |
217 | |
218 | return EmitVBRValue(Val, OS); |
219 | } |
220 | |
221 | // This is expensive and slow. |
222 | static std::string getIncludePath(const Record *R) { |
223 | std::string str; |
224 | raw_string_ostream Stream(str); |
225 | auto Locs = R->getLoc(); |
226 | SMLoc L; |
227 | if (Locs.size() > 1) { |
228 | // Get where the pattern prototype was instantiated |
229 | L = Locs[1]; |
230 | } else if (Locs.size() == 1) { |
231 | L = Locs[0]; |
232 | } |
233 | unsigned CurBuf = SrcMgr.FindBufferContainingLoc(L); |
234 | assert(CurBuf && "Invalid or unspecified location!")(static_cast <bool> (CurBuf && "Invalid or unspecified location!" ) ? void (0) : __assert_fail ("CurBuf && \"Invalid or unspecified location!\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 234, __extension__ __PRETTY_FUNCTION__)); |
235 | |
236 | Stream << SrcMgr.getBufferInfo(CurBuf).Buffer->getBufferIdentifier() << ":" |
237 | << SrcMgr.FindLineNumber(L, CurBuf); |
238 | return str; |
239 | } |
240 | |
241 | /// This function traverses the matcher tree and sizes all the nodes |
242 | /// that are children of the three kinds of nodes that have them. |
243 | unsigned MatcherTableEmitter:: |
244 | SizeMatcherList(Matcher *N, raw_ostream &OS) { |
245 | unsigned Size = 0; |
246 | while (N) { |
247 | Size += SizeMatcher(N, OS); |
248 | N = N->getNext(); |
249 | } |
250 | return Size; |
251 | } |
252 | |
253 | /// This function sizes the children of the three kinds of nodes that |
254 | /// have them. It does so by using special cases for those three |
255 | /// nodes, but sharing the code in EmitMatcher() for the other kinds. |
256 | unsigned MatcherTableEmitter:: |
257 | SizeMatcher(Matcher *N, raw_ostream &OS) { |
258 | unsigned Idx = 0; |
259 | |
260 | ++OpcodeCounts[N->getKind()]; |
261 | switch (N->getKind()) { |
262 | // The Scope matcher has its kind, a series of child size + child, |
263 | // and a trailing zero. |
264 | case Matcher::Scope: { |
265 | ScopeMatcher *SM = cast<ScopeMatcher>(N); |
266 | assert(SM->getNext() == nullptr && "Scope matcher should not have next")(static_cast <bool> (SM->getNext() == nullptr && "Scope matcher should not have next") ? void (0) : __assert_fail ("SM->getNext() == nullptr && \"Scope matcher should not have next\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 266, __extension__ __PRETTY_FUNCTION__)); |
267 | unsigned Size = 1; // Count the kind. |
268 | for (unsigned i = 0, e = SM->getNumChildren(); i != e; ++i) { |
269 | const unsigned ChildSize = SizeMatcherList(SM->getChild(i), OS); |
270 | assert(ChildSize != 0 && "Matcher cannot have child of size 0")(static_cast <bool> (ChildSize != 0 && "Matcher cannot have child of size 0" ) ? void (0) : __assert_fail ("ChildSize != 0 && \"Matcher cannot have child of size 0\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 270, __extension__ __PRETTY_FUNCTION__)); |
271 | SM->getChild(i)->setSize(ChildSize); |
272 | Size += GetVBRSize(ChildSize) + ChildSize; // Count VBR and child size. |
273 | } |
274 | ++Size; // Count the zero sentinel. |
275 | return Size; |
276 | } |
277 | |
278 | // SwitchOpcode and SwitchType have their kind, a series of child size + |
279 | // opcode/type + child, and a trailing zero. |
280 | case Matcher::SwitchOpcode: |
281 | case Matcher::SwitchType: { |
282 | unsigned Size = 1; // Count the kind. |
283 | unsigned NumCases; |
284 | if (const SwitchOpcodeMatcher *SOM = dyn_cast<SwitchOpcodeMatcher>(N)) |
285 | NumCases = SOM->getNumCases(); |
286 | else |
287 | NumCases = cast<SwitchTypeMatcher>(N)->getNumCases(); |
288 | for (unsigned i = 0, e = NumCases; i != e; ++i) { |
289 | Matcher *Child; |
290 | if (SwitchOpcodeMatcher *SOM = dyn_cast<SwitchOpcodeMatcher>(N)) { |
291 | Child = SOM->getCaseMatcher(i); |
292 | Size += 2; // Count the child's opcode. |
293 | } else { |
294 | Child = cast<SwitchTypeMatcher>(N)->getCaseMatcher(i); |
295 | ++Size; // Count the child's type. |
296 | } |
297 | const unsigned ChildSize = SizeMatcherList(Child, OS); |
298 | assert(ChildSize != 0 && "Matcher cannot have child of size 0")(static_cast <bool> (ChildSize != 0 && "Matcher cannot have child of size 0" ) ? void (0) : __assert_fail ("ChildSize != 0 && \"Matcher cannot have child of size 0\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 298, __extension__ __PRETTY_FUNCTION__)); |
299 | Child->setSize(ChildSize); |
300 | Size += GetVBRSize(ChildSize) + ChildSize; // Count VBR and child size. |
301 | } |
302 | ++Size; // Count the zero sentinel. |
303 | return Size; |
304 | } |
305 | |
306 | default: |
307 | // Employ the matcher emitter to size other matchers. |
308 | return EmitMatcher(N, 0, Idx, OS); |
309 | } |
310 | llvm_unreachable("Unreachable")::llvm::llvm_unreachable_internal("Unreachable", "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp" , 310); |
311 | } |
312 | |
313 | static void BeginEmitFunction(raw_ostream &OS, StringRef RetType, |
314 | StringRef Decl, bool AddOverride) { |
315 | OS << "#ifdef GET_DAGISEL_DECL\n"; |
316 | OS << RetType << ' ' << Decl; |
317 | if (AddOverride) |
318 | OS << " override"; |
319 | OS << ";\n" |
320 | "#endif\n" |
321 | "#if defined(GET_DAGISEL_BODY) || DAGISEL_INLINE\n"; |
322 | OS << RetType << " DAGISEL_CLASS_COLONCOLON " << Decl << "\n"; |
323 | if (AddOverride) { |
324 | OS << "#if DAGISEL_INLINE\n" |
325 | " override\n" |
326 | "#endif\n"; |
327 | } |
328 | } |
329 | |
330 | static void EndEmitFunction(raw_ostream &OS) { |
331 | OS << "#endif // GET_DAGISEL_BODY\n\n"; |
332 | } |
333 | |
334 | void MatcherTableEmitter::EmitPatternMatchTable(raw_ostream &OS) { |
335 | |
336 | assert(isUInt<16>(VecPatterns.size()) &&(static_cast <bool> (isUInt<16>(VecPatterns.size( )) && "Using only 16 bits to encode offset into Pattern Table" ) ? void (0) : __assert_fail ("isUInt<16>(VecPatterns.size()) && \"Using only 16 bits to encode offset into Pattern Table\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 337, __extension__ __PRETTY_FUNCTION__)) |
337 | "Using only 16 bits to encode offset into Pattern Table")(static_cast <bool> (isUInt<16>(VecPatterns.size( )) && "Using only 16 bits to encode offset into Pattern Table" ) ? void (0) : __assert_fail ("isUInt<16>(VecPatterns.size()) && \"Using only 16 bits to encode offset into Pattern Table\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 337, __extension__ __PRETTY_FUNCTION__)); |
338 | assert(VecPatterns.size() == VecIncludeStrings.size() &&(static_cast <bool> (VecPatterns.size() == VecIncludeStrings .size() && "The sizes of Pattern and include vectors should be the same" ) ? void (0) : __assert_fail ("VecPatterns.size() == VecIncludeStrings.size() && \"The sizes of Pattern and include vectors should be the same\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 339, __extension__ __PRETTY_FUNCTION__)) |
339 | "The sizes of Pattern and include vectors should be the same")(static_cast <bool> (VecPatterns.size() == VecIncludeStrings .size() && "The sizes of Pattern and include vectors should be the same" ) ? void (0) : __assert_fail ("VecPatterns.size() == VecIncludeStrings.size() && \"The sizes of Pattern and include vectors should be the same\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 339, __extension__ __PRETTY_FUNCTION__)); |
340 | |
341 | BeginEmitFunction(OS, "StringRef", "getPatternForIndex(unsigned Index)", |
342 | true/*AddOverride*/); |
343 | OS << "{\n"; |
344 | OS << "static const char *PATTERN_MATCH_TABLE[] = {\n"; |
345 | |
346 | for (const auto &It : VecPatterns) { |
347 | OS << "\"" << It.first << "\",\n"; |
348 | } |
349 | |
350 | OS << "\n};"; |
351 | OS << "\nreturn StringRef(PATTERN_MATCH_TABLE[Index]);"; |
352 | OS << "\n}\n"; |
353 | EndEmitFunction(OS); |
354 | |
355 | BeginEmitFunction(OS, "StringRef", "getIncludePathForIndex(unsigned Index)", |
356 | true/*AddOverride*/); |
357 | OS << "{\n"; |
358 | OS << "static const char *INCLUDE_PATH_TABLE[] = {\n"; |
359 | |
360 | for (const auto &It : VecIncludeStrings) { |
361 | OS << "\"" << It << "\",\n"; |
362 | } |
363 | |
364 | OS << "\n};"; |
365 | OS << "\nreturn StringRef(INCLUDE_PATH_TABLE[Index]);"; |
366 | OS << "\n}\n"; |
367 | EndEmitFunction(OS); |
368 | } |
369 | |
370 | /// EmitMatcher - Emit bytes for the specified matcher and return |
371 | /// the number of bytes emitted. |
372 | unsigned MatcherTableEmitter:: |
373 | EmitMatcher(const Matcher *N, const unsigned Indent, unsigned CurrentIdx, |
374 | raw_ostream &OS) { |
375 | OS.indent(Indent); |
376 | |
377 | switch (N->getKind()) { |
378 | case Matcher::Scope: { |
379 | const ScopeMatcher *SM = cast<ScopeMatcher>(N); |
380 | unsigned StartIdx = CurrentIdx; |
381 | |
382 | // Emit all of the children. |
383 | for (unsigned i = 0, e = SM->getNumChildren(); i != e; ++i) { |
384 | if (i == 0) { |
385 | OS << "OPC_Scope, "; |
386 | ++CurrentIdx; |
387 | } else { |
388 | if (!OmitComments) { |
389 | OS << "/*" << format_decimal(CurrentIdx, IndexWidth) << "*/"; |
390 | OS.indent(Indent) << "/*Scope*/ "; |
391 | } else |
392 | OS.indent(Indent); |
393 | } |
394 | |
395 | unsigned ChildSize = SM->getChild(i)->getSize(); |
396 | unsigned VBRSize = EmitVBRValue(ChildSize, OS); |
397 | if (!OmitComments) { |
398 | OS << "/*->" << CurrentIdx + VBRSize + ChildSize << "*/"; |
399 | if (i == 0) |
400 | OS << " // " << SM->getNumChildren() << " children in Scope"; |
401 | } |
402 | OS << '\n'; |
403 | |
404 | ChildSize = EmitMatcherList(SM->getChild(i), Indent+1, |
405 | CurrentIdx + VBRSize, OS); |
406 | assert(ChildSize == SM->getChild(i)->getSize() &&(static_cast <bool> (ChildSize == SM->getChild(i)-> getSize() && "Emitted child size does not match calculated size" ) ? void (0) : __assert_fail ("ChildSize == SM->getChild(i)->getSize() && \"Emitted child size does not match calculated size\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 407, __extension__ __PRETTY_FUNCTION__)) |
407 | "Emitted child size does not match calculated size")(static_cast <bool> (ChildSize == SM->getChild(i)-> getSize() && "Emitted child size does not match calculated size" ) ? void (0) : __assert_fail ("ChildSize == SM->getChild(i)->getSize() && \"Emitted child size does not match calculated size\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 407, __extension__ __PRETTY_FUNCTION__)); |
408 | CurrentIdx += VBRSize + ChildSize; |
409 | } |
410 | |
411 | // Emit a zero as a sentinel indicating end of 'Scope'. |
412 | if (!OmitComments) |
413 | OS << "/*" << format_decimal(CurrentIdx, IndexWidth) << "*/"; |
414 | OS.indent(Indent) << "0, "; |
415 | if (!OmitComments) |
416 | OS << "/*End of Scope*/"; |
417 | OS << '\n'; |
418 | return CurrentIdx - StartIdx + 1; |
419 | } |
420 | |
421 | case Matcher::RecordNode: |
422 | OS << "OPC_RecordNode,"; |
423 | if (!OmitComments) |
424 | OS << " // #" |
425 | << cast<RecordMatcher>(N)->getResultNo() << " = " |
426 | << cast<RecordMatcher>(N)->getWhatFor(); |
427 | OS << '\n'; |
428 | return 1; |
429 | |
430 | case Matcher::RecordChild: |
431 | OS << "OPC_RecordChild" << cast<RecordChildMatcher>(N)->getChildNo() |
432 | << ','; |
433 | if (!OmitComments) |
434 | OS << " // #" |
435 | << cast<RecordChildMatcher>(N)->getResultNo() << " = " |
436 | << cast<RecordChildMatcher>(N)->getWhatFor(); |
437 | OS << '\n'; |
438 | return 1; |
439 | |
440 | case Matcher::RecordMemRef: |
441 | OS << "OPC_RecordMemRef,\n"; |
442 | return 1; |
443 | |
444 | case Matcher::CaptureGlueInput: |
445 | OS << "OPC_CaptureGlueInput,\n"; |
446 | return 1; |
447 | |
448 | case Matcher::MoveChild: { |
449 | const auto *MCM = cast<MoveChildMatcher>(N); |
450 | |
451 | OS << "OPC_MoveChild"; |
452 | // Handle the specialized forms. |
453 | if (MCM->getChildNo() >= 8) |
454 | OS << ", "; |
455 | OS << MCM->getChildNo() << ",\n"; |
456 | return (MCM->getChildNo() >= 8) ? 2 : 1; |
457 | } |
458 | |
459 | case Matcher::MoveParent: |
460 | OS << "OPC_MoveParent,\n"; |
461 | return 1; |
462 | |
463 | case Matcher::CheckSame: |
464 | OS << "OPC_CheckSame, " |
465 | << cast<CheckSameMatcher>(N)->getMatchNumber() << ",\n"; |
466 | return 2; |
467 | |
468 | case Matcher::CheckChildSame: |
469 | OS << "OPC_CheckChild" |
470 | << cast<CheckChildSameMatcher>(N)->getChildNo() << "Same, " |
471 | << cast<CheckChildSameMatcher>(N)->getMatchNumber() << ",\n"; |
472 | return 2; |
473 | |
474 | case Matcher::CheckPatternPredicate: { |
475 | StringRef Pred =cast<CheckPatternPredicateMatcher>(N)->getPredicate(); |
476 | OS << "OPC_CheckPatternPredicate, " << getPatternPredicate(Pred) << ','; |
477 | if (!OmitComments) |
478 | OS << " // " << Pred; |
479 | OS << '\n'; |
480 | return 2; |
481 | } |
482 | case Matcher::CheckPredicate: { |
483 | TreePredicateFn Pred = cast<CheckPredicateMatcher>(N)->getPredicate(); |
484 | unsigned OperandBytes = 0; |
485 | |
486 | if (Pred.usesOperands()) { |
487 | unsigned NumOps = cast<CheckPredicateMatcher>(N)->getNumOperands(); |
488 | OS << "OPC_CheckPredicateWithOperands, " << NumOps << "/*#Ops*/, "; |
489 | for (unsigned i = 0; i < NumOps; ++i) |
490 | OS << cast<CheckPredicateMatcher>(N)->getOperandNo(i) << ", "; |
491 | OperandBytes = 1 + NumOps; |
492 | } else { |
493 | OS << "OPC_CheckPredicate, "; |
494 | } |
495 | |
496 | OS << getNodePredicate(Pred) << ','; |
497 | if (!OmitComments) |
498 | OS << " // " << Pred.getFnName(); |
499 | OS << '\n'; |
500 | return 2 + OperandBytes; |
501 | } |
502 | |
503 | case Matcher::CheckOpcode: |
504 | OS << "OPC_CheckOpcode, TARGET_VAL(" |
505 | << cast<CheckOpcodeMatcher>(N)->getOpcode().getEnumName() << "),\n"; |
506 | return 3; |
507 | |
508 | case Matcher::SwitchOpcode: |
509 | case Matcher::SwitchType: { |
510 | unsigned StartIdx = CurrentIdx; |
511 | |
512 | unsigned NumCases; |
513 | if (const SwitchOpcodeMatcher *SOM = dyn_cast<SwitchOpcodeMatcher>(N)) { |
514 | OS << "OPC_SwitchOpcode "; |
515 | NumCases = SOM->getNumCases(); |
516 | } else { |
517 | OS << "OPC_SwitchType "; |
518 | NumCases = cast<SwitchTypeMatcher>(N)->getNumCases(); |
519 | } |
520 | |
521 | if (!OmitComments) |
522 | OS << "/*" << NumCases << " cases */"; |
523 | OS << ", "; |
524 | ++CurrentIdx; |
525 | |
526 | // For each case we emit the size, then the opcode, then the matcher. |
527 | for (unsigned i = 0, e = NumCases; i != e; ++i) { |
528 | const Matcher *Child; |
529 | unsigned IdxSize; |
530 | if (const SwitchOpcodeMatcher *SOM = dyn_cast<SwitchOpcodeMatcher>(N)) { |
531 | Child = SOM->getCaseMatcher(i); |
532 | IdxSize = 2; // size of opcode in table is 2 bytes. |
533 | } else { |
534 | Child = cast<SwitchTypeMatcher>(N)->getCaseMatcher(i); |
535 | IdxSize = 1; // size of type in table is 1 byte. |
536 | } |
537 | |
538 | if (i != 0) { |
539 | if (!OmitComments) |
540 | OS << "/*" << format_decimal(CurrentIdx, IndexWidth) << "*/"; |
541 | OS.indent(Indent); |
542 | if (!OmitComments) |
543 | OS << (isa<SwitchOpcodeMatcher>(N) ? |
544 | "/*SwitchOpcode*/ " : "/*SwitchType*/ "); |
545 | } |
546 | |
547 | unsigned ChildSize = Child->getSize(); |
548 | CurrentIdx += EmitVBRValue(ChildSize, OS) + IdxSize; |
549 | if (const SwitchOpcodeMatcher *SOM = dyn_cast<SwitchOpcodeMatcher>(N)) |
550 | OS << "TARGET_VAL(" << SOM->getCaseOpcode(i).getEnumName() << "),"; |
551 | else |
552 | OS << getEnumName(cast<SwitchTypeMatcher>(N)->getCaseType(i)) << ','; |
553 | if (!OmitComments) |
554 | OS << "// ->" << CurrentIdx + ChildSize; |
555 | OS << '\n'; |
556 | |
557 | ChildSize = EmitMatcherList(Child, Indent+1, CurrentIdx, OS); |
558 | assert(ChildSize == Child->getSize() &&(static_cast <bool> (ChildSize == Child->getSize() && "Emitted child size does not match calculated size") ? void ( 0) : __assert_fail ("ChildSize == Child->getSize() && \"Emitted child size does not match calculated size\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 559, __extension__ __PRETTY_FUNCTION__)) |
559 | "Emitted child size does not match calculated size")(static_cast <bool> (ChildSize == Child->getSize() && "Emitted child size does not match calculated size") ? void ( 0) : __assert_fail ("ChildSize == Child->getSize() && \"Emitted child size does not match calculated size\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 559, __extension__ __PRETTY_FUNCTION__)); |
560 | CurrentIdx += ChildSize; |
561 | } |
562 | |
563 | // Emit the final zero to terminate the switch. |
564 | if (!OmitComments) |
565 | OS << "/*" << format_decimal(CurrentIdx, IndexWidth) << "*/"; |
566 | OS.indent(Indent) << "0,"; |
567 | if (!OmitComments) |
568 | OS << (isa<SwitchOpcodeMatcher>(N) ? |
569 | " // EndSwitchOpcode" : " // EndSwitchType"); |
570 | |
571 | OS << '\n'; |
572 | return CurrentIdx - StartIdx + 1; |
573 | } |
574 | |
575 | case Matcher::CheckType: |
576 | if (cast<CheckTypeMatcher>(N)->getResNo() == 0) { |
577 | OS << "OPC_CheckType, " |
578 | << getEnumName(cast<CheckTypeMatcher>(N)->getType()) << ",\n"; |
579 | return 2; |
580 | } |
581 | OS << "OPC_CheckTypeRes, " << cast<CheckTypeMatcher>(N)->getResNo() |
582 | << ", " << getEnumName(cast<CheckTypeMatcher>(N)->getType()) << ",\n"; |
583 | return 3; |
584 | |
585 | case Matcher::CheckChildType: |
586 | OS << "OPC_CheckChild" |
587 | << cast<CheckChildTypeMatcher>(N)->getChildNo() << "Type, " |
588 | << getEnumName(cast<CheckChildTypeMatcher>(N)->getType()) << ",\n"; |
589 | return 2; |
590 | |
591 | case Matcher::CheckInteger: { |
592 | OS << "OPC_CheckInteger, "; |
593 | unsigned Bytes = |
594 | 1 + EmitSignedVBRValue(cast<CheckIntegerMatcher>(N)->getValue(), OS); |
595 | OS << '\n'; |
596 | return Bytes; |
597 | } |
598 | case Matcher::CheckChildInteger: { |
599 | OS << "OPC_CheckChild" << cast<CheckChildIntegerMatcher>(N)->getChildNo() |
600 | << "Integer, "; |
601 | unsigned Bytes = 1 + EmitSignedVBRValue( |
602 | cast<CheckChildIntegerMatcher>(N)->getValue(), OS); |
603 | OS << '\n'; |
604 | return Bytes; |
605 | } |
606 | case Matcher::CheckCondCode: |
607 | OS << "OPC_CheckCondCode, ISD::" |
608 | << cast<CheckCondCodeMatcher>(N)->getCondCodeName() << ",\n"; |
609 | return 2; |
610 | |
611 | case Matcher::CheckChild2CondCode: |
612 | OS << "OPC_CheckChild2CondCode, ISD::" |
613 | << cast<CheckChild2CondCodeMatcher>(N)->getCondCodeName() << ",\n"; |
614 | return 2; |
615 | |
616 | case Matcher::CheckValueType: |
617 | OS << "OPC_CheckValueType, MVT::" |
618 | << cast<CheckValueTypeMatcher>(N)->getTypeName() << ",\n"; |
619 | return 2; |
620 | |
621 | case Matcher::CheckComplexPat: { |
622 | const CheckComplexPatMatcher *CCPM = cast<CheckComplexPatMatcher>(N); |
623 | const ComplexPattern &Pattern = CCPM->getPattern(); |
624 | OS << "OPC_CheckComplexPat, /*CP*/" << getComplexPat(Pattern) << ", /*#*/" |
625 | << CCPM->getMatchNumber() << ','; |
626 | |
627 | if (!OmitComments) { |
628 | OS << " // " << Pattern.getSelectFunc(); |
629 | OS << ":$" << CCPM->getName(); |
630 | for (unsigned i = 0, e = Pattern.getNumOperands(); i != e; ++i) |
631 | OS << " #" << CCPM->getFirstResult()+i; |
632 | |
633 | if (Pattern.hasProperty(SDNPHasChain)) |
634 | OS << " + chain result"; |
635 | } |
636 | OS << '\n'; |
637 | return 3; |
638 | } |
639 | |
640 | case Matcher::CheckAndImm: { |
641 | OS << "OPC_CheckAndImm, "; |
642 | unsigned Bytes=1+EmitVBRValue(cast<CheckAndImmMatcher>(N)->getValue(), OS); |
643 | OS << '\n'; |
644 | return Bytes; |
645 | } |
646 | |
647 | case Matcher::CheckOrImm: { |
648 | OS << "OPC_CheckOrImm, "; |
649 | unsigned Bytes = 1+EmitVBRValue(cast<CheckOrImmMatcher>(N)->getValue(), OS); |
650 | OS << '\n'; |
651 | return Bytes; |
652 | } |
653 | |
654 | case Matcher::CheckFoldableChainNode: |
655 | OS << "OPC_CheckFoldableChainNode,\n"; |
656 | return 1; |
657 | |
658 | case Matcher::CheckImmAllOnesV: |
659 | OS << "OPC_CheckImmAllOnesV,\n"; |
660 | return 1; |
661 | |
662 | case Matcher::CheckImmAllZerosV: |
663 | OS << "OPC_CheckImmAllZerosV,\n"; |
664 | return 1; |
665 | |
666 | case Matcher::EmitInteger: { |
667 | int64_t Val = cast<EmitIntegerMatcher>(N)->getValue(); |
668 | OS << "OPC_EmitInteger, " |
669 | << getEnumName(cast<EmitIntegerMatcher>(N)->getVT()) << ", "; |
670 | unsigned Bytes = 2 + EmitSignedVBRValue(Val, OS); |
671 | OS << '\n'; |
672 | return Bytes; |
673 | } |
674 | case Matcher::EmitStringInteger: { |
675 | const std::string &Val = cast<EmitStringIntegerMatcher>(N)->getValue(); |
676 | // These should always fit into 7 bits. |
677 | OS << "OPC_EmitStringInteger, " |
678 | << getEnumName(cast<EmitStringIntegerMatcher>(N)->getVT()) << ", " << Val |
679 | << ",\n"; |
680 | return 3; |
681 | } |
682 | |
683 | case Matcher::EmitRegister: { |
684 | const EmitRegisterMatcher *Matcher = cast<EmitRegisterMatcher>(N); |
685 | const CodeGenRegister *Reg = Matcher->getReg(); |
686 | // If the enum value of the register is larger than one byte can handle, |
687 | // use EmitRegister2. |
688 | if (Reg && Reg->EnumValue > 255) { |
689 | OS << "OPC_EmitRegister2, " << getEnumName(Matcher->getVT()) << ", "; |
690 | OS << "TARGET_VAL(" << getQualifiedName(Reg->TheDef) << "),\n"; |
691 | return 4; |
692 | } else { |
693 | OS << "OPC_EmitRegister, " << getEnumName(Matcher->getVT()) << ", "; |
694 | if (Reg) { |
695 | OS << getQualifiedName(Reg->TheDef) << ",\n"; |
696 | } else { |
697 | OS << "0 "; |
698 | if (!OmitComments) |
699 | OS << "/*zero_reg*/"; |
700 | OS << ",\n"; |
701 | } |
702 | return 3; |
703 | } |
704 | } |
705 | |
706 | case Matcher::EmitConvertToTarget: |
707 | OS << "OPC_EmitConvertToTarget, " |
708 | << cast<EmitConvertToTargetMatcher>(N)->getSlot() << ",\n"; |
709 | return 2; |
710 | |
711 | case Matcher::EmitMergeInputChains: { |
712 | const EmitMergeInputChainsMatcher *MN = |
713 | cast<EmitMergeInputChainsMatcher>(N); |
714 | |
715 | // Handle the specialized forms OPC_EmitMergeInputChains1_0, 1_1, and 1_2. |
716 | if (MN->getNumNodes() == 1 && MN->getNode(0) < 3) { |
717 | OS << "OPC_EmitMergeInputChains1_" << MN->getNode(0) << ",\n"; |
718 | return 1; |
719 | } |
720 | |
721 | OS << "OPC_EmitMergeInputChains, " << MN->getNumNodes() << ", "; |
722 | for (unsigned i = 0, e = MN->getNumNodes(); i != e; ++i) |
723 | OS << MN->getNode(i) << ", "; |
724 | OS << '\n'; |
725 | return 2+MN->getNumNodes(); |
726 | } |
727 | case Matcher::EmitCopyToReg: { |
728 | const auto *C2RMatcher = cast<EmitCopyToRegMatcher>(N); |
729 | int Bytes = 3; |
730 | const CodeGenRegister *Reg = C2RMatcher->getDestPhysReg(); |
731 | if (Reg->EnumValue > 255) { |
732 | assert(isUInt<16>(Reg->EnumValue) && "not handled")(static_cast <bool> (isUInt<16>(Reg->EnumValue ) && "not handled") ? void (0) : __assert_fail ("isUInt<16>(Reg->EnumValue) && \"not handled\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 732, __extension__ __PRETTY_FUNCTION__)); |
733 | OS << "OPC_EmitCopyToReg2, " << C2RMatcher->getSrcSlot() << ", " |
734 | << "TARGET_VAL(" << getQualifiedName(Reg->TheDef) << "),\n"; |
735 | ++Bytes; |
736 | } else { |
737 | OS << "OPC_EmitCopyToReg, " << C2RMatcher->getSrcSlot() << ", " |
738 | << getQualifiedName(Reg->TheDef) << ",\n"; |
739 | } |
740 | |
741 | return Bytes; |
742 | } |
743 | case Matcher::EmitNodeXForm: { |
744 | const EmitNodeXFormMatcher *XF = cast<EmitNodeXFormMatcher>(N); |
745 | OS << "OPC_EmitNodeXForm, " << getNodeXFormID(XF->getNodeXForm()) << ", " |
746 | << XF->getSlot() << ','; |
747 | if (!OmitComments) |
748 | OS << " // "<<XF->getNodeXForm()->getName(); |
749 | OS <<'\n'; |
750 | return 3; |
751 | } |
752 | |
753 | case Matcher::EmitNode: |
754 | case Matcher::MorphNodeTo: { |
755 | auto NumCoveredBytes = 0; |
756 | if (InstrumentCoverage) { |
757 | if (const MorphNodeToMatcher *SNT = dyn_cast<MorphNodeToMatcher>(N)) { |
758 | NumCoveredBytes = 3; |
759 | OS << "OPC_Coverage, "; |
760 | std::string src = |
761 | GetPatFromTreePatternNode(SNT->getPattern().getSrcPattern()); |
762 | std::string dst = |
763 | GetPatFromTreePatternNode(SNT->getPattern().getDstPattern()); |
764 | Record *PatRecord = SNT->getPattern().getSrcRecord(); |
765 | std::string include_src = getIncludePath(PatRecord); |
766 | unsigned Offset = |
767 | getPatternIdxFromTable(src + " -> " + dst, std::move(include_src)); |
768 | OS << "TARGET_VAL(" << Offset << "),\n"; |
769 | OS.indent(FullIndexWidth + Indent); |
770 | } |
771 | } |
772 | const EmitNodeMatcherCommon *EN = cast<EmitNodeMatcherCommon>(N); |
773 | OS << (isa<EmitNodeMatcher>(EN) ? "OPC_EmitNode" : "OPC_MorphNodeTo"); |
774 | bool CompressVTs = EN->getNumVTs() < 3; |
775 | if (CompressVTs) |
776 | OS << EN->getNumVTs(); |
777 | |
778 | const CodeGenInstruction &CGI = EN->getInstruction(); |
779 | OS << ", TARGET_VAL(" << CGI.Namespace << "::" << CGI.TheDef->getName() |
780 | << "), 0"; |
781 | |
782 | if (EN->hasChain()) OS << "|OPFL_Chain"; |
783 | if (EN->hasInGlue()) OS << "|OPFL_GlueInput"; |
784 | if (EN->hasOutGlue()) OS << "|OPFL_GlueOutput"; |
785 | if (EN->hasMemRefs()) OS << "|OPFL_MemRefs"; |
786 | if (EN->getNumFixedArityOperands() != -1) |
787 | OS << "|OPFL_Variadic" << EN->getNumFixedArityOperands(); |
788 | OS << ",\n"; |
789 | |
790 | OS.indent(FullIndexWidth + Indent+4); |
791 | if (!CompressVTs) { |
792 | OS << EN->getNumVTs(); |
793 | if (!OmitComments) |
794 | OS << "/*#VTs*/"; |
795 | OS << ", "; |
796 | } |
797 | for (unsigned i = 0, e = EN->getNumVTs(); i != e; ++i) |
798 | OS << getEnumName(EN->getVT(i)) << ", "; |
799 | |
800 | OS << EN->getNumOperands(); |
801 | if (!OmitComments) |
802 | OS << "/*#Ops*/"; |
803 | OS << ", "; |
804 | unsigned NumOperandBytes = 0; |
805 | for (unsigned i = 0, e = EN->getNumOperands(); i != e; ++i) |
806 | NumOperandBytes += EmitVBRValue(EN->getOperand(i), OS); |
807 | |
808 | if (!OmitComments) { |
809 | // Print the result #'s for EmitNode. |
810 | if (const EmitNodeMatcher *E = dyn_cast<EmitNodeMatcher>(EN)) { |
811 | if (unsigned NumResults = EN->getNumVTs()) { |
812 | OS << " // Results ="; |
813 | unsigned First = E->getFirstResultSlot(); |
814 | for (unsigned i = 0; i != NumResults; ++i) |
815 | OS << " #" << First+i; |
816 | } |
817 | } |
818 | OS << '\n'; |
819 | |
820 | if (const MorphNodeToMatcher *SNT = dyn_cast<MorphNodeToMatcher>(N)) { |
821 | OS.indent(FullIndexWidth + Indent) << "// Src: " |
822 | << *SNT->getPattern().getSrcPattern() << " - Complexity = " |
823 | << SNT->getPattern().getPatternComplexity(CGP) << '\n'; |
824 | OS.indent(FullIndexWidth + Indent) << "// Dst: " |
825 | << *SNT->getPattern().getDstPattern() << '\n'; |
826 | } |
827 | } else |
828 | OS << '\n'; |
829 | |
830 | return 5 + !CompressVTs + EN->getNumVTs() + NumOperandBytes + |
831 | NumCoveredBytes; |
832 | } |
833 | case Matcher::CompleteMatch: { |
834 | const CompleteMatchMatcher *CM = cast<CompleteMatchMatcher>(N); |
835 | auto NumCoveredBytes = 0; |
836 | if (InstrumentCoverage) { |
837 | NumCoveredBytes = 3; |
838 | OS << "OPC_Coverage, "; |
839 | std::string src = |
840 | GetPatFromTreePatternNode(CM->getPattern().getSrcPattern()); |
841 | std::string dst = |
842 | GetPatFromTreePatternNode(CM->getPattern().getDstPattern()); |
843 | Record *PatRecord = CM->getPattern().getSrcRecord(); |
844 | std::string include_src = getIncludePath(PatRecord); |
845 | unsigned Offset = |
846 | getPatternIdxFromTable(src + " -> " + dst, std::move(include_src)); |
847 | OS << "TARGET_VAL(" << Offset << "),\n"; |
848 | OS.indent(FullIndexWidth + Indent); |
849 | } |
850 | OS << "OPC_CompleteMatch, " << CM->getNumResults() << ", "; |
851 | unsigned NumResultBytes = 0; |
852 | for (unsigned i = 0, e = CM->getNumResults(); i != e; ++i) |
853 | NumResultBytes += EmitVBRValue(CM->getResult(i), OS); |
854 | OS << '\n'; |
855 | if (!OmitComments) { |
856 | OS.indent(FullIndexWidth + Indent) << " // Src: " |
857 | << *CM->getPattern().getSrcPattern() << " - Complexity = " |
858 | << CM->getPattern().getPatternComplexity(CGP) << '\n'; |
859 | OS.indent(FullIndexWidth + Indent) << " // Dst: " |
860 | << *CM->getPattern().getDstPattern(); |
861 | } |
862 | OS << '\n'; |
863 | return 2 + NumResultBytes + NumCoveredBytes; |
864 | } |
865 | } |
866 | llvm_unreachable("Unreachable")::llvm::llvm_unreachable_internal("Unreachable", "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp" , 866); |
867 | } |
868 | |
869 | /// This function traverses the matcher tree and emits all the nodes. |
870 | /// The nodes have already been sized. |
871 | unsigned MatcherTableEmitter:: |
872 | EmitMatcherList(const Matcher *N, const unsigned Indent, unsigned CurrentIdx, |
873 | raw_ostream &OS) { |
874 | unsigned Size = 0; |
875 | while (N) { |
876 | if (!OmitComments) |
877 | OS << "/*" << format_decimal(CurrentIdx, IndexWidth) << "*/"; |
878 | unsigned MatcherSize = EmitMatcher(N, Indent, CurrentIdx, OS); |
879 | Size += MatcherSize; |
880 | CurrentIdx += MatcherSize; |
881 | |
882 | // If there are other nodes in this list, iterate to them, otherwise we're |
883 | // done. |
884 | N = N->getNext(); |
885 | } |
886 | return Size; |
887 | } |
888 | |
889 | void MatcherTableEmitter::EmitNodePredicatesFunction( |
890 | const std::vector<TreePredicateFn> &Preds, StringRef Decl, |
891 | raw_ostream &OS) { |
892 | if (Preds.empty()) |
893 | return; |
894 | |
895 | BeginEmitFunction(OS, "bool", Decl, true/*AddOverride*/); |
896 | OS << "{\n"; |
897 | OS << " switch (PredNo) {\n"; |
898 | OS << " default: llvm_unreachable(\"Invalid predicate in table?\");\n"; |
899 | for (unsigned i = 0, e = Preds.size(); i != e; ++i) { |
900 | // Emit the predicate code corresponding to this pattern. |
901 | const TreePredicateFn PredFn = Preds[i]; |
902 | assert(!PredFn.isAlwaysTrue() && "No code in this predicate")(static_cast <bool> (!PredFn.isAlwaysTrue() && "No code in this predicate" ) ? void (0) : __assert_fail ("!PredFn.isAlwaysTrue() && \"No code in this predicate\"" , "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp", 902, __extension__ __PRETTY_FUNCTION__)); |
903 | std::string PredFnCodeStr = PredFn.getCodeToRunOnSDNode(); |
904 | |
905 | OS << " case " << i << ": {\n"; |
906 | for (auto *SimilarPred : NodePredicatesByCodeToRun[PredFnCodeStr]) |
907 | OS << " // " << TreePredicateFn(SimilarPred).getFnName() << '\n'; |
908 | OS << PredFnCodeStr << "\n }\n"; |
909 | } |
910 | OS << " }\n"; |
911 | OS << "}\n"; |
912 | EndEmitFunction(OS); |
913 | } |
914 | |
915 | void MatcherTableEmitter::EmitPredicateFunctions(raw_ostream &OS) { |
916 | // Emit pattern predicates. |
917 | if (!PatternPredicates.empty()) { |
918 | BeginEmitFunction(OS, "bool", |
919 | "CheckPatternPredicate(unsigned PredNo) const", true/*AddOverride*/); |
920 | OS << "{\n"; |
921 | OS << " switch (PredNo) {\n"; |
922 | OS << " default: llvm_unreachable(\"Invalid predicate in table?\");\n"; |
923 | for (unsigned i = 0, e = PatternPredicates.size(); i != e; ++i) |
924 | OS << " case " << i << ": return " << PatternPredicates[i] << ";\n"; |
925 | OS << " }\n"; |
926 | OS << "}\n"; |
927 | EndEmitFunction(OS); |
928 | } |
929 | |
930 | // Emit Node predicates. |
931 | EmitNodePredicatesFunction( |
932 | NodePredicates, "CheckNodePredicate(SDNode *Node, unsigned PredNo) const", |
933 | OS); |
934 | EmitNodePredicatesFunction( |
935 | NodePredicatesWithOperands, |
936 | "CheckNodePredicateWithOperands(SDNode *Node, unsigned PredNo, " |
937 | "const SmallVectorImpl<SDValue> &Operands) const", |
938 | OS); |
939 | |
940 | // Emit CompletePattern matchers. |
941 | // FIXME: This should be const. |
942 | if (!ComplexPatterns.empty()) { |
943 | BeginEmitFunction(OS, "bool", |
944 | "CheckComplexPattern(SDNode *Root, SDNode *Parent,\n" |
945 | " SDValue N, unsigned PatternNo,\n" |
946 | " SmallVectorImpl<std::pair<SDValue, SDNode *>> &Result)", |
947 | true/*AddOverride*/); |
948 | OS << "{\n"; |
949 | OS << " unsigned NextRes = Result.size();\n"; |
950 | OS << " switch (PatternNo) {\n"; |
951 | OS << " default: llvm_unreachable(\"Invalid pattern # in table?\");\n"; |
952 | for (unsigned i = 0, e = ComplexPatterns.size(); i != e; ++i) { |
953 | const ComplexPattern &P = *ComplexPatterns[i]; |
954 | unsigned NumOps = P.getNumOperands(); |
955 | |
956 | if (P.hasProperty(SDNPHasChain)) |
957 | ++NumOps; // Get the chained node too. |
958 | |
959 | OS << " case " << i << ":\n"; |
960 | if (InstrumentCoverage) |
961 | OS << " {\n"; |
962 | OS << " Result.resize(NextRes+" << NumOps << ");\n"; |
963 | if (InstrumentCoverage) |
964 | OS << " bool Succeeded = " << P.getSelectFunc(); |
965 | else |
966 | OS << " return " << P.getSelectFunc(); |
967 | |
968 | OS << "("; |
969 | // If the complex pattern wants the root of the match, pass it in as the |
970 | // first argument. |
971 | if (P.hasProperty(SDNPWantRoot)) |
972 | OS << "Root, "; |
973 | |
974 | // If the complex pattern wants the parent of the operand being matched, |
975 | // pass it in as the next argument. |
976 | if (P.hasProperty(SDNPWantParent)) |
977 | OS << "Parent, "; |
978 | |
979 | OS << "N"; |
980 | for (unsigned i = 0; i != NumOps; ++i) |
981 | OS << ", Result[NextRes+" << i << "].first"; |
982 | OS << ");\n"; |
983 | if (InstrumentCoverage) { |
984 | OS << " if (Succeeded)\n"; |
985 | OS << " dbgs() << \"\\nCOMPLEX_PATTERN: " << P.getSelectFunc() |
986 | << "\\n\" ;\n"; |
987 | OS << " return Succeeded;\n"; |
988 | OS << " }\n"; |
989 | } |
990 | } |
991 | OS << " }\n"; |
992 | OS << "}\n"; |
993 | EndEmitFunction(OS); |
994 | } |
995 | |
996 | |
997 | // Emit SDNodeXForm handlers. |
998 | // FIXME: This should be const. |
999 | if (!NodeXForms.empty()) { |
1000 | BeginEmitFunction(OS, "SDValue", |
1001 | "RunSDNodeXForm(SDValue V, unsigned XFormNo)", true/*AddOverride*/); |
1002 | OS << "{\n"; |
1003 | OS << " switch (XFormNo) {\n"; |
1004 | OS << " default: llvm_unreachable(\"Invalid xform # in table?\");\n"; |
1005 | |
1006 | // FIXME: The node xform could take SDValue's instead of SDNode*'s. |
1007 | for (unsigned i = 0, e = NodeXForms.size(); i != e; ++i) { |
1008 | const CodeGenDAGPatterns::NodeXForm &Entry = |
1009 | CGP.getSDNodeTransform(NodeXForms[i]); |
1010 | |
1011 | Record *SDNode = Entry.first; |
1012 | const std::string &Code = Entry.second; |
1013 | |
1014 | OS << " case " << i << ": { "; |
1015 | if (!OmitComments) |
1016 | OS << "// " << NodeXForms[i]->getName(); |
1017 | OS << '\n'; |
1018 | |
1019 | std::string ClassName = |
1020 | std::string(CGP.getSDNodeInfo(SDNode).getSDClassName()); |
1021 | if (ClassName == "SDNode") |
1022 | OS << " SDNode *N = V.getNode();\n"; |
1023 | else |
1024 | OS << " " << ClassName << " *N = cast<" << ClassName |
1025 | << ">(V.getNode());\n"; |
1026 | OS << Code << "\n }\n"; |
1027 | } |
1028 | OS << " }\n"; |
1029 | OS << "}\n"; |
1030 | EndEmitFunction(OS); |
1031 | } |
1032 | } |
1033 | |
1034 | static StringRef getOpcodeString(Matcher::KindTy Kind) { |
1035 | switch (Kind) { |
1036 | case Matcher::Scope: return "OPC_Scope"; break; |
1037 | case Matcher::RecordNode: return "OPC_RecordNode"; break; |
1038 | case Matcher::RecordChild: return "OPC_RecordChild"; break; |
1039 | case Matcher::RecordMemRef: return "OPC_RecordMemRef"; break; |
1040 | case Matcher::CaptureGlueInput: return "OPC_CaptureGlueInput"; break; |
1041 | case Matcher::MoveChild: return "OPC_MoveChild"; break; |
1042 | case Matcher::MoveParent: return "OPC_MoveParent"; break; |
1043 | case Matcher::CheckSame: return "OPC_CheckSame"; break; |
1044 | case Matcher::CheckChildSame: return "OPC_CheckChildSame"; break; |
1045 | case Matcher::CheckPatternPredicate: |
1046 | return "OPC_CheckPatternPredicate"; break; |
1047 | case Matcher::CheckPredicate: return "OPC_CheckPredicate"; break; |
1048 | case Matcher::CheckOpcode: return "OPC_CheckOpcode"; break; |
1049 | case Matcher::SwitchOpcode: return "OPC_SwitchOpcode"; break; |
1050 | case Matcher::CheckType: return "OPC_CheckType"; break; |
1051 | case Matcher::SwitchType: return "OPC_SwitchType"; break; |
1052 | case Matcher::CheckChildType: return "OPC_CheckChildType"; break; |
1053 | case Matcher::CheckInteger: return "OPC_CheckInteger"; break; |
1054 | case Matcher::CheckChildInteger: return "OPC_CheckChildInteger"; break; |
1055 | case Matcher::CheckCondCode: return "OPC_CheckCondCode"; break; |
1056 | case Matcher::CheckChild2CondCode: return "OPC_CheckChild2CondCode"; break; |
1057 | case Matcher::CheckValueType: return "OPC_CheckValueType"; break; |
1058 | case Matcher::CheckComplexPat: return "OPC_CheckComplexPat"; break; |
1059 | case Matcher::CheckAndImm: return "OPC_CheckAndImm"; break; |
1060 | case Matcher::CheckOrImm: return "OPC_CheckOrImm"; break; |
1061 | case Matcher::CheckFoldableChainNode: |
1062 | return "OPC_CheckFoldableChainNode"; break; |
1063 | case Matcher::CheckImmAllOnesV: return "OPC_CheckImmAllOnesV"; break; |
1064 | case Matcher::CheckImmAllZerosV: return "OPC_CheckImmAllZerosV"; break; |
1065 | case Matcher::EmitInteger: return "OPC_EmitInteger"; break; |
1066 | case Matcher::EmitStringInteger: return "OPC_EmitStringInteger"; break; |
1067 | case Matcher::EmitRegister: return "OPC_EmitRegister"; break; |
1068 | case Matcher::EmitConvertToTarget: return "OPC_EmitConvertToTarget"; break; |
1069 | case Matcher::EmitMergeInputChains: return "OPC_EmitMergeInputChains"; break; |
1070 | case Matcher::EmitCopyToReg: return "OPC_EmitCopyToReg"; break; |
1071 | case Matcher::EmitNode: return "OPC_EmitNode"; break; |
1072 | case Matcher::MorphNodeTo: return "OPC_MorphNodeTo"; break; |
1073 | case Matcher::EmitNodeXForm: return "OPC_EmitNodeXForm"; break; |
1074 | case Matcher::CompleteMatch: return "OPC_CompleteMatch"; break; |
1075 | } |
1076 | |
1077 | llvm_unreachable("Unhandled opcode?")::llvm::llvm_unreachable_internal("Unhandled opcode?", "llvm/utils/TableGen/DAGISelMatcherEmitter.cpp" , 1077); |
1078 | } |
1079 | |
1080 | void MatcherTableEmitter::EmitHistogram(const Matcher *M, |
1081 | raw_ostream &OS) { |
1082 | if (OmitComments) |
1083 | return; |
1084 | |
1085 | OS << " // Opcode Histogram:\n"; |
1086 | for (unsigned i = 0, e = OpcodeCounts.size(); i != e; ++i) { |
1087 | OS << " // #" |
1088 | << left_justify(getOpcodeString((Matcher::KindTy)i), HistOpcWidth) |
1089 | << " = " << OpcodeCounts[i] << '\n'; |
1090 | } |
1091 | OS << '\n'; |
1092 | } |
1093 | |
1094 | |
1095 | void llvm::EmitMatcherTable(Matcher *TheMatcher, |
1096 | const CodeGenDAGPatterns &CGP, |
1097 | raw_ostream &OS) { |
1098 | OS << "#if defined(GET_DAGISEL_DECL) && defined(GET_DAGISEL_BODY)\n"; |
1099 | OS << "#error GET_DAGISEL_DECL and GET_DAGISEL_BODY cannot be both defined, "; |
1100 | OS << "undef both for inline definitions\n"; |
1101 | OS << "#endif\n\n"; |
1102 | |
1103 | // Emit a check for omitted class name. |
1104 | OS << "#ifdef GET_DAGISEL_BODY\n"; |
1105 | OS << "#define LOCAL_DAGISEL_STRINGIZE(X) LOCAL_DAGISEL_STRINGIZE_(X)\n"; |
1106 | OS << "#define LOCAL_DAGISEL_STRINGIZE_(X) #X\n"; |
1107 | OS << "static_assert(sizeof(LOCAL_DAGISEL_STRINGIZE(GET_DAGISEL_BODY)) > 1," |
1108 | "\n"; |
1109 | OS << " \"GET_DAGISEL_BODY is empty: it should be defined with the class " |
1110 | "name\");\n"; |
1111 | OS << "#undef LOCAL_DAGISEL_STRINGIZE_\n"; |
1112 | OS << "#undef LOCAL_DAGISEL_STRINGIZE\n"; |
1113 | OS << "#endif\n\n"; |
1114 | |
1115 | OS << "#if !defined(GET_DAGISEL_DECL) && !defined(GET_DAGISEL_BODY)\n"; |
1116 | OS << "#define DAGISEL_INLINE 1\n"; |
1117 | OS << "#else\n"; |
1118 | OS << "#define DAGISEL_INLINE 0\n"; |
1119 | OS << "#endif\n\n"; |
1120 | |
1121 | OS << "#if !DAGISEL_INLINE\n"; |
1122 | OS << "#define DAGISEL_CLASS_COLONCOLON GET_DAGISEL_BODY ::\n"; |
1123 | OS << "#else\n"; |
1124 | OS << "#define DAGISEL_CLASS_COLONCOLON\n"; |
1125 | OS << "#endif\n\n"; |
1126 | |
1127 | BeginEmitFunction(OS, "void", "SelectCode(SDNode *N)", false/*AddOverride*/); |
1128 | MatcherTableEmitter MatcherEmitter(CGP); |
1129 | |
1130 | // First we size all the children of the three kinds of matchers that have |
1131 | // them. This is done by sharing the code in EmitMatcher(). but we don't |
1132 | // want to emit anything, so we turn off comments and use a null stream. |
1133 | bool SaveOmitComments = OmitComments; |
1134 | OmitComments = true; |
1135 | raw_null_ostream NullOS; |
1136 | unsigned TotalSize = MatcherEmitter.SizeMatcherList(TheMatcher, NullOS); |
Value stored to 'TotalSize' during its initialization is never read | |
1137 | OmitComments = SaveOmitComments; |
1138 | |
1139 | // Now that the matchers are sized, we can emit the code for them to the |
1140 | // final stream. |
1141 | OS << "{\n"; |
1142 | OS << " // Some target values are emitted as 2 bytes, TARGET_VAL handles\n"; |
1143 | OS << " // this.\n"; |
1144 | OS << " #define TARGET_VAL(X) X & 255, unsigned(X) >> 8\n"; |
1145 | OS << " static const unsigned char MatcherTable[] = {\n"; |
1146 | TotalSize = MatcherEmitter.EmitMatcherList(TheMatcher, 1, 0, OS); |
1147 | OS << " 0\n }; // Total Array size is " << (TotalSize+1) << " bytes\n\n"; |
1148 | |
1149 | MatcherEmitter.EmitHistogram(TheMatcher, OS); |
1150 | |
1151 | OS << " #undef TARGET_VAL\n"; |
1152 | OS << " SelectCodeCommon(N, MatcherTable,sizeof(MatcherTable));\n"; |
1153 | OS << "}\n"; |
1154 | EndEmitFunction(OS); |
1155 | |
1156 | // Next up, emit the function for node and pattern predicates: |
1157 | MatcherEmitter.EmitPredicateFunctions(OS); |
1158 | |
1159 | if (InstrumentCoverage) |
1160 | MatcherEmitter.EmitPatternMatchTable(OS); |
1161 | |
1162 | // Clean up the preprocessor macros. |
1163 | OS << "\n"; |
1164 | OS << "#ifdef DAGISEL_INLINE\n"; |
1165 | OS << "#undef DAGISEL_INLINE\n"; |
1166 | OS << "#endif\n"; |
1167 | OS << "#ifdef DAGISEL_CLASS_COLONCOLON\n"; |
1168 | OS << "#undef DAGISEL_CLASS_COLONCOLON\n"; |
1169 | OS << "#endif\n"; |
1170 | OS << "#ifdef GET_DAGISEL_DECL\n"; |
1171 | OS << "#undef GET_DAGISEL_DECL\n"; |
1172 | OS << "#endif\n"; |
1173 | OS << "#ifdef GET_DAGISEL_BODY\n"; |
1174 | OS << "#undef GET_DAGISEL_BODY\n"; |
1175 | OS << "#endif\n"; |
1176 | } |