aboutsummaryrefslogtreecommitdiff
path: root/lib/CodeGen/TargetSchedule.cpp
diff options
context:
space:
mode:
authorAndrew Trick <atrick@apple.com>2012-10-10 05:43:09 +0000
committerAndrew Trick <atrick@apple.com>2012-10-10 05:43:09 +0000
commit412cd2f81374865dfa708bef6d5b896ca10dece0 (patch)
treeb31990739e14173a9c6ba0bd63b07a5473fc4c3a /lib/CodeGen/TargetSchedule.cpp
parent6312cb099734263f348f36a31b8892b1373a7076 (diff)
misched: Use the TargetSchedModel interface wherever possible.
Allows the new machine model to be used for NumMicroOps and OutputLatency. Allows the HazardRecognizer to be disabled along with itineraries. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@165603 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/CodeGen/TargetSchedule.cpp')
-rw-r--r--lib/CodeGen/TargetSchedule.cpp49
1 files changed, 49 insertions, 0 deletions
diff --git a/lib/CodeGen/TargetSchedule.cpp b/lib/CodeGen/TargetSchedule.cpp
index cf9d059492..edf68157ea 100644
--- a/lib/CodeGen/TargetSchedule.cpp
+++ b/lib/CodeGen/TargetSchedule.cpp
@@ -14,6 +14,7 @@
#include "llvm/CodeGen/TargetSchedule.h"
#include "llvm/Target/TargetInstrInfo.h"
+#include "llvm/Target/TargetMachine.h"
#include "llvm/Target/TargetRegisterInfo.h"
#include "llvm/Target/TargetSubtargetInfo.h"
#include "llvm/Support/CommandLine.h"
@@ -44,6 +45,17 @@ void TargetSchedModel::init(const MCSchedModel &sm,
STI->initInstrItins(InstrItins);
}
+unsigned TargetSchedModel::getNumMicroOps(MachineInstr *MI) const {
+ if (hasInstrItineraries()) {
+ int UOps = InstrItins.getNumMicroOps(MI->getDesc().getSchedClass());
+ return (UOps >= 0) ? UOps : TII->getNumMicroOps(&InstrItins, MI);
+ }
+ if (hasInstrSchedModel())
+ return resolveSchedClass(MI)->NumMicroOps;
+
+ return 1;
+}
+
/// If we can determine the operand latency from the def only, without machine
/// model or itinerary lookup, do so. Otherwise return -1.
int TargetSchedModel::getDefLatency(const MachineInstr *DefMI,
@@ -209,3 +221,40 @@ unsigned TargetSchedModel::computeInstrLatency(const MachineInstr *MI) const {
}
return TII->defaultDefLatency(&SchedModel, MI);
}
+
+unsigned TargetSchedModel::
+computeOutputLatency(const MachineInstr *DefMI, unsigned DefOperIdx,
+ const MachineInstr *DepMI) const {
+ // MinLatency == -1 is for in-order processors that always have unit
+ // MinLatency. MinLatency > 0 is for in-order processors with varying min
+ // latencies, but since this is not a RAW dep, we always use unit latency.
+ if (SchedModel.MinLatency != 0)
+ return 1;
+
+ // MinLatency == 0 indicates an out-of-order processor that can dispatch
+ // WAW dependencies in the same cycle.
+
+ // Treat predication as a data dependency for out-of-order cpus. In-order
+ // cpus do not need to treat predicated writes specially.
+ //
+ // TODO: The following hack exists because predication passes do not
+ // correctly append imp-use operands, and readsReg() strangely returns false
+ // for predicated defs.
+ unsigned Reg = DefMI->getOperand(DefOperIdx).getReg();
+ const MachineFunction &MF = *DefMI->getParent()->getParent();
+ const TargetRegisterInfo *TRI = MF.getTarget().getRegisterInfo();
+ if (!DepMI->readsRegister(Reg, TRI) && TII->isPredicated(DepMI))
+ return computeInstrLatency(DefMI);
+
+ // If we have a per operand scheduling model, check if this def is writing
+ // an unbuffered resource. If so, it treated like an in-order cpu.
+ if (hasInstrSchedModel()) {
+ const MCSchedClassDesc *SCDesc = resolveSchedClass(DefMI);
+ for (const MCWriteProcResEntry *PRI = STI->getWriteProcResBegin(SCDesc),
+ *PRE = STI->getWriteProcResEnd(SCDesc); PRI != PRE; ++PRI) {
+ if (!SchedModel.getProcResource(PRI->ProcResourceIdx)->IsBuffered)
+ return 1;
+ }
+ }
+ return 0;
+}