The new isel was not properly handling patterns that covered
[oota-llvm.git] / utils / TableGen / DAGISelMatcher.h
1 //===- DAGISelMatcher.h - Representation of DAG pattern matcher -----------===//
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 TBLGEN_DAGISELMATCHER_H
11 #define TBLGEN_DAGISELMATCHER_H
12
13 #include "llvm/CodeGen/ValueTypes.h"
14 #include "llvm/ADT/OwningPtr.h"
15 #include "llvm/ADT/StringRef.h"
16 #include "llvm/ADT/SmallVector.h"
17 #include "llvm/Support/Casting.h"
18
19 namespace llvm {
20   class CodeGenDAGPatterns;
21   class MatcherNode;
22   class PatternToMatch;
23   class raw_ostream;
24   class ComplexPattern;
25   class Record;
26
27 MatcherNode *ConvertPatternToMatcher(const PatternToMatch &Pattern,
28                                      const CodeGenDAGPatterns &CGP);
29
30 void EmitMatcherTable(const MatcherNode *Matcher, raw_ostream &OS);
31
32   
33 /// MatcherNode - Base class for all the the DAG ISel Matcher representation
34 /// nodes.
35 class MatcherNode {
36   // The next matcher node that is executed after this one.  Null if this is the
37   // last stage of a match.
38   OwningPtr<MatcherNode> Next;
39 public:
40   enum KindTy {
41     // Matcher state manipulation.
42     Push,                 // Push a checking scope.
43     RecordNode,           // Record the current node.
44     RecordMemRef,         // Record the memref in the current node.
45     CaptureFlagInput,     // If the current node has an input flag, save it.
46     MoveChild,            // Move current node to specified child.
47     MoveParent,           // Move current node to parent.
48     
49     // Predicate checking.
50     CheckSame,            // Fail if not same as prev match.
51     CheckPatternPredicate,
52     CheckPredicate,       // Fail if node predicate fails.
53     CheckOpcode,          // Fail if not opcode.
54     CheckMultiOpcode,     // Fail if not in opcode list.
55     CheckType,            // Fail if not correct type.
56     CheckInteger,         // Fail if wrong val.
57     CheckCondCode,        // Fail if not condcode.
58     CheckValueType,
59     CheckComplexPat,
60     CheckAndImm,
61     CheckOrImm,
62     CheckFoldableChainNode,
63     CheckChainCompatible,
64     
65     // Node creation/emisssion.
66     EmitInteger,          // Create a TargetConstant
67     EmitStringInteger,    // Create a TargetConstant from a string.
68     EmitRegister,         // Create a register.
69     EmitConvertToTarget,  // Convert a imm/fpimm to target imm/fpimm
70     EmitMergeInputChains, // Merge together a chains for an input.
71     EmitCopyToReg,        // Emit a copytoreg into a physreg.
72     EmitNode,             // Create a DAG node
73     EmitNodeXForm,        // Run a SDNodeXForm
74     MarkFlagResults,      // Indicate which interior nodes have flag results.
75     CompleteMatch         // Finish a match and update the results.
76   };
77   const KindTy Kind;
78
79 protected:
80   MatcherNode(KindTy K) : Kind(K) {}
81 public:
82   virtual ~MatcherNode() {}
83   
84   KindTy getKind() const { return Kind; }
85
86   MatcherNode *getNext() { return Next.get(); }
87   const MatcherNode *getNext() const { return Next.get(); }
88   void setNext(MatcherNode *C) { Next.reset(C); }
89   
90   static inline bool classof(const MatcherNode *) { return true; }
91   
92   virtual void print(raw_ostream &OS, unsigned indent = 0) const = 0;
93   void dump() const;
94 protected:
95   void printNext(raw_ostream &OS, unsigned indent) const;
96 };
97   
98 /// PushMatcherNode - This pushes a failure scope on the stack and evaluates
99 /// 'Next'.  If 'Next' fails to match, it pops its scope and attempts to
100 /// match 'Failure'.
101 class PushMatcherNode : public MatcherNode {
102   OwningPtr<MatcherNode> Failure;
103 public:
104   PushMatcherNode(MatcherNode *next = 0, MatcherNode *failure = 0)
105     : MatcherNode(Push), Failure(failure) {
106     setNext(next);
107   }
108   
109   MatcherNode *getFailure() { return Failure.get(); }
110   const MatcherNode *getFailure() const { return Failure.get(); }
111   void setFailure(MatcherNode *N) { Failure.reset(N); }
112
113   static inline bool classof(const MatcherNode *N) {
114     return N->getKind() == Push;
115   }
116   
117   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
118 };
119
120 /// RecordMatcherNode - Save the current node in the operand list.
121 class RecordMatcherNode : public MatcherNode {
122   /// WhatFor - This is a string indicating why we're recording this.  This
123   /// should only be used for comment generation not anything semantic.
124   std::string WhatFor;
125 public:
126   RecordMatcherNode(const std::string &whatfor)
127     : MatcherNode(RecordNode), WhatFor(whatfor) {}
128   
129   const std::string &getWhatFor() const { return WhatFor; }
130   
131   static inline bool classof(const MatcherNode *N) {
132     return N->getKind() == RecordNode;
133   }
134   
135   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
136 };
137   
138 /// RecordMemRefMatcherNode - Save the current node's memref.
139 class RecordMemRefMatcherNode : public MatcherNode {
140 public:
141   RecordMemRefMatcherNode() : MatcherNode(RecordMemRef) {}
142   
143   static inline bool classof(const MatcherNode *N) {
144     return N->getKind() == RecordMemRef;
145   }
146   
147   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
148 };
149
150   
151 /// CaptureFlagInputMatcherNode - If the current record has a flag input, record
152 /// it so that it is used as an input to the generated code.
153 class CaptureFlagInputMatcherNode : public MatcherNode {
154 public:
155   CaptureFlagInputMatcherNode()
156     : MatcherNode(CaptureFlagInput) {}
157   
158   static inline bool classof(const MatcherNode *N) {
159     return N->getKind() == CaptureFlagInput;
160   }
161   
162   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
163 };
164   
165 /// MoveChildMatcherNode - This tells the interpreter to move into the
166 /// specified child node.
167 class MoveChildMatcherNode : public MatcherNode {
168   unsigned ChildNo;
169 public:
170   MoveChildMatcherNode(unsigned childNo)
171   : MatcherNode(MoveChild), ChildNo(childNo) {}
172   
173   unsigned getChildNo() const { return ChildNo; }
174   
175   static inline bool classof(const MatcherNode *N) {
176     return N->getKind() == MoveChild;
177   }
178   
179   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
180 };
181   
182 /// MoveParentMatcherNode - This tells the interpreter to move to the parent
183 /// of the current node.
184 class MoveParentMatcherNode : public MatcherNode {
185 public:
186   MoveParentMatcherNode()
187   : MatcherNode(MoveParent) {}
188   
189   static inline bool classof(const MatcherNode *N) {
190     return N->getKind() == MoveParent;
191   }
192   
193   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
194 };
195
196 /// CheckSameMatcherNode - This checks to see if this node is exactly the same
197 /// node as the specified match that was recorded with 'Record'.  This is used
198 /// when patterns have the same name in them, like '(mul GPR:$in, GPR:$in)'.
199 class CheckSameMatcherNode : public MatcherNode {
200   unsigned MatchNumber;
201 public:
202   CheckSameMatcherNode(unsigned matchnumber)
203   : MatcherNode(CheckSame), MatchNumber(matchnumber) {}
204   
205   unsigned getMatchNumber() const { return MatchNumber; }
206   
207   static inline bool classof(const MatcherNode *N) {
208     return N->getKind() == CheckSame;
209   }
210   
211   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
212 };
213   
214 /// CheckPatternPredicateMatcherNode - This checks the target-specific predicate
215 /// to see if the entire pattern is capable of matching.  This predicate does
216 /// not take a node as input.  This is used for subtarget feature checks etc.
217 class CheckPatternPredicateMatcherNode : public MatcherNode {
218   std::string Predicate;
219 public:
220   CheckPatternPredicateMatcherNode(StringRef predicate)
221   : MatcherNode(CheckPatternPredicate), Predicate(predicate) {}
222   
223   StringRef getPredicate() const { return Predicate; }
224   
225   static inline bool classof(const MatcherNode *N) {
226     return N->getKind() == CheckPatternPredicate;
227   }
228   
229   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
230 };
231   
232 /// CheckPredicateMatcherNode - This checks the target-specific predicate to
233 /// see if the node is acceptable.
234 class CheckPredicateMatcherNode : public MatcherNode {
235   StringRef PredName;
236 public:
237   CheckPredicateMatcherNode(StringRef predname)
238     : MatcherNode(CheckPredicate), PredName(predname) {}
239   
240   StringRef getPredicateName() const { return PredName; }
241
242   static inline bool classof(const MatcherNode *N) {
243     return N->getKind() == CheckPredicate;
244   }
245   
246   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
247 };
248   
249   
250 /// CheckOpcodeMatcherNode - This checks to see if the current node has the
251 /// specified opcode, if not it fails to match.
252 class CheckOpcodeMatcherNode : public MatcherNode {
253   StringRef OpcodeName;
254 public:
255   CheckOpcodeMatcherNode(StringRef opcodename)
256     : MatcherNode(CheckOpcode), OpcodeName(opcodename) {}
257   
258   StringRef getOpcodeName() const { return OpcodeName; }
259   
260   static inline bool classof(const MatcherNode *N) {
261     return N->getKind() == CheckOpcode;
262   }
263   
264   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
265 };
266   
267 /// CheckMultiOpcodeMatcherNode - This checks to see if the current node has one
268 /// of the specified opcode, if not it fails to match.
269 class CheckMultiOpcodeMatcherNode : public MatcherNode {
270   SmallVector<StringRef, 4> OpcodeNames;
271 public:
272   CheckMultiOpcodeMatcherNode(const StringRef *opcodes, unsigned numops)
273   : MatcherNode(CheckMultiOpcode), OpcodeNames(opcodes, opcodes+numops) {}
274   
275   unsigned getNumOpcodeNames() const { return OpcodeNames.size(); }
276   StringRef getOpcodeName(unsigned i) const { return OpcodeNames[i]; }
277   
278   static inline bool classof(const MatcherNode *N) {
279     return N->getKind() == CheckMultiOpcode;
280   }
281   
282   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
283 };
284   
285   
286   
287 /// CheckTypeMatcherNode - This checks to see if the current node has the
288 /// specified type, if not it fails to match.
289 class CheckTypeMatcherNode : public MatcherNode {
290   MVT::SimpleValueType Type;
291 public:
292   CheckTypeMatcherNode(MVT::SimpleValueType type)
293     : MatcherNode(CheckType), Type(type) {}
294   
295   MVT::SimpleValueType getType() const { return Type; }
296   
297   static inline bool classof(const MatcherNode *N) {
298     return N->getKind() == CheckType;
299   }
300   
301   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
302 };
303
304 /// CheckIntegerMatcherNode - This checks to see if the current node is a
305 /// ConstantSDNode with the specified integer value, if not it fails to match.
306 class CheckIntegerMatcherNode : public MatcherNode {
307   int64_t Value;
308 public:
309   CheckIntegerMatcherNode(int64_t value)
310     : MatcherNode(CheckInteger), Value(value) {}
311   
312   int64_t getValue() const { return Value; }
313   
314   static inline bool classof(const MatcherNode *N) {
315     return N->getKind() == CheckInteger;
316   }
317   
318   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
319 };
320   
321 /// CheckCondCodeMatcherNode - This checks to see if the current node is a
322 /// CondCodeSDNode with the specified condition, if not it fails to match.
323 class CheckCondCodeMatcherNode : public MatcherNode {
324   StringRef CondCodeName;
325 public:
326   CheckCondCodeMatcherNode(StringRef condcodename)
327   : MatcherNode(CheckCondCode), CondCodeName(condcodename) {}
328   
329   StringRef getCondCodeName() const { return CondCodeName; }
330   
331   static inline bool classof(const MatcherNode *N) {
332     return N->getKind() == CheckCondCode;
333   }
334   
335   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
336 };
337   
338 /// CheckValueTypeMatcherNode - This checks to see if the current node is a
339 /// VTSDNode with the specified type, if not it fails to match.
340 class CheckValueTypeMatcherNode : public MatcherNode {
341   StringRef TypeName;
342 public:
343   CheckValueTypeMatcherNode(StringRef type_name)
344   : MatcherNode(CheckValueType), TypeName(type_name) {}
345   
346   StringRef getTypeName() const { return TypeName; }
347
348   static inline bool classof(const MatcherNode *N) {
349     return N->getKind() == CheckValueType;
350   }
351   
352   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
353 };
354   
355   
356   
357 /// CheckComplexPatMatcherNode - This node runs the specified ComplexPattern on
358 /// the current node.
359 class CheckComplexPatMatcherNode : public MatcherNode {
360   const ComplexPattern &Pattern;
361 public:
362   CheckComplexPatMatcherNode(const ComplexPattern &pattern)
363   : MatcherNode(CheckComplexPat), Pattern(pattern) {}
364   
365   const ComplexPattern &getPattern() const { return Pattern; }
366   
367   static inline bool classof(const MatcherNode *N) {
368     return N->getKind() == CheckComplexPat;
369   }
370   
371   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
372 };
373   
374 /// CheckAndImmMatcherNode - This checks to see if the current node is an 'and'
375 /// with something equivalent to the specified immediate.
376 class CheckAndImmMatcherNode : public MatcherNode {
377   int64_t Value;
378 public:
379   CheckAndImmMatcherNode(int64_t value)
380   : MatcherNode(CheckAndImm), Value(value) {}
381   
382   int64_t getValue() const { return Value; }
383   
384   static inline bool classof(const MatcherNode *N) {
385     return N->getKind() == CheckAndImm;
386   }
387   
388   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
389 };
390
391 /// CheckOrImmMatcherNode - This checks to see if the current node is an 'and'
392 /// with something equivalent to the specified immediate.
393 class CheckOrImmMatcherNode : public MatcherNode {
394   int64_t Value;
395 public:
396   CheckOrImmMatcherNode(int64_t value)
397     : MatcherNode(CheckOrImm), Value(value) {}
398   
399   int64_t getValue() const { return Value; }
400
401   static inline bool classof(const MatcherNode *N) {
402     return N->getKind() == CheckOrImm;
403   }
404   
405   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
406 };
407
408 /// CheckFoldableChainNodeMatcherNode - This checks to see if the current node
409 /// (which defines a chain operand) is safe to fold into a larger pattern.
410 class CheckFoldableChainNodeMatcherNode : public MatcherNode {
411 public:
412   CheckFoldableChainNodeMatcherNode()
413     : MatcherNode(CheckFoldableChainNode) {}
414   
415   static inline bool classof(const MatcherNode *N) {
416     return N->getKind() == CheckFoldableChainNode;
417   }
418   
419   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
420 };
421
422 /// CheckChainCompatibleMatcherNode - Verify that the current node's chain
423 /// operand is 'compatible' with the specified recorded node's.
424 class CheckChainCompatibleMatcherNode : public MatcherNode {
425   unsigned PreviousOp;
426 public:
427   CheckChainCompatibleMatcherNode(unsigned previousop)
428     : MatcherNode(CheckChainCompatible), PreviousOp(previousop) {}
429   
430   unsigned getPreviousOp() const { return PreviousOp; }
431   
432   static inline bool classof(const MatcherNode *N) {
433     return N->getKind() == CheckChainCompatible;
434   }
435   
436   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
437 };
438   
439 /// EmitIntegerMatcherNode - This creates a new TargetConstant.
440 class EmitIntegerMatcherNode : public MatcherNode {
441   int64_t Val;
442   MVT::SimpleValueType VT;
443 public:
444   EmitIntegerMatcherNode(int64_t val, MVT::SimpleValueType vt)
445   : MatcherNode(EmitInteger), Val(val), VT(vt) {}
446   
447   int64_t getValue() const { return Val; }
448   MVT::SimpleValueType getVT() const { return VT; }
449   
450   static inline bool classof(const MatcherNode *N) {
451     return N->getKind() == EmitInteger;
452   }
453   
454   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
455 };
456
457 /// EmitStringIntegerMatcherNode - A target constant whose value is represented
458 /// by a string.
459 class EmitStringIntegerMatcherNode : public MatcherNode {
460   std::string Val;
461   MVT::SimpleValueType VT;
462 public:
463   EmitStringIntegerMatcherNode(const std::string &val, MVT::SimpleValueType vt)
464     : MatcherNode(EmitStringInteger), Val(val), VT(vt) {}
465   
466   const std::string &getValue() const { return Val; }
467   MVT::SimpleValueType getVT() const { return VT; }
468   
469   static inline bool classof(const MatcherNode *N) {
470     return N->getKind() == EmitStringInteger;
471   }
472   
473   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
474 };
475   
476 /// EmitRegisterMatcherNode - This creates a new TargetConstant.
477 class EmitRegisterMatcherNode : public MatcherNode {
478   /// Reg - The def for the register that we're emitting.  If this is null, then
479   /// this is a reference to zero_reg.
480   Record *Reg;
481   MVT::SimpleValueType VT;
482 public:
483   EmitRegisterMatcherNode(Record *reg, MVT::SimpleValueType vt)
484     : MatcherNode(EmitRegister), Reg(reg), VT(vt) {}
485   
486   Record *getReg() const { return Reg; }
487   MVT::SimpleValueType getVT() const { return VT; }
488   
489   static inline bool classof(const MatcherNode *N) {
490     return N->getKind() == EmitRegister;
491   }
492   
493   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
494 };
495
496 /// EmitConvertToTargetMatcherNode - Emit an operation that reads a specified
497 /// recorded node and converts it from being a ISD::Constant to
498 /// ISD::TargetConstant, likewise for ConstantFP.
499 class EmitConvertToTargetMatcherNode : public MatcherNode {
500   unsigned Slot;
501 public:
502   EmitConvertToTargetMatcherNode(unsigned slot)
503     : MatcherNode(EmitConvertToTarget), Slot(slot) {}
504   
505   unsigned getSlot() const { return Slot; }
506   
507   static inline bool classof(const MatcherNode *N) {
508     return N->getKind() == EmitConvertToTarget;
509   }
510   
511   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
512 };
513   
514 /// EmitMergeInputChainsMatcherNode - Emit a node that merges a list of input
515 /// chains together with a token factor.  The list of nodes are the nodes in the
516 /// matched pattern that have chain input/outputs.  This node adds all input
517 /// chains of these nodes if they are not themselves a node in the pattern.
518 class EmitMergeInputChainsMatcherNode : public MatcherNode {
519   SmallVector<unsigned, 3> ChainNodes;
520 public:
521   EmitMergeInputChainsMatcherNode(const unsigned *nodes, unsigned NumNodes)
522   : MatcherNode(EmitMergeInputChains), ChainNodes(nodes, nodes+NumNodes) {}
523   
524   unsigned getNumNodes() const { return ChainNodes.size(); }
525   
526   unsigned getNode(unsigned i) const {
527     assert(i < ChainNodes.size());
528     return ChainNodes[i];
529   }  
530   
531   static inline bool classof(const MatcherNode *N) {
532     return N->getKind() == EmitMergeInputChains;
533   }
534   
535   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
536 };
537   
538 /// EmitCopyToRegMatcherNode - Emit a CopyToReg node from a value to a physreg,
539 /// pushing the chain and flag results.
540 ///
541 class EmitCopyToRegMatcherNode : public MatcherNode {
542   unsigned SrcSlot; // Value to copy into the physreg.
543   Record *DestPhysReg;
544 public:
545   EmitCopyToRegMatcherNode(unsigned srcSlot, Record *destPhysReg)
546   : MatcherNode(EmitCopyToReg), SrcSlot(srcSlot), DestPhysReg(destPhysReg) {}
547   
548   unsigned getSrcSlot() const { return SrcSlot; }
549   Record *getDestPhysReg() const { return DestPhysReg; }
550   
551   static inline bool classof(const MatcherNode *N) {
552     return N->getKind() == EmitCopyToReg;
553   }
554   
555   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
556 };
557   
558     
559   
560 /// EmitNodeXFormMatcherNode - Emit an operation that runs an SDNodeXForm on a
561 /// recorded node and records the result.
562 class EmitNodeXFormMatcherNode : public MatcherNode {
563   unsigned Slot;
564   Record *NodeXForm;
565 public:
566   EmitNodeXFormMatcherNode(unsigned slot, Record *nodeXForm)
567   : MatcherNode(EmitNodeXForm), Slot(slot), NodeXForm(nodeXForm) {}
568   
569   unsigned getSlot() const { return Slot; }
570   Record *getNodeXForm() const { return NodeXForm; }
571   
572   static inline bool classof(const MatcherNode *N) {
573     return N->getKind() == EmitNodeXForm;
574   }
575   
576   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
577 };
578   
579 /// EmitNodeMatcherNode - This signals a successful match and generates a node.
580 class EmitNodeMatcherNode : public MatcherNode {
581   std::string OpcodeName;
582   const SmallVector<MVT::SimpleValueType, 3> VTs;
583   const SmallVector<unsigned, 6> Operands;
584   bool HasChain, HasFlag, HasMemRefs;
585   
586   /// NumFixedArityOperands - If this is a fixed arity node, this is set to -1.
587   /// If this is a varidic node, this is set to the number of fixed arity
588   /// operands in the root of the pattern.  The rest are appended to this node.
589   int NumFixedArityOperands;
590 public:
591   EmitNodeMatcherNode(const std::string &opcodeName,
592                       const MVT::SimpleValueType *vts, unsigned numvts,
593                       const unsigned *operands, unsigned numops,
594                       bool hasChain, bool hasFlag, bool hasmemrefs,
595                       int numfixedarityoperands)
596     : MatcherNode(EmitNode), OpcodeName(opcodeName),
597       VTs(vts, vts+numvts), Operands(operands, operands+numops),
598       HasChain(hasChain), HasFlag(hasFlag), HasMemRefs(hasmemrefs),
599       NumFixedArityOperands(numfixedarityoperands) {}
600   
601   const std::string &getOpcodeName() const { return OpcodeName; }
602   
603   unsigned getNumVTs() const { return VTs.size(); }
604   MVT::SimpleValueType getVT(unsigned i) const {
605     assert(i < VTs.size());
606     return VTs[i];
607   }
608   
609   unsigned getNumOperands() const { return Operands.size(); }
610   unsigned getOperand(unsigned i) const {
611     assert(i < Operands.size());
612     return Operands[i];
613   }  
614   
615   bool hasChain() const { return HasChain; }
616   bool hasFlag() const { return HasFlag; }
617   bool hasMemRefs() const { return HasMemRefs; }
618   int getNumFixedArityOperands() const { return NumFixedArityOperands; }
619   
620   static inline bool classof(const MatcherNode *N) {
621     return N->getKind() == EmitNode;
622   }
623   
624   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
625 };
626   
627 /// MarkFlagResultsMatcherNode - This node indicates which non-root nodes in the
628 /// pattern produce flags.  This allows CompleteMatchMatcherNode to update them
629 /// with the output flag of the resultant code.
630 class MarkFlagResultsMatcherNode : public MatcherNode {
631   SmallVector<unsigned, 3> FlagResultNodes;
632 public:
633   MarkFlagResultsMatcherNode(const unsigned *nodes, unsigned NumNodes)
634   : MatcherNode(MarkFlagResults), FlagResultNodes(nodes, nodes+NumNodes) {}
635   
636   unsigned getNumNodes() const { return FlagResultNodes.size(); }
637   
638   unsigned getNode(unsigned i) const {
639     assert(i < FlagResultNodes.size());
640     return FlagResultNodes[i];
641   }  
642   
643   static inline bool classof(const MatcherNode *N) {
644     return N->getKind() == MarkFlagResults;
645   }
646   
647   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
648 };
649
650 /// CompleteMatchMatcherNode - Complete a match by replacing the results of the
651 /// pattern with the newly generated nodes.  This also prints a comment
652 /// indicating the source and dest patterns.
653 class CompleteMatchMatcherNode : public MatcherNode {
654   SmallVector<unsigned, 2> Results;
655   const PatternToMatch &Pattern;
656 public:
657   CompleteMatchMatcherNode(const unsigned *results, unsigned numresults,
658                            const PatternToMatch &pattern)
659   : MatcherNode(CompleteMatch), Results(results, results+numresults),
660     Pattern(pattern) {}
661
662   unsigned getNumResults() const { return Results.size(); }
663   unsigned getResult(unsigned R) const { return Results[R]; }
664   const PatternToMatch &getPattern() const { return Pattern; }
665   
666   static inline bool classof(const MatcherNode *N) {
667     return N->getKind() == CompleteMatch;
668   }
669   
670   virtual void print(raw_ostream &OS, unsigned indent = 0) const;
671 };
672  
673   
674 } // end namespace llvm
675
676 #endif