mirror of
https://github.com/RPCSX/llvm.git
synced 2025-04-02 16:21:36 +00:00
MachineScheduler: Remember top/bottom choice in bidirectional scheduling
Remember the last choice for the top/bottom scheduling boundary in bidirectional scheduling mode. The top choice should not change if we schedule at the bottom and vice versa. This allows us to improve compiletime: We only recalculate the best pick for one border and re-use the cached top-pick from the other border. Differential Revision: http://reviews.llvm.org/D19350 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@273766 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
16fa6f1061
commit
2feb69ebcd
@ -779,6 +779,15 @@ public:
|
||||
unsigned DemandResIdx;
|
||||
|
||||
CandPolicy(): ReduceLatency(false), ReduceResIdx(0), DemandResIdx(0) {}
|
||||
|
||||
bool operator==(const CandPolicy &RHS) const {
|
||||
return ReduceLatency == RHS.ReduceLatency &&
|
||||
ReduceResIdx == RHS.ReduceResIdx &&
|
||||
DemandResIdx == RHS.DemandResIdx;
|
||||
}
|
||||
bool operator!=(const CandPolicy &RHS) const {
|
||||
return !(*this == RHS);
|
||||
}
|
||||
};
|
||||
|
||||
/// Status of an instruction's critical resource consumption.
|
||||
@ -820,8 +829,17 @@ public:
|
||||
// Critical resource consumption of the best candidate.
|
||||
SchedResourceDelta ResDelta;
|
||||
|
||||
SchedCandidate(const CandPolicy &policy)
|
||||
: Policy(policy), SU(nullptr), Reason(NoCand), AtTop(false) {}
|
||||
SchedCandidate() { reset(CandPolicy()); }
|
||||
SchedCandidate(const CandPolicy &Policy) { reset(Policy); }
|
||||
|
||||
void reset(const CandPolicy &NewPolicy) {
|
||||
Policy = NewPolicy;
|
||||
SU = nullptr;
|
||||
Reason = NoCand;
|
||||
AtTop = false;
|
||||
RPDelta = RegPressureDelta();
|
||||
ResDelta = SchedResourceDelta();
|
||||
}
|
||||
|
||||
bool isValid() const { return SU; }
|
||||
|
||||
@ -866,6 +884,11 @@ class GenericScheduler : public GenericSchedulerBase {
|
||||
SchedBoundary Top;
|
||||
SchedBoundary Bot;
|
||||
|
||||
/// Candidate last picked from Top boundary.
|
||||
SchedCandidate TopCand;
|
||||
/// Candidate last picked from Bot boundary.
|
||||
SchedCandidate BotCand;
|
||||
|
||||
MachineSchedPolicy RegionPolicy;
|
||||
public:
|
||||
GenericScheduler(const MachineSchedContext *C):
|
||||
@ -894,10 +917,12 @@ public:
|
||||
|
||||
void releaseTopNode(SUnit *SU) override {
|
||||
Top.releaseTopNode(SU);
|
||||
TopCand.SU = nullptr;
|
||||
}
|
||||
|
||||
void releaseBottomNode(SUnit *SU) override {
|
||||
Bot.releaseBottomNode(SU);
|
||||
BotCand.SU = nullptr;
|
||||
}
|
||||
|
||||
void registerRoots() override;
|
||||
|
@ -2557,6 +2557,8 @@ void GenericScheduler::initialize(ScheduleDAGMI *dag) {
|
||||
DAG->MF.getSubtarget().getInstrInfo()->CreateTargetMIHazardRecognizer(
|
||||
Itin, DAG);
|
||||
}
|
||||
TopCand.SU = nullptr;
|
||||
BotCand.SU = nullptr;
|
||||
}
|
||||
|
||||
/// Initialize the per-region scheduling policy.
|
||||
@ -2954,17 +2956,56 @@ SUnit *GenericScheduler::pickNodeBidirectional(bool &IsTopNode) {
|
||||
CandPolicy TopPolicy;
|
||||
setPolicy(TopPolicy, /*IsPostRA=*/false, Top, &Bot);
|
||||
|
||||
// Prefer bottom scheduling when heuristics are silent.
|
||||
CandPolicy NoPolicy;
|
||||
SchedCandidate Cand(NoPolicy);
|
||||
// See if BotCand is still valid (because we previously scheduled from Top).
|
||||
DEBUG(dbgs() << "Picking from Bot:\n");
|
||||
pickNodeFromQueue(Bot, BotPolicy, DAG->getBotRPTracker(), Cand);
|
||||
assert(Cand.Reason != NoCand && "failed to find the first candidate");
|
||||
if (!BotCand.isValid() || BotCand.SU->isScheduled ||
|
||||
BotCand.Policy != BotPolicy) {
|
||||
BotCand.reset(CandPolicy());
|
||||
pickNodeFromQueue(Bot, BotPolicy, DAG->getBotRPTracker(), BotCand);
|
||||
assert(BotCand.Reason != NoCand && "failed to find the first candidate");
|
||||
} else {
|
||||
DEBUG(traceCandidate(BotCand));
|
||||
#ifndef NDEBUG
|
||||
if (VerifyScheduling) {
|
||||
SchedCandidate TCand;
|
||||
TCand.reset(CandPolicy());
|
||||
pickNodeFromQueue(Bot, BotPolicy, DAG->getBotRPTracker(), TCand);
|
||||
assert(TCand.SU == BotCand.SU &&
|
||||
"Last pick result should correspond to re-picking right now");
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
// Check if the top Q has a better candidate.
|
||||
DEBUG(dbgs() << "Picking from Top:\n");
|
||||
pickNodeFromQueue(Top, TopPolicy, DAG->getTopRPTracker(), Cand);
|
||||
assert(Cand.Reason != NoCand && "failed to find the first candidate");
|
||||
if (!TopCand.isValid() || TopCand.SU->isScheduled ||
|
||||
TopCand.Policy != TopPolicy) {
|
||||
TopCand.reset(CandPolicy());
|
||||
pickNodeFromQueue(Top, TopPolicy, DAG->getTopRPTracker(), TopCand);
|
||||
assert(TopCand.Reason != NoCand && "failed to find the first candidate");
|
||||
} else {
|
||||
DEBUG(traceCandidate(TopCand));
|
||||
#ifndef NDEBUG
|
||||
if (VerifyScheduling) {
|
||||
SchedCandidate TCand;
|
||||
TCand.reset(CandPolicy());
|
||||
pickNodeFromQueue(Top, TopPolicy, DAG->getTopRPTracker(), TCand);
|
||||
assert(TCand.SU == TopCand.SU &&
|
||||
"Last pick result should correspond to re-picking right now");
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
// Pick best from BotCand and TopCand.
|
||||
assert(BotCand.isValid());
|
||||
assert(TopCand.isValid());
|
||||
SchedCandidate Cand = BotCand;
|
||||
TopCand.Reason = NoCand;
|
||||
tryCandidate(Cand, TopCand, nullptr);
|
||||
if (TopCand.Reason != NoCand) {
|
||||
Cand.setBest(TopCand);
|
||||
DEBUG(traceCandidate(Cand));
|
||||
}
|
||||
|
||||
IsTopNode = Cand.AtTop;
|
||||
tracePick(Cand);
|
||||
@ -2984,7 +3025,7 @@ SUnit *GenericScheduler::pickNode(bool &IsTopNode) {
|
||||
SU = Top.pickOnlyChoice();
|
||||
if (!SU) {
|
||||
CandPolicy NoPolicy;
|
||||
SchedCandidate TopCand(NoPolicy);
|
||||
TopCand.reset(NoPolicy);
|
||||
pickNodeFromQueue(Top, NoPolicy, DAG->getTopRPTracker(), TopCand);
|
||||
assert(TopCand.Reason != NoCand && "failed to find a candidate");
|
||||
tracePick(TopCand);
|
||||
@ -2995,7 +3036,7 @@ SUnit *GenericScheduler::pickNode(bool &IsTopNode) {
|
||||
SU = Bot.pickOnlyChoice();
|
||||
if (!SU) {
|
||||
CandPolicy NoPolicy;
|
||||
SchedCandidate BotCand(NoPolicy);
|
||||
BotCand.reset(NoPolicy);
|
||||
pickNodeFromQueue(Bot, NoPolicy, DAG->getBotRPTracker(), BotCand);
|
||||
assert(BotCand.Reason != NoCand && "failed to find a candidate");
|
||||
tracePick(BotCand);
|
||||
|
Loading…
x
Reference in New Issue
Block a user