From: Chris Lattner Date: Wed, 31 Aug 2005 21:09:52 +0000 (+0000) Subject: Move FCTIWZ handling out of the instruction selectors and into legalization, X-Git-Url: http://demsky.eecs.uci.edu/git/?a=commitdiff_plain;h=f76053269ecc6c7bd3d0b1e90ebdd0cef1bb2bdc;p=oota-llvm.git Move FCTIWZ handling out of the instruction selectors and into legalization, getting them out of the business of making stack slots. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@23180 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/Target/PowerPC/PPCISelDAGToDAG.cpp b/lib/Target/PowerPC/PPCISelDAGToDAG.cpp index 9a978295b84..082c876859b 100644 --- a/lib/Target/PowerPC/PPCISelDAGToDAG.cpp +++ b/lib/Target/PowerPC/PPCISelDAGToDAG.cpp @@ -17,7 +17,6 @@ #include "PPC32ISelLowering.h" #include "llvm/CodeGen/MachineInstrBuilder.h" #include "llvm/CodeGen/MachineFunction.h" -#include "llvm/CodeGen/MachineFrameInfo.h" #include "llvm/CodeGen/SSARegMap.h" #include "llvm/CodeGen/SelectionDAG.h" #include "llvm/CodeGen/SelectionDAGISel.h" @@ -793,6 +792,10 @@ SDOperand PPC32DAGToDAGISel::Select(SDOperand Op) { Select(N->getOperand(1)), Select(N->getOperand(2))); break; + case PPCISD::FCTIWZ: + CurDAG->SelectNodeTo(N, PPC::FCTIWZ, N->getValueType(0), + Select(N->getOperand(0))); + break; case ISD::ADD: { MVT::ValueType Ty = N->getValueType(0); if (Ty == MVT::i32) { @@ -1119,18 +1122,6 @@ SDOperand PPC32DAGToDAGISel::Select(SDOperand Op) { MVT::f64 == N->getOperand(0).getValueType() && "Illegal FP_ROUND"); CurDAG->SelectNodeTo(N, PPC::FRSP, MVT::f32, Select(N->getOperand(0))); break; - case ISD::FP_TO_SINT: { - SDOperand In = Select(N->getOperand(0)); - In = CurDAG->getTargetNode(PPC::FCTIWZ, MVT::f64, In); - - int FrameIdx = BB->getParent()->getFrameInfo()->CreateStackObject(8, 8); - SDOperand FI = CurDAG->getTargetFrameIndex(FrameIdx, MVT::f64); - SDOperand ST = CurDAG->getTargetNode(PPC::STFD, MVT::Other, In, - getI32Imm(0), FI); - CurDAG->SelectNodeTo(N, PPC::LWZ, MVT::i32, MVT::Other, - getI32Imm(4), FI, ST); - break; - } case ISD::FNEG: { SDOperand Val = Select(N->getOperand(0)); MVT::ValueType Ty = N->getValueType(0); diff --git a/lib/Target/PowerPC/PPCISelLowering.cpp b/lib/Target/PowerPC/PPCISelLowering.cpp index 987ffe1612b..5b77784819f 100644 --- a/lib/Target/PowerPC/PPCISelLowering.cpp +++ b/lib/Target/PowerPC/PPCISelLowering.cpp @@ -84,6 +84,9 @@ PPC32TargetLowering::PPC32TargetLowering(TargetMachine &TM) // PowerPC does not have FP_TO_UINT setOperationAction(ISD::FP_TO_UINT, MVT::i32, Expand); + // PowerPC turns FP_TO_SINT into FCTIWZ and some load/stores. + setOperationAction(ISD::FP_TO_SINT, MVT::i32, Custom); + // PowerPC does not have [U|S]INT_TO_FP setOperationAction(ISD::SINT_TO_FP, MVT::i32, Expand); setOperationAction(ISD::UINT_TO_FP, MVT::i32, Expand); @@ -111,61 +114,76 @@ static bool isFloatingPointZero(SDOperand Op) { SDOperand PPC32TargetLowering::LowerOperation(SDOperand Op, SelectionDAG &DAG) { switch (Op.getOpcode()) { default: assert(0 && "Wasn't expecting to be able to lower this!"); - case ISD::SELECT_CC: + case ISD::FP_TO_SINT: { + assert(Op.getValueType() == MVT::i32 && + MVT::isFloatingPoint(Op.getOperand(0).getValueType())); + Op = DAG.getNode(PPCISD::FCTIWZ, MVT::f64, Op.getOperand(0)); + + int FrameIdx = + DAG.getMachineFunction().getFrameInfo()->CreateStackObject(8, 8); + SDOperand FI = DAG.getFrameIndex(FrameIdx, MVT::i32); + SDOperand ST = DAG.getNode(ISD::STORE, MVT::Other, DAG.getEntryNode(), + Op, FI, DAG.getSrcValue(0)); + FI = DAG.getNode(ISD::ADD, MVT::i32, FI, DAG.getConstant(4, MVT::i32)); + return DAG.getLoad(MVT::i32, ST, FI, DAG.getSrcValue(0)); + } + case ISD::SELECT_CC: { // Turn FP only select_cc's into fsel instructions. - if (MVT::isFloatingPoint(Op.getOperand(0).getValueType()) && - MVT::isFloatingPoint(Op.getOperand(2).getValueType())) { - ISD::CondCode CC = cast(Op.getOperand(4))->get(); - - // Cannot handle SETEQ/SETNE. - if (CC == ISD::SETEQ || CC == ISD::SETNE) break; - - MVT::ValueType ResVT = Op.getValueType(); - MVT::ValueType CmpVT = Op.getOperand(0).getValueType(); - SDOperand LHS = Op.getOperand(0), RHS = Op.getOperand(1); - SDOperand TV = Op.getOperand(2), FV = Op.getOperand(3); + if (!MVT::isFloatingPoint(Op.getOperand(0).getValueType()) || + !MVT::isFloatingPoint(Op.getOperand(2).getValueType())) + break; + + ISD::CondCode CC = cast(Op.getOperand(4))->get(); + + // Cannot handle SETEQ/SETNE. + if (CC == ISD::SETEQ || CC == ISD::SETNE) break; + + MVT::ValueType ResVT = Op.getValueType(); + MVT::ValueType CmpVT = Op.getOperand(0).getValueType(); + SDOperand LHS = Op.getOperand(0), RHS = Op.getOperand(1); + SDOperand TV = Op.getOperand(2), FV = Op.getOperand(3); - // If the RHS of the comparison is a 0.0, we don't need to do the - // subtraction at all. - if (isFloatingPointZero(RHS)) - switch (CC) { - default: assert(0 && "Invalid FSEL condition"); abort(); - case ISD::SETULT: - case ISD::SETLT: - std::swap(TV, FV); // fsel is natively setge, swap operands for setlt - case ISD::SETUGE: - case ISD::SETGE: - return DAG.getNode(PPCISD::FSEL, ResVT, LHS, TV, FV); - case ISD::SETUGT: - case ISD::SETGT: - std::swap(TV, FV); // fsel is natively setge, swap operands for setlt - case ISD::SETULE: - case ISD::SETLE: - return DAG.getNode(PPCISD::FSEL, ResVT, - DAG.getNode(ISD::FNEG, ResVT, LHS), TV, FV); - } - + // If the RHS of the comparison is a 0.0, we don't need to do the + // subtraction at all. + if (isFloatingPointZero(RHS)) switch (CC) { default: assert(0 && "Invalid FSEL condition"); abort(); case ISD::SETULT: case ISD::SETLT: - return DAG.getNode(PPCISD::FSEL, ResVT, - DAG.getNode(ISD::SUB, CmpVT, LHS, RHS), FV, TV); + std::swap(TV, FV); // fsel is natively setge, swap operands for setlt case ISD::SETUGE: case ISD::SETGE: - return DAG.getNode(PPCISD::FSEL, ResVT, - DAG.getNode(ISD::SUB, CmpVT, LHS, RHS), TV, FV); + return DAG.getNode(PPCISD::FSEL, ResVT, LHS, TV, FV); case ISD::SETUGT: case ISD::SETGT: - return DAG.getNode(PPCISD::FSEL, ResVT, - DAG.getNode(ISD::SUB, CmpVT, RHS, LHS), FV, TV); + std::swap(TV, FV); // fsel is natively setge, swap operands for setlt case ISD::SETULE: case ISD::SETLE: return DAG.getNode(PPCISD::FSEL, ResVT, - DAG.getNode(ISD::SUB, CmpVT, RHS, LHS), TV, FV); + DAG.getNode(ISD::FNEG, ResVT, LHS), TV, FV); } + + switch (CC) { + default: assert(0 && "Invalid FSEL condition"); abort(); + case ISD::SETULT: + case ISD::SETLT: + return DAG.getNode(PPCISD::FSEL, ResVT, + DAG.getNode(ISD::SUB, CmpVT, LHS, RHS), FV, TV); + case ISD::SETUGE: + case ISD::SETGE: + return DAG.getNode(PPCISD::FSEL, ResVT, + DAG.getNode(ISD::SUB, CmpVT, LHS, RHS), TV, FV); + case ISD::SETUGT: + case ISD::SETGT: + return DAG.getNode(PPCISD::FSEL, ResVT, + DAG.getNode(ISD::SUB, CmpVT, RHS, LHS), FV, TV); + case ISD::SETULE: + case ISD::SETLE: + return DAG.getNode(PPCISD::FSEL, ResVT, + DAG.getNode(ISD::SUB, CmpVT, RHS, LHS), TV, FV); } - break; + break; + } case ISD::SHL: { assert(Op.getValueType() == MVT::i64 && Op.getOperand(1).getValueType() == MVT::i32 && "Unexpected SHL!"); diff --git a/lib/Target/PowerPC/PPCISelLowering.h b/lib/Target/PowerPC/PPCISelLowering.h index bdd55480b74..924a672d2cc 100644 --- a/lib/Target/PowerPC/PPCISelLowering.h +++ b/lib/Target/PowerPC/PPCISelLowering.h @@ -28,6 +28,10 @@ namespace llvm { /// FSEL - Traditional three-operand fsel node. /// FSEL, + + /// FCTIWZ - The FCTIWZ instruction, taking an f32 or f64 operand, + /// producing an f64 value. + FCTIWZ, }; } diff --git a/lib/Target/PowerPC/PPCISelPattern.cpp b/lib/Target/PowerPC/PPCISelPattern.cpp index eba1419f43b..8c4b2b6a9a8 100644 --- a/lib/Target/PowerPC/PPCISelPattern.cpp +++ b/lib/Target/PowerPC/PPCISelPattern.cpp @@ -22,7 +22,6 @@ #include "llvm/Function.h" #include "llvm/CodeGen/MachineConstantPool.h" #include "llvm/CodeGen/MachineFunction.h" -#include "llvm/CodeGen/MachineFrameInfo.h" #include "llvm/CodeGen/SelectionDAG.h" #include "llvm/CodeGen/SelectionDAGISel.h" #include "llvm/CodeGen/SSARegMap.h" @@ -818,6 +817,10 @@ unsigned ISel::SelectExpr(SDOperand N, bool Recording) { Tmp3 = SelectExpr(N.getOperand(2)); BuildMI(BB, PPC::FSEL, 3, Result).addReg(Tmp1).addReg(Tmp2).addReg(Tmp3); return Result; + case PPCISD::FCTIWZ: + Tmp1 = SelectExpr(N.getOperand(0)); + BuildMI(BB, PPC::FCTIWZ, 1, Result).addReg(Tmp1); + return Result; case ISD::UNDEF: if (Node->getValueType(0) == MVT::i32) BuildMI(BB, PPC::IMPLICIT_DEF_GPR, 0, Result); @@ -1436,16 +1439,6 @@ unsigned ISel::SelectExpr(SDOperand N, bool Recording) { return Result+N.ResNo; } - case ISD::FP_TO_SINT: { - Tmp1 = SelectExpr(N.getOperand(0)); - Tmp2 = MakeFPReg(); - BuildMI(BB, PPC::FCTIWZ, 1, Tmp2).addReg(Tmp1); - int FrameIdx = BB->getParent()->getFrameInfo()->CreateStackObject(8, 8); - addFrameReference(BuildMI(BB, PPC::STFD, 3).addReg(Tmp2), FrameIdx); - addFrameReference(BuildMI(BB, PPC::LWZ, 2, Result), FrameIdx, 4); - return Result; - } - case ISD::SETCC: { ISD::CondCode CC = cast(Node->getOperand(2))->get(); if (isIntImmediate(Node->getOperand(1), Tmp3)) {