[llvm-commits] CVS: llvm/lib/Target/X86/X86ISelLowering.cpp X86ISelLowering.h X86InstrSSE.td

Evan Cheng evan.cheng at apple.com
Fri Nov 10 13:43:51 PST 2006



Changes in directory llvm/lib/Target/X86:

X86ISelLowering.cpp updated: 1.289 -> 1.290
X86ISelLowering.h updated: 1.79 -> 1.80
X86InstrSSE.td updated: 1.170 -> 1.171
---
Log message:

Don't dag combine floating point select to max and min intrinsics. Those
take v4f32 / v2f64 operands and may end up causing larger spills / restores.
Added X86 specific nodes X86ISD::FMAX, X86ISD::FMIN instead.

This fixes PR996: http://llvm.org/PR996 .


---
Diffs of the changes:  (+21 -59)

 X86ISelLowering.cpp |   36 +++++++++---------------------------
 X86ISelLowering.h   |    6 +++++-
 X86InstrSSE.td      |   38 +++++++-------------------------------
 3 files changed, 21 insertions(+), 59 deletions(-)


Index: llvm/lib/Target/X86/X86ISelLowering.cpp
diff -u llvm/lib/Target/X86/X86ISelLowering.cpp:1.289 llvm/lib/Target/X86/X86ISelLowering.cpp:1.290
--- llvm/lib/Target/X86/X86ISelLowering.cpp:1.289	Thu Nov  9 18:48:12 2006
+++ llvm/lib/Target/X86/X86ISelLowering.cpp	Fri Nov 10 15:43:37 2006
@@ -4983,6 +4983,8 @@
   case X86ISD::S2VEC:              return "X86ISD::S2VEC";
   case X86ISD::PEXTRW:             return "X86ISD::PEXTRW";
   case X86ISD::PINSRW:             return "X86ISD::PINSRW";
+  case X86ISD::FMAX:               return "X86ISD::FMAX";
+  case X86ISD::FMIN:               return "X86ISD::FMIN";
   }
 }
 
@@ -5363,7 +5365,7 @@
       SDOperand RHS = N->getOperand(2);
       ISD::CondCode CC = cast<CondCodeSDNode>(Cond.getOperand(2))->get();
       
-      unsigned IntNo = 0;
+      unsigned Opcode = 0;
       if (LHS == Cond.getOperand(0) && RHS == Cond.getOperand(1)) {
         switch (CC) {
         default: break;
@@ -5374,8 +5376,7 @@
           // FALL THROUGH.
         case ISD::SETOLT:  // (X olt/lt Y) ? X : Y -> min
         case ISD::SETLT:
-          IntNo = LHS.getValueType() == MVT::f32 ? Intrinsic::x86_sse_min_ss :
-                                                   Intrinsic::x86_sse2_min_sd;
+          Opcode = X86ISD::FMIN;
           break;
           
         case ISD::SETOGT: // (X > Y) ? X : Y -> max
@@ -5385,8 +5386,7 @@
           // FALL THROUGH.
         case ISD::SETUGE:  // (X uge/ge Y) ? X : Y -> max
         case ISD::SETGE:
-          IntNo = LHS.getValueType() == MVT::f32 ? Intrinsic::x86_sse_max_ss :
-                                                   Intrinsic::x86_sse2_max_sd;
+          Opcode = X86ISD::FMAX;
           break;
         }
       } else if (LHS == Cond.getOperand(1) && RHS == Cond.getOperand(0)) {
@@ -5399,8 +5399,7 @@
           // FALL THROUGH.
         case ISD::SETUGE:  // (X uge/ge Y) ? Y : X -> min
         case ISD::SETGE:
-          IntNo = LHS.getValueType() == MVT::f32 ? Intrinsic::x86_sse_min_ss :
-                                                   Intrinsic::x86_sse2_min_sd;
+          Opcode = X86ISD::FMIN;
           break;
           
         case ISD::SETOLE:   // (X <= Y) ? Y : X -> max
@@ -5410,30 +5409,13 @@
           // FALL THROUGH.
         case ISD::SETOLT:   // (X olt/lt Y) ? Y : X -> max
         case ISD::SETLT:
-          IntNo = LHS.getValueType() == MVT::f32 ? Intrinsic::x86_sse_max_ss :
-                                                   Intrinsic::x86_sse2_max_sd;
+          Opcode = X86ISD::FMAX;
           break;
         }
       }
       
