rename priorityqueue -> availablequeue. When a node is scheduled, remember
[oota-llvm.git] / lib / CodeGen / SelectionDAG / ScheduleDAGList.cpp
1 //===---- ScheduleDAGList.cpp - Implement a list scheduler for isel DAG ---===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file was developed by Evan Cheng and is distributed under the
6 // University of Illinois Open Source License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This implements bottom-up and top-down list schedulers, using standard
11 // algorithms.  The basic approach uses a priority queue of available nodes to
12 // schedule.  One at a time, nodes are taken from the priority queue (thus in
13 // priority order), checked for legality to schedule, and emitted if legal.
14 //
15 // Nodes may not be legal to schedule either due to structural hazards (e.g.
16 // pipeline or resource constraints) or because an input to the instruction has
17 // not completed execution.
18 //
19 //===----------------------------------------------------------------------===//
20
21 #define DEBUG_TYPE "sched"
22 #include "llvm/CodeGen/ScheduleDAG.h"
23 #include "llvm/Target/TargetMachine.h"
24 #include "llvm/Target/TargetInstrInfo.h"
25 #include "llvm/Support/Debug.h"
26 #include "llvm/ADT/Statistic.h"
27 #include <climits>
28 #include <iostream>
29 #include <queue>
30 #include <set>
31 #include <vector>
32 #include "llvm/Support/CommandLine.h"
33 using namespace llvm;
34
35 namespace {
36   Statistic<> NumNoops ("scheduler", "Number of noops inserted");
37   Statistic<> NumStalls("scheduler", "Number of pipeline stalls");
38
39   /// SUnit - Scheduling unit. It's an wrapper around either a single SDNode or
40   /// a group of nodes flagged together.
41   struct SUnit {
42     SDNode *Node;                       // Representative node.
43     std::vector<SDNode*> FlaggedNodes;  // All nodes flagged to Node.
44     
45     // Preds/Succs - The SUnits before/after us in the graph.  The boolean value
46     // is true if the edge is a token chain edge, false if it is a value edge. 
47     std::set<std::pair<SUnit*,bool> > Preds;  // All sunit predecessors.
48     std::set<std::pair<SUnit*,bool> > Succs;  // All sunit successors.
49
50     short NumPredsLeft;                 // # of preds not scheduled.
51     short NumSuccsLeft;                 // # of succs not scheduled.
52     short NumChainPredsLeft;            // # of chain preds not scheduled.
53     short NumChainSuccsLeft;            // # of chain succs not scheduled.
54     bool isTwoAddress     : 1;          // Is a two-address instruction.
55     bool isDefNUseOperand : 1;          // Is a def&use operand.
56     bool isAvailable      : 1;          // True once available.
57     bool isScheduled      : 1;          // True once scheduled.
58     unsigned short Latency;             // Node latency.
59     unsigned CycleBound;                // Upper/lower cycle to be scheduled at.
60     unsigned Cycle;                     // Once scheduled, the cycle of the op.
61     unsigned NodeNum;                   // Entry # of node in the node vector.
62     
63     SUnit(SDNode *node, unsigned nodenum)
64       : Node(node), NumPredsLeft(0), NumSuccsLeft(0),
65       NumChainPredsLeft(0), NumChainSuccsLeft(0),
66       isTwoAddress(false), isDefNUseOperand(false),
67       isAvailable(false), isScheduled(false), 
68       Latency(0), CycleBound(0), Cycle(0), NodeNum(nodenum) {}
69     
70     void dump(const SelectionDAG *G) const;
71     void dumpAll(const SelectionDAG *G) const;
72   };
73 }
74
75 void SUnit::dump(const SelectionDAG *G) const {
76   std::cerr << "SU: ";
77   Node->dump(G);
78   std::cerr << "\n";
79   if (FlaggedNodes.size() != 0) {
80     for (unsigned i = 0, e = FlaggedNodes.size(); i != e; i++) {
81       std::cerr << "    ";
82       FlaggedNodes[i]->dump(G);
83       std::cerr << "\n";
84     }
85   }
86 }
87
88 void SUnit::dumpAll(const SelectionDAG *G) const {
89   dump(G);
90
91   std::cerr << "  # preds left       : " << NumPredsLeft << "\n";
92   std::cerr << "  # succs left       : " << NumSuccsLeft << "\n";
93   std::cerr << "  # chain preds left : " << NumChainPredsLeft << "\n";
94   std::cerr << "  # chain succs left : " << NumChainSuccsLeft << "\n";
95   std::cerr << "  Latency            : " << Latency << "\n";
96
97   if (Preds.size() != 0) {
98     std::cerr << "  Predecessors:\n";
99     for (std::set<std::pair<SUnit*,bool> >::const_iterator I = Preds.begin(),
100            E = Preds.end(); I != E; ++I) {
101       if (I->second)
102         std::cerr << "   ch  ";
103       else
104         std::cerr << "   val ";
105       I->first->dump(G);
106     }
107   }
108   if (Succs.size() != 0) {
109     std::cerr << "  Successors:\n";
110     for (std::set<std::pair<SUnit*, bool> >::const_iterator I = Succs.begin(),
111            E = Succs.end(); I != E; ++I) {
112       if (I->second)
113         std::cerr << "   ch  ";
114       else
115         std::cerr << "   val ";
116       I->first->dump(G);
117     }
118   }
119   std::cerr << "\n";
120 }
121
122 //===----------------------------------------------------------------------===//
123 /// SchedulingPriorityQueue - This interface is used to plug different
124 /// priorities computation algorithms into the list scheduler. It implements the
125 /// interface of a standard priority queue, where nodes are inserted in 
126 /// arbitrary order and returned in priority order.  The computation of the
127 /// priority and the representation of the queue are totally up to the
128 /// implementation to decide.
129 /// 
130 namespace {
131 class SchedulingPriorityQueue {
132 public:
133   virtual ~SchedulingPriorityQueue() {}
134   
135   virtual void initNodes(const std::vector<SUnit> &SUnits) = 0;
136   virtual void releaseState() = 0;
137   
138   virtual bool empty() const = 0;
139   virtual void push(SUnit *U) = 0;
140   
141   virtual void push_all(const std::vector<SUnit *> &Nodes) = 0;
142   virtual SUnit *pop() = 0;
143   
144   /// ScheduledNode - As each node is scheduled, this method is invoked.  This
145   /// allows the priority function to adjust the priority of node that have
146   /// already been emitted.
147   virtual void ScheduledNode(SUnit *Node) {}
148 };
149 }
150
151
152
153 namespace {
154 //===----------------------------------------------------------------------===//
155 /// ScheduleDAGList - The actual list scheduler implementation.  This supports
156 /// both top-down and bottom-up scheduling.
157 ///
158 class ScheduleDAGList : public ScheduleDAG {
159 private:
160   // SDNode to SUnit mapping (many to one).
161   std::map<SDNode*, SUnit*> SUnitMap;
162   // The schedule.  Null SUnit*'s represent noop instructions.
163   std::vector<SUnit*> Sequence;
164   
165   // The scheduling units.
166   std::vector<SUnit> SUnits;
167
168   /// isBottomUp - This is true if the scheduling problem is bottom-up, false if
169   /// it is top-down.
170   bool isBottomUp;
171   
172   /// AvailableQueue - The priority queue to use for the available SUnits.
173   ///
174   SchedulingPriorityQueue *AvailableQueue;
175   
176   /// HazardRec - The hazard recognizer to use.
177   HazardRecognizer *HazardRec;
178   
179 public:
180   ScheduleDAGList(SelectionDAG &dag, MachineBasicBlock *bb,
181                   const TargetMachine &tm, bool isbottomup,
182                   SchedulingPriorityQueue *availqueue,
183                   HazardRecognizer *HR)
184     : ScheduleDAG(dag, bb, tm), isBottomUp(isbottomup), 
185       AvailableQueue(availqueue), HazardRec(HR) {
186     }
187
188   ~ScheduleDAGList() {
189     delete HazardRec;
190     delete AvailableQueue;
191   }
192
193   void Schedule();
194
195   void dumpSchedule() const;
196
197 private:
198   SUnit *NewSUnit(SDNode *N);
199   void ReleasePred(SUnit *PredSU, bool isChain, unsigned CurCycle);
200   void ReleaseSucc(SUnit *SuccSU, bool isChain, unsigned CurCycle);
201   void ScheduleNodeBottomUp(SUnit *SU, unsigned CurCycle);
202   void ScheduleNodeTopDown(SUnit *SU, unsigned CurCycle);
203   void ListScheduleTopDown();
204   void ListScheduleBottomUp();
205   void BuildSchedUnits();
206   void EmitSchedule();
207 };
208 }  // end anonymous namespace
209
210 HazardRecognizer::~HazardRecognizer() {}
211
212
213 /// NewSUnit - Creates a new SUnit and return a ptr to it.
214 SUnit *ScheduleDAGList::NewSUnit(SDNode *N) {
215   SUnits.push_back(SUnit(N, SUnits.size()));
216   return &SUnits.back();
217 }
218
219 /// BuildSchedUnits - Build SUnits from the selection dag that we are input.
220 /// This SUnit graph is similar to the SelectionDAG, but represents flagged
221 /// together nodes with a single SUnit.
222 void ScheduleDAGList::BuildSchedUnits() {
223   // Reserve entries in the vector for each of the SUnits we are creating.  This
224   // ensure that reallocation of the vector won't happen, so SUnit*'s won't get
225   // invalidated.
226   SUnits.reserve(std::distance(DAG.allnodes_begin(), DAG.allnodes_end()));
227   
228   const InstrItineraryData &InstrItins = TM.getInstrItineraryData();
229   
230   for (SelectionDAG::allnodes_iterator NI = DAG.allnodes_begin(),
231        E = DAG.allnodes_end(); NI != E; ++NI) {
232     if (isPassiveNode(NI))  // Leaf node, e.g. a TargetImmediate.
233       continue;
234     
235     // If this node has already been processed, stop now.
236     if (SUnitMap[NI]) continue;
237     
238     SUnit *NodeSUnit = NewSUnit(NI);
239     
240     // See if anything is flagged to this node, if so, add them to flagged
241     // nodes.  Nodes can have at most one flag input and one flag output.  Flags
242     // are required the be the last operand and result of a node.
243     
244     // Scan up, adding flagged preds to FlaggedNodes.
245     SDNode *N = NI;
246     while (N->getNumOperands() &&
247            N->getOperand(N->getNumOperands()-1).getValueType() == MVT::Flag) {
248       N = N->getOperand(N->getNumOperands()-1).Val;
249       NodeSUnit->FlaggedNodes.push_back(N);
250       SUnitMap[N] = NodeSUnit;
251     }
252     
253     // Scan down, adding this node and any flagged succs to FlaggedNodes if they
254     // have a user of the flag operand.
255     N = NI;
256     while (N->getValueType(N->getNumValues()-1) == MVT::Flag) {
257       SDOperand FlagVal(N, N->getNumValues()-1);
258       
259       // There are either zero or one users of the Flag result.
260       bool HasFlagUse = false;
261       for (SDNode::use_iterator UI = N->use_begin(), E = N->use_end(); 
262            UI != E; ++UI)
263         if (FlagVal.isOperand(*UI)) {
264           HasFlagUse = true;
265           NodeSUnit->FlaggedNodes.push_back(N);
266           SUnitMap[N] = NodeSUnit;
267           N = *UI;
268           break;
269         }
270           if (!HasFlagUse) break;
271     }
272     
273     // Now all flagged nodes are in FlaggedNodes and N is the bottom-most node.
274     // Update the SUnit
275     NodeSUnit->Node = N;
276     SUnitMap[N] = NodeSUnit;
277     
278     // Compute the latency for the node.  We use the sum of the latencies for
279     // all nodes flagged together into this SUnit.
280     if (InstrItins.isEmpty()) {
281       // No latency information.
282       NodeSUnit->Latency = 1;
283     } else {
284       NodeSUnit->Latency = 0;
285       if (N->isTargetOpcode()) {
286         unsigned SchedClass = TII->getSchedClass(N->getTargetOpcode());
287         InstrStage *S = InstrItins.begin(SchedClass);
288         InstrStage *E = InstrItins.end(SchedClass);
289         for (; S != E; ++S)
290           NodeSUnit->Latency += S->Cycles;
291       }
292       for (unsigned i = 0, e = NodeSUnit->FlaggedNodes.size(); i != e; ++i) {
293         SDNode *FNode = NodeSUnit->FlaggedNodes[i];
294         if (FNode->isTargetOpcode()) {
295           unsigned SchedClass = TII->getSchedClass(FNode->getTargetOpcode());
296           InstrStage *S = InstrItins.begin(SchedClass);
297           InstrStage *E = InstrItins.end(SchedClass);
298           for (; S != E; ++S)
299             NodeSUnit->Latency += S->Cycles;
300         }
301       }
302     }
303   }
304   
305   // Pass 2: add the preds, succs, etc.
306   for (unsigned su = 0, e = SUnits.size(); su != e; ++su) {
307     SUnit *SU = &SUnits[su];
308     SDNode *MainNode = SU->Node;
309     
310     if (MainNode->isTargetOpcode() &&
311         TII->isTwoAddrInstr(MainNode->getTargetOpcode()))
312       SU->isTwoAddress = true;
313     
314     // Find all predecessors and successors of the group.
315     // Temporarily add N to make code simpler.
316     SU->FlaggedNodes.push_back(MainNode);
317     
318     for (unsigned n = 0, e = SU->FlaggedNodes.size(); n != e; ++n) {
319       SDNode *N = SU->FlaggedNodes[n];
320       
321       for (unsigned i = 0, e = N->getNumOperands(); i != e; ++i) {
322         SDNode *OpN = N->getOperand(i).Val;
323         if (isPassiveNode(OpN)) continue;   // Not scheduled.
324         SUnit *OpSU = SUnitMap[OpN];
325         assert(OpSU && "Node has no SUnit!");
326         if (OpSU == SU) continue;           // In the same group.
327         
328         MVT::ValueType OpVT = N->getOperand(i).getValueType();
329         assert(OpVT != MVT::Flag && "Flagged nodes should be in same sunit!");
330         bool isChain = OpVT == MVT::Other;
331         
332         if (SU->Preds.insert(std::make_pair(OpSU, isChain)).second) {
333           if (!isChain) {
334             SU->NumPredsLeft++;
335           } else {
336             SU->NumChainPredsLeft++;
337           }
338         }
339         if (OpSU->Succs.insert(std::make_pair(SU, isChain)).second) {
340           if (!isChain) {
341             OpSU->NumSuccsLeft++;
342           } else {
343             OpSU->NumChainSuccsLeft++;
344           }
345         }
346       }
347     }
348     
349     // Remove MainNode from FlaggedNodes again.
350     SU->FlaggedNodes.pop_back();
351   }
352   DEBUG(for (unsigned su = 0, e = SUnits.size(); su != e; ++su)
353         SUnits[su].dumpAll(&DAG));
354 }
355
356 /// EmitSchedule - Emit the machine code in scheduled order.
357 void ScheduleDAGList::EmitSchedule() {
358   std::map<SDNode*, unsigned> VRBaseMap;
359   for (unsigned i = 0, e = Sequence.size(); i != e; i++) {
360     if (SUnit *SU = Sequence[i]) {
361       for (unsigned j = 0, ee = SU->FlaggedNodes.size(); j != ee; j++)
362         EmitNode(SU->FlaggedNodes[j], VRBaseMap);
363       EmitNode(SU->Node, VRBaseMap);
364     } else {
365       // Null SUnit* is a noop.
366       EmitNoop();
367     }
368   }
369 }
370
371 /// dump - dump the schedule.
372 void ScheduleDAGList::dumpSchedule() const {
373   for (unsigned i = 0, e = Sequence.size(); i != e; i++) {
374     if (SUnit *SU = Sequence[i])
375       SU->dump(&DAG);
376     else
377       std::cerr << "**** NOOP ****\n";
378   }
379 }
380
381 /// Schedule - Schedule the DAG using list scheduling.
382 /// FIXME: Right now it only supports the burr (bottom up register reducing)
383 /// heuristic.
384 void ScheduleDAGList::Schedule() {
385   DEBUG(std::cerr << "********** List Scheduling **********\n");
386   
387   // Build scheduling units.
388   BuildSchedUnits();
389   
390   AvailableQueue->initNodes(SUnits);
391   
392   // Execute the actual scheduling loop Top-Down or Bottom-Up as appropriate.
393   if (isBottomUp)
394     ListScheduleBottomUp();
395   else
396     ListScheduleTopDown();
397   
398   AvailableQueue->releaseState();
399   
400   DEBUG(std::cerr << "*** Final schedule ***\n");
401   DEBUG(dumpSchedule());
402   DEBUG(std::cerr << "\n");
403   
404   // Emit in scheduled order
405   EmitSchedule();
406 }
407
408 //===----------------------------------------------------------------------===//
409 //  Bottom-Up Scheduling
410 //===----------------------------------------------------------------------===//
411
412 /// ReleasePred - Decrement the NumSuccsLeft count of a predecessor. Add it to
413 /// the Available queue is the count reaches zero. Also update its cycle bound.
414 void ScheduleDAGList::ReleasePred(SUnit *PredSU, bool isChain, 
415                                   unsigned CurCycle) {
416   // FIXME: the distance between two nodes is not always == the predecessor's
417   // latency. For example, the reader can very well read the register written
418   // by the predecessor later than the issue cycle. It also depends on the
419   // interrupt model (drain vs. freeze).
420   PredSU->CycleBound = std::max(PredSU->CycleBound, CurCycle + PredSU->Latency);
421
422   if (!isChain)
423     PredSU->NumSuccsLeft--;
424   else
425     PredSU->NumChainSuccsLeft--;
426   
427 #ifndef NDEBUG
428   if (PredSU->NumSuccsLeft < 0 || PredSU->NumChainSuccsLeft < 0) {
429     std::cerr << "*** List scheduling failed! ***\n";
430     PredSU->dump(&DAG);
431     std::cerr << " has been released too many times!\n";
432     assert(0);
433   }
434 #endif
435   
436   if ((PredSU->NumSuccsLeft + PredSU->NumChainSuccsLeft) == 0) {
437     // EntryToken has to go last!  Special case it here.
438     if (PredSU->Node->getOpcode() != ISD::EntryToken) {
439       PredSU->isAvailable = true;
440       AvailableQueue->push(PredSU);
441     }
442   }
443 }
444 /// ScheduleNodeBottomUp - Add the node to the schedule. Decrement the pending
445 /// count of its predecessors. If a predecessor pending count is zero, add it to
446 /// the Available queue.
447 void ScheduleDAGList::ScheduleNodeBottomUp(SUnit *SU, unsigned CurCycle) {
448   DEBUG(std::cerr << "*** Scheduling: ");
449   DEBUG(SU->dump(&DAG));
450   SU->Cycle = CurCycle;
451
452   Sequence.push_back(SU);
453
454   // Bottom up: release predecessors
455   for (std::set<std::pair<SUnit*, bool> >::iterator I = SU->Preds.begin(),
456          E = SU->Preds.end(); I != E; ++I) {
457     ReleasePred(I->first, I->second, CurCycle);
458     // FIXME: This is something used by the priority function that it should
459     // calculate directly.
460     if (!I->second)
461       SU->NumPredsLeft--;
462   }
463 }
464
465 /// isReady - True if node's lower cycle bound is less or equal to the current
466 /// scheduling cycle. Always true if all nodes have uniform latency 1.
467 static inline bool isReady(SUnit *SU, unsigned CurrCycle) {
468   return SU->CycleBound <= CurrCycle;
469 }
470
471 /// ListScheduleBottomUp - The main loop of list scheduling for bottom-up
472 /// schedulers.
473 void ScheduleDAGList::ListScheduleBottomUp() {
474   unsigned CurrCycle = 0;
475   // Add root to Available queue.
476   AvailableQueue->push(SUnitMap[DAG.getRoot().Val]);
477
478   // While Available queue is not empty, grab the node with the highest
479   // priority. If it is not ready put it back. Schedule the node.
480   std::vector<SUnit*> NotReady;
481   while (!AvailableQueue->empty()) {
482     SUnit *CurrNode = AvailableQueue->pop();
483
484     while (!isReady(CurrNode, CurrCycle)) {
485       NotReady.push_back(CurrNode);
486       CurrNode = AvailableQueue->pop();
487     }
488     
489     // Add the nodes that aren't ready back onto the available list.
490     AvailableQueue->push_all(NotReady);
491     NotReady.clear();
492
493     ScheduleNodeBottomUp(CurrNode, CurrCycle);
494     CurrCycle++;
495     CurrNode->isScheduled = true;
496     AvailableQueue->ScheduledNode(CurrNode);
497   }
498
499   // Add entry node last
500   if (DAG.getEntryNode().Val != DAG.getRoot().Val) {
501     SUnit *Entry = SUnitMap[DAG.getEntryNode().Val];
502     Sequence.push_back(Entry);
503   }
504
505   // Reverse the order if it is bottom up.
506   std::reverse(Sequence.begin(), Sequence.end());
507   
508   
509 #ifndef NDEBUG
510   // Verify that all SUnits were scheduled.
511   bool AnyNotSched = false;
512   for (unsigned i = 0, e = SUnits.size(); i != e; ++i) {
513     if (SUnits[i].NumSuccsLeft != 0 || SUnits[i].NumChainSuccsLeft != 0) {
514       if (!AnyNotSched)
515         std::cerr << "*** List scheduling failed! ***\n";
516       SUnits[i].dump(&DAG);
517       std::cerr << "has not been scheduled!\n";
518       AnyNotSched = true;
519     }
520   }
521   assert(!AnyNotSched);
522 #endif
523 }
524
525 //===----------------------------------------------------------------------===//
526 //  Top-Down Scheduling
527 //===----------------------------------------------------------------------===//
528
529 /// ReleaseSucc - Decrement the NumPredsLeft count of a successor. Add it to
530 /// the Available queue is the count reaches zero. Also update its cycle bound.
531 void ScheduleDAGList::ReleaseSucc(SUnit *SuccSU, bool isChain,
532                                   unsigned CurCycle) {
533   // FIXME: the distance between two nodes is not always == the predecessor's
534   // latency. For example, the reader can very well read the register written
535   // by the predecessor later than the issue cycle. It also depends on the
536   // interrupt model (drain vs. freeze).
537   SuccSU->CycleBound = std::max(SuccSU->CycleBound, CurCycle + SuccSU->Latency);
538   
539   if (!isChain)
540     SuccSU->NumPredsLeft--;
541   else
542     SuccSU->NumChainPredsLeft--;
543   
544 #ifndef NDEBUG
545   if (SuccSU->NumPredsLeft < 0 || SuccSU->NumChainPredsLeft < 0) {
546     std::cerr << "*** List scheduling failed! ***\n";
547     SuccSU->dump(&DAG);
548     std::cerr << " has been released too many times!\n";
549     abort();
550   }
551 #endif
552   
553   if ((SuccSU->NumPredsLeft + SuccSU->NumChainPredsLeft) == 0) {
554     SuccSU->isAvailable = true;
555     AvailableQueue->push(SuccSU);
556   }
557 }
558
559 /// ScheduleNodeTopDown - Add the node to the schedule. Decrement the pending
560 /// count of its successors. If a successor pending count is zero, add it to
561 /// the Available queue.
562 void ScheduleDAGList::ScheduleNodeTopDown(SUnit *SU, unsigned CurCycle) {
563   DEBUG(std::cerr << "*** Scheduling: ");
564   DEBUG(SU->dump(&DAG));
565   
566   Sequence.push_back(SU);
567   SU->Cycle = CurCycle;
568   
569   // Bottom up: release successors.
570   for (std::set<std::pair<SUnit*, bool> >::iterator I = SU->Succs.begin(),
571        E = SU->Succs.end(); I != E; ++I)
572     ReleaseSucc(I->first, I->second, CurCycle);
573 }
574
575 /// ListScheduleTopDown - The main loop of list scheduling for top-down
576 /// schedulers.
577 void ScheduleDAGList::ListScheduleTopDown() {
578   unsigned CurrCycle = 0;
579   // Emit the entry node first.
580   SUnit *Entry = SUnitMap[DAG.getEntryNode().Val];
581   ScheduleNodeTopDown(Entry, CurrCycle);
582   HazardRec->EmitInstruction(Entry->Node);
583                       
584   // All leaves to Available queue.
585   for (unsigned i = 0, e = SUnits.size(); i != e; ++i) {
586     // It is available if it has no predecessors.
587     if (SUnits[i].Preds.size() == 0 && &SUnits[i] != Entry)
588       AvailableQueue->push(&SUnits[i]);
589   }
590   
591   // While Available queue is not empty, grab the node with the highest
592   // priority. If it is not ready put it back.  Schedule the node.
593   std::vector<SUnit*> NotReady;
594   while (!AvailableQueue->empty()) {
595     SUnit *FoundNode = 0;
596
597     bool HasNoopHazards = false;
598     do {
599       SUnit *CurNode = AvailableQueue->pop();
600       
601       // Get the node represented by this SUnit.
602       SDNode *N = CurNode->Node;
603       // If this is a pseudo op, like copyfromreg, look to see if there is a
604       // real target node flagged to it.  If so, use the target node.
605       for (unsigned i = 0, e = CurNode->FlaggedNodes.size(); 
606            N->getOpcode() < ISD::BUILTIN_OP_END && i != e; ++i)
607         N = CurNode->FlaggedNodes[i];
608       
609       HazardRecognizer::HazardType HT = HazardRec->getHazardType(N);
610       if (HT == HazardRecognizer::NoHazard) {
611         FoundNode = CurNode;
612         break;
613       }
614       
615       // Remember if this is a noop hazard.
616       HasNoopHazards |= HT == HazardRecognizer::NoopHazard;
617       
618       NotReady.push_back(CurNode);
619     } while (!AvailableQueue->empty());
620     
621     // Add the nodes that aren't ready back onto the available list.
622     AvailableQueue->push_all(NotReady);
623     NotReady.clear();
624
625     // If we found a node to schedule, do it now.
626     if (FoundNode) {
627       ScheduleNodeTopDown(FoundNode, CurrCycle);
628       CurrCycle++;   // Fixme don't increment for pseudo-ops!
629       HazardRec->EmitInstruction(FoundNode->Node);
630       FoundNode->isScheduled = true;
631       AvailableQueue->ScheduledNode(FoundNode);
632     } else if (!HasNoopHazards) {
633       // Otherwise, we have a pipeline stall, but no other problem, just advance
634       // the current cycle and try again.
635       DEBUG(std::cerr << "*** Advancing cycle, no work to do\n");
636       HazardRec->AdvanceCycle();
637       ++NumStalls;
638     } else {
639       // Otherwise, we have no instructions to issue and we have instructions
640       // that will fault if we don't do this right.  This is the case for
641       // processors without pipeline interlocks and other cases.
642       DEBUG(std::cerr << "*** Emitting noop\n");
643       HazardRec->EmitNoop();
644       Sequence.push_back(0);   // NULL SUnit* -> noop
645       ++NumNoops;
646     }
647   }
648
649 #ifndef NDEBUG
650   // Verify that all SUnits were scheduled.
651   bool AnyNotSched = false;
652   for (unsigned i = 0, e = SUnits.size(); i != e; ++i) {
653     if (SUnits[i].NumPredsLeft != 0 || SUnits[i].NumChainPredsLeft != 0) {
654       if (!AnyNotSched)
655         std::cerr << "*** List scheduling failed! ***\n";
656       SUnits[i].dump(&DAG);
657       std::cerr << "has not been scheduled!\n";
658       AnyNotSched = true;
659     }
660   }
661   assert(!AnyNotSched);
662 #endif
663 }
664
665 //===----------------------------------------------------------------------===//
666 //                RegReductionPriorityQueue Implementation
667 //===----------------------------------------------------------------------===//
668 //
669 // This is a SchedulingPriorityQueue that schedules using Sethi Ullman numbers
670 // to reduce register pressure.
671 // 
672 namespace {
673   class RegReductionPriorityQueue;
674   
675   /// Sorting functions for the Available queue.
676   struct ls_rr_sort : public std::binary_function<SUnit*, SUnit*, bool> {
677     RegReductionPriorityQueue *SPQ;
678     ls_rr_sort(RegReductionPriorityQueue *spq) : SPQ(spq) {}
679     ls_rr_sort(const ls_rr_sort &RHS) : SPQ(RHS.SPQ) {}
680     
681     bool operator()(const SUnit* left, const SUnit* right) const;
682   };
683 }  // end anonymous namespace
684
685 namespace {
686   class RegReductionPriorityQueue : public SchedulingPriorityQueue {
687     // SUnits - The SUnits for the current graph.
688     const std::vector<SUnit> *SUnits;
689     
690     // SethiUllmanNumbers - The SethiUllman number for each node.
691     std::vector<int> SethiUllmanNumbers;
692     
693     std::priority_queue<SUnit*, std::vector<SUnit*>, ls_rr_sort> Queue;
694   public:
695     RegReductionPriorityQueue() : Queue(ls_rr_sort(this)) {
696     }
697     
698     void initNodes(const std::vector<SUnit> &sunits) {
699       SUnits = &sunits;
700       // Calculate node priorities.
701       CalculatePriorities();
702     }
703     void releaseState() {
704       SUnits = 0;
705       SethiUllmanNumbers.clear();
706     }
707     
708     unsigned getSethiUllmanNumber(unsigned NodeNum) const {
709       assert(NodeNum < SethiUllmanNumbers.size());
710       return SethiUllmanNumbers[NodeNum];
711     }
712     
713     bool empty() const { return Queue.empty(); }
714     
715     void push(SUnit *U) {
716       Queue.push(U);
717     }
718     void push_all(const std::vector<SUnit *> &Nodes) {
719       for (unsigned i = 0, e = Nodes.size(); i != e; ++i)
720         Queue.push(Nodes[i]);
721     }
722     
723     SUnit *pop() {
724       SUnit *V = Queue.top();
725       Queue.pop();
726       return V;
727     }
728   private:
729     void CalculatePriorities();
730     int CalcNodePriority(const SUnit *SU);
731   };
732 }
733
734 bool ls_rr_sort::operator()(const SUnit *left, const SUnit *right) const {
735   unsigned LeftNum  = left->NodeNum;
736   unsigned RightNum = right->NodeNum;
737   
738   int LBonus = (int)left ->isDefNUseOperand;
739   int RBonus = (int)right->isDefNUseOperand;
740   
741   // Special tie breaker: if two nodes share a operand, the one that
742   // use it as a def&use operand is preferred.
743   if (left->isTwoAddress && !right->isTwoAddress) {
744     SDNode *DUNode = left->Node->getOperand(0).Val;
745     if (DUNode->isOperand(right->Node))
746       LBonus++;
747   }
748   if (!left->isTwoAddress && right->isTwoAddress) {
749     SDNode *DUNode = right->Node->getOperand(0).Val;
750     if (DUNode->isOperand(left->Node))
751       RBonus++;
752   }
753   
754   // Priority1 is just the number of live range genned.
755   int LPriority1 = left ->NumPredsLeft - LBonus;
756   int RPriority1 = right->NumPredsLeft - RBonus;
757   int LPriority2 = SPQ->getSethiUllmanNumber(LeftNum) + LBonus;
758   int RPriority2 = SPQ->getSethiUllmanNumber(RightNum) + RBonus;
759   
760   if (LPriority1 > RPriority1)
761     return true;
762   else if (LPriority1 == RPriority1)
763     if (LPriority2 < RPriority2)
764       return true;
765     else if (LPriority2 == RPriority2)
766       if (left->CycleBound > right->CycleBound) 
767         return true;
768   
769   return false;
770 }
771
772
773 /// CalcNodePriority - Priority is the Sethi Ullman number. 
774 /// Smaller number is the higher priority.
775 int RegReductionPriorityQueue::CalcNodePriority(const SUnit *SU) {
776   int &SethiUllmanNumber = SethiUllmanNumbers[SU->NodeNum];
777   if (SethiUllmanNumber != INT_MIN)
778     return SethiUllmanNumber;
779   
780   if (SU->Preds.size() == 0) {
781     SethiUllmanNumber = 1;
782   } else {
783     int Extra = 0;
784     for (std::set<std::pair<SUnit*, bool> >::const_iterator
785          I = SU->Preds.begin(), E = SU->Preds.end(); I != E; ++I) {
786       if (I->second) continue;  // ignore chain preds.
787       SUnit *PredSU = I->first;
788       int PredSethiUllman = CalcNodePriority(PredSU);
789       if (PredSethiUllman > SethiUllmanNumber) {
790         SethiUllmanNumber = PredSethiUllman;
791         Extra = 0;
792       } else if (PredSethiUllman == SethiUllmanNumber)
793         Extra++;
794     }
795     
796     if (SU->Node->getOpcode() != ISD::TokenFactor)
797       SethiUllmanNumber += Extra;
798     else
799       SethiUllmanNumber = (Extra == 1) ? 0 : Extra-1;
800   }
801   
802   return SethiUllmanNumber;
803 }
804
805 /// CalculatePriorities - Calculate priorities of all scheduling units.
806 void RegReductionPriorityQueue::CalculatePriorities() {
807   SethiUllmanNumbers.assign(SUnits->size(), INT_MIN);
808   
809   for (unsigned i = 0, e = SUnits->size(); i != e; ++i)
810     CalcNodePriority(&(*SUnits)[i]);
811 }
812
813 //===----------------------------------------------------------------------===//
814 //                    LatencyPriorityQueue Implementation
815 //===----------------------------------------------------------------------===//
816 //
817 // This is a SchedulingPriorityQueue that schedules using latency information to
818 // reduce the length of the critical path through the basic block.
819 // 
820 namespace {
821   class LatencyPriorityQueue;
822   
823   /// Sorting functions for the Available queue.
824   struct latency_sort : public std::binary_function<SUnit*, SUnit*, bool> {
825     LatencyPriorityQueue *PQ;
826     latency_sort(LatencyPriorityQueue *pq) : PQ(pq) {}
827     latency_sort(const latency_sort &RHS) : PQ(RHS.PQ) {}
828     
829     bool operator()(const SUnit* left, const SUnit* right) const;
830   };
831 }  // end anonymous namespace
832
833 namespace {
834   class LatencyPriorityQueue : public SchedulingPriorityQueue {
835     // SUnits - The SUnits for the current graph.
836     const std::vector<SUnit> *SUnits;
837     
838     // Latencies - The latency (max of latency from this node to the bb exit)
839     // for each node.
840     std::vector<int> Latencies;
841
842     /// NumNodesSolelyBlocking - This vector contains, for every node in the
843     /// Queue, the number of nodes that the node is the sole unscheduled
844     /// predecessor for.  This is used as a tie-breaker heuristic for better
845     /// mobility.
846     std::vector<unsigned> NumNodesSolelyBlocking;
847
848     std::priority_queue<SUnit*, std::vector<SUnit*>, latency_sort> Queue;
849 public:
850     LatencyPriorityQueue() : Queue(latency_sort(this)) {
851     }
852     
853     void initNodes(const std::vector<SUnit> &sunits) {
854       SUnits = &sunits;
855       // Calculate node priorities.
856       CalculatePriorities();
857     }
858     void releaseState() {
859       SUnits = 0;
860       Latencies.clear();
861     }
862     
863     unsigned getLatency(unsigned NodeNum) const {
864       assert(NodeNum < Latencies.size());
865       return Latencies[NodeNum];
866     }
867     
868     unsigned getNumSolelyBlockNodes(unsigned NodeNum) const {
869       assert(NodeNum < NumNodesSolelyBlocking.size());
870       return NumNodesSolelyBlocking[NodeNum];
871     }
872     
873     bool empty() const { return Queue.empty(); }
874     
875     virtual void push(SUnit *U) {
876       push_impl(U);
877     }
878     void push_impl(SUnit *U);
879     
880     void push_all(const std::vector<SUnit *> &Nodes) {
881       for (unsigned i = 0, e = Nodes.size(); i != e; ++i)
882         push_impl(Nodes[i]);
883     }
884     
885     SUnit *pop() {
886       SUnit *V = Queue.top();
887       Queue.pop();
888       return V;
889     }
890     
891     // ScheduledNode - As nodes are scheduled, we look to see if there are any
892     // successor nodes that have a single unscheduled predecessor.  If so, that
893     // single predecessor has a higher priority, since scheduling it will make
894     // the node available.
895     void ScheduledNode(SUnit *Node);
896     
897 private:
898     void CalculatePriorities();
899     int CalcLatency(const SUnit &SU);
900     void AdjustPriorityOfUnscheduledPreds(SUnit *SU);
901     
902     /// RemoveFromPriorityQueue - This is a really inefficient way to remove a
903     /// node from a priority queue.  We should roll our own heap to make this
904     /// better or something.
905     void RemoveFromPriorityQueue(SUnit *SU) {
906       std::vector<SUnit*> Temp;
907       
908       assert(!Queue.empty() && "Not in queue!");
909       while (Queue.top() != SU) {
910         Temp.push_back(Queue.top());
911         Queue.pop();
912         assert(!Queue.empty() && "Not in queue!");
913       }
914
915       // Remove the node from the PQ.
916       Queue.pop();
917       
918       // Add all the other nodes back.
919       for (unsigned i = 0, e = Temp.size(); i != e; ++i)
920         Queue.push(Temp[i]);
921     }
922   };
923 }
924
925 bool latency_sort::operator()(const SUnit *LHS, const SUnit *RHS) const {
926   unsigned LHSNum = LHS->NodeNum;
927   unsigned RHSNum = RHS->NodeNum;
928
929   // The most important heuristic is scheduling the critical path.
930   unsigned LHSLatency = PQ->getLatency(LHSNum);
931   unsigned RHSLatency = PQ->getLatency(RHSNum);
932   if (LHSLatency < RHSLatency) return true;
933   if (LHSLatency > RHSLatency) return false;
934   
935   // After that, if two nodes have identical latencies, look to see if one will
936   // unblock more other nodes than the other.
937   unsigned LHSBlocked = PQ->getNumSolelyBlockNodes(LHSNum);
938   unsigned RHSBlocked = PQ->getNumSolelyBlockNodes(RHSNum);
939   if (LHSBlocked < RHSBlocked) return true;
940   if (LHSBlocked > RHSBlocked) return false;
941   
942   // Finally, just to provide a stable ordering, use the node number as a
943   // deciding factor.
944   return LHSNum < RHSNum;
945 }
946
947
948 /// CalcNodePriority - Calculate the maximal path from the node to the exit.
949 ///
950 int LatencyPriorityQueue::CalcLatency(const SUnit &SU) {
951   int &Latency = Latencies[SU.NodeNum];
952   if (Latency != -1)
953     return Latency;
954   
955   int MaxSuccLatency = 0;
956   for (std::set<std::pair<SUnit*, bool> >::const_iterator I = SU.Succs.begin(),
957        E = SU.Succs.end(); I != E; ++I)
958     MaxSuccLatency = std::max(MaxSuccLatency, CalcLatency(*I->first));
959
960   return Latency = MaxSuccLatency + SU.Latency;
961 }
962
963 /// CalculatePriorities - Calculate priorities of all scheduling units.
964 void LatencyPriorityQueue::CalculatePriorities() {
965   Latencies.assign(SUnits->size(), -1);
966   NumNodesSolelyBlocking.assign(SUnits->size(), 0);
967   
968   for (unsigned i = 0, e = SUnits->size(); i != e; ++i)
969     CalcLatency((*SUnits)[i]);
970 }
971
972 /// getSingleUnscheduledPred - If there is exactly one unscheduled predecessor
973 /// of SU, return it, otherwise return null.
974 static SUnit *getSingleUnscheduledPred(SUnit *SU) {
975   SUnit *OnlyAvailablePred = 0;
976   for (std::set<std::pair<SUnit*, bool> >::const_iterator I = SU->Preds.begin(),
977        E = SU->Preds.end(); I != E; ++I)
978     if (!I->first->isScheduled) {
979       // We found an available, but not scheduled, predecessor.  If it's the
980       // only one we have found, keep track of it... otherwise give up.
981       if (OnlyAvailablePred && OnlyAvailablePred != I->first)
982         return 0;
983       OnlyAvailablePred = I->first;
984     }
985       
986   return OnlyAvailablePred;
987 }
988
989 void LatencyPriorityQueue::push_impl(SUnit *SU) {
990   // Look at all of the successors of this node.  Count the number of nodes that
991   // this node is the sole unscheduled node for.
992   unsigned NumNodesBlocking = 0;
993   for (std::set<std::pair<SUnit*, bool> >::const_iterator I = SU->Succs.begin(),
994        E = SU->Succs.end(); I != E; ++I)
995     if (getSingleUnscheduledPred(I->first) == SU)
996       ++NumNodesBlocking;
997   NumNodesSolelyBlocking[SU->NodeNum] = NumNodesBlocking;
998   
999   Queue.push(SU);
1000 }
1001
1002
1003 // ScheduledNode - As nodes are scheduled, we look to see if there are any
1004 // successor nodes that have a single unscheduled predecessor.  If so, that
1005 // single predecessor has a higher priority, since scheduling it will make
1006 // the node available.
1007 void LatencyPriorityQueue::ScheduledNode(SUnit *SU) {
1008   for (std::set<std::pair<SUnit*, bool> >::const_iterator I = SU->Succs.begin(),
1009        E = SU->Succs.end(); I != E; ++I)
1010     AdjustPriorityOfUnscheduledPreds(I->first);
1011 }
1012
1013 /// AdjustPriorityOfUnscheduledPreds - One of the predecessors of SU was just
1014 /// scheduled.  If SU is not itself available, then there is at least one
1015 /// predecessor node that has not been scheduled yet.  If SU has exactly ONE
1016 /// unscheduled predecessor, we want to increase its priority: it getting
1017 /// scheduled will make this node available, so it is better than some other
1018 /// node of the same priority that will not make a node available.
1019 void LatencyPriorityQueue::AdjustPriorityOfUnscheduledPreds(SUnit *SU) {
1020   if (SU->isAvailable) return;  // All preds scheduled.
1021   
1022   SUnit *OnlyAvailablePred = getSingleUnscheduledPred(SU);
1023   if (OnlyAvailablePred == 0 || !OnlyAvailablePred->isAvailable) return;
1024   
1025   // Okay, we found a single predecessor that is available, but not scheduled.
1026   // Since it is available, it must be in the priority queue.  First remove it.
1027   RemoveFromPriorityQueue(OnlyAvailablePred);
1028
1029   // Reinsert the node into the priority queue, which recomputes its
1030   // NumNodesSolelyBlocking value.
1031   push(OnlyAvailablePred);
1032 }
1033
1034
1035 //===----------------------------------------------------------------------===//
1036 //                         Public Constructor Functions
1037 //===----------------------------------------------------------------------===//
1038
1039 llvm::ScheduleDAG* llvm::createBURRListDAGScheduler(SelectionDAG &DAG,
1040                                                     MachineBasicBlock *BB) {
1041   return new ScheduleDAGList(DAG, BB, DAG.getTarget(), true, 
1042                              new RegReductionPriorityQueue(),
1043                              new HazardRecognizer());
1044 }
1045
1046 /// createTDListDAGScheduler - This creates a top-down list scheduler with the
1047 /// specified hazard recognizer.
1048 ScheduleDAG* llvm::createTDListDAGScheduler(SelectionDAG &DAG,
1049                                             MachineBasicBlock *BB,
1050                                             HazardRecognizer *HR) {
1051   return new ScheduleDAGList(DAG, BB, DAG.getTarget(), false,
1052                              new LatencyPriorityQueue(),
1053                              HR);
1054 }