1 //===- DAGISelMatcher.h - Representation of DAG pattern matcher -*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #ifndef LLVM_UTILS_TABLEGEN_DAGISELMATCHER_H 11 #define LLVM_UTILS_TABLEGEN_DAGISELMATCHER_H 12 13 #include "llvm/ADT/ArrayRef.h" 14 #include "llvm/ADT/SmallVector.h" 15 #include "llvm/ADT/StringRef.h" 16 #include "llvm/CodeGen/MachineValueType.h" 17 #include "llvm/Support/Casting.h" 18 19 namespace llvm { 20 struct CodeGenRegister; 21 class CodeGenDAGPatterns; 22 class Matcher; 23 class PatternToMatch; 24 class raw_ostream; 25 class ComplexPattern; 26 class Record; 27 class SDNodeInfo; 28 class TreePredicateFn; 29 class TreePattern; 30 31 Matcher *ConvertPatternToMatcher(const PatternToMatch &Pattern,unsigned Variant, 32 const CodeGenDAGPatterns &CGP); 33 void OptimizeMatcher(std::unique_ptr<Matcher> &Matcher, 34 const CodeGenDAGPatterns &CGP); 35 void EmitMatcherTable(const Matcher *Matcher, const CodeGenDAGPatterns &CGP, 36 raw_ostream &OS); 37 38 39 /// Matcher - Base class for all the DAG ISel Matcher representation 40 /// nodes. 41 class Matcher { 42 // The next matcher node that is executed after this one. Null if this is the 43 // last stage of a match. 44 std::unique_ptr<Matcher> Next; 45 virtual void anchor(); 46 public: 47 enum KindTy { 48 // Matcher state manipulation. 49 Scope, // Push a checking scope. 50 RecordNode, // Record the current node. 51 RecordChild, // Record a child of the current node. 52 RecordMemRef, // Record the memref in the current node. 53 CaptureGlueInput, // If the current node has an input glue, save it. 54 MoveChild, // Move current node to specified child. 55 MoveParent, // Move current node to parent. 56 57 // Predicate checking. 58 CheckSame, // Fail if not same as prev match. 59 CheckChildSame, // Fail if child not same as prev match. 60 CheckPatternPredicate, 61 CheckPredicate, // Fail if node predicate fails. 62 CheckOpcode, // Fail if not opcode. 63 SwitchOpcode, // Dispatch based on opcode. 64 CheckType, // Fail if not correct type. 65 SwitchType, // Dispatch based on type. 66 CheckChildType, // Fail if child has wrong type. 67 CheckInteger, // Fail if wrong val. 68 CheckChildInteger, // Fail if child is wrong val. 69 CheckCondCode, // Fail if not condcode. 70 CheckValueType, 71 CheckComplexPat, 72 CheckAndImm, 73 CheckOrImm, 74 CheckFoldableChainNode, 75 76 // Node creation/emisssion. 77 EmitInteger, // Create a TargetConstant 78 EmitStringInteger, // Create a TargetConstant from a string. 79 EmitRegister, // Create a register. 80 EmitConvertToTarget, // Convert a imm/fpimm to target imm/fpimm 81 EmitMergeInputChains, // Merge together a chains for an input. 82 EmitCopyToReg, // Emit a copytoreg into a physreg. 83 EmitNode, // Create a DAG node 84 EmitNodeXForm, // Run a SDNodeXForm 85 CompleteMatch, // Finish a match and update the results. 86 MorphNodeTo // Build a node, finish a match and update results. 87 }; 88 const KindTy Kind; 89 90 protected: Matcher(KindTy K)91 Matcher(KindTy K) : Kind(K) {} 92 public: ~Matcher()93 virtual ~Matcher() {} 94 getKind()95 KindTy getKind() const { return Kind; } 96 getNext()97 Matcher *getNext() { return Next.get(); } getNext()98 const Matcher *getNext() const { return Next.get(); } setNext(Matcher * C)99 void setNext(Matcher *C) { Next.reset(C); } takeNext()100 Matcher *takeNext() { return Next.release(); } 101 getNextPtr()102 std::unique_ptr<Matcher> &getNextPtr() { return Next; } 103 isEqual(const Matcher * M)104 bool isEqual(const Matcher *M) const { 105 if (getKind() != M->getKind()) return false; 106 return isEqualImpl(M); 107 } 108 109 /// isSimplePredicateNode - Return true if this is a simple predicate that 110 /// operates on the node or its children without potential side effects or a 111 /// change of the current node. isSimplePredicateNode()112 bool isSimplePredicateNode() const { 113 switch (getKind()) { 114 default: return false; 115 case CheckSame: 116 case CheckChildSame: 117 case CheckPatternPredicate: 118 case CheckPredicate: 119 case CheckOpcode: 120 case CheckType: 121 case CheckChildType: 122 case CheckInteger: 123 case CheckChildInteger: 124 case CheckCondCode: 125 case CheckValueType: 126 case CheckAndImm: 127 case CheckOrImm: 128 case CheckFoldableChainNode: 129 return true; 130 } 131 } 132 133 /// isSimplePredicateOrRecordNode - Return true if this is a record node or 134 /// a simple predicate. isSimplePredicateOrRecordNode()135 bool isSimplePredicateOrRecordNode() const { 136 return isSimplePredicateNode() || 137 getKind() == RecordNode || getKind() == RecordChild; 138 } 139 140 /// unlinkNode - Unlink the specified node from this chain. If Other == this, 141 /// we unlink the next pointer and return it. Otherwise we unlink Other from 142 /// the list and return this. 143 Matcher *unlinkNode(Matcher *Other); 144 145 /// canMoveBefore - Return true if this matcher is the same as Other, or if 146 /// we can move this matcher past all of the nodes in-between Other and this 147 /// node. Other must be equal to or before this. 148 bool canMoveBefore(const Matcher *Other) const; 149 150 /// canMoveBeforeNode - Return true if it is safe to move the current matcher 151 /// across the specified one. 152 bool canMoveBeforeNode(const Matcher *Other) const; 153 154 /// isContradictory - Return true of these two matchers could never match on 155 /// the same node. isContradictory(const Matcher * Other)156 bool isContradictory(const Matcher *Other) const { 157 // Since this predicate is reflexive, we canonicalize the ordering so that 158 // we always match a node against nodes with kinds that are greater or equal 159 // to them. For example, we'll pass in a CheckType node as an argument to 160 // the CheckOpcode method, not the other way around. 161 if (getKind() < Other->getKind()) 162 return isContradictoryImpl(Other); 163 return Other->isContradictoryImpl(this); 164 } 165 166 void print(raw_ostream &OS, unsigned indent = 0) const; 167 void printOne(raw_ostream &OS) const; 168 void dump() const; 169 protected: 170 virtual void printImpl(raw_ostream &OS, unsigned indent) const = 0; 171 virtual bool isEqualImpl(const Matcher *M) const = 0; isContradictoryImpl(const Matcher * M)172 virtual bool isContradictoryImpl(const Matcher *M) const { return false; } 173 }; 174 175 /// ScopeMatcher - This attempts to match each of its children to find the first 176 /// one that successfully matches. If one child fails, it tries the next child. 177 /// If none of the children match then this check fails. It never has a 'next'. 178 class ScopeMatcher : public Matcher { 179 SmallVector<Matcher*, 4> Children; 180 public: ScopeMatcher(ArrayRef<Matcher * > children)181 ScopeMatcher(ArrayRef<Matcher *> children) 182 : Matcher(Scope), Children(children.begin(), children.end()) { 183 } 184 ~ScopeMatcher() override; 185 getNumChildren()186 unsigned getNumChildren() const { return Children.size(); } 187 getChild(unsigned i)188 Matcher *getChild(unsigned i) { return Children[i]; } getChild(unsigned i)189 const Matcher *getChild(unsigned i) const { return Children[i]; } 190 resetChild(unsigned i,Matcher * N)191 void resetChild(unsigned i, Matcher *N) { 192 delete Children[i]; 193 Children[i] = N; 194 } 195 takeChild(unsigned i)196 Matcher *takeChild(unsigned i) { 197 Matcher *Res = Children[i]; 198 Children[i] = nullptr; 199 return Res; 200 } 201 setNumChildren(unsigned NC)202 void setNumChildren(unsigned NC) { 203 if (NC < Children.size()) { 204 // delete any children we're about to lose pointers to. 205 for (unsigned i = NC, e = Children.size(); i != e; ++i) 206 delete Children[i]; 207 } 208 Children.resize(NC); 209 } 210 classof(const Matcher * N)211 static inline bool classof(const Matcher *N) { 212 return N->getKind() == Scope; 213 } 214 215 private: 216 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)217 bool isEqualImpl(const Matcher *M) const override { return false; } 218 }; 219 220 /// RecordMatcher - Save the current node in the operand list. 221 class RecordMatcher : public Matcher { 222 /// WhatFor - This is a string indicating why we're recording this. This 223 /// should only be used for comment generation not anything semantic. 224 std::string WhatFor; 225 226 /// ResultNo - The slot number in the RecordedNodes vector that this will be, 227 /// just printed as a comment. 228 unsigned ResultNo; 229 public: RecordMatcher(const std::string & whatfor,unsigned resultNo)230 RecordMatcher(const std::string &whatfor, unsigned resultNo) 231 : Matcher(RecordNode), WhatFor(whatfor), ResultNo(resultNo) {} 232 getWhatFor()233 const std::string &getWhatFor() const { return WhatFor; } getResultNo()234 unsigned getResultNo() const { return ResultNo; } 235 classof(const Matcher * N)236 static inline bool classof(const Matcher *N) { 237 return N->getKind() == RecordNode; 238 } 239 240 private: 241 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)242 bool isEqualImpl(const Matcher *M) const override { return true; } 243 }; 244 245 /// RecordChildMatcher - Save a numbered child of the current node, or fail 246 /// the match if it doesn't exist. This is logically equivalent to: 247 /// MoveChild N + RecordNode + MoveParent. 248 class RecordChildMatcher : public Matcher { 249 unsigned ChildNo; 250 251 /// WhatFor - This is a string indicating why we're recording this. This 252 /// should only be used for comment generation not anything semantic. 253 std::string WhatFor; 254 255 /// ResultNo - The slot number in the RecordedNodes vector that this will be, 256 /// just printed as a comment. 257 unsigned ResultNo; 258 public: RecordChildMatcher(unsigned childno,const std::string & whatfor,unsigned resultNo)259 RecordChildMatcher(unsigned childno, const std::string &whatfor, 260 unsigned resultNo) 261 : Matcher(RecordChild), ChildNo(childno), WhatFor(whatfor), 262 ResultNo(resultNo) {} 263 getChildNo()264 unsigned getChildNo() const { return ChildNo; } getWhatFor()265 const std::string &getWhatFor() const { return WhatFor; } getResultNo()266 unsigned getResultNo() const { return ResultNo; } 267 classof(const Matcher * N)268 static inline bool classof(const Matcher *N) { 269 return N->getKind() == RecordChild; 270 } 271 272 private: 273 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)274 bool isEqualImpl(const Matcher *M) const override { 275 return cast<RecordChildMatcher>(M)->getChildNo() == getChildNo(); 276 } 277 }; 278 279 /// RecordMemRefMatcher - Save the current node's memref. 280 class RecordMemRefMatcher : public Matcher { 281 public: RecordMemRefMatcher()282 RecordMemRefMatcher() : Matcher(RecordMemRef) {} 283 classof(const Matcher * N)284 static inline bool classof(const Matcher *N) { 285 return N->getKind() == RecordMemRef; 286 } 287 288 private: 289 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)290 bool isEqualImpl(const Matcher *M) const override { return true; } 291 }; 292 293 294 /// CaptureGlueInputMatcher - If the current record has a glue input, record 295 /// it so that it is used as an input to the generated code. 296 class CaptureGlueInputMatcher : public Matcher { 297 public: CaptureGlueInputMatcher()298 CaptureGlueInputMatcher() : Matcher(CaptureGlueInput) {} 299 classof(const Matcher * N)300 static inline bool classof(const Matcher *N) { 301 return N->getKind() == CaptureGlueInput; 302 } 303 304 private: 305 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)306 bool isEqualImpl(const Matcher *M) const override { return true; } 307 }; 308 309 /// MoveChildMatcher - This tells the interpreter to move into the 310 /// specified child node. 311 class MoveChildMatcher : public Matcher { 312 unsigned ChildNo; 313 public: MoveChildMatcher(unsigned childNo)314 MoveChildMatcher(unsigned childNo) : Matcher(MoveChild), ChildNo(childNo) {} 315 getChildNo()316 unsigned getChildNo() const { return ChildNo; } 317 classof(const Matcher * N)318 static inline bool classof(const Matcher *N) { 319 return N->getKind() == MoveChild; 320 } 321 322 private: 323 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)324 bool isEqualImpl(const Matcher *M) const override { 325 return cast<MoveChildMatcher>(M)->getChildNo() == getChildNo(); 326 } 327 }; 328 329 /// MoveParentMatcher - This tells the interpreter to move to the parent 330 /// of the current node. 331 class MoveParentMatcher : public Matcher { 332 public: MoveParentMatcher()333 MoveParentMatcher() : Matcher(MoveParent) {} 334 classof(const Matcher * N)335 static inline bool classof(const Matcher *N) { 336 return N->getKind() == MoveParent; 337 } 338 339 private: 340 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)341 bool isEqualImpl(const Matcher *M) const override { return true; } 342 }; 343 344 /// CheckSameMatcher - This checks to see if this node is exactly the same 345 /// node as the specified match that was recorded with 'Record'. This is used 346 /// when patterns have the same name in them, like '(mul GPR:$in, GPR:$in)'. 347 class CheckSameMatcher : public Matcher { 348 unsigned MatchNumber; 349 public: CheckSameMatcher(unsigned matchnumber)350 CheckSameMatcher(unsigned matchnumber) 351 : Matcher(CheckSame), MatchNumber(matchnumber) {} 352 getMatchNumber()353 unsigned getMatchNumber() const { return MatchNumber; } 354 classof(const Matcher * N)355 static inline bool classof(const Matcher *N) { 356 return N->getKind() == CheckSame; 357 } 358 359 private: 360 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)361 bool isEqualImpl(const Matcher *M) const override { 362 return cast<CheckSameMatcher>(M)->getMatchNumber() == getMatchNumber(); 363 } 364 }; 365 366 /// CheckChildSameMatcher - This checks to see if child node is exactly the same 367 /// node as the specified match that was recorded with 'Record'. This is used 368 /// when patterns have the same name in them, like '(mul GPR:$in, GPR:$in)'. 369 class CheckChildSameMatcher : public Matcher { 370 unsigned ChildNo; 371 unsigned MatchNumber; 372 public: CheckChildSameMatcher(unsigned childno,unsigned matchnumber)373 CheckChildSameMatcher(unsigned childno, unsigned matchnumber) 374 : Matcher(CheckChildSame), ChildNo(childno), MatchNumber(matchnumber) {} 375 getChildNo()376 unsigned getChildNo() const { return ChildNo; } getMatchNumber()377 unsigned getMatchNumber() const { return MatchNumber; } 378 classof(const Matcher * N)379 static inline bool classof(const Matcher *N) { 380 return N->getKind() == CheckChildSame; 381 } 382 383 private: 384 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)385 bool isEqualImpl(const Matcher *M) const override { 386 return cast<CheckChildSameMatcher>(M)->ChildNo == ChildNo && 387 cast<CheckChildSameMatcher>(M)->MatchNumber == MatchNumber; 388 } 389 }; 390 391 /// CheckPatternPredicateMatcher - This checks the target-specific predicate 392 /// to see if the entire pattern is capable of matching. This predicate does 393 /// not take a node as input. This is used for subtarget feature checks etc. 394 class CheckPatternPredicateMatcher : public Matcher { 395 std::string Predicate; 396 public: CheckPatternPredicateMatcher(StringRef predicate)397 CheckPatternPredicateMatcher(StringRef predicate) 398 : Matcher(CheckPatternPredicate), Predicate(predicate) {} 399 getPredicate()400 StringRef getPredicate() const { return Predicate; } 401 classof(const Matcher * N)402 static inline bool classof(const Matcher *N) { 403 return N->getKind() == CheckPatternPredicate; 404 } 405 406 private: 407 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)408 bool isEqualImpl(const Matcher *M) const override { 409 return cast<CheckPatternPredicateMatcher>(M)->getPredicate() == Predicate; 410 } 411 }; 412 413 /// CheckPredicateMatcher - This checks the target-specific predicate to 414 /// see if the node is acceptable. 415 class CheckPredicateMatcher : public Matcher { 416 TreePattern *Pred; 417 public: 418 CheckPredicateMatcher(const TreePredicateFn &pred); 419 420 TreePredicateFn getPredicate() const; 421 classof(const Matcher * N)422 static inline bool classof(const Matcher *N) { 423 return N->getKind() == CheckPredicate; 424 } 425 426 private: 427 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)428 bool isEqualImpl(const Matcher *M) const override { 429 return cast<CheckPredicateMatcher>(M)->Pred == Pred; 430 } 431 }; 432 433 434 /// CheckOpcodeMatcher - This checks to see if the current node has the 435 /// specified opcode, if not it fails to match. 436 class CheckOpcodeMatcher : public Matcher { 437 const SDNodeInfo &Opcode; 438 public: CheckOpcodeMatcher(const SDNodeInfo & opcode)439 CheckOpcodeMatcher(const SDNodeInfo &opcode) 440 : Matcher(CheckOpcode), Opcode(opcode) {} 441 getOpcode()442 const SDNodeInfo &getOpcode() const { return Opcode; } 443 classof(const Matcher * N)444 static inline bool classof(const Matcher *N) { 445 return N->getKind() == CheckOpcode; 446 } 447 448 private: 449 void printImpl(raw_ostream &OS, unsigned indent) const override; 450 bool isEqualImpl(const Matcher *M) const override; 451 bool isContradictoryImpl(const Matcher *M) const override; 452 }; 453 454 /// SwitchOpcodeMatcher - Switch based on the current node's opcode, dispatching 455 /// to one matcher per opcode. If the opcode doesn't match any of the cases, 456 /// then the match fails. This is semantically equivalent to a Scope node where 457 /// every child does a CheckOpcode, but is much faster. 458 class SwitchOpcodeMatcher : public Matcher { 459 SmallVector<std::pair<const SDNodeInfo*, Matcher*>, 8> Cases; 460 public: SwitchOpcodeMatcher(ArrayRef<std::pair<const SDNodeInfo *,Matcher * >> cases)461 SwitchOpcodeMatcher(ArrayRef<std::pair<const SDNodeInfo*, Matcher*> > cases) 462 : Matcher(SwitchOpcode), Cases(cases.begin(), cases.end()) {} 463 ~SwitchOpcodeMatcher() override; 464 classof(const Matcher * N)465 static inline bool classof(const Matcher *N) { 466 return N->getKind() == SwitchOpcode; 467 } 468 getNumCases()469 unsigned getNumCases() const { return Cases.size(); } 470 getCaseOpcode(unsigned i)471 const SDNodeInfo &getCaseOpcode(unsigned i) const { return *Cases[i].first; } getCaseMatcher(unsigned i)472 Matcher *getCaseMatcher(unsigned i) { return Cases[i].second; } getCaseMatcher(unsigned i)473 const Matcher *getCaseMatcher(unsigned i) const { return Cases[i].second; } 474 475 private: 476 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)477 bool isEqualImpl(const Matcher *M) const override { return false; } 478 }; 479 480 /// CheckTypeMatcher - This checks to see if the current node has the 481 /// specified type at the specified result, if not it fails to match. 482 class CheckTypeMatcher : public Matcher { 483 MVT::SimpleValueType Type; 484 unsigned ResNo; 485 public: CheckTypeMatcher(MVT::SimpleValueType type,unsigned resno)486 CheckTypeMatcher(MVT::SimpleValueType type, unsigned resno) 487 : Matcher(CheckType), Type(type), ResNo(resno) {} 488 getType()489 MVT::SimpleValueType getType() const { return Type; } getResNo()490 unsigned getResNo() const { return ResNo; } 491 classof(const Matcher * N)492 static inline bool classof(const Matcher *N) { 493 return N->getKind() == CheckType; 494 } 495 496 private: 497 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)498 bool isEqualImpl(const Matcher *M) const override { 499 return cast<CheckTypeMatcher>(M)->Type == Type; 500 } 501 bool isContradictoryImpl(const Matcher *M) const override; 502 }; 503 504 /// SwitchTypeMatcher - Switch based on the current node's type, dispatching 505 /// to one matcher per case. If the type doesn't match any of the cases, 506 /// then the match fails. This is semantically equivalent to a Scope node where 507 /// every child does a CheckType, but is much faster. 508 class SwitchTypeMatcher : public Matcher { 509 SmallVector<std::pair<MVT::SimpleValueType, Matcher*>, 8> Cases; 510 public: SwitchTypeMatcher(ArrayRef<std::pair<MVT::SimpleValueType,Matcher * >> cases)511 SwitchTypeMatcher(ArrayRef<std::pair<MVT::SimpleValueType, Matcher*> > cases) 512 : Matcher(SwitchType), Cases(cases.begin(), cases.end()) {} 513 ~SwitchTypeMatcher() override; 514 classof(const Matcher * N)515 static inline bool classof(const Matcher *N) { 516 return N->getKind() == SwitchType; 517 } 518 getNumCases()519 unsigned getNumCases() const { return Cases.size(); } 520 getCaseType(unsigned i)521 MVT::SimpleValueType getCaseType(unsigned i) const { return Cases[i].first; } getCaseMatcher(unsigned i)522 Matcher *getCaseMatcher(unsigned i) { return Cases[i].second; } getCaseMatcher(unsigned i)523 const Matcher *getCaseMatcher(unsigned i) const { return Cases[i].second; } 524 525 private: 526 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)527 bool isEqualImpl(const Matcher *M) const override { return false; } 528 }; 529 530 531 /// CheckChildTypeMatcher - This checks to see if a child node has the 532 /// specified type, if not it fails to match. 533 class CheckChildTypeMatcher : public Matcher { 534 unsigned ChildNo; 535 MVT::SimpleValueType Type; 536 public: CheckChildTypeMatcher(unsigned childno,MVT::SimpleValueType type)537 CheckChildTypeMatcher(unsigned childno, MVT::SimpleValueType type) 538 : Matcher(CheckChildType), ChildNo(childno), Type(type) {} 539 getChildNo()540 unsigned getChildNo() const { return ChildNo; } getType()541 MVT::SimpleValueType getType() const { return Type; } 542 classof(const Matcher * N)543 static inline bool classof(const Matcher *N) { 544 return N->getKind() == CheckChildType; 545 } 546 547 private: 548 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)549 bool isEqualImpl(const Matcher *M) const override { 550 return cast<CheckChildTypeMatcher>(M)->ChildNo == ChildNo && 551 cast<CheckChildTypeMatcher>(M)->Type == Type; 552 } 553 bool isContradictoryImpl(const Matcher *M) const override; 554 }; 555 556 557 /// CheckIntegerMatcher - This checks to see if the current node is a 558 /// ConstantSDNode with the specified integer value, if not it fails to match. 559 class CheckIntegerMatcher : public Matcher { 560 int64_t Value; 561 public: CheckIntegerMatcher(int64_t value)562 CheckIntegerMatcher(int64_t value) 563 : Matcher(CheckInteger), Value(value) {} 564 getValue()565 int64_t getValue() const { return Value; } 566 classof(const Matcher * N)567 static inline bool classof(const Matcher *N) { 568 return N->getKind() == CheckInteger; 569 } 570 571 private: 572 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)573 bool isEqualImpl(const Matcher *M) const override { 574 return cast<CheckIntegerMatcher>(M)->Value == Value; 575 } 576 bool isContradictoryImpl(const Matcher *M) const override; 577 }; 578 579 /// CheckChildIntegerMatcher - This checks to see if the child node is a 580 /// ConstantSDNode with a specified integer value, if not it fails to match. 581 class CheckChildIntegerMatcher : public Matcher { 582 unsigned ChildNo; 583 int64_t Value; 584 public: CheckChildIntegerMatcher(unsigned childno,int64_t value)585 CheckChildIntegerMatcher(unsigned childno, int64_t value) 586 : Matcher(CheckChildInteger), ChildNo(childno), Value(value) {} 587 getChildNo()588 unsigned getChildNo() const { return ChildNo; } getValue()589 int64_t getValue() const { return Value; } 590 classof(const Matcher * N)591 static inline bool classof(const Matcher *N) { 592 return N->getKind() == CheckChildInteger; 593 } 594 595 private: 596 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)597 bool isEqualImpl(const Matcher *M) const override { 598 return cast<CheckChildIntegerMatcher>(M)->ChildNo == ChildNo && 599 cast<CheckChildIntegerMatcher>(M)->Value == Value; 600 } 601 bool isContradictoryImpl(const Matcher *M) const override; 602 }; 603 604 /// CheckCondCodeMatcher - This checks to see if the current node is a 605 /// CondCodeSDNode with the specified condition, if not it fails to match. 606 class CheckCondCodeMatcher : public Matcher { 607 StringRef CondCodeName; 608 public: CheckCondCodeMatcher(StringRef condcodename)609 CheckCondCodeMatcher(StringRef condcodename) 610 : Matcher(CheckCondCode), CondCodeName(condcodename) {} 611 getCondCodeName()612 StringRef getCondCodeName() const { return CondCodeName; } 613 classof(const Matcher * N)614 static inline bool classof(const Matcher *N) { 615 return N->getKind() == CheckCondCode; 616 } 617 618 private: 619 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)620 bool isEqualImpl(const Matcher *M) const override { 621 return cast<CheckCondCodeMatcher>(M)->CondCodeName == CondCodeName; 622 } 623 }; 624 625 /// CheckValueTypeMatcher - This checks to see if the current node is a 626 /// VTSDNode with the specified type, if not it fails to match. 627 class CheckValueTypeMatcher : public Matcher { 628 StringRef TypeName; 629 public: CheckValueTypeMatcher(StringRef type_name)630 CheckValueTypeMatcher(StringRef type_name) 631 : Matcher(CheckValueType), TypeName(type_name) {} 632 getTypeName()633 StringRef getTypeName() const { return TypeName; } 634 classof(const Matcher * N)635 static inline bool classof(const Matcher *N) { 636 return N->getKind() == CheckValueType; 637 } 638 639 private: 640 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)641 bool isEqualImpl(const Matcher *M) const override { 642 return cast<CheckValueTypeMatcher>(M)->TypeName == TypeName; 643 } 644 bool isContradictoryImpl(const Matcher *M) const override; 645 }; 646 647 648 649 /// CheckComplexPatMatcher - This node runs the specified ComplexPattern on 650 /// the current node. 651 class CheckComplexPatMatcher : public Matcher { 652 const ComplexPattern &Pattern; 653 654 /// MatchNumber - This is the recorded nodes slot that contains the node we 655 /// want to match against. 656 unsigned MatchNumber; 657 658 /// Name - The name of the node we're matching, for comment emission. 659 std::string Name; 660 661 /// FirstResult - This is the first slot in the RecordedNodes list that the 662 /// result of the match populates. 663 unsigned FirstResult; 664 public: CheckComplexPatMatcher(const ComplexPattern & pattern,unsigned matchnumber,const std::string & name,unsigned firstresult)665 CheckComplexPatMatcher(const ComplexPattern &pattern, unsigned matchnumber, 666 const std::string &name, unsigned firstresult) 667 : Matcher(CheckComplexPat), Pattern(pattern), MatchNumber(matchnumber), 668 Name(name), FirstResult(firstresult) {} 669 getPattern()670 const ComplexPattern &getPattern() const { return Pattern; } getMatchNumber()671 unsigned getMatchNumber() const { return MatchNumber; } 672 getName()673 const std::string getName() const { return Name; } getFirstResult()674 unsigned getFirstResult() const { return FirstResult; } 675 classof(const Matcher * N)676 static inline bool classof(const Matcher *N) { 677 return N->getKind() == CheckComplexPat; 678 } 679 680 private: 681 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)682 bool isEqualImpl(const Matcher *M) const override { 683 return &cast<CheckComplexPatMatcher>(M)->Pattern == &Pattern && 684 cast<CheckComplexPatMatcher>(M)->MatchNumber == MatchNumber; 685 } 686 }; 687 688 /// CheckAndImmMatcher - This checks to see if the current node is an 'and' 689 /// with something equivalent to the specified immediate. 690 class CheckAndImmMatcher : public Matcher { 691 int64_t Value; 692 public: CheckAndImmMatcher(int64_t value)693 CheckAndImmMatcher(int64_t value) 694 : Matcher(CheckAndImm), Value(value) {} 695 getValue()696 int64_t getValue() const { return Value; } 697 classof(const Matcher * N)698 static inline bool classof(const Matcher *N) { 699 return N->getKind() == CheckAndImm; 700 } 701 702 private: 703 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)704 bool isEqualImpl(const Matcher *M) const override { 705 return cast<CheckAndImmMatcher>(M)->Value == Value; 706 } 707 }; 708 709 /// CheckOrImmMatcher - This checks to see if the current node is an 'and' 710 /// with something equivalent to the specified immediate. 711 class CheckOrImmMatcher : public Matcher { 712 int64_t Value; 713 public: CheckOrImmMatcher(int64_t value)714 CheckOrImmMatcher(int64_t value) 715 : Matcher(CheckOrImm), Value(value) {} 716 getValue()717 int64_t getValue() const { return Value; } 718 classof(const Matcher * N)719 static inline bool classof(const Matcher *N) { 720 return N->getKind() == CheckOrImm; 721 } 722 723 private: 724 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)725 bool isEqualImpl(const Matcher *M) const override { 726 return cast<CheckOrImmMatcher>(M)->Value == Value; 727 } 728 }; 729 730 /// CheckFoldableChainNodeMatcher - This checks to see if the current node 731 /// (which defines a chain operand) is safe to fold into a larger pattern. 732 class CheckFoldableChainNodeMatcher : public Matcher { 733 public: CheckFoldableChainNodeMatcher()734 CheckFoldableChainNodeMatcher() 735 : Matcher(CheckFoldableChainNode) {} 736 classof(const Matcher * N)737 static inline bool classof(const Matcher *N) { 738 return N->getKind() == CheckFoldableChainNode; 739 } 740 741 private: 742 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)743 bool isEqualImpl(const Matcher *M) const override { return true; } 744 }; 745 746 /// EmitIntegerMatcher - This creates a new TargetConstant. 747 class EmitIntegerMatcher : public Matcher { 748 int64_t Val; 749 MVT::SimpleValueType VT; 750 public: EmitIntegerMatcher(int64_t val,MVT::SimpleValueType vt)751 EmitIntegerMatcher(int64_t val, MVT::SimpleValueType vt) 752 : Matcher(EmitInteger), Val(val), VT(vt) {} 753 getValue()754 int64_t getValue() const { return Val; } getVT()755 MVT::SimpleValueType getVT() const { return VT; } 756 classof(const Matcher * N)757 static inline bool classof(const Matcher *N) { 758 return N->getKind() == EmitInteger; 759 } 760 761 private: 762 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)763 bool isEqualImpl(const Matcher *M) const override { 764 return cast<EmitIntegerMatcher>(M)->Val == Val && 765 cast<EmitIntegerMatcher>(M)->VT == VT; 766 } 767 }; 768 769 /// EmitStringIntegerMatcher - A target constant whose value is represented 770 /// by a string. 771 class EmitStringIntegerMatcher : public Matcher { 772 std::string Val; 773 MVT::SimpleValueType VT; 774 public: EmitStringIntegerMatcher(const std::string & val,MVT::SimpleValueType vt)775 EmitStringIntegerMatcher(const std::string &val, MVT::SimpleValueType vt) 776 : Matcher(EmitStringInteger), Val(val), VT(vt) {} 777 getValue()778 const std::string &getValue() const { return Val; } getVT()779 MVT::SimpleValueType getVT() const { return VT; } 780 classof(const Matcher * N)781 static inline bool classof(const Matcher *N) { 782 return N->getKind() == EmitStringInteger; 783 } 784 785 private: 786 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)787 bool isEqualImpl(const Matcher *M) const override { 788 return cast<EmitStringIntegerMatcher>(M)->Val == Val && 789 cast<EmitStringIntegerMatcher>(M)->VT == VT; 790 } 791 }; 792 793 /// EmitRegisterMatcher - This creates a new TargetConstant. 794 class EmitRegisterMatcher : public Matcher { 795 /// Reg - The def for the register that we're emitting. If this is null, then 796 /// this is a reference to zero_reg. 797 const CodeGenRegister *Reg; 798 MVT::SimpleValueType VT; 799 public: EmitRegisterMatcher(const CodeGenRegister * reg,MVT::SimpleValueType vt)800 EmitRegisterMatcher(const CodeGenRegister *reg, MVT::SimpleValueType vt) 801 : Matcher(EmitRegister), Reg(reg), VT(vt) {} 802 getReg()803 const CodeGenRegister *getReg() const { return Reg; } getVT()804 MVT::SimpleValueType getVT() const { return VT; } 805 classof(const Matcher * N)806 static inline bool classof(const Matcher *N) { 807 return N->getKind() == EmitRegister; 808 } 809 810 private: 811 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)812 bool isEqualImpl(const Matcher *M) const override { 813 return cast<EmitRegisterMatcher>(M)->Reg == Reg && 814 cast<EmitRegisterMatcher>(M)->VT == VT; 815 } 816 }; 817 818 /// EmitConvertToTargetMatcher - Emit an operation that reads a specified 819 /// recorded node and converts it from being a ISD::Constant to 820 /// ISD::TargetConstant, likewise for ConstantFP. 821 class EmitConvertToTargetMatcher : public Matcher { 822 unsigned Slot; 823 public: EmitConvertToTargetMatcher(unsigned slot)824 EmitConvertToTargetMatcher(unsigned slot) 825 : Matcher(EmitConvertToTarget), Slot(slot) {} 826 getSlot()827 unsigned getSlot() const { return Slot; } 828 classof(const Matcher * N)829 static inline bool classof(const Matcher *N) { 830 return N->getKind() == EmitConvertToTarget; 831 } 832 833 private: 834 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)835 bool isEqualImpl(const Matcher *M) const override { 836 return cast<EmitConvertToTargetMatcher>(M)->Slot == Slot; 837 } 838 }; 839 840 /// EmitMergeInputChainsMatcher - Emit a node that merges a list of input 841 /// chains together with a token factor. The list of nodes are the nodes in the 842 /// matched pattern that have chain input/outputs. This node adds all input 843 /// chains of these nodes if they are not themselves a node in the pattern. 844 class EmitMergeInputChainsMatcher : public Matcher { 845 SmallVector<unsigned, 3> ChainNodes; 846 public: EmitMergeInputChainsMatcher(ArrayRef<unsigned> nodes)847 EmitMergeInputChainsMatcher(ArrayRef<unsigned> nodes) 848 : Matcher(EmitMergeInputChains), ChainNodes(nodes.begin(), nodes.end()) {} 849 getNumNodes()850 unsigned getNumNodes() const { return ChainNodes.size(); } 851 getNode(unsigned i)852 unsigned getNode(unsigned i) const { 853 assert(i < ChainNodes.size()); 854 return ChainNodes[i]; 855 } 856 classof(const Matcher * N)857 static inline bool classof(const Matcher *N) { 858 return N->getKind() == EmitMergeInputChains; 859 } 860 861 private: 862 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)863 bool isEqualImpl(const Matcher *M) const override { 864 return cast<EmitMergeInputChainsMatcher>(M)->ChainNodes == ChainNodes; 865 } 866 }; 867 868 /// EmitCopyToRegMatcher - Emit a CopyToReg node from a value to a physreg, 869 /// pushing the chain and glue results. 870 /// 871 class EmitCopyToRegMatcher : public Matcher { 872 unsigned SrcSlot; // Value to copy into the physreg. 873 Record *DestPhysReg; 874 public: EmitCopyToRegMatcher(unsigned srcSlot,Record * destPhysReg)875 EmitCopyToRegMatcher(unsigned srcSlot, Record *destPhysReg) 876 : Matcher(EmitCopyToReg), SrcSlot(srcSlot), DestPhysReg(destPhysReg) {} 877 getSrcSlot()878 unsigned getSrcSlot() const { return SrcSlot; } getDestPhysReg()879 Record *getDestPhysReg() const { return DestPhysReg; } 880 classof(const Matcher * N)881 static inline bool classof(const Matcher *N) { 882 return N->getKind() == EmitCopyToReg; 883 } 884 885 private: 886 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)887 bool isEqualImpl(const Matcher *M) const override { 888 return cast<EmitCopyToRegMatcher>(M)->SrcSlot == SrcSlot && 889 cast<EmitCopyToRegMatcher>(M)->DestPhysReg == DestPhysReg; 890 } 891 }; 892 893 894 895 /// EmitNodeXFormMatcher - Emit an operation that runs an SDNodeXForm on a 896 /// recorded node and records the result. 897 class EmitNodeXFormMatcher : public Matcher { 898 unsigned Slot; 899 Record *NodeXForm; 900 public: EmitNodeXFormMatcher(unsigned slot,Record * nodeXForm)901 EmitNodeXFormMatcher(unsigned slot, Record *nodeXForm) 902 : Matcher(EmitNodeXForm), Slot(slot), NodeXForm(nodeXForm) {} 903 getSlot()904 unsigned getSlot() const { return Slot; } getNodeXForm()905 Record *getNodeXForm() const { return NodeXForm; } 906 classof(const Matcher * N)907 static inline bool classof(const Matcher *N) { 908 return N->getKind() == EmitNodeXForm; 909 } 910 911 private: 912 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)913 bool isEqualImpl(const Matcher *M) const override { 914 return cast<EmitNodeXFormMatcher>(M)->Slot == Slot && 915 cast<EmitNodeXFormMatcher>(M)->NodeXForm == NodeXForm; 916 } 917 }; 918 919 /// EmitNodeMatcherCommon - Common class shared between EmitNode and 920 /// MorphNodeTo. 921 class EmitNodeMatcherCommon : public Matcher { 922 std::string OpcodeName; 923 const SmallVector<MVT::SimpleValueType, 3> VTs; 924 const SmallVector<unsigned, 6> Operands; 925 bool HasChain, HasInGlue, HasOutGlue, HasMemRefs; 926 927 /// NumFixedArityOperands - If this is a fixed arity node, this is set to -1. 928 /// If this is a varidic node, this is set to the number of fixed arity 929 /// operands in the root of the pattern. The rest are appended to this node. 930 int NumFixedArityOperands; 931 public: EmitNodeMatcherCommon(const std::string & opcodeName,ArrayRef<MVT::SimpleValueType> vts,ArrayRef<unsigned> operands,bool hasChain,bool hasInGlue,bool hasOutGlue,bool hasmemrefs,int numfixedarityoperands,bool isMorphNodeTo)932 EmitNodeMatcherCommon(const std::string &opcodeName, 933 ArrayRef<MVT::SimpleValueType> vts, 934 ArrayRef<unsigned> operands, 935 bool hasChain, bool hasInGlue, bool hasOutGlue, 936 bool hasmemrefs, 937 int numfixedarityoperands, bool isMorphNodeTo) 938 : Matcher(isMorphNodeTo ? MorphNodeTo : EmitNode), OpcodeName(opcodeName), 939 VTs(vts.begin(), vts.end()), Operands(operands.begin(), operands.end()), 940 HasChain(hasChain), HasInGlue(hasInGlue), HasOutGlue(hasOutGlue), 941 HasMemRefs(hasmemrefs), NumFixedArityOperands(numfixedarityoperands) {} 942 getOpcodeName()943 const std::string &getOpcodeName() const { return OpcodeName; } 944 getNumVTs()945 unsigned getNumVTs() const { return VTs.size(); } getVT(unsigned i)946 MVT::SimpleValueType getVT(unsigned i) const { 947 assert(i < VTs.size()); 948 return VTs[i]; 949 } 950 getNumOperands()951 unsigned getNumOperands() const { return Operands.size(); } getOperand(unsigned i)952 unsigned getOperand(unsigned i) const { 953 assert(i < Operands.size()); 954 return Operands[i]; 955 } 956 getVTList()957 const SmallVectorImpl<MVT::SimpleValueType> &getVTList() const { return VTs; } getOperandList()958 const SmallVectorImpl<unsigned> &getOperandList() const { return Operands; } 959 960 hasChain()961 bool hasChain() const { return HasChain; } hasInFlag()962 bool hasInFlag() const { return HasInGlue; } hasOutFlag()963 bool hasOutFlag() const { return HasOutGlue; } hasMemRefs()964 bool hasMemRefs() const { return HasMemRefs; } getNumFixedArityOperands()965 int getNumFixedArityOperands() const { return NumFixedArityOperands; } 966 classof(const Matcher * N)967 static inline bool classof(const Matcher *N) { 968 return N->getKind() == EmitNode || N->getKind() == MorphNodeTo; 969 } 970 971 private: 972 void printImpl(raw_ostream &OS, unsigned indent) const override; 973 bool isEqualImpl(const Matcher *M) const override; 974 }; 975 976 /// EmitNodeMatcher - This signals a successful match and generates a node. 977 class EmitNodeMatcher : public EmitNodeMatcherCommon { 978 void anchor() override; 979 unsigned FirstResultSlot; 980 public: EmitNodeMatcher(const std::string & opcodeName,ArrayRef<MVT::SimpleValueType> vts,ArrayRef<unsigned> operands,bool hasChain,bool hasInFlag,bool hasOutFlag,bool hasmemrefs,int numfixedarityoperands,unsigned firstresultslot)981 EmitNodeMatcher(const std::string &opcodeName, 982 ArrayRef<MVT::SimpleValueType> vts, 983 ArrayRef<unsigned> operands, 984 bool hasChain, bool hasInFlag, bool hasOutFlag, 985 bool hasmemrefs, 986 int numfixedarityoperands, unsigned firstresultslot) 987 : EmitNodeMatcherCommon(opcodeName, vts, operands, hasChain, 988 hasInFlag, hasOutFlag, hasmemrefs, 989 numfixedarityoperands, false), 990 FirstResultSlot(firstresultslot) {} 991 getFirstResultSlot()992 unsigned getFirstResultSlot() const { return FirstResultSlot; } 993 classof(const Matcher * N)994 static inline bool classof(const Matcher *N) { 995 return N->getKind() == EmitNode; 996 } 997 998 }; 999 1000 class MorphNodeToMatcher : public EmitNodeMatcherCommon { 1001 void anchor() override; 1002 const PatternToMatch &Pattern; 1003 public: MorphNodeToMatcher(const std::string & opcodeName,ArrayRef<MVT::SimpleValueType> vts,ArrayRef<unsigned> operands,bool hasChain,bool hasInFlag,bool hasOutFlag,bool hasmemrefs,int numfixedarityoperands,const PatternToMatch & pattern)1004 MorphNodeToMatcher(const std::string &opcodeName, 1005 ArrayRef<MVT::SimpleValueType> vts, 1006 ArrayRef<unsigned> operands, 1007 bool hasChain, bool hasInFlag, bool hasOutFlag, 1008 bool hasmemrefs, 1009 int numfixedarityoperands, const PatternToMatch &pattern) 1010 : EmitNodeMatcherCommon(opcodeName, vts, operands, hasChain, 1011 hasInFlag, hasOutFlag, hasmemrefs, 1012 numfixedarityoperands, true), 1013 Pattern(pattern) { 1014 } 1015 getPattern()1016 const PatternToMatch &getPattern() const { return Pattern; } 1017 classof(const Matcher * N)1018 static inline bool classof(const Matcher *N) { 1019 return N->getKind() == MorphNodeTo; 1020 } 1021 }; 1022 1023 /// CompleteMatchMatcher - Complete a match by replacing the results of the 1024 /// pattern with the newly generated nodes. This also prints a comment 1025 /// indicating the source and dest patterns. 1026 class CompleteMatchMatcher : public Matcher { 1027 SmallVector<unsigned, 2> Results; 1028 const PatternToMatch &Pattern; 1029 public: CompleteMatchMatcher(ArrayRef<unsigned> results,const PatternToMatch & pattern)1030 CompleteMatchMatcher(ArrayRef<unsigned> results, 1031 const PatternToMatch &pattern) 1032 : Matcher(CompleteMatch), Results(results.begin(), results.end()), 1033 Pattern(pattern) {} 1034 getNumResults()1035 unsigned getNumResults() const { return Results.size(); } getResult(unsigned R)1036 unsigned getResult(unsigned R) const { return Results[R]; } getPattern()1037 const PatternToMatch &getPattern() const { return Pattern; } 1038 classof(const Matcher * N)1039 static inline bool classof(const Matcher *N) { 1040 return N->getKind() == CompleteMatch; 1041 } 1042 1043 private: 1044 void printImpl(raw_ostream &OS, unsigned indent) const override; isEqualImpl(const Matcher * M)1045 bool isEqualImpl(const Matcher *M) const override { 1046 return cast<CompleteMatchMatcher>(M)->Results == Results && 1047 &cast<CompleteMatchMatcher>(M)->Pattern == &Pattern; 1048 } 1049 }; 1050 1051 } // end namespace llvm 1052 1053 #endif 1054