summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorArnold Schwaighofer <aschwaighofer@apple.com>2013-04-05 04:42:00 +0000
committerArnold Schwaighofer <aschwaighofer@apple.com>2013-04-05 04:42:00 +0000
commit08da4865576056f997a9c8013240d716018f7edf (patch)
treef99588a26e23f5554daa91c4393b8088eb19f222
parentd4d7613af3fa3ba9abd7ea0828d9dadc23dd73ea (diff)
downloadllvm-08da4865576056f997a9c8013240d716018f7edf.tar.gz
llvm-08da4865576056f997a9c8013240d716018f7edf.tar.bz2
llvm-08da4865576056f997a9c8013240d716018f7edf.tar.xz
ARM scheduler model: Swift has varying latencies, uops for simple ALU ops
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@178842 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--lib/Target/ARM/ARMBaseInstrInfo.cpp12
-rw-r--r--lib/Target/ARM/ARMBaseInstrInfo.h4
-rw-r--r--lib/Target/ARM/ARMSchedule.td2
-rw-r--r--lib/Target/ARM/ARMScheduleSwift.td44
4 files changed, 57 insertions, 5 deletions
diff --git a/lib/Target/ARM/ARMBaseInstrInfo.cpp b/lib/Target/ARM/ARMBaseInstrInfo.cpp
index 126f160f6d..9e68ff4489 100644
--- a/lib/Target/ARM/ARMBaseInstrInfo.cpp
+++ b/lib/Target/ARM/ARMBaseInstrInfo.cpp
@@ -4123,3 +4123,15 @@ breakPartialRegDependency(MachineBasicBlock::iterator MI,
bool ARMBaseInstrInfo::hasNOP() const {
return (Subtarget.getFeatureBits() & ARM::HasV6T2Ops) != 0;
}
+
+bool ARMBaseInstrInfo::isSwiftFastImmShift(const MachineInstr *MI) const {
+ unsigned ShOpVal = MI->getOperand(3).getImm();
+ unsigned ShImm = ARM_AM::getSORegOffset(ShOpVal);
+ // Swift supports faster shifts for: lsl 2, lsl 1, and lsr 1.
+ if ((ShImm == 1 && ARM_AM::getSORegShOp(ShOpVal) == ARM_AM::lsr) ||
+ ((ShImm == 1 || ShImm == 2) &&
+ ARM_AM::getSORegShOp(ShOpVal) == ARM_AM::lsl))
+ return true;
+
+ return false;
+}
diff --git a/lib/Target/ARM/ARMBaseInstrInfo.h b/lib/Target/ARM/ARMBaseInstrInfo.h
index 2698132d2d..7c107bb419 100644
--- a/lib/Target/ARM/ARMBaseInstrInfo.h
+++ b/lib/Target/ARM/ARMBaseInstrInfo.h
@@ -314,6 +314,10 @@ public:
bool canCauseFpMLxStall(unsigned Opcode) const {
return MLxHazardOpcodes.count(Opcode);
}
+
+ /// Returns true if the instruction has a shift by immediate that can be
+ /// executed in one cycle less.
+ bool isSwiftFastImmShift(const MachineInstr *MI) const;
};
static inline
diff --git a/lib/Target/ARM/ARMSchedule.td b/lib/Target/ARM/ARMSchedule.td
index 7eb5ff665a..136a90aa95 100644
--- a/lib/Target/ARM/ARMSchedule.td
+++ b/lib/Target/ARM/ARMSchedule.td
@@ -71,6 +71,8 @@ def : PredicateProlog<[{
(void)TII;
}]>;
+def IsPredicatedPred : SchedPredicate<[{TII->isPredicated(MI)}]>;
+
//===----------------------------------------------------------------------===//
// Instruction Itinerary classes used for ARM
//
diff --git a/lib/Target/ARM/ARMScheduleSwift.td b/lib/Target/ARM/ARMScheduleSwift.td
index 28bb429feb..4a87faaac0 100644
--- a/lib/Target/ARM/ARMScheduleSwift.td
+++ b/lib/Target/ARM/ARMScheduleSwift.td
@@ -1083,6 +1083,9 @@ def SwiftModel : SchedMachineModel {
let Itineraries = SwiftItineraries;
}
+// Swift predicates.
+def IsFastImmShiftSwiftPred : SchedPredicate<[{TII->isSwiftFastImmShift(MI)}]>;
+
// Swift resource mapping.
let SchedModel = SwiftModel in {
// Processor resources.
@@ -1092,15 +1095,46 @@ let SchedModel = SwiftModel in {
def SwiftUnitP2 : ProcResource<1>; // LS unit.
def SwiftUnitDiv : ProcResource<1>;
+ // Generic resource requirements.
+ def SwiftWriteP01TwoCycle : SchedWriteRes<[SwiftUnitP01]> { let Latency = 2; }
+ def SwiftWriteP01ThreeCycleTwoUops :
+ SchedWriteRes<[SwiftUnitP01, SwiftUnitP01]> {
+ let Latency = 3;
+ let NumMicroOps = 2;
+ }
+ def SwiftWriteP0ThreeCycleThreeUops : SchedWriteRes<[SwiftUnitP0]> {
+ let Latency = 3;
+ let NumMicroOps = 3;
+ let ResourceCycles = [3];
+ }
+
// 4.2.4 Arithmetic and Logical.
+ // ALU operation register shifted by immediate variant.
+ def SwiftWriteALUsi : SchedWriteVariant<[
+ // lsl #2, lsl #1, or lsr #1.
+ SchedVar<IsFastImmShiftSwiftPred, [SwiftWriteP01TwoCycle]>,
+ // Arbitrary imm shift.
+ SchedVar<NoSchedPred, [WriteALU]>
+ ]>;
+ def SwiftWriteALUsr : SchedWriteVariant<[
+ SchedVar<IsPredicatedPred, [SwiftWriteP01ThreeCycleTwoUops]>,
+ SchedVar<NoSchedPred, [SwiftWriteP01TwoCycle]>
+ ]>;
+ def SwiftWriteALUSsr : SchedWriteVariant<[
+ SchedVar<IsPredicatedPred, [SwiftWriteP0ThreeCycleThreeUops]>,
+ SchedVar<NoSchedPred, [SwiftWriteP01TwoCycle]>
+ ]>;
+ def SwiftReadAdvanceALUsr : SchedReadVariant<[
+ SchedVar<IsPredicatedPred, [SchedReadAdvance<2>]>,
+ SchedVar<NoSchedPred, [NoReadAdvance]>
+ ]>;
// ADC,ADD,NEG,RSB,RSC,SBC,SUB,ADR
// AND,BIC, EOR,ORN,ORR
// CLZ,RBIT,REV,REV16,REVSH,PKH
- // Single cycle.
def : WriteRes<WriteALU, [SwiftUnitP01]>;
- def : WriteRes<WriteALUsi, [SwiftUnitP01]>;
- def : WriteRes<WriteALUsr, [SwiftUnitP01]>;
- def : WriteRes<WriteALUSsr, [SwiftUnitP01]>;
+ def : SchedAlias<WriteALUsi, SwiftWriteALUsi>;
+ def : SchedAlias<WriteALUsr, SwiftWriteALUsr>;
+ def : SchedAlias<WriteALUSsr, SwiftWriteALUSsr>;
def : ReadAdvance<ReadALU, 0>;
- def : ReadAdvance<ReadALUsr, 2>;
+ def : SchedAlias<ReadALUsr, SwiftReadAdvanceALUsr>;
}