-      // minss/maxss take a v4f32 operand.
-      if (IntNo) {
-        if (LHS.getValueType() == MVT::f32) {
-          LHS = DAG.getNode(ISD::SCALAR_TO_VECTOR, MVT::v4f32, LHS);
-          RHS = DAG.getNode(ISD::SCALAR_TO_VECTOR, MVT::v4f32, RHS);
-        } else {
-          LHS = DAG.getNode(ISD::SCALAR_TO_VECTOR, MVT::v2f64, LHS);
-          RHS = DAG.getNode(ISD::SCALAR_TO_VECTOR, MVT::v2f64, RHS);
-        }
-        
-        MVT::ValueType PtrTy = Subtarget->is64Bit() ? MVT::i64 : MVT::i32;
-        SDOperand IntNoN = DAG.getConstant(IntNo, PtrTy);
-        
-        SDOperand Val = DAG.getNode(ISD::INTRINSIC_WO_CHAIN, LHS.getValueType(),
-                                    IntNoN, LHS, RHS);
-        return DAG.getNode(ISD::EXTRACT_VECTOR_ELT, N->getValueType(0), Val,
-                           DAG.getConstant(0, PtrTy));
-      }
+      if (Opcode)
+        return DAG.getNode(Opcode, N->getValueType(0), LHS, RHS);
     }
     
   }


Index: llvm/lib/Target/X86/X86ISelLowering.h
diff -u llvm/lib/Target/X86/X86ISelLowering.h:1.79 llvm/lib/Target/X86/X86ISelLowering.h:1.80
--- llvm/lib/Target/X86/X86ISelLowering.h:1.79	Tue Nov  7 16:14:24 2006
+++ llvm/lib/Target/X86/X86ISelLowering.h	Fri Nov 10 15:43:37 2006
@@ -160,7 +160,11 @@
 
       /// PINSRW - Insert the lower 16-bits of a 32-bit value to a vector,
       /// corresponds to X86::PINSRW.
-      PINSRW
+      PINSRW,
+
+      /// FMAX, FMIN - Floating point max and min.
+      ///
+      FMAX, FMIN
     };
   }
 


Index: llvm/lib/Target/X86/X86InstrSSE.td
diff -u llvm/lib/Target/X86/X86InstrSSE.td:1.170 llvm/lib/Target/X86/X86InstrSSE.td:1.171
--- llvm/lib/Target/X86/X86InstrSSE.td:1.170	Tue Nov  7 16:14:24 2006
+++ llvm/lib/Target/X86/X86InstrSSE.td	Fri Nov 10 15:43:37 2006
@@ -20,6 +20,8 @@
 
 def X86loadp   : SDNode<"X86ISD::LOAD_PACK", SDTLoad, [SDNPHasChain]>;
 def X86loadu   : SDNode<"X86ISD::LOAD_UA",   SDTLoad, [SDNPHasChain]>;
+def X86fmin    : SDNode<"X86ISD::FMIN",      SDTFPBinOp>;
+def X86fmax    : SDNode<"X86ISD::FMAX",      SDTFPBinOp>;
 def X86fand    : SDNode<"X86ISD::FAND",      SDTFPBinOp,
                         [SDNPCommutative, SDNPAssociative]>;
 def X86fxor    : SDNode<"X86ISD::FXOR",      SDTFPBinOp,
@@ -380,6 +382,11 @@
 defm DIV : scalar_sse12_fp_binop_rm<0x5E, "div", fdiv,
                                     int_x86_sse_div_ss, int_x86_sse2_div_sd>;
 
