[llvm-commits] [llvm] r47798 - in /llvm/trunk/lib: CodeGen/SelectionDAG/LegalizeDAG.cpp Target/X86/X86ISelLowering.cpp Target/X86/X86ISelLowering.h Target/X86/X86InstrInfo.td

Andrew Lenharth alenhar2 at cs.uiuc.edu
Sat Mar 1 13:52:35 PST 2008


Author: alenhar2
Date: Sat Mar  1 15:52:34 2008
New Revision: 47798

URL: http://llvm.org/viewvc/llvm-project?rev=47798&view=rev
Log:
all but CAS working on x86

Modified:
    llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp
    llvm/trunk/lib/Target/X86/X86ISelLowering.cpp
    llvm/trunk/lib/Target/X86/X86ISelLowering.h
    llvm/trunk/lib/Target/X86/X86InstrInfo.td

Modified: llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp?rev=47798&r1=47797&r2=47798&view=diff

==============================================================================
--- llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp (original)
+++ llvm/trunk/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp Sat Mar  1 15:52:34 2008
@@ -1165,23 +1165,24 @@
     assert(((Node->getNumOperands() == 4 && Node->getOpcode() == ISD::ATOMIC_LCS) ||
             (Node->getNumOperands() == 3 && Node->getOpcode() == ISD::ATOMIC_LAS) ||
             (Node->getNumOperands() == 3 && Node->getOpcode() == ISD::ATOMIC_SWAP)) &&
-           "Invalid MemBarrier node!");
+           "Invalid Atomic node!");
     int num = Node->getOpcode() == ISD::ATOMIC_LCS ? 4 : 3;
-    MVT::ValueType VT = Node->getValueType(0);
-    switch (TLI.getOperationAction(ISD::ATOMIC_LCS, VT)) {
+    SDOperand Ops[4];
+    for (int x = 0; x < num; ++x)
+      Ops[x] = LegalizeOp(Node->getOperand(x));
+    Result = DAG.UpdateNodeOperands(Result, &Ops[0], num);
+    
+    switch (TLI.getOperationAction(Node->getOpcode(), Node->getValueType(0))) {
     default: assert(0 && "This action is not supported yet!");
-    case TargetLowering::Legal: {
-      SDOperand Ops[4];
-      for (int x = 0; x < num; ++x)
-        Ops[x] = LegalizeOp(Node->getOperand(x));
-      Result = DAG.UpdateNodeOperands(Result, &Ops[0], num);
-      AddLegalizedOperand(SDOperand(Node, 0), Result.getValue(0));
-      AddLegalizedOperand(SDOperand(Node, 1), Result.getValue(1));
-      return Result.getValue(Op.ResNo);
+    case TargetLowering::Custom:
+      Result = TLI.LowerOperation(Result, DAG);
+      break;
+    case TargetLowering::Legal:
       break;
     }
-    }
-    break;
+    AddLegalizedOperand(SDOperand(Node, 0), Result.getValue(0));
+    AddLegalizedOperand(SDOperand(Node, 1), Result.getValue(1));
+    return Result.getValue(Op.ResNo);
   }
 
   case ISD::Constant: {

Modified: llvm/trunk/lib/Target/X86/X86ISelLowering.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/X86/X86ISelLowering.cpp?rev=47798&r1=47797&r2=47798&view=diff

==============================================================================
--- llvm/trunk/lib/Target/X86/X86ISelLowering.cpp (original)
+++ llvm/trunk/lib/Target/X86/X86ISelLowering.cpp Sat Mar  1 15:52:34 2008
@@ -283,6 +283,9 @@
   if (!Subtarget->hasSSE2())
     setOperationAction(ISD::MEMBARRIER    , MVT::Other, Expand);
 
+  setOperationAction(ISD::ATOMIC_LCS     , MVT::i8, Custom);
+  setOperationAction(ISD::ATOMIC_LCS     , MVT::i16, Custom);
+  setOperationAction(ISD::ATOMIC_LCS     , MVT::i32, Custom);
 
   // Use the default ISD::LOCATION, ISD::DECLARE expansion.
   setOperationAction(ISD::LOCATION, MVT::Other, Expand);
@@ -5345,11 +5348,35 @@
   return Op;
 }
 
