llvm.org GIT mirror llvm / 5437906
Rework our internal representation of node predicates to expose more structure and fix some fixmes. We now have a TreePredicateFn class that handles all of the decoding of these things. This is an internal cleanup that has no impact on the code generated by tblgen. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@129670 91177308-0d34-0410-b5e6-96231b3b80d8 Chris Lattner 9 years ago
7 changed file(s) with 158 addition(s) and 67 deletion(s). Raw diff Collapse all Expand all
489489
490490 def NOOP_SDNodeXForm : SDNodeXForm;
491491
492 //===----------------------------------------------------------------------===//
493 // PatPred Subclasses.
494 //
495 // These allow specifying different sorts of predicates that control whether a
496 // node is matched.
497 //
498 class PatPred;
499
500 class CodePatPred : PatPred {
501 code PredicateCode = predicate;
502 }
503
492504
493505 //===----------------------------------------------------------------------===//
494506 // Selection DAG Pattern Fragments.
506518 SDNodeXForm xform = NOOP_SDNodeXForm> : SDPatternOperator {
507519 dag Operands = ops;
508520 dag Fragment = frag;
509 code Predicate = pred;
521 code PredicateCode = pred;
510522 SDNodeXForm OperandTransform = xform;
511523 }
512524
458458 include "X86InstrFormats.td"
459459
460460 //===----------------------------------------------------------------------===//
461 // Pattern fragments...
461 // Pattern fragments.
462462 //
463463
464464 // X86 specific condition code. These correspond to CondCode in
579579 /// Const iterator shorthand for DepVarMap
580580 typedef DepVarMap::const_iterator DepVarMap_citer;
581581
582 namespace {
583 void FindDepVarsOf(TreePatternNode *N, DepVarMap &DepMap) {
582 static void FindDepVarsOf(TreePatternNode *N, DepVarMap &DepMap) {
584583 if (N->isLeaf()) {
585 if (dynamic_cast(N->getLeafValue()) != NULL) {
584 if (dynamic_cast(N->getLeafValue()) != NULL)
586585 DepMap[N->getName()]++;
587 }
588586 } else {
589587 for (size_t i = 0, e = N->getNumChildren(); i != e; ++i)
590588 FindDepVarsOf(N->getChild(i), DepMap);
591589 }
592590 }
593
594 //! Find dependent variables within child patterns
595 /*!
596 */
597 void FindDepVars(TreePatternNode *N, MultipleUseVarSet &DepVars) {
591
592 /// Find dependent variables within child patterns
593 static void FindDepVars(TreePatternNode *N, MultipleUseVarSet &DepVars) {
598594 DepVarMap depcounts;
599595 FindDepVarsOf(N, depcounts);
600596 for (DepVarMap_citer i = depcounts.begin(); i != depcounts.end(); ++i) {
601 if (i->second > 1) { // std::pair
597 if (i->second > 1) // std::pair
602598 DepVars.insert(i->first);
603 }
604 }
605 }
606
607 //! Dump the dependent variable set:
599 }
600 }
601
608602 #ifndef NDEBUG
609 void DumpDepVars(MultipleUseVarSet &DepVars) {
603 /// Dump the dependent variable set:
604 static void DumpDepVars(MultipleUseVarSet &DepVars) {
610605 if (DepVars.empty()) {
611606 DEBUG(errs() << "");
612607 } else {
620615 }
621616 #endif
622617
618
619 //===----------------------------------------------------------------------===//
620 // TreePredicateFn Implementation
621 //===----------------------------------------------------------------------===//
622
623 std::string TreePredicateFn::getPredCode() const {
624 return PatFragRec->getRecord()->getValueAsCode("PredicateCode");
625 }
626
627
628 /// isAlwaysTrue - Return true if this is a noop predicate.
629 bool TreePredicateFn::isAlwaysTrue() const {
630 return getPredCode().empty();
631 }
632
633 /// Return the name to use in the generated code to reference this, this is
634 /// "Predicate_foo" if from a pattern fragment "foo".
635 std::string TreePredicateFn::getFnName() const {
636 return "Predicate_" + PatFragRec->getRecord()->getName();
637 }
638
639 /// getCodeToRunOnSDNode - Return the code for the function body that
640 /// evaluates this predicate. The argument is expected to be in "Node",
641 /// not N. This handles casting and conversion to a concrete node type as
642 /// appropriate.
643 std::string TreePredicateFn::getCodeToRunOnSDNode() const {
644 std::string ClassName;
645 if (PatFragRec->getOnlyTree()->isLeaf())
646 ClassName = "SDNode";
647 else {
648 Record *Op = PatFragRec->getOnlyTree()->getOperator();
649 ClassName = PatFragRec->getDAGPatterns().getSDNodeInfo(Op).getSDClassName();
650 }
651 std::string Result;
652 if (ClassName == "SDNode")
653 Result = " SDNode *N = Node;\n";
654 else
655 Result = " " + ClassName + "*N = cast<" + ClassName + ">(Node);\n";
656
657 return Result + getPredCode();
623658 }
624659
625660 //===----------------------------------------------------------------------===//
10141049 }
10151050
10161051 for (unsigned i = 0, e = PredicateFns.size(); i != e; ++i)
1017 OS << "< << ">>";
1052 OS << "<.getFnName() << ">>";
10181053 if (TransformFn)
10191054 OS << "<getName() << ">>";
10201055 if (!getName().empty())
11491184
11501185 TreePatternNode *FragTree = Frag->getOnlyTree()->clone();
11511186
1152 std::string Code = Op->getValueAsCode("Predicate");
1153 if (!Code.empty())
1154 FragTree->addPredicateFn("Predicate_"+Op->getName());
1187 TreePredicateFn PredFn(Frag);
1188 if (!PredFn.isAlwaysTrue())
1189 FragTree->addPredicateFn(PredFn);
11551190
11561191 // Resolve formal arguments to their actual value.
11571192 if (Frag->getNumArgs()) {
20622097
20632098 // If there is a code init for this fragment, keep track of the fact that
20642099 // this fragment uses it.
2065 std::string Code = Fragments[i]->getValueAsCode("Predicate");
2066 if (!Code.empty())
2067 P->getOnlyTree()->addPredicateFn("Predicate_"+Fragments[i]->getName());
2100 TreePredicateFn PredFn(P);
2101 if (!PredFn.isAlwaysTrue())
2102 P->getOnlyTree()->addPredicateFn(PredFn);
20682103
20692104 // If there is a node transformation corresponding to this, keep track of
20702105 // it.
238238 return MadeChange;
239239 }
240240 };
241
242 /// TreePredicateFn - This is an abstraction that represents the predicates on
243 /// a PatFrag node. This is a simple one-word wrapper around a pointer to
244 /// provide nice accessors.
245 class TreePredicateFn {
246 /// PatFragRec - This is the TreePattern for the PatFrag that we
247 /// originally came from.
248 TreePattern *PatFragRec;
249 public:
250 /// TreePredicateFn constructor. Here 'N' is a subclass of PatFrag.
251 TreePredicateFn(TreePattern *N) : PatFragRec(N) {}
252
253
254 TreePattern *getOrigPatFragRecord() const { return PatFragRec; }
255
256 /// isAlwaysTrue - Return true if this is a noop predicate.
257 bool isAlwaysTrue() const;
258
259
260 bool operator==(const TreePredicateFn &RHS) const {
261 return PatFragRec == RHS.PatFragRec;
262 }
263
264 bool operator!=(const TreePredicateFn &RHS) const { return !(*this == RHS); }
265
266 /// Return the name to use in the generated code to reference this, this is
267 /// "Predicate_foo" if from a pattern fragment "foo".
268 std::string getFnName() const;
269
270 /// getCodeToRunOnSDNode - Return the code for the function body that
271 /// evaluates this predicate. The argument is expected to be in "Node",
272 /// not N. This handles casting and conversion to a concrete node type as
273 /// appropriate.
274 std::string getCodeToRunOnSDNode() const;
275
276 private:
277 std::string getPredCode() const;
278 };
279
241280
242281 /// FIXME: TreePatternNode's can be shared in some cases (due to dag-shaped
243282 /// patterns), and as such should be ref counted. We currently just leak all
262301
263302 /// PredicateFns - The predicate functions to execute on this node to check
264303 /// for a match. If this list is empty, no predicate is involved.
265 std::vector<std::string> PredicateFns;
304 std::vector<TreePredicateFn> PredicateFns;
266305
267306 /// TransformFn - The transformation function to execute on this node before
268307 /// it can be substituted into the resulting instruction on a pattern match.
322361 return false;
323362 }
324363
325 const std::vector &getPredicateFns() const {return PredicateFns;}
364 bool hasAnyPredicate() const { return !PredicateFns.empty(); }
365
366 const std::vector &getPredicateFns() const {
367 return PredicateFns;
368 }
326369 void clearPredicateFns() { PredicateFns.clear(); }
327 void setPredicateFns(const std::vector<std::string> &Fns) {
370 void setPredicateFns(const std::vector<TreePredicateFn> &Fns) {
328371 assert(PredicateFns.empty() && "Overwriting non-empty predicate list!");
329372 PredicateFns = Fns;
330373 }
331 void addPredicateFn(const std::string &Fn) {
332 assert(!Fn.empty() && "Empty predicate string!");
374 void addPredicateFn(const TreePredicateFn &Fn) {
375 assert(!Fn.isAlwaysTrue() && "Empty predicate string!");
333376 if (std::find(PredicateFns.begin(), PredicateFns.end(), Fn) ==
334377 PredicateFns.end())
335378 PredicateFns.push_back(Fn);
8282 }
8383
8484
85 CheckPredicateMatcher::CheckPredicateMatcher(const TreePredicateFn &pred)
86 : Matcher(CheckPredicate), Pred(pred.getOrigPatFragRecord()) {}
87
88 TreePredicateFn CheckPredicateMatcher::getPredicate() const {
89 return TreePredicateFn(Pred);
90 }
91
92
93
8594 // printImpl methods.
8695
8796 void ScopeMatcher::printImpl(raw_ostream &OS, unsigned indent) const {
128137 }
129138
130139 void CheckPredicateMatcher::printImpl(raw_ostream &OS, unsigned indent) const {
131 OS.indent(indent) << "CheckPredicate " << PredName << '\n';
140 OS.indent(indent) << "CheckPredicate " << getPredicate().getFnName() << '\n';
132141 }
133142
134143 void CheckOpcodeMatcher::printImpl(raw_ostream &OS, unsigned indent) const {
262271 }
263272
264273 unsigned CheckPredicateMatcher::getHashImpl() const {
265 return HashString(PredName);
274 return HashString(getPredicate().getFnName());
266275 }
267276
268277 unsigned CheckOpcodeMatcher::getHashImpl() const {
299308 return cast(M)->Opcode.getEnumName() ==
300309 Opcode.getEnumName();
301310 }
302
303311
304312 bool EmitNodeMatcherCommon::isEqualImpl(const Matcher *m) const {
305313 const EmitNodeMatcherCommon *M = cast(m);
2424 class ComplexPattern;
2525 class Record;
2626 class SDNodeInfo;
27 class TreePredicateFn;
28 class TreePattern;
2729
2830 Matcher *ConvertPatternToMatcher(const PatternToMatch &Pattern,unsigned Variant,
2931 const CodeGenDAGPatterns &CGP);
418420 /// CheckPredicateMatcher - This checks the target-specific predicate to
419421 /// see if the node is acceptable.
420422 class CheckPredicateMatcher : public Matcher {
421 StringRef PredName;
422 public:
423 CheckPredicateMatcher(StringRef predname)
424 : Matcher(CheckPredicate), PredName(predname) {}
425
426 StringRef getPredicateName() const { return PredName; }
423 TreePattern *Pred;
424 public:
425 CheckPredicateMatcher(const TreePredicateFn &pred);
426
427 TreePredicateFn getPredicate() const;
427428
428429 static inline bool classof(const Matcher *N) {
429430 return N->getKind() == CheckPredicate;
435436 private:
436437 virtual void printImpl(raw_ostream &OS, unsigned indent) const;
437438 virtual bool isEqualImpl(const Matcher *M) const {
438 return cast(M)->PredName == PredName;
439 return cast(M)->Pred == Pred;
439440 }
440441 virtual unsigned getHashImpl() const;
441442 };
3232 namespace {
3333 class MatcherTableEmitter {
3434 const CodeGenDAGPatterns &CGP;
35 StringMap NodePredicateMap, PatternPredicateMap;
36 std::vector NodePredicates, PatternPredicates;
35
36 DenseMap NodePredicateMap;
37 std::vector NodePredicates;
38
39 StringMap PatternPredicateMap;
40 std::vector PatternPredicates;
3741
3842 DenseMap ComplexPatternMap;
3943 std::vector ComplexPatterns;
5660 unsigned EmitMatcher(const Matcher *N, unsigned Indent, unsigned CurrentIdx,
5761 formatted_raw_ostream &OS);
5862
59 unsigned getNodePredicate(StringRef PredName) {
60 unsigned &Entry = NodePredicateMap[PredName];
63 unsigned getNodePredicate(TreePredicateFn Pred) {
64 unsigned &Entry = NodePredicateMap[Pred.getOrigPatFragRecord()];
6165 if (Entry == 0) {
62 NodePredicates.push_back(PredName.str());
66 NodePredicates.push_back(Pred);
6367 Entry = NodePredicates.size();
6468 }
6569 return Entry-1;
6670 }
71
6772 unsigned getPatternPredicate(StringRef PredName) {
6873 unsigned &Entry = PatternPredicateMap[PredName];
6974 if (Entry == 0) {
7277 }
7378 return Entry-1;
7479 }
75
7680 unsigned getComplexPat(const ComplexPattern &P) {
7781 unsigned &Entry = ComplexPatternMap[&P];
7882 if (Entry == 0) {
238242 return 2;
239243
240244 case Matcher::CheckPatternPredicate: {
241 StringRef Pred = cast(N)->getPredicate();
245 StringRef Pred =cast(N)->getPredicate();
242246 OS << "OPC_CheckPatternPredicate, " << getPatternPredicate(Pred) << ',';
243247 if (!OmitComments)
244248 OS.PadToColumn(CommentIndent) << "// " << Pred;
246250 return 2;
247251 }
248252 case Matcher::CheckPredicate: {
249 StringRef Pred = cast(N)->getPredicateName();
253 TreePredicateFn Pred = cast(N)->getPredicate();
250254 OS << "OPC_CheckPredicate, " << getNodePredicate(Pred) << ',';
251255 if (!OmitComments)
252 OS.PadToColumn(CommentIndent) << "// " << Pred;
256 OS.PadToColumn(CommentIndent) << "// " << Pred.getFnName();
253257 OS << '\n';
254258 return 2;
255259 }
616620 OS << " switch (PredNo) {\n";
617621 OS << " default: assert(0 && \"Invalid predicate in table?\");\n";
618622 for (unsigned i = 0, e = NodePredicates.size(); i != e; ++i) {
619 // FIXME: Storing this by name is horrible.
620 TreePattern *P =PFsByName[NodePredicates[i].substr(strlen("Predicate_"))];
621 assert(P && "Unknown name?");
622
623623 // Emit the predicate code corresponding to this pattern.
624 std::string Code = P->getRecord()->getValueAsCode("Predicate");
625 assert(!Code.empty() && "No code in this predicate");
626 OS << " case " << i << ": { // " << NodePredicates[i] << '\n';
627 std::string ClassName;
628 if (P->getOnlyTree()->isLeaf())
629 ClassName = "SDNode";
630 else
631 ClassName =
632 CGP.getSDNodeInfo(P->getOnlyTree()->getOperator()).getSDClassName();
633 if (ClassName == "SDNode")
634 OS << " SDNode *N = Node;\n";
635 else
636 OS << " " << ClassName << "*N = cast<" << ClassName << ">(Node);\n";
637 OS << Code << "\n }\n";
624 TreePredicateFn PredFn = NodePredicates[i];
625
626 assert(!PredFn.isAlwaysTrue() && "No code in this predicate");
627 OS << " case " << i << ": { // " << NodePredicates[i].getFnName() <<'\n';
628
629 OS << PredFn.getCodeToRunOnSDNode() << "\n }\n";
638630 }
639631 OS << " }\n";
640632 OS << "}\n\n";