1 //=- llvm/CodeGen/ScoreboardHazardRecognizer.h - Schedule Support -*- 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 // This file defines the ScoreboardHazardRecognizer class, which 11 // encapsulates hazard-avoidance heuristics for scheduling, based on the 12 // scheduling itineraries specified for the target. 13 // 14 //===----------------------------------------------------------------------===// 15 16 #ifndef LLVM_CODEGEN_SCOREBOARDHAZARDRECOGNIZER_H 17 #define LLVM_CODEGEN_SCOREBOARDHAZARDRECOGNIZER_H 18 19 #include "llvm/CodeGen/ScheduleHazardRecognizer.h" 20 #include "llvm/Support/DataTypes.h" 21 22 #include <cassert> 23 #include <cstring> 24 25 namespace llvm { 26 27 class InstrItineraryData; 28 class ScheduleDAG; 29 class SUnit; 30 31 class ScoreboardHazardRecognizer : public ScheduleHazardRecognizer { 32 // Scoreboard to track function unit usage. Scoreboard[0] is a 33 // mask of the FUs in use in the cycle currently being 34 // schedule. Scoreboard[1] is a mask for the next cycle. The 35 // Scoreboard is used as a circular buffer with the current cycle 36 // indicated by Head. 37 // 38 // Scoreboard always counts cycles in forward execution order. If used by a 39 // bottom-up scheduler, then the scoreboard cycles are the inverse of the 40 // scheduler's cycles. 41 class Scoreboard { 42 unsigned *Data; 43 44 // The maximum number of cycles monitored by the Scoreboard. This 45 // value is determined based on the target itineraries to ensure 46 // that all hazards can be tracked. 47 size_t Depth; 48 // Indices into the Scoreboard that represent the current cycle. 49 size_t Head; 50 public: Scoreboard()51 Scoreboard():Data(NULL), Depth(0), Head(0) { } ~Scoreboard()52 ~Scoreboard() { 53 delete[] Data; 54 } 55 getDepth()56 size_t getDepth() const { return Depth; } 57 unsigned& operator[](size_t idx) const { 58 // Depth is expected to be a power-of-2. 59 assert(Depth && !(Depth & (Depth - 1)) && 60 "Scoreboard was not initialized properly!"); 61 62 return Data[(Head + idx) & (Depth-1)]; 63 } 64 65 void reset(size_t d = 1) { 66 if (Data == NULL) { 67 Depth = d; 68 Data = new unsigned[Depth]; 69 } 70 71 memset(Data, 0, Depth * sizeof(Data[0])); 72 Head = 0; 73 } 74 advance()75 void advance() { 76 Head = (Head + 1) & (Depth-1); 77 } 78 recede()79 void recede() { 80 Head = (Head - 1) & (Depth-1); 81 } 82 83 // Print the scoreboard. 84 void dump() const; 85 }; 86 87 #ifndef NDEBUG 88 // Support for tracing ScoreboardHazardRecognizer as a component within 89 // another module. Follows the current thread-unsafe model of tracing. 90 static const char *DebugType; 91 #endif 92 93 // Itinerary data for the target. 94 const InstrItineraryData *ItinData; 95 96 const ScheduleDAG *DAG; 97 98 /// IssueWidth - Max issue per cycle. 0=Unknown. 99 unsigned IssueWidth; 100 101 /// IssueCount - Count instructions issued in this cycle. 102 unsigned IssueCount; 103 104 Scoreboard ReservedScoreboard; 105 Scoreboard RequiredScoreboard; 106 107 public: 108 ScoreboardHazardRecognizer(const InstrItineraryData *ItinData, 109 const ScheduleDAG *DAG, 110 const char *ParentDebugType = ""); 111 112 /// atIssueLimit - Return true if no more instructions may be issued in this 113 /// cycle. 114 virtual bool atIssueLimit() const; 115 116 // Stalls provides an cycle offset at which SU will be scheduled. It will be 117 // negative for bottom-up scheduling. 118 virtual HazardType getHazardType(SUnit *SU, int Stalls); 119 virtual void Reset(); 120 virtual void EmitInstruction(SUnit *SU); 121 virtual void AdvanceCycle(); 122 virtual void RecedeCycle(); 123 }; 124 125 } 126 127 #endif //!LLVM_CODEGEN_SCOREBOARDHAZARDRECOGNIZER_H 128