+defm MAX : scalar_sse12_fp_binop_rm<0x5F, "max", X86fmax,
+                                    int_x86_sse_max_ss, int_x86_sse2_max_sd>;
+defm MIN : scalar_sse12_fp_binop_rm<0x5D, "min", X86fmin,
+                                    int_x86_sse_min_ss, int_x86_sse2_min_sd>;
+
 
 def SQRTSSr : SSI<0x51, MRMSrcReg, (ops FR32:$dst, FR32:$src),
                 "sqrtss {$src, $dst|$dst, $src}",
@@ -394,24 +401,6 @@
                  "sqrtsd {$src, $dst|$dst, $src}",
                  [(set FR64:$dst, (fsqrt (loadf64 addr:$src)))]>;
 
-class SS_Intrr<bits<8> o, string OpcodeStr, Intrinsic IntId>
-  : SSI<o, MRMSrcReg, (ops VR128:$dst, VR128:$src1, VR128:$src2),
-        !strconcat(OpcodeStr, " {$src2, $dst|$dst, $src2}"),
-        [(set VR128:$dst, (v4f32 (IntId VR128:$src1, VR128:$src2)))]>;
-class SS_Intrm<bits<8> o, string OpcodeStr, Intrinsic IntId>
-  : SSI<o, MRMSrcMem, (ops VR128:$dst, VR128:$src1, ssmem:$src2),
-        !strconcat(OpcodeStr, " {$src2, $dst|$dst, $src2}"),
-        [(set VR128:$dst, (v4f32 (IntId VR128:$src1, sse_load_f32:$src2)))]>;
-class SD_Intrr<bits<8> o, string OpcodeStr, Intrinsic IntId>
-  : SDI<o, MRMSrcReg, (ops VR128:$dst, VR128:$src1, VR128:$src2),
-        !strconcat(OpcodeStr, " {$src2, $dst|$dst, $src2}"),
-        [(set VR128:$dst, (v2f64 (IntId VR128:$src1, VR128:$src2)))]>;
-class SD_Intrm<bits<8> o, string OpcodeStr, Intrinsic IntId>
-  : SDI<o, MRMSrcMem, (ops VR128:$dst, VR128:$src1, sdmem:$src2),
-        !strconcat(OpcodeStr, " {$src2, $dst|$dst, $src2}"),
-        [(set VR128:$dst, (v2f64 (IntId VR128:$src1, sse_load_f64:$src2)))]>;
-
-
 // Aliases to match intrinsics which expect XMM operand(s).
 
 defm SQRTSS_Int  : SS_IntUnary<0x51, "sqrtss" , int_x86_sse_sqrt_ss>;
@@ -419,19 +408,6 @@
 defm RSQRTSS_Int : SS_IntUnary<0x52, "rsqrtss", int_x86_sse_rsqrt_ss>;
 defm RCPSS_Int   : SS_IntUnary<0x53, "rcpss"  , int_x86_sse_rcp_ss>;
 
-let isTwoAddress = 1 in {
-let isCommutable = 1 in {
-def Int_MAXSSrr : SS_Intrr<0x5F, "maxss", int_x86_sse_max_ss>;
-def Int_MAXSDrr : SD_Intrr<0x5F, "maxsd", int_x86_sse2_max_sd>;
-def Int_MINSSrr : SS_Intrr<0x5D, "minss", int_x86_sse_min_ss>;
-def Int_MINSDrr : SD_Intrr<0x5D, "minsd", int_x86_sse2_min_sd>;
-}
-def Int_MAXSSrm : SS_Intrm<0x5F, "maxss", int_x86_sse_max_ss>;
-def Int_MAXSDrm : SD_Intrm<0x5F, "maxsd", int_x86_sse2_max_sd>;
-def Int_MINSSrm : SS_Intrm<0x5D, "minss", int_x86_sse_min_ss>;
-def Int_MINSDrm : SD_Intrm<0x5D, "minsd", int_x86_sse2_min_sd>;
-}
-
 // Conversion instructions
 def CVTTSS2SIrr: SSI<0x2C, MRMSrcReg, (ops GR32:$dst, FR32:$src),
                     "cvttss2si {$src, $dst|$dst, $src}",






More information about the llvm-commits mailing list