[llvm-commits] CVS: llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp PPCISelLowering.cpp PPCInstrInfo.td

Chris Lattner lattner at cs.uiuc.edu
Sun Mar 19 22:51:22 PST 2006



Changes in directory llvm/lib/Target/PowerPC:

PPCISelDAGToDAG.cpp updated: 1.169 -> 1.170
PPCISelLowering.cpp updated: 1.103 -> 1.104
PPCInstrInfo.td updated: 1.196 -> 1.197
---
Log message:

Add support for generating vspltw, instead of a vperm instruction with a 
constant pool load.  This generates significantly nicer code for splats.

When tblgen gets bugfixed, we can remove the custom selection code.



---
Diffs of the changes:  (+41 -13)

 PPCISelDAGToDAG.cpp |   16 ++++++++++++++++
 PPCISelLowering.cpp |   28 +++++++++++++++++++---------
 PPCInstrInfo.td     |   10 ++++++----
 3 files changed, 41 insertions(+), 13 deletions(-)


Index: llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp
diff -u llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp:1.169 llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp:1.170
--- llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp:1.169	Thu Mar 16 19:40:33 2006
+++ llvm/lib/Target/PowerPC/PPCISelDAGToDAG.cpp	Mon Mar 20 00:51:10 2006
@@ -927,6 +927,22 @@
   
   switch (N->getOpcode()) {
   default: break;
+  case ISD::VECTOR_SHUFFLE:
+    // FIXME: This should be autogenerated from the .td file, it is here for now
+    // due to bugs in tblgen.
+    if (Op.getOperand(1).getOpcode() == ISD::UNDEF &&
+        (Op.getValueType() == MVT::v4f32 || Op.getValueType() == MVT::v4i32) &&
+        PPC::isSplatShuffleMask(Op.getOperand(2).Val)) {
+      SDOperand N0;
+      Select(N0, N->getOperand(0));
+
+      Result = CodeGenMap[Op] = 
+        SDOperand(CurDAG->getTargetNode(PPC::VSPLTW, MVT::v4f32,
+                      getI32Imm(PPC::getVSPLTImmediate(Op.getOperand(2).Val)),
+                                        N0), 0);
+      return;
+    }
+    assert(0 && "ILLEGAL VECTOR_SHUFFLE!");
   case ISD::SETCC:
     Result = SelectSETCC(Op);
     return;


Index: llvm/lib/Target/PowerPC/PPCISelLowering.cpp
diff -u llvm/lib/Target/PowerPC/PPCISelLowering.cpp:1.103 llvm/lib/Target/PowerPC/PPCISelLowering.cpp:1.104
--- llvm/lib/Target/PowerPC/PPCISelLowering.cpp:1.103	Mon Mar 20 00:37:44 2006
+++ llvm/lib/Target/PowerPC/PPCISelLowering.cpp	Mon Mar 20 00:51:10 2006
@@ -245,6 +245,12 @@
 /// VSPLTB/VSPLTH/VSPLTW.
 bool PPC::isSplatShuffleMask(SDNode *N) {
   assert(N->getOpcode() == ISD::BUILD_VECTOR);
+  
+  // We can only splat 8-bit, 16-bit, and 32-bit quantities.
+  if (N->getNumOperands() != 4 && N->getNumOperands() != 8 &&
+      N->getNumOperands() != 16)
+    return false;
+  
   // This is a splat operation if each element of the permute is the same, and
   // if the value doesn't reference the second vector.
   SDOperand Elt = N->getOperand(0);
@@ -263,11 +269,10 @@
 /// specified isSplatShuffleMask VECTOR_SHUFFLE mask.
 unsigned PPC::getVSPLTImmediate(SDNode *N) {
   assert(isSplatShuffleMask(N));
-  return cast<ConstantSDNode>(N)->getValue();
+  return cast<ConstantSDNode>(N->getOperand(0))->getValue();
 }
 
 
-
 /// LowerOperation - Provide custom lowering hooks for some operations.
 ///
 SDOperand PPCTargetLowering::LowerOperation(SDOperand Op, SelectionDAG &DAG) {
@@ -602,17 +607,22 @@
                        DAG.getSrcValue(NULL));
   }
   case ISD::VECTOR_SHUFFLE: {
-    // FIXME: Cases that are handled by instructions that take permute
-    // immediates (such as vsplt*) shouldn't be lowered here!  Also handle cases
-    // that are cheaper to do as multiple such instructions than as a constant
-    // pool load/vperm pair.
+    SDOperand V1 = Op.getOperand(0);
+    SDOperand V2 = Op.getOperand(1);
+    SDOperand PermMask = Op.getOperand(2);
+    
+    // Cases that are handled by instructions that take permute immediates
+    // (such as vsplt*) should be left as VECTOR_SHUFFLE nodes so they can be
+    // selected by the instruction selector.
+    if (PPC::isSplatShuffleMask(PermMask.Val) && V2.getOpcode() == ISD::UNDEF)
+      break;
+    
+    // TODO: Handle more cases, and also handle cases that are cheaper to do as
+    // multiple such instructions than as a constant pool load/vperm pair.
     
     // Lower this to a VPERM(V1, V2, V3) expression, where V3 is a constant
     // vector that will get spilled to the constant pool.
-    SDOperand V1 = Op.getOperand(0);
-    SDOperand V2 = Op.getOperand(1);
     if (V2.getOpcode() == ISD::UNDEF) V2 = V1;
-    SDOperand PermMask = Op.getOperand(2);
     
     // The SHUFFLE_VECTOR mask is almost exactly what we want for vperm, except
     // that it is in input element units, not in bytes.  Convert now.


Index: llvm/lib/Target/PowerPC/PPCInstrInfo.td
diff -u llvm/lib/Target/PowerPC/PPCInstrInfo.td:1.196 llvm/lib/Target/PowerPC/PPCInstrInfo.td:1.197
--- llvm/lib/Target/PowerPC/PPCInstrInfo.td:1.196	Mon Mar 20 00:15:45 2006
+++ llvm/lib/Target/PowerPC/PPCInstrInfo.td	Mon Mar 20 00:51:10 2006
@@ -1032,10 +1032,12 @@
                       "vsplth $vD, $vB, $UIMM", VecPerm,
                       []>;
                       
-//def VSPLTW : VXForm_1<652, (ops VRRC:$vD, u5imm:$UIMM, VRRC:$vB),
-//                      "vspltw $vD, $vB, $UIMM", VecPerm,
-//                      [(set VRRC:$vD, (vector_shuffle (v4f32 VRRC:$vB), (undef),
-//                                      VSPLT_shuffle_mask:$UIMM))]>;
+def VSPLTW : VXForm_1<652, (ops VRRC:$vD, u5imm:$UIMM, VRRC:$vB),
+                      "vspltw $vD, $vB, $UIMM", VecPerm,
+                      [/*
+                       (set VRRC:$vD, (vector_shuffle (v4f32 VRRC:$vB), (undef),
+                                      VSPLT_shuffle_mask:$UIMM))*/]>;
+                      // FIXME: ALSO ADD SUPPORT FOR v4i32!
                       
 // VX-Form Pseudo Instructions
 






More information about the llvm-commits mailing list