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

Anton Korobeynikov asl at math.spbu.ru
Mon Nov 20 16:01:20 PST 2006



Changes in directory llvm/lib/Target/X86:

X86ISelLowering.cpp updated: 1.293 -> 1.294
X86Subtarget.h updated: 1.20 -> 1.21
---
Log message:

Refactored *GVRequiresExtraLoad() to Subtarget method.


---
Diffs of the changes:  (+109 -120)

 X86ISelLowering.cpp |  201 ++++++++++++++++++++++------------------------------
 X86Subtarget.h      |   28 +++++--
 2 files changed, 109 insertions(+), 120 deletions(-)


Index: llvm/lib/Target/X86/X86ISelLowering.cpp
diff -u llvm/lib/Target/X86/X86ISelLowering.cpp:1.293 llvm/lib/Target/X86/X86ISelLowering.cpp:1.294
--- llvm/lib/Target/X86/X86ISelLowering.cpp:1.293	Mon Nov 20 04:46:14 2006
+++ llvm/lib/Target/X86/X86ISelLowering.cpp	Mon Nov 20 18:01:06 2006
@@ -35,8 +35,6 @@
 #include "llvm/ADT/StringExtras.h"
 using namespace llvm;
 
-static bool WindowsGVRequiresExtraLoad(GlobalValue *GV);
-
 // FIXME: temporary.
 static cl::opt<bool> EnableFastCC("enable-x86-fastcc", cl::Hidden,
                                   cl::desc("Enable fastcc on X86"));
@@ -59,7 +57,7 @@
   if (!Subtarget->isTargetDarwin())
     // Darwin should use _setjmp/_longjmp instead of setjmp/longjmp.
     setUseUnderscoreSetJmpLongJmp(true);
-    
+
   // Add legal addressing mode scale values.
   addLegalAddressScale(8);
   addLegalAddressScale(4);
@@ -69,7 +67,7 @@
   addLegalAddressScale(9);
   addLegalAddressScale(5);
   addLegalAddressScale(3);
-  
+
   // Set up the register classes.
   addRegisterClass(MVT::i8, X86::GR8RegisterClass);
   addRegisterClass(MVT::i16, X86::GR16RegisterClass);
@@ -229,12 +227,12 @@
 
   // VASTART needs to be custom lowered to use the VarArgsFrameIndex
   setOperationAction(ISD::VASTART           , MVT::Other, Custom);
-  
+
   // Use the default implementation.
   setOperationAction(ISD::VAARG             , MVT::Other, Expand);
   setOperationAction(ISD::VACOPY            , MVT::Other, Expand);
   setOperationAction(ISD::VAEND             , MVT::Other, Expand);
-  setOperationAction(ISD::STACKSAVE,          MVT::Other, Expand); 
+  setOperationAction(ISD::STACKSAVE,          MVT::Other, Expand);
   setOperationAction(ISD::STACKRESTORE,       MVT::Other, Expand);
   if (Subtarget->is64Bit())
     setOperationAction(ISD::DYNAMIC_STACKALLOC, MVT::i64, Expand);
