Fix order of operands for copytoreg node when emitting calls. This fixes
[oota-llvm.git] / lib / Target / PowerPC / PPCISelDAGToDAG.cpp
index 934f811fb14524cdc76492491dce00272f21f638..89f0f64223bda675c266e68e2e47eaa3664d2fd3 100644 (file)
@@ -17,6 +17,7 @@
 #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"
@@ -996,7 +997,7 @@ SDOperand PPC32DAGToDAGISel::Select(SDOperand Op) {
     if (isOprNot(N)) {
       unsigned Opc;
       SDOperand Val = Select(N->getOperand(0));
-      switch (Val.getTargetOpcode()) {
+      switch (Val.isTargetOpcode() ? Val.getTargetOpcode() : 0) {
       default:        Opc = 0;          break;
       case PPC::OR:   Opc = PPC::NOR;   break;
       case PPC::AND:  Opc = PPC::NAND;  break;
@@ -1080,21 +1081,32 @@ SDOperand PPC32DAGToDAGISel::Select(SDOperand Op) {
   case ISD::FP_EXTEND: {
     assert(MVT::f64 == N->getValueType(0) && 
            MVT::f32 == N->getOperand(0).getValueType() && "Illegal FP_EXTEND");
-    SDOperand Tmp = Select(N->getOperand(0));
-    CurDAG->ReplaceAllUsesWith(Op, Tmp);  // Just use the operand as the result.
-    return Tmp;
+    std::vector<SDOperand> Tmp;
+    Tmp.push_back(Select(N->getOperand(0)));
+    CurDAG->ReplaceAllUsesWith(N, Tmp);  // Just use the operand as the result.
+    return Tmp[0];
   }
   case ISD::FP_ROUND:
     assert(MVT::f32 == N->getValueType(0) && 
            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);
     if (Val.Val->hasOneUse()) {
       unsigned Opc;
-      switch (Val.getTargetOpcode()) {
+      switch (Val.isTargetOpcode() ? Val.getTargetOpcode() : 0) {
       default:          Opc = 0;            break;
       case PPC::FABS:   Opc = PPC::FNABS;   break;
       case PPC::FMADD:  Opc = PPC::FNMADD;  break;
@@ -1400,8 +1412,17 @@ SDOperand PPC32DAGToDAGISel::Select(SDOperand Op) {
                                  Tmp.getValue(1));
             break;
           }
-    
-    assert(0 && "Select_cc not implemented yet!");
+
+    SDOperand CCReg = SelectCC(Select(N->getOperand(0)),
+                               Select(N->getOperand(1)), CC);
+    unsigned BROpc = getBCCForSetCC(CC);
+
+    bool isFP = MVT::isFloatingPoint(N->getValueType(0));
+    unsigned SelectCCOp = isFP ? PPC::SELECT_CC_FP : PPC::SELECT_CC_Int;
+    CurDAG->SelectNodeTo(N, SelectCCOp, N->getValueType(0), CCReg,
+                         Select(N->getOperand(2)), Select(N->getOperand(3)),
+                         getI32Imm(BROpc));
+    break;
   }
     
   case ISD::CALLSEQ_START:
@@ -1436,7 +1457,7 @@ SDOperand PPC32DAGToDAGISel::Select(SDOperand Op) {
 
       // Copy the callee address into R12 on darwin.
       SDOperand R12 = CurDAG->getRegister(PPC::R12, MVT::i32);
-      Chain = CurDAG->getNode(ISD::CopyToReg, MVT::Other, R12, Callee, Chain);
+      Chain = CurDAG->getNode(ISD::CopyToReg, MVT::Other, Chain, R12, Callee);
       
       CallOperands.push_back(getI32Imm(20));  // Information to encode indcall
       CallOperands.push_back(getI32Imm(0));   // Information to encode indcall