summaryrefslogtreecommitdiff
path: root/lib/Target/SystemZ
diff options
context:
space:
mode:
Diffstat (limited to 'lib/Target/SystemZ')
-rw-r--r--lib/Target/SystemZ/AsmPrinter/SystemZAsmPrinter.cpp3
-rw-r--r--lib/Target/SystemZ/SystemZISelLowering.cpp26
-rw-r--r--lib/Target/SystemZ/SystemZISelLowering.h5
-rw-r--r--lib/Target/SystemZ/SystemZInstrFP.td6
-rw-r--r--lib/Target/SystemZ/SystemZInstrInfo.td50
5 files changed, 53 insertions, 37 deletions
diff --git a/lib/Target/SystemZ/AsmPrinter/SystemZAsmPrinter.cpp b/lib/Target/SystemZ/AsmPrinter/SystemZAsmPrinter.cpp
index a128992934be..a4a8d6aabbb3 100644
--- a/lib/Target/SystemZ/AsmPrinter/SystemZAsmPrinter.cpp
+++ b/lib/Target/SystemZ/AsmPrinter/SystemZAsmPrinter.cpp
@@ -33,7 +33,6 @@
#include "llvm/Target/TargetLoweringObjectFile.h"
#include "llvm/Target/TargetRegistry.h"
#include "llvm/ADT/Statistic.h"
-#include "llvm/Support/Compiler.h"
#include "llvm/Support/FormattedStream.h"
#include "llvm/Support/Mangler.h"
@@ -42,7 +41,7 @@ using namespace llvm;
STATISTIC(EmittedInsts, "Number of machine instrs printed");
namespace {
- class VISIBILITY_HIDDEN SystemZAsmPrinter : public AsmPrinter {
+ class SystemZAsmPrinter : public AsmPrinter {
public:
SystemZAsmPrinter(formatted_raw_ostream &O, TargetMachine &TM,
const MCAsmInfo *MAI, bool V)
diff --git a/lib/Target/SystemZ/SystemZISelLowering.cpp b/lib/Target/SystemZ/SystemZISelLowering.cpp
index 07e0d8305806..5c8cae0cd763 100644
--- a/lib/Target/SystemZ/SystemZISelLowering.cpp
+++ b/lib/Target/SystemZ/SystemZISelLowering.cpp
@@ -53,11 +53,6 @@ SystemZTargetLowering::SystemZTargetLowering(SystemZTargetMachine &tm) :
if (!UseSoftFloat) {
addRegisterClass(MVT::f32, SystemZ::FP32RegisterClass);
addRegisterClass(MVT::f64, SystemZ::FP64RegisterClass);
-
- addLegalFPImmediate(APFloat(+0.0)); // lzer
- addLegalFPImmediate(APFloat(+0.0f)); // lzdr
- addLegalFPImmediate(APFloat(-0.0)); // lzer + lner
- addLegalFPImmediate(APFloat(-0.0f)); // lzdr + lndr
}
// Compute derived properties from the register classes
@@ -80,7 +75,13 @@ SystemZTargetLowering::SystemZTargetLowering(SystemZTargetMachine &tm) :
setLoadExtAction(ISD::EXTLOAD, MVT::f64, Expand);
setStackPointerRegisterToSaveRestore(SystemZ::R15D);
- setSchedulingPreference(SchedulingForLatency);
+
+ // TODO: It may be better to default to latency-oriented scheduling, however
+ // LLVM's current latency-oriented scheduler can't handle physreg definitions
+ // such as SystemZ has with PSW, so set this to the register-pressure
+ // scheduler, because it can.
+ setSchedulingPreference(SchedulingForRegPressure);
+
setBooleanContents(ZeroOrOneBooleanContent);
setOperationAction(ISD::BR_JT, MVT::Other, Expand);
@@ -169,6 +170,17 @@ SDValue SystemZTargetLowering::LowerOperation(SDValue Op, SelectionDAG &DAG) {
}
}
+bool SystemZTargetLowering::isFPImmLegal(const APFloat &Imm, EVT VT) const {
+ if (UseSoftFloat || (VT != MVT::f32 && VT != MVT::f64))
+ return false;
+
+ // +0.0 lzer
+ // +0.0f lzdr
+ // -0.0 lzer + lner
+ // -0.0f lzdr + lndr
+ return Imm.isZero() || Imm.isNegZero();
+}
+
//===----------------------------------------------------------------------===//
// SystemZ Inline Assembly Support
//===----------------------------------------------------------------------===//
@@ -657,7 +669,7 @@ SDValue SystemZTargetLowering::EmitCmp(SDValue LHS, SDValue RHS,
DebugLoc dl = LHS.getDebugLoc();
return DAG.getNode((isUnsigned ? SystemZISD::UCMP : SystemZISD::CMP),
- dl, MVT::Flag, LHS, RHS);
+ dl, MVT::i64, LHS, RHS);
}
diff --git a/lib/Target/SystemZ/SystemZISelLowering.h b/lib/Target/SystemZ/SystemZISelLowering.h
index c2c24bc1f3ab..5bf1ed68c4c7 100644
--- a/lib/Target/SystemZ/SystemZISelLowering.h
+++ b/lib/Target/SystemZ/SystemZISelLowering.h
@@ -89,6 +89,11 @@ namespace llvm {
MachineBasicBlock *BB,
DenseMap<MachineBasicBlock*, MachineBasicBlock*> *EM) const;
+ /// isFPImmLegal - Returns true if the target can instruction select the
+ /// specified FP immediate natively. If false, the legalizer will
+ /// materialize the FP immediate as a load from a constant pool.
+ virtual bool isFPImmLegal(const APFloat &Imm, EVT VT) const;
+
private:
SDValue LowerCCCCallTo(SDValue Chain, SDValue Callee,
CallingConv::ID CallConv, bool isVarArg,
diff --git a/lib/Target/SystemZ/SystemZInstrFP.td b/lib/Target/SystemZ/SystemZInstrFP.td
index 8a202d4523a5..336e20ed895c 100644
--- a/lib/Target/SystemZ/SystemZInstrFP.td
+++ b/lib/Target/SystemZ/SystemZInstrFP.td
@@ -25,15 +25,15 @@ def fpimmneg0 : PatLeaf<(fpimm), [{
return N->isExactlyValue(-0.0);
}]>;
-let usesCustomDAGSchedInserter = 1 in {
+let Uses = [PSW], usesCustomInserter = 1 in {
def SelectF32 : Pseudo<(outs FP32:$dst), (ins FP32:$src1, FP32:$src2, i8imm:$cc),
"# SelectF32 PSEUDO",
[(set FP32:$dst,
- (SystemZselect FP32:$src1, FP32:$src2, imm:$cc))]>;
+ (SystemZselect FP32:$src1, FP32:$src2, imm:$cc, PSW))]>;
def SelectF64 : Pseudo<(outs FP64:$dst), (ins FP64:$src1, FP64:$src2, i8imm:$cc),
"# SelectF64 PSEUDO",
[(set FP64:$dst,
- (SystemZselect FP64:$src1, FP64:$src2, imm:$cc))]>;
+ (SystemZselect FP64:$src1, FP64:$src2, imm:$cc, PSW))]>;
}
//===----------------------------------------------------------------------===//
diff --git a/lib/Target/SystemZ/SystemZInstrInfo.td b/lib/Target/SystemZ/SystemZInstrInfo.td
index 56d75ddfc0c7..1891bba2aa4a 100644
--- a/lib/Target/SystemZ/SystemZInstrInfo.td
+++ b/lib/Target/SystemZ/SystemZInstrInfo.td
@@ -32,12 +32,12 @@ def SDT_SystemZCall : SDTypeProfile<0, -1, [SDTCisPtrTy<0>]>;
def SDT_SystemZCallSeqStart : SDCallSeqStart<[SDTCisI64<0>]>;
def SDT_SystemZCallSeqEnd : SDCallSeqEnd<[SDTCisI64<0>, SDTCisI64<1>]>;
def SDT_CmpTest : SDTypeProfile<0, 2, [SDTCisSameAs<0, 1>]>;
-def SDT_BrCond : SDTypeProfile<0, 2,
+def SDT_BrCond : SDTypeProfile<0, 3,
[SDTCisVT<0, OtherVT>,
- SDTCisI8<1>]>;
-def SDT_SelectCC : SDTypeProfile<1, 3,
+ SDTCisI8<1>, SDTCisVT<2, i64>]>;
+def SDT_SelectCC : SDTypeProfile<1, 4,
[SDTCisSameAs<0, 1>, SDTCisSameAs<1, 2>,
- SDTCisI8<3>]>;
+ SDTCisI8<3>, SDTCisVT<4, i64>]>;
def SDT_Address : SDTypeProfile<1, 1,
[SDTCisSameAs<0, 1>, SDTCisPtrTy<0>]>;
@@ -54,11 +54,11 @@ def SystemZcallseq_start :
def SystemZcallseq_end :
SDNode<"ISD::CALLSEQ_END", SDT_SystemZCallSeqEnd,
[SDNPHasChain, SDNPOptInFlag, SDNPOutFlag]>;
-def SystemZcmp : SDNode<"SystemZISD::CMP", SDT_CmpTest, [SDNPOutFlag]>;
-def SystemZucmp : SDNode<"SystemZISD::UCMP", SDT_CmpTest, [SDNPOutFlag]>;
+def SystemZcmp : SDNode<"SystemZISD::CMP", SDT_CmpTest>;
+def SystemZucmp : SDNode<"SystemZISD::UCMP", SDT_CmpTest>;
def SystemZbrcond : SDNode<"SystemZISD::BRCOND", SDT_BrCond,
- [SDNPHasChain, SDNPInFlag]>;
-def SystemZselect : SDNode<"SystemZISD::SELECT", SDT_SelectCC, [SDNPInFlag]>;
+ [SDNPHasChain]>;
+def SystemZselect : SDNode<"SystemZISD::SELECT", SDT_SelectCC>;
def SystemZpcrelwrapper : SDNode<"SystemZISD::PCRelativeWrapper", SDT_Address, []>;
@@ -74,15 +74,15 @@ def ADJCALLSTACKUP : Pseudo<(outs), (ins i64imm:$amt1, i64imm:$amt2),
"#ADJCALLSTACKUP",
[(SystemZcallseq_end timm:$amt1, timm:$amt2)]>;
-let usesCustomDAGSchedInserter = 1 in {
+let Uses = [PSW], usesCustomInserter = 1 in {
def Select32 : Pseudo<(outs GR32:$dst), (ins GR32:$src1, GR32:$src2, i8imm:$cc),
"# Select32 PSEUDO",
[(set GR32:$dst,
- (SystemZselect GR32:$src1, GR32:$src2, imm:$cc))]>;
+ (SystemZselect GR32:$src1, GR32:$src2, imm:$cc, PSW))]>;
def Select64 : Pseudo<(outs GR64:$dst), (ins GR64:$src1, GR64:$src2, i8imm:$cc),
"# Select64 PSEUDO",
[(set GR64:$dst,
- (SystemZselect GR64:$src1, GR64:$src2, imm:$cc))]>;
+ (SystemZselect GR64:$src1, GR64:$src2, imm:$cc, PSW))]>;
}
@@ -106,46 +106,46 @@ let isBranch = 1, isTerminator = 1 in {
let Uses = [PSW] in {
def JO : Pseudo<(outs), (ins brtarget:$dst),
"jo\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_O)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_O, PSW)]>;
def JH : Pseudo<(outs), (ins brtarget:$dst),
"jh\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_H)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_H, PSW)]>;
def JNLE: Pseudo<(outs), (ins brtarget:$dst),
"jnle\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NLE)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NLE, PSW)]>;
def JL : Pseudo<(outs), (ins brtarget:$dst),
"jl\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_L)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_L, PSW)]>;
def JNHE: Pseudo<(outs), (ins brtarget:$dst),
"jnhe\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NHE)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NHE, PSW)]>;
def JLH : Pseudo<(outs), (ins brtarget:$dst),
"jlh\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_LH)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_LH, PSW)]>;
def JNE : Pseudo<(outs), (ins brtarget:$dst),
"jne\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NE)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NE, PSW)]>;
def JE : Pseudo<(outs), (ins brtarget:$dst),
"je\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_E)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_E, PSW)]>;
def JNLH: Pseudo<(outs), (ins brtarget:$dst),
"jnlh\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NLH)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NLH, PSW)]>;
def JHE : Pseudo<(outs), (ins brtarget:$dst),
"jhe\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_HE)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_HE, PSW)]>;
def JNL : Pseudo<(outs), (ins brtarget:$dst),
"jnl\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NL)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NL, PSW)]>;
def JLE : Pseudo<(outs), (ins brtarget:$dst),
"jle\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_LE)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_LE, PSW)]>;
def JNH : Pseudo<(outs), (ins brtarget:$dst),
"jnh\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NH)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NH, PSW)]>;
def JNO : Pseudo<(outs), (ins brtarget:$dst),
"jno\t$dst",
- [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NO)]>;
+ [(SystemZbrcond bb:$dst, SYSTEMZ_COND_NO, PSW)]>;
} // Uses = [PSW]
} // isBranch = 1