+SDOperand X86TargetLowering::LowerCAS(SDOperand Op, SelectionDAG &DAG) {
+  MVT::ValueType T = cast<AtomicSDNode>(Op.Val)->getVT();
+  unsigned Reg;
+  unsigned size;
+  switch(T) {
+  case MVT::i8:  Reg = X86::AL;  size = 1; break;
+  case MVT::i16: Reg = X86::AX;  size = 2; break;
+  case MVT::i32: Reg = X86::EAX; size = 4; break;
+  };
+  SDOperand cpIn = DAG.getCopyToReg(Op.getOperand(0), Reg,
+                                    Op.getOperand(2), SDOperand());
+  SDOperand Ops[] = { cpIn.getValue(0),
+                       Op.getOperand(1),
+                       Op.getOperand(3),
+                       DAG.getTargetConstant(size, MVT::i8),
+                       cpIn.getValue(1) };
+  SDVTList Tys = DAG.getVTList(MVT::Other, MVT::Flag);
+  SDOperand Result = DAG.getNode(X86ISD::LCMPXCHG_DAG, Tys, Ops, 5);
+  SDOperand cpOut = 
+    DAG.getCopyFromReg(Result.getValue(0), Reg, T, Result.getValue(1));
+  return cpOut;
+}
+
 /// LowerOperation - Provide custom lowering hooks for some operations.
 ///
 SDOperand X86TargetLowering::LowerOperation(SDOperand Op, SelectionDAG &DAG) {
   switch (Op.getOpcode()) {
   default: assert(0 && "Should not custom lower this!");
+  case ISD::ATOMIC_LCS:         return LowerCAS(Op,DAG);
   case ISD::BUILD_VECTOR:       return LowerBUILD_VECTOR(Op, DAG);
   case ISD::VECTOR_SHUFFLE:     return LowerVECTOR_SHUFFLE(Op, DAG);
   case ISD::EXTRACT_VECTOR_ELT: return LowerEXTRACT_VECTOR_ELT(Op, DAG);
@@ -5454,6 +5481,7 @@
   case X86ISD::EH_RETURN:          return "X86ISD::EH_RETURN";
   case X86ISD::TC_RETURN:          return "X86ISD::TC_RETURN";
   case X86ISD::FNSTCW16m:          return "X86ISD::FNSTCW16m";
+  case X86ISD::LCMPXCHG_DAG:       return "x86ISD::LCMPXCHG_DAG";
   }
 }
 

Modified: llvm/trunk/lib/Target/X86/X86ISelLowering.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/X86/X86ISelLowering.h?rev=47798&r1=47797&r2=47798&view=diff

==============================================================================
--- llvm/trunk/lib/Target/X86/X86ISelLowering.h (original)
+++ llvm/trunk/lib/Target/X86/X86ISelLowering.h Sat Mar  1 15:52:34 2008
@@ -208,6 +208,9 @@
       //   operand #3 optional in flag
       TC_RETURN,
 
+      // compare and swap
+      LCMPXCHG_DAG,
+
       // Store FP control world into i16 memory
       FNSTCW16m
     };
@@ -540,6 +543,7 @@
     SDOperand LowerFLT_ROUNDS_(SDOperand Op, SelectionDAG &DAG);
     SDOperand LowerCTLZ(SDOperand Op, SelectionDAG &DAG);
     SDOperand LowerCTTZ(SDOperand Op, SelectionDAG &DAG);
+    SDOperand LowerCAS(SDOperand Op, SelectionDAG &DAG);
     SDNode *ExpandFP_TO_SINT(SDNode *N, SelectionDAG &DAG);
     SDNode *ExpandREADCYCLECOUNTER(SDNode *N, SelectionDAG &DAG);
   };

Modified: llvm/trunk/lib/Target/X86/X86InstrInfo.td
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/X86/X86InstrInfo.td?rev=47798&r1=47797&r2=47798&view=diff

==============================================================================
--- llvm/trunk/lib/Target/X86/X86InstrInfo.td (original)
+++ llvm/trunk/lib/Target/X86/X86InstrInfo.td Sat Mar  1 15:52:34 2008
@@ -35,6 +35,9 @@
                                   [SDTCisVT<0, i8>,
                                    SDTCisVT<1, i8>, SDTCisVT<2, i32>]>;
 
+def SDTX86cas : SDTypeProfile<0, 3, [SDTCisPtrTy<0>, SDTCisInt<1>, 
+                                     SDTCisVT<2, i8>]>;
+
 def SDTX86Ret     : SDTypeProfile<0, 1, [SDTCisVT<0, i16>]>;
 
 def SDT_X86CallSeqStart : SDCallSeqStart<[ SDTCisVT<0, i32> ]>;
@@ -69,6 +72,10 @@
                         [SDNPHasChain]>;
 def X86setcc   : SDNode<"X86ISD::SETCC",    SDTX86SetCC>;
 
+def X86cas : SDNode<"X86ISD::LCMPXCHG_DAG", SDTX86cas,
+                        [SDNPHasChain, SDNPInFlag, SDNPOutFlag, SDNPMayStore,
+                         SDNPMayLoad]>;
+
 def X86retflag : SDNode<"X86ISD::RET_FLAG", SDTX86Ret,
                         [SDNPHasChain, SDNPOptInFlag]>;
 
@@ -2539,28 +2546,29 @@
 // Atomic support
 //
 