@@ -272,9 +270,9 @@
   } else {
     // Set up the FP register classes.
     addRegisterClass(MVT::f64, X86::RFPRegisterClass);
-    
+
     setOperationAction(ISD::UNDEF, MVT::f64, Expand);
-    
+
     if (!UnsafeFPMath) {
       setOperationAction(ISD::FSIN           , MVT::f64  , Expand);
       setOperationAction(ISD::FCOS           , MVT::f64  , Expand);
@@ -372,7 +370,7 @@
     setOperationAction(ISD::EXTRACT_VECTOR_ELT, MVT::v2f64, Custom);
     setOperationAction(ISD::EXTRACT_VECTOR_ELT, MVT::v2i64, Custom);
 
-    // Promote v16i8, v8i16, v4i32 load, select, and, or, xor to v2i64. 
+    // Promote v16i8, v8i16, v4i32 load, select, and, or, xor to v2i64.
     for (unsigned VT = (unsigned)MVT::v16i8; VT != (unsigned)MVT::v2i64; VT++) {
       setOperationAction(ISD::AND,    (MVT::ValueType)VT, Promote);
       AddPromotedToType (ISD::AND,    (MVT::ValueType)VT, MVT::v2i64);
@@ -655,8 +653,7 @@
   // turn it into a TargetGlobalAddress node so that legalize doesn't hack it.
   if (GlobalAddressSDNode *G = dyn_cast<GlobalAddressSDNode>(Callee)) {
     // We should use extra load for direct calls to dllimported functions
-    if (!((Subtarget->isTargetCygwin() || Subtarget->isTargetWindows()) &&
-          WindowsGVRequiresExtraLoad(G->getGlobal())))
+    if (!Subtarget->GVRequiresExtraLoad(G->getGlobal(), true))
       Callee = DAG.getTargetGlobalAddress(G->getGlobal(), getPointerTy());
   } else if (ExternalSymbolSDNode *S = dyn_cast<ExternalSymbolSDNode>(Callee))
     Callee = DAG.getTargetExternalSymbol(S->getSymbol(), getPointerTy());
@@ -671,7 +668,7 @@
   // Add argument registers to the end of the list so that they are known live
   // into the call.
   for (unsigned i = 0, e = RegsToPass.size(); i != e; ++i)
-    Ops.push_back(DAG.getRegister(RegsToPass[i].first, 
+    Ops.push_back(DAG.getRegister(RegsToPass[i].first,
                                   RegsToPass[i].second.getValueType()));
 
   if (InFlag.Val)
@@ -689,7 +686,7 @@
   // This is common for Darwin/X86, Linux & Mingw32 targets.
   if (CallingConv == CallingConv::CSRet)
     NumBytesForCalleeToPush = 4;
-  
+
   NodeTys.clear();
   NodeTys.push_back(MVT::Other);   // Returns a chain
   if (RetVT != MVT::Other)
@@ -702,7 +699,7 @@
   Chain = DAG.getNode(ISD::CALLSEQ_END, NodeTys, &Ops[0], Ops.size());
   if (RetVT != MVT::Other)
     InFlag = Chain.getValue(1);
-  
+
   std::vector<SDOperand> ResultVals;
   NodeTys.clear();
   switch (RetVT) {
@@ -751,7 +748,7 @@
     std::vector<SDOperand> Ops;
     Ops.push_back(Chain);
     Ops.push_back(InFlag);
-    SDOperand RetVal = DAG.getNode(X86ISD::FP_GET_RESULT, Tys, 
+    SDOperand RetVal = DAG.getNode(X86ISD::FP_GET_RESULT, Tys,
                                    &Ops[0], Ops.size());
     Chain  = RetVal.getValue(1);
     InFlag = RetVal.getValue(2);
@@ -788,7 +785,7 @@
   // If the function returns void, just return the chain.
   if (ResultVals.empty())
     return Chain;
-  
+
   // Otherwise, merge everything together with a MERGE_VALUES node.
   NodeTys.push_back(MVT::Other);
   ResultVals.push_back(Chain);
@@ -923,7 +920,7 @@
         TargetRegisterClass *RC = NULL;
         switch (ObjectVT) {
         default: break;
-        case MVT::i8: 
+        case MVT::i8:
           RC = X86::GR8RegisterClass;
           Reg = GPR8ArgRegs[NumIntRegs];
           break;
@@ -1193,8 +1190,7 @@
   // turn it into a TargetGlobalAddress node so that legalize doesn't hack it.
   if (GlobalAddressSDNode *G = dyn_cast<GlobalAddressSDNode>(Callee)) {
     // We should use extra load for direct calls to dllimported functions
-    if (!((Subtarget->isTargetCygwin() || Subtarget->isTargetWindows()) &&
-          WindowsGVRequiresExtraLoad(G->getGlobal())))
+    if (!Subtarget->GVRequiresExtraLoad(G->getGlobal(), true))
       Callee = DAG.getTargetGlobalAddress(G->getGlobal(), getPointerTy());
   } else if (ExternalSymbolSDNode *S = dyn_cast<ExternalSymbolSDNode>(Callee))
     Callee = DAG.getTargetExternalSymbol(S->getSymbol(), getPointerTy());
@@ -1209,7 +1205,7 @@
   // Add argument registers to the end of the list so that they are known live
   // into the call.
   for (unsigned i = 0, e = RegsToPass.size(); i != e; ++i)
-    Ops.push_back(DAG.getRegister(RegsToPass[i].first, 
+    Ops.push_back(DAG.getRegister(RegsToPass[i].first,
                                   RegsToPass[i].second.getValueType()));
 
   if (InFlag.Val)
@@ -1232,7 +1228,7 @@
   Chain = DAG.getNode(ISD::CALLSEQ_END, NodeTys, &Ops[0], Ops.size());
   if (RetVT != MVT::Other)
     InFlag = Chain.getValue(1);
-  
+
   std::vector<SDOperand> ResultVals;
   NodeTys.clear();
   switch (RetVT) {
@@ -1286,7 +1282,7 @@
   // If the function returns void, just return the chain.
   if (ResultVals.empty())
     return Chain;
-  
+
   // Otherwise, merge everything together with a MERGE_VALUES node.
   NodeTys.push_back(MVT::Other);
   ResultVals.push_back(Chain);
@@ -1407,7 +1403,7 @@
   static const unsigned XMMArgRegs[] = {
     X86::XMM0, X86::XMM1, X86::XMM2, X86::XMM3
   };
-  
+
   for (unsigned i = 0; i < NumArgs; ++i) {
     MVT::ValueType ObjectVT = Op.getValue(i).getValueType();
     unsigned ArgIncrement = 4;
@@ -1558,7 +1554,7 @@
     { X86::CL,  X86::DL },
     { X86::CX,  X86::DX },
     { X86::ECX, X86::EDX }
-  };  
+  };
 #endif
   static const unsigned XMMArgRegs[] = {
     X86::XMM0, X86::XMM1, X86::XMM2, X86::XMM3
@@ -1668,7 +1664,7 @@
          PtrOff = DAG.getNode(ISD::ADD, getPointerTy(), StackPtr, PtrOff);
          MemOpChains.push_back(DAG.getStore(Chain, Arg, PtrOff, NULL, 0));
          ArgOffset += 16;
-       }       
+       }
      }
      break;
     }
@@ -1691,8 +1687,7 @@
   // turn it into a TargetGlobalAddress node so that legalize doesn't hack it.
   if (GlobalAddressSDNode *G = dyn_cast<GlobalAddressSDNode>(Callee)) {
     // We should use extra load for direct calls to dllimported functions
-    if (!((Subtarget->isTargetCygwin() || Subtarget->isTargetWindows()) &&
-          WindowsGVRequiresExtraLoad(G->getGlobal())))
+    if (!Subtarget->GVRequiresExtraLoad(G->getGlobal(), true))
       Callee = DAG.getTargetGlobalAddress(G->getGlobal(), getPointerTy());
   } else if (ExternalSymbolSDNode *S = dyn_cast<ExternalSymbolSDNode>(Callee))
     Callee = DAG.getTargetExternalSymbol(S->getSymbol(), getPointerTy());
@@ -1707,7 +1702,7 @@
   // Add argument registers to the end of the list so that they are known live
   // into the call.
   for (unsigned i = 0, e = RegsToPass.size(); i != e; ++i)
-    Ops.push_back(DAG.getRegister(RegsToPass[i].first, 
+    Ops.push_back(DAG.getRegister(RegsToPass[i].first,
                                   RegsToPass[i].second.getValueType()));
 
   if (InFlag.Val)
@@ -1730,7 +1725,7 @@
   Chain = DAG.getNode(ISD::CALLSEQ_END, NodeTys, &Ops[0], Ops.size());
   if (RetVT != MVT::Other)
     InFlag = Chain.getValue(1);
-  
+
   std::vector<SDOperand> ResultVals;
   NodeTys.clear();
   switch (RetVT) {
@@ -1821,7 +1816,7 @@
   // If the function returns void, just return the chain.
   if (ResultVals.empty())
     return Chain;
-  
+
   // Otherwise, merge everything together with a MERGE_VALUES node.
   NodeTys.push_back(MVT::Other);
   ResultVals.push_back(Chain);
@@ -1888,7 +1883,7 @@
   }
 
   ArgValues.push_back(Root);
-  
+
   // If the function takes variable number of arguments, make a frame index for
   // the start of the first vararg value... for expansion of llvm.va_start.
   bool isVarArg = cast<ConstantSDNode>(Op.getOperand(2))->getValue() != 0;
@@ -1904,7 +1899,7 @@
   ReturnAddrIndex = 0;              // No return address slot generated yet.
 
   MF.getInfo<X86FunctionInfo>()->setBytesToPopOnReturn(BytesToPopOnReturn);
-  
+
   // Return the new list of results.
   std::vector<MVT::ValueType> RetVTs(Op.Val->value_begin(),
                                      Op.Val->value_end());
@@ -1919,8 +1914,8 @@
   bool isTailCall     = cast<ConstantSDNode>(Op.getOperand(3))->getValue() != 0;
   SDOperand Callee    = Op.getOperand(4);
   MVT::ValueType RetVT= Op.Val->getValueType(0);
-  unsigned NumOps     = (Op.getNumOperands() - 5) / 2;  
-  
+  unsigned NumOps     = (Op.getNumOperands() - 5) / 2;
+
   // Count how many bytes are to be pushed on the stack.
   unsigned NumBytes = 0;
   for (unsigned i = 0; i != NumOps; ++i) {
@@ -1940,7 +1935,7 @@
       break;
     }
   }
-  
+
   Chain = DAG.getCALLSEQ_START(Chain,DAG.getConstant(NumBytes, getPointerTy()));
 
   // Arguments go on the stack in reverse order, as specified by the ABI.
@@ -1990,8 +1985,7 @@
   // turn it into a TargetGlobalAddress node so that legalize doesn't hack it.
   if (GlobalAddressSDNode *G = dyn_cast<GlobalAddressSDNode>(Callee)) {
     // We should use extra load for direct calls to dllimported functions
-    if (!((Subtarget->isTargetCygwin() || Subtarget->isTargetWindows()) &&
-          WindowsGVRequiresExtraLoad(G->getGlobal())))
+    if (!Subtarget->GVRequiresExtraLoad(G->getGlobal(), true))
       Callee = DAG.getTargetGlobalAddress(G->getGlobal(), getPointerTy());
   } else if (ExternalSymbolSDNode *S = dyn_cast<ExternalSymbolSDNode>(Callee))
     Callee = DAG.getTargetExternalSymbol(S->getSymbol(), getPointerTy());
@@ -2009,7 +2003,7 @@
 
   // Create the CALLSEQ_END node.
   unsigned NumBytesForCalleeToPush;
-  
+
   if (isVarArg) {
     NumBytesForCalleeToPush = 0;
   } else {
@@ -2028,7 +2022,7 @@
   Chain = DAG.getNode(ISD::CALLSEQ_END, NodeTys, &Ops[0], Ops.size());
   if (RetVT != MVT::Other)
     InFlag = Chain.getValue(1);
-  
+
   std::vector<SDOperand> ResultVals;
   NodeTys.clear();
   switch (RetVT) {
@@ -2067,7 +2061,7 @@
     std::vector<SDOperand> Ops;
     Ops.push_back(Chain);
     Ops.push_back(InFlag);
-    SDOperand RetVal = DAG.getNode(X86ISD::FP_GET_RESULT, Tys, 
+    SDOperand RetVal = DAG.getNode(X86ISD::FP_GET_RESULT, Tys,
                                    &Ops[0], Ops.size());
     Chain  = RetVal.getValue(1);
     InFlag = RetVal.getValue(2);
@@ -2104,7 +2098,7 @@
   // If the function returns void, just return the chain.
   if (ResultVals.empty())
     return Chain;
-  
+
   // Otherwise, merge everything together with a MERGE_VALUES node.
   NodeTys.push_back(MVT::Other);
   ResultVals.push_back(Chain);
@@ -2240,7 +2234,7 @@
         }
         break;
       }
-      
+
       NumIntRegs += ObjIntRegs;
     }
 
@@ -2357,7 +2351,7 @@
         return true;
       }
     }
-    
+
     switch (SetCCOpcode) {
     default: break;
     case ISD::SETEQ:  X86CC = X86::COND_E;  break;
@@ -2426,25 +2420,6 @@
   }
 }
 
-/// DarwinGVRequiresExtraLoad - true if accessing the GV requires an extra
-/// load. For Darwin, external and weak symbols are indirect, loading the value
-/// at address GV rather then the value of GV itself. This means that the
-/// GlobalAddress must be in the base or index register of the address, not the
-/// GV offset field.
-static bool DarwinGVRequiresExtraLoad(GlobalValue *GV) {
-  return (GV->hasWeakLinkage() || GV->hasLinkOnceLinkage() ||
-          (GV->isExternal() && !GV->hasNotBeenReadFromBytecode()));
-}
-
-/// WindowsGVRequiresExtraLoad - true if accessing the GV requires an extra
-/// load. For Windows, dllimported symbols are indirect, loading the value at
-/// address GV rather then the value of GV itself. This means that the
-/// GlobalAddress must be in the base or index register of the address, not the
-/// GV offset field.
-static bool WindowsGVRequiresExtraLoad(GlobalValue *GV) {
-  return (GV->hasDLLImportLinkage());  
-}
-
 /// isUndefOrInRange - Op is either an undef node or a ConstantSDNode.  Return
 /// true if Op is undef or if its value falls within the specified range (L, H].
 static bool isUndefOrInRange(SDOperand Op, unsigned Low, unsigned Hi) {
@@ -2904,7 +2879,7 @@
 bool X86::isSplatLoMask(SDNode *N) {
   assert(N->getOpcode() == ISD::BUILD_VECTOR);
 
-  for (unsigned i = 0, e = N->getNumOperands(); i < e; ++i) 
+  for (unsigned i = 0, e = N->getNumOperands(); i < e; ++i)
     if (!isUndefOrEqual(N->getOperand(i), 0))
       return false;
   return true;
@@ -3034,7 +3009,7 @@
 /// ShouldXformToMOVHLPS - Return true if the node should be transformed to
 /// match movhlps. The lower half elements should come from upper half of
 /// V1 (and in order), and the upper half elements should come from the upper
-/// half of V2 (and in order). 
+/// half of V2 (and in order).
 static bool ShouldXformToMOVHLPS(SDNode *Mask) {
   unsigned NumElems = Mask->getNumOperands();
   if (NumElems != 4)
@@ -3431,7 +3406,7 @@
     }
 
     // Take advantage of the fact GR32 to VR128 scalar_to_vector (i.e. movd)
-    // clears the upper bits. 
+    // clears the upper bits.
     // FIXME: we can do the same for v4f32 case when we know both parts of
     // the lower half come from scalar_to_vector (loadf32). We should do
     // that in post legalizer dag combiner with target specific hooks.
@@ -3502,7 +3477,7 @@
 
   if (X86::isMOVLMask(PermMask.Val))
     return (V1IsUndef) ? V2 : Op;
-      
+
   if (X86::isMOVSHDUPMask(PermMask.Val) ||
       X86::isMOVSLDUPMask(PermMask.Val) ||
       X86::isMOVHLPSMask(PermMask.Val) ||
@@ -3545,7 +3520,7 @@
 
   if (V2IsSplat) {
     // Normalize mask so all entries that point to V2 points to its first
-    // element then try to match unpck{h|l} again. If match, return a 
+    // element then try to match unpck{h|l} again. If match, return a
     // new vector_shuffle with the corrected mask.
     SDOperand NewMask = NormalizeMask(PermMask, DAG);
     if (NewMask.Val != PermMask.Val) {
@@ -3703,7 +3678,7 @@
       DAG.getNode(ISD::VECTOR_SHUFFLE, VT, V1, V2,
                   DAG.getNode(ISD::BUILD_VECTOR, MaskVT,
                               &LoMask[0], LoMask.size()));
-    SDOperand HiShuffle = 
+    SDOperand HiShuffle =
       DAG.getNode(ISD::VECTOR_SHUFFLE, VT, V1, V2,
                   DAG.getNode(ISD::BUILD_VECTOR, MaskVT,
                               &HiMask[0], HiMask.size()));
@@ -3845,7 +3820,7 @@
   return DAG.getNode(X86ISD::S2VEC, Op.getValueType(), AnyExt);
 }
 
-// ConstantPool, JumpTable, GlobalAddress, and ExternalSymbol are lowered as 
+// ConstantPool, JumpTable, GlobalAddress, and ExternalSymbol are lowered as
 // their target countpart wrapped in the X86ISD::Wrapper node. Suppose N is
 // one of the above mentioned nodes. It has to be wrapped because otherwise
 // Select(N) returns N. So the raw TargetGlobalAddress nodes, etc. can only
@@ -3888,14 +3863,11 @@
     // the GlobalAddress must be in the base or index register of the address,
     // not the GV offset field.
     if (getTargetMachine().getRelocationModel() != Reloc::Static &&
-        DarwinGVRequiresExtraLoad(GV))
-      Result = DAG.getLoad(getPointerTy(), DAG.getEntryNode(), Result, NULL, 0);
-  } else if (Subtarget->isTargetCygwin() || Subtarget->isTargetWindows()) {
-    // FIXME: What about PIC?
-    if (WindowsGVRequiresExtraLoad(GV))
+        Subtarget->GVRequiresExtraLoad(GV, false))
       Result = DAG.getLoad(getPointerTy(), DAG.getEntryNode(), Result, NULL, 0);
+  } else if (Subtarget->GVRequiresExtraLoad(GV, false)) {
+    Result = DAG.getLoad(getPointerTy(), DAG.getEntryNode(), Result, NULL, 0);
   }
-  
 
   return Result;
 }
@@ -4149,7 +4121,7 @@
   bool isFP = MVT::isFloatingPoint(Op.getOperand(1).getValueType());
   unsigned X86CC;
 
-  if (translateX86CC(cast<CondCodeSDNode>(CC)->get(), isFP, X86CC, 
+  if (translateX86CC(cast<CondCodeSDNode>(CC)->get(), isFP, X86CC,
                      Op0, Op1, DAG)) {
     SDOperand Ops1[] = { Chain, Op0, Op1 };
     Cond = DAG.getNode(X86ISD::CMP, VTs1, 2, Ops1, 3).getValue(1);
@@ -4281,7 +4253,7 @@
         getTargetMachine().getRelocationModel() == Reloc::PIC_)
       Result = DAG.getNode(ISD::ADD, getPointerTy(),
                            DAG.getNode(X86ISD::GlobalBaseReg, getPointerTy()),
-                           Result);    
+                           Result);
   }
 
   return Result;
@@ -4289,13 +4261,13 @@
 
 SDOperand X86TargetLowering::LowerCALL(SDOperand Op, SelectionDAG &DAG) {
   unsigned CallingConv= cast<ConstantSDNode>(Op.getOperand(1))->getValue();
-  
+
   if (Subtarget->is64Bit())
     return LowerX86_64CCCCallTo(Op, DAG);
   else
     switch (CallingConv) {
     default:
-      assert(0 && "Unsupported calling convention");      
+      assert(0 && "Unsupported calling convention");
     case CallingConv::Fast:
       if (EnableFastCC) {
         return LowerFastCCCallTo(Op, DAG, false);
@@ -4304,7 +4276,7 @@
     case CallingConv::C:
     case CallingConv::CSRet:
       return LowerCCCCallTo(Op, DAG);
-    case CallingConv::X86_StdCall: 
+    case CallingConv::X86_StdCall:
       return LowerStdCallCCCallTo(Op, DAG);
     case CallingConv::X86_FastCall:
       return LowerFastCCCallTo(Op, DAG, true);
@@ -4313,7 +4285,7 @@
 
 SDOperand X86TargetLowering::LowerRET(SDOperand Op, SelectionDAG &DAG) {
   SDOperand Copy;
-    
+
   switch(Op.getNumOperands()) {
     default:
       assert(0 && "Do not know how to return this many arguments!");
@@ -4323,7 +4295,7 @@
                         DAG.getConstant(getBytesToPopOnReturn(), MVT::i16));
     case 3: {
       MVT::ValueType ArgVT = Op.getOperand(1).getValueType();
-      
+
       if (MVT::isVector(ArgVT) ||
           (Subtarget->is64Bit() && MVT::isFloatingPoint(ArgVT))) {
         // Integer or FP vector result -> XMM0.
@@ -4403,7 +4375,7 @@
         DAG.getMachineFunction().addLiveOut(Reg2);
       }
 
-      Copy = DAG.getCopyToReg(Op.getOperand(0), Reg2, Op.getOperand(3), 
+      Copy = DAG.getCopyToReg(Op.getOperand(0), Reg2, Op.getOperand(3),
                               SDOperand());
       Copy = DAG.getCopyToReg(Copy, Reg1, Op.getOperand(1), Copy.getValue(1));
       break;
@@ -4757,7 +4729,7 @@
   SDOperand rd = DAG.getNode(X86ISD::RDTSC_DAG, Tys, &Ops[0], Ops.size());
   Ops.clear();
   Ops.push_back(DAG.getCopyFromReg(rd, X86::EAX, MVT::i32, rd.getValue(1)));
-  Ops.push_back(DAG.getCopyFromReg(Ops[0].getValue(1), X86::EDX, 
+  Ops.push_back(DAG.getCopyFromReg(Ops[0].getValue(1), X86::EDX,
                                    MVT::i32, Ops[0].getValue(2)));
   Ops.push_back(Ops[1].getValue(1));
   Tys[0] = Tys[1] = MVT::i32;
@@ -4849,8 +4821,8 @@
     ISD::CondCode CC = ISD::SETCC_INVALID;
     switch (IntNo) {
     default: break;
-    case Intrinsic::x86_sse_comieq_ss: 
-    case Intrinsic::x86_sse2_comieq_sd: 
+    case Intrinsic::x86_sse_comieq_ss:
+    case Intrinsic::x86_sse2_comieq_sd:
       Opc = X86ISD::COMI;
       CC = ISD::SETEQ;
       break;
@@ -5020,7 +4992,7 @@
     if (RModel == Reloc::Static)
       return true;
     else if (RModel == Reloc::DynamicNoPIC)
-      return !DarwinGVRequiresExtraLoad(GV);
+      return !(Subtarget->GVRequiresExtraLoad(GV, false));
     else
       return false;
   } else
@@ -5078,7 +5050,7 @@
     const BasicBlock *LLVM_BB = BB->getBasicBlock();
     ilist<MachineBasicBlock>::iterator It = BB;
     ++It;
-  
+
     //  thisMBB:
     //  ...
     //   TrueVal = ...
@@ -5088,7 +5060,7 @@
     MachineBasicBlock *thisMBB = BB;
     MachineBasicBlock *copy0MBB = new MachineBasicBlock(LLVM_BB);
     MachineBasicBlock *sinkMBB = new MachineBasicBlock(LLVM_BB);
-    unsigned Opc = 
+    unsigned Opc =
       X86::GetCondBranchFromCond((X86::CondCode)MI->getOperand(3).getImm());
     BuildMI(BB, Opc, 1).addMBB(sinkMBB);
     MachineFunction *F = BB->getParent();
@@ -5096,7 +5068,7 @@
     F->getBasicBlockList().insert(It, sinkMBB);
     // Update machine-CFG edges by first adding all successors of the current
     // block to the new block which will contain the Phi node for the select.
-    for(MachineBasicBlock::succ_iterator i = BB->succ_begin(), 
+    for(MachineBasicBlock::succ_iterator i = BB->succ_begin(),
         e = BB->succ_end(); i != e; ++i)
       sinkMBB->addSuccessor(*i);
     // Next, remove all successors of the current block, and add the true
@@ -5105,15 +5077,15 @@
       BB->removeSuccessor(BB->succ_begin());
     BB->addSuccessor(copy0MBB);
     BB->addSuccessor(sinkMBB);
-  
+
     //  copy0MBB:
     //   %FalseValue = ...
     //   # fallthrough to sinkMBB
     BB = copy0MBB;
-  
+
     // Update machine-CFG edges
     BB->addSuccessor(sinkMBB);
-  
+
     //  sinkMBB:
     //   %Result = phi [ %FalseValue, copy0MBB ], [ %TrueValue, thisMBB ]
     //  ...
@@ -5196,7 +5168,7 @@
 
 void X86TargetLowering::computeMaskedBitsForTargetNode(const SDOperand Op,
                                                        uint64_t Mask,
-                                                       uint64_t &KnownZero, 
+                                                       uint64_t &KnownZero,
                                                        uint64_t &KnownOne,
                                                        unsigned Depth) const {
   unsigned Opc = Op.getOpcode();
@@ -5210,7 +5182,7 @@
   KnownZero = KnownOne = 0;   // Don't know anything.
   switch (Opc) {
   default: break;
-  case X86ISD::SETCC: 
+  case X86ISD::SETCC:
     KnownZero |= (MVT::getIntVTBitMask(Op.getValueType()) ^ 1ULL);
     break;
   }
@@ -5369,7 +5341,7 @@
 static SDOperand PerformSELECTCombine(SDNode *N, SelectionDAG &DAG,
                                       const X86Subtarget *Subtarget) {
   SDOperand Cond = N->getOperand(0);
-  
+
   // If we have SSE[12] support, try to form min/max nodes.
   if (Subtarget->hasSSE2() &&
       (N->getValueType(0) == MVT::f32 || N->getValueType(0) == MVT::f64)) {
@@ -5378,7 +5350,7 @@
       SDOperand LHS = N->getOperand(1);
       SDOperand RHS = N->getOperand(2);
       ISD::CondCode CC = cast<CondCodeSDNode>(Cond.getOperand(2))->get();
-      
+
       unsigned Opcode = 0;
       if (LHS == Cond.getOperand(0) && RHS == Cond.getOperand(1)) {
         switch (CC) {
@@ -5392,7 +5364,7 @@
         case ISD::SETLT:
           Opcode = X86ISD::FMIN;
           break;
-          
+
         case ISD::SETOGT: // (X > Y) ? X : Y -> max
         case ISD::SETUGT:
         case ISD::SETGT:
@@ -5415,7 +5387,7 @@
         case ISD::SETGE:
           Opcode = X86ISD::FMIN;
           break;
-          
+
         case ISD::SETOLE:   // (X <= Y) ? Y : X -> max
         case ISD::SETULE:
         case ISD::SETLE:
@@ -5427,18 +5399,18 @@
           break;
         }
       }
-      
+
       if (Opcode)
         return DAG.getNode(Opcode, N->getValueType(0), LHS, RHS);
     }
-    
+
   }
 
   return SDOperand();
 }
 
 
-SDOperand X86TargetLowering::PerformDAGCombine(SDNode *N, 
+SDOperand X86TargetLowering::PerformDAGCombine(SDNode *N,
                                                DAGCombinerInfo &DCI) const {
   SelectionDAG &DAG = DCI.DAG;
   switch (N->getOpcode()) {
@@ -5484,19 +5456,19 @@
   case 'i':
     // Literal immediates are always ok.
     if (isa<ConstantSDNode>(Op)) return Op;
-    
+
     // If we are in non-pic codegen mode, we allow the address of a global to
     // be used with 'i'.
     if (GlobalAddressSDNode *GA = dyn_cast<GlobalAddressSDNode>(Op)) {
       if (getTargetMachine().getRelocationModel() == Reloc::PIC_)
         return SDOperand(0, 0);
-      
+
       if (GA->getOpcode() != ISD::TargetGlobalAddress)
         Op = DAG.getTargetGlobalAddress(GA->getGlobal(), GA->getValueType(0),
                                         GA->getOffset());
       return Op;
     }
-    
+
     // Otherwise, not valid for this mode.
     return SDOperand(0, 0);
   }
@@ -5522,7 +5494,7 @@
         return make_vector<unsigned>(X86::EAX, X86::EDX, X86::ECX, X86::EBX,
                                      X86::ESI, X86::EDI, X86::EBP, X86::ESP, 0);
       else if (VT == MVT::i16)
-        return make_vector<unsigned>(X86::AX, X86::DX, X86::CX, X86::BX, 
+        return make_vector<unsigned>(X86::AX, X86::DX, X86::CX, X86::BX,
                                      X86::SI, X86::DI, X86::BP, X86::SP, 0);
       else if (VT == MVT::i8)
         return make_vector<unsigned>(X86::AL, X86::DL, X86::CL, X86::DL, 0);
@@ -5532,7 +5504,7 @@
         return make_vector<unsigned>(X86::EAX, X86::EDX, X86::ECX, X86::EBX,
                                      X86::ESI, X86::EDI, X86::EBP, 0);
       else if (VT == MVT::i16)
-        return make_vector<unsigned>(X86::AX, X86::DX, X86::CX, X86::BX, 
+        return make_vector<unsigned>(X86::AX, X86::DX, X86::CX, X86::BX,
                                      X86::SI, X86::DI, X86::BP, 0);
       else if (VT == MVT::i8)
         return make_vector<unsigned>(X86::AL, X86::DL, X86::CL, X86::DL, 0);
@@ -5560,11 +5532,11 @@
       return std::vector<unsigned>();
     }
   }
-  
+
   return std::vector<unsigned>();
 }
 
-std::pair<unsigned, const TargetRegisterClass*> 
+std::pair<unsigned, const TargetRegisterClass*>
 X86TargetLowering::getRegForInlineAsmConstraint(const std::string &Constraint,
                                                 MVT::ValueType VT) const {
   // Use the default implementation in TargetLowering to convert the register
@@ -5579,23 +5551,23 @@
       Res.first = X86::ST0;
       Res.second = X86::RSTRegisterClass;
     }
-    
+
     return Res;
   }
-  
+
   // Otherwise, check to see if this is a register class of the wrong value
   // type.  For example, we want to map "{ax},i32" -> {eax}, we don't want it to
   // turn into {ax},{dx}.
   if (Res.second->hasType(VT))
     return Res;   // Correct type already, nothing to do.
-  
+
   // All of the single-register GCC register classes map their values onto
   // 16-bit register pieces "ax","dx","cx","bx","si","di","bp","sp".  If we
   // really want an 8-bit or 32-bit register, map to the appropriate register
   // class and return the appropriate register.
   if (Res.second != X86::GR16RegisterClass)
     return Res;
-  
+
   if (VT == MVT::i8) {
     unsigned DestReg = 0;
     switch (Res.first) {
@@ -5644,7 +5616,6 @@
       Res.second = Res.second = X86::GR64RegisterClass;
     }
   }
-  
+
   return Res;
 }
-


Index: llvm/lib/Target/X86/X86Subtarget.h
diff -u llvm/lib/Target/X86/X86Subtarget.h:1.20 llvm/lib/Target/X86/X86Subtarget.h:1.21
--- llvm/lib/Target/X86/X86Subtarget.h:1.20	Mon Oct 16 16:00:37 2006
+++ llvm/lib/Target/X86/X86Subtarget.h	Mon Nov 20 18:01:06 2006
@@ -14,6 +14,7 @@
 #ifndef X86SUBTARGET_H
 #define X86SUBTARGET_H
 
+#include "llvm/GlobalValue.h"
 #include "llvm/Target/TargetSubtarget.h"
 
 #include <string>
@@ -64,7 +65,7 @@
   enum {
     isELF, isCygwin, isDarwin, isWindows
   } TargetType;
-    
+
   /// This constructor initializes the data members to match that
   /// of the specified module.
   ///
@@ -80,8 +81,8 @@
   /// instruction. This is only used if the src / dst alignment is not DWORD
   /// aligned.
   unsigned getMinRepStrSizeThreshold() const { return MinRepStrSizeThreshold; }
- 
-  /// ParseSubtargetFeatures - Parses features string setting specified 
+
+  /// ParseSubtargetFeatures - Parses features string setting specified
   /// subtarget options.  Definition of function is auto generated by tblgen.
   void ParseSubtargetFeatures(const std::string &FS, const std::string &CPU);
 
@@ -97,14 +98,31 @@
   bool hasSSE3() const { return X86SSELevel >= SSE3; }
   bool has3DNow() const { return X863DNowLevel >= ThreeDNow; }
   bool has3DNowA() const { return X863DNowLevel >= ThreeDNowA; }
-  
+
   bool isFlavorAtt() const { return AsmFlavor == att; }
   bool isFlavorIntel() const { return AsmFlavor == intel; }
 
   bool isTargetDarwin() const { return TargetType == isDarwin; }
   bool isTargetELF() const { return TargetType == isELF; }
   bool isTargetWindows() const { return TargetType == isWindows; }
-  bool isTargetCygwin() const { return TargetType == isCygwin; }  
+  bool isTargetCygwin() const { return TargetType == isCygwin; }
+
+  /// True if accessing the GV requires an extra load. For Windows, dllimported
+  /// symbols are indirect, loading the value at address GV rather then the
+  /// value of GV itself. This means that the GlobalAddress must be in the base
+  /// or index register of the address, not the GV offset field.
+  bool GVRequiresExtraLoad(const GlobalValue* GV, bool isDirectCall) const
+  {
+    if (isTargetDarwin()) {
+      return (!isDirectCall &&
+              (GV->hasWeakLinkage() || GV->hasLinkOnceLinkage() ||
+               (GV->isExternal() && !GV->hasNotBeenReadFromBytecode())));
+    } else if (isTargetCygwin() || isTargetWindows()) {
+      return (GV->hasDLLImportLinkage());
+    }
+
+    return false;
+  }
 };
 
 namespace X86 {






More information about the llvm-commits mailing list