LLVM 17.0.0git
Go to the documentation of this file.
1//=-- SystemZHazardRecognizer.h - SystemZ Hazard Recognizer -----*- C++ -*-===//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
9// This file declares a hazard recognizer for the SystemZ scheduler.
11// This class is used by the SystemZ scheduling strategy to maintain
12// the state during scheduling, and provide cost functions for
13// scheduling candidates. This includes:
15// * Decoder grouping. A decoder group can maximally hold 3 uops, and
16// instructions that always begin a new group should be scheduled when
17// the current decoder group is empty.
18// * Processor resources usage. It is beneficial to balance the use of
19// resources.
21// A goal is to consider all instructions, also those outside of any
22// scheduling region. Such instructions are "advanced" past and include
23// single instructions before a scheduling region, branches etc.
25// A block that has only one predecessor continues scheduling with the state
26// of it (which may be updated by emitting branches).
28// ===---------------------------------------------------------------------===//
33#include "SystemZSubtarget.h"
38#include "llvm/MC/MCInstrDesc.h"
40#include <string>
42namespace llvm {
44/// SystemZHazardRecognizer maintains the state for one MBB during scheduling.
47 const SystemZInstrInfo *TII;
48 const TargetSchedModel *SchedModel;
50 /// Keep track of the number of decoder slots used in the current
51 /// decoder group.
52 unsigned CurrGroupSize;
54 /// True if an instruction with four reg operands have been scheduled into
55 /// the current decoder group.
56 bool CurrGroupHas4RegOps;
58 /// The tracking of resources here are quite similar to the common
59 /// code use of a critical resource. However, z13 differs in the way
60 /// that it has two processor sides which may be interesting to
61 /// model in the future (a work in progress).
63 /// Counters for the number of uops scheduled per processor
64 /// resource.
65 SmallVector<int, 0> ProcResourceCounters;
67 /// This is the resource with the greatest queue, which the
68 /// scheduler tries to avoid.
69 unsigned CriticalResourceIdx;
71 /// Return the number of decoder slots MI requires.
72 inline unsigned getNumDecoderSlots(SUnit *SU) const;
74 /// Return true if MI fits into current decoder group.
75 bool fitsIntoCurrentGroup(SUnit *SU) const;
77 /// Return true if this instruction has four register operands.
78 bool has4RegOps(const MachineInstr *MI) const;
80 /// Two decoder groups per cycle are formed (for z13), meaning 2x3
81 /// instructions. This function returns a number between 0 and 5,
82 /// representing the current decoder slot of the current cycle. If an SU
83 /// is passed which will begin a new decoder group, the returned value is
84 /// the cycle index of the next group.
85 unsigned getCurrCycleIdx(SUnit *SU = nullptr) const;
87 /// LastFPdOpCycleIdx stores the numbeer returned by getCurrCycleIdx()
88 /// when a stalling operation is scheduled (which uses the FPd resource).
89 unsigned LastFPdOpCycleIdx;
91 /// A counter of decoder groups scheduled.
92 unsigned GrpCount;
94 unsigned getCurrGroupSize() {return CurrGroupSize;};
96 /// Start next decoder group.
97 void nextGroup();
99 /// Clear all counters for processor resources.
100 void clearProcResCounters();
102 /// With the goal of alternating processor sides for stalling (FPd)
103 /// ops, return true if it seems good to schedule an FPd op next.
104 bool isFPdOpPreferred_distance(SUnit *SU) const;
106 /// Last emitted instruction or nullptr.
107 MachineInstr *LastEmittedMI;
111 const TargetSchedModel *SM)
112 : TII(tii), SchedModel(SM) {
113 Reset();
114 }
116 HazardType getHazardType(SUnit *SU, int Stalls = 0) override;
117 void Reset() override;
118 void EmitInstruction(SUnit *SU) override;
120 /// Resolves and cache a resolved scheduling class for an SUnit.
122 if (!SU->SchedClass && SchedModel->hasInstrSchedModel())
123 SU->SchedClass = SchedModel->resolveSchedClass(SU->getInstr());
124 return SU->SchedClass;
125 }
127 /// Wrap a non-scheduled instruction in an SU and emit it.
128 void emitInstruction(MachineInstr *MI, bool TakenBranch = false);
130 // Cost functions used by SystemZPostRASchedStrategy while
131 // evaluating candidates.
133 /// Return the cost of decoder grouping for SU. If SU must start a
134 /// new decoder group, this is negative if this fits the schedule or
135 /// positive if it would mean ending a group prematurely. For normal
136 /// instructions this returns 0.
137 int groupingCost(SUnit *SU) const;
139 /// Return the cost of SU in regards to processor resources usage.
140 /// A positive value means it would be better to wait with SU, while
141 /// a negative value means it would be good to schedule SU next.
142 int resourcesCost(SUnit *SU);
144#ifndef NDEBUG
145 // Debug dumping.
146 std::string CurGroupDbg; // current group as text
147 void dumpSU(SUnit *SU, raw_ostream &OS) const;
148 void dumpCurrGroup(std::string Msg = "") const;
149 void dumpProcResourceCounters() const;
150 void dumpState() const;
155 /// Copy counters from end of single predecessor.
156 void copyState(SystemZHazardRecognizer *Incoming);
159} // namespace llvm
const HexagonInstrInfo * TII
IRTranslator LLVM IR MI
This file defines the SmallVector class.
Representation of each machine instruction.
Definition: MachineInstr.h:68
Scheduling unit. This is a node in the scheduling DAG.
Definition: ScheduleDAG.h:242
const MCSchedClassDesc * SchedClass
nullptr or resolved SchedClass.
Definition: ScheduleDAG.h:253
MachineInstr * getInstr() const
Returns the representative MachineInstr for this SUnit.
Definition: ScheduleDAG.h:373
HazardRecognizer - This determines whether or not an instruction can be issued this cycle,...
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition: SmallVector.h:1200
SystemZHazardRecognizer maintains the state for one MBB during scheduling.
int groupingCost(SUnit *SU) const
Return the cost of decoder grouping for SU.
void emitInstruction(MachineInstr *MI, bool TakenBranch=false)
Wrap a non-scheduled instruction in an SU and emit it.
const MCSchedClassDesc * getSchedClass(SUnit *SU) const
Resolves and cache a resolved scheduling class for an SUnit.
void copyState(SystemZHazardRecognizer *Incoming)
Copy counters from end of single predecessor.
void Reset() override
Reset - This callback is invoked when a new block of instructions is about to be schedule.
void dumpSU(SUnit *SU, raw_ostream &OS) const
HazardType getHazardType(SUnit *SU, int Stalls=0) override
getHazardType - Return the hazard type of emitting this node.
MachineBasicBlock::iterator getLastEmittedMI()
void dumpCurrGroup(std::string Msg="") const
int resourcesCost(SUnit *SU)
Return the cost of SU in regards to processor resources usage.
void EmitInstruction(SUnit *SU) override
EmitInstruction - This callback is invoked when an instruction is emitted, to advance the hazard stat...
SystemZHazardRecognizer(const SystemZInstrInfo *tii, const TargetSchedModel *SM)
Provide an instruction scheduling machine model to CodeGen passes.
bool hasInstrSchedModel() const
Return true if this machine model includes an instruction-level scheduling model.
const MCSchedClassDesc * resolveSchedClass(const MachineInstr *MI) const
Return the MCSchedClassDesc for this instruction.
This class implements an extremely fast bulk output stream that can only output to a stream.
Definition: raw_ostream.h:52
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
Summarize the scheduling resources required for an instruction of a particular scheduling class.
Definition: MCSchedule.h:109