-//FIXME: Please check the format
-
-let Defs = [EAX], Uses = [EAX] in {
-def CMPXCHG32 : I<0xB1, Pseudo, (outs), (ins GR32:$ptr, GR32:$swap),
-               "cmpxchgl $swap,($ptr)", []>, TB;
-def LCMPXCHG32 : I<0xB1, Pseudo, (outs), (ins GR32:$ptr, GR32:$swap),
-               "lock cmpxchgl $swap,($ptr)", []>, TB, LOCK;
+//FIXME: Please check the format Pseudo is certainly wrong, but the opcode and
+//       prefixes should be correct
+let Defs = [EAX, EFLAGS], Uses = [EAX] in {
+def CMPXCHG32 : I<0xB1, Pseudo, (outs), (ins i32mem:$ptr, GR32:$swap),
+               "cmpxchgl $swap,$ptr", []>, TB;
+def LCMPXCHG32 : I<0xB1, Pseudo, (outs), (ins i32mem:$ptr, GR32:$swap),
+               "lock cmpxchgl $swap,$ptr", [(X86cas addr:$ptr, GR32:$swap, 4)]>, TB, LOCK;
 }
-let Defs = [AX], Uses = [AX] in {
-def CMPXCHG16 : I<0xB1, Pseudo, (outs), (ins GR32:$ptr, GR16:$swap),
+
+let Defs = [AX, EFLAGS], Uses = [AX] in {
+def CMPXCHG16 : I<0xB1, Pseudo, (outs), (ins i16mem:$ptr, GR16:$swap),
                "cmpxchgw $swap,($ptr)", []>, TB, OpSize;
-def LCMPXCHG16 : I<0xB1, Pseudo, (outs), (ins GR32:$ptr, GR16:$swap),
-               "cmpxchgw $swap,($ptr)", []>, TB, OpSize, LOCK;
+def LCMPXCHG16 : I<0xB1, Pseudo, (outs), (ins i16mem:$ptr, GR16:$swap),
+               "lock cmpxchgw $swap,$ptr", [(X86cas addr:$ptr, GR16:$swap, 2)]>, TB, OpSize, LOCK;
 }
-let Defs = [AL], Uses = [AL] in {
-def CMPXCHG8 : I<0xB0, Pseudo, (outs), (ins GR32:$ptr, GR8:$swap),
+let Defs = [AL, EFLAGS], Uses = [AL] in {
+def CMPXCHG8 : I<0xB0, Pseudo, (outs), (ins i8mem:$ptr, GR8:$swap),
                "cmpxchgb $swap,($ptr)", []>, TB;
-def LCMPXCHG8 : I<0xB0, Pseudo, (outs), (ins GR32:$ptr, GR8:$swap),
-               "cmpxchgb $swap,($ptr)", []>, TB, LOCK;
+def LCMPXCHG8 : I<0xB0, Pseudo, (outs), (ins i8mem:$ptr, GR8:$swap),
+               "lock cmpxchgb $swap,$ptr", [(X86cas addr:$ptr, GR8:$swap, 1)]>, TB, LOCK;
 }
 
-let Constraints = "$val = $dst" in {
+let Constraints = "$val = $dst", Defs = [EFLAGS] in {
 def LXADD32 : I<0xC1, Pseudo, (outs GR32:$dst), (ins i32mem:$ptr, GR32:$val),
                "lock xadd $val, $ptr", 
                [(set GR32:$dst, (atomic_las_32 addr:$ptr, GR32:$val))]>,
@@ -2598,23 +2606,6 @@
                "lock xchg $val, $ptr", []>;
 }
 
-//FIXME: these are a hack until the patterns using the LCMPXCHG written
-let Defs = [EAX], Uses = [EAX] in
-def PLCMPXCHG32 : I<0, Pseudo, (outs GR32:$dst), 
-                  (ins i32mem:$ptr, GR32:$cmp, GR32:$swap),
-                  "movl $cmp, %eax \n lock \n cmpxchgl $swap,$ptr \n movl %eax, $dst",
-                  [(set GR32:$dst, (atomic_lcs_32 addr:$ptr, GR32:$cmp, GR32:$swap))]>;
-let Defs = [AX] in
-def PLCMPXCHG16 : I<0, Pseudo, (outs GR16:$dst), 
-                  (ins i16mem:$ptr, GR16:$cmp, GR16:$swap),
-                  "movw $cmp, %ax \n lock \n cmpxchgw $swap,$ptr \n movw %ax, $dst",
-                  [(set GR16:$dst, (atomic_lcs_16 addr:$ptr, GR16:$cmp, GR16:$swap))]>;
-let Defs = [AL] in
-def PLCMPXCHG8 : I<0, Pseudo, (outs GR8:$dst), 
-                  (ins i8mem:$ptr, GR8:$cmp, GR8:$swap),
-                  "movb $cmp, %al \n lock cmpxchgb $swap,$ptr \n movb %al, $dst",
-                  [(set GR8:$dst, (atomic_lcs_8 addr:$ptr, GR8:$cmp, GR8:$swap))]>;
-
 //===----------------------------------------------------------------------===//
 // Non-Instruction Patterns
 //===----------------------------------------------------------------------===//





More information about the llvm-commits mailing list