diff options
Diffstat (limited to 'llvm')
| -rw-r--r-- | llvm/include/llvm/Target/TargetData.h | 8 | ||||
| -rw-r--r-- | llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp | 6 | ||||
| -rw-r--r-- | llvm/lib/Target/TargetData.cpp | 25 | ||||
| -rw-r--r-- | llvm/lib/Target/X86/X86Subtarget.h | 2 | ||||
| -rw-r--r-- | llvm/test/CodeGen/X86/byval3.ll | 25 | 
5 files changed, 57 insertions, 9 deletions
diff --git a/llvm/include/llvm/Target/TargetData.h b/llvm/include/llvm/Target/TargetData.h index 6003e607b7a..f2e55f10e11 100644 --- a/llvm/include/llvm/Target/TargetData.h +++ b/llvm/include/llvm/Target/TargetData.h @@ -38,7 +38,8 @@ enum AlignTypeEnum {    INTEGER_ALIGN = 'i',               ///< Integer type alignment    VECTOR_ALIGN = 'v',                ///< Vector type alignment    FLOAT_ALIGN = 'f',                 ///< Floating point type alignment -  AGGREGATE_ALIGN = 'a'              ///< Aggregate alignment +  AGGREGATE_ALIGN = 'a',             ///< Aggregate alignment +  STACK_ALIGN = 's'                  ///< Stack objects alignment  };  /// Target alignment element.  /// @@ -166,6 +167,11 @@ public:    /// specified type.    unsigned char getABITypeAlignment(const Type *Ty) const; +  /// getCallFrameTypeAlignment - Return the minimum ABI-required alignment +  /// for the specified type when it is part of a call frame. +  unsigned char getCallFrameTypeAlignment(const Type *Ty) const; + +    /// getPrefTypeAlignment - Return the preferred stack/global alignment for    /// the specified type.    unsigned char getPrefTypeAlignment(const Type *Ty) const; diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp index d512ef9b1d1..e18beb5018a 100644 --- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp @@ -3870,7 +3870,8 @@ TargetLowering::LowerArguments(Function &F, SelectionDAG &DAG) {        Flags |= ISD::ParamFlags::ByVal;        const PointerType *Ty = cast<PointerType>(I->getType());        const StructType *STy = cast<StructType>(Ty->getElementType()); -      unsigned StructAlign = Log2_32(getTargetData()->getABITypeAlignment(STy)); +      unsigned StructAlign = +          Log2_32(getTargetData()->getCallFrameTypeAlignment(STy));        unsigned StructSize  = getTargetData()->getTypeSize(STy);        Flags |= (StructAlign << ISD::ParamFlags::ByValAlignOffs);        Flags |= (StructSize  << ISD::ParamFlags::ByValSizeOffs); @@ -3999,7 +4000,8 @@ TargetLowering::LowerCallTo(SDOperand Chain, const Type *RetTy,        Flags |= ISD::ParamFlags::ByVal;        const PointerType *Ty = cast<PointerType>(Args[i].Ty);        const StructType *STy = cast<StructType>(Ty->getElementType()); -      unsigned StructAlign = Log2_32(getTargetData()->getABITypeAlignment(STy)); +      unsigned StructAlign = +          Log2_32(getTargetData()->getCallFrameTypeAlignment(STy));        unsigned StructSize  = getTargetData()->getTypeSize(STy);        Flags |= (StructAlign << ISD::ParamFlags::ByValAlignOffs);        Flags |= (StructSize  << ISD::ParamFlags::ByValSizeOffs); diff --git a/llvm/lib/Target/TargetData.cpp b/llvm/lib/Target/TargetData.cpp index bb1fff5de5f..9f7cb003791 100644 --- a/llvm/lib/Target/TargetData.cpp +++ b/llvm/lib/Target/TargetData.cpp @@ -182,7 +182,8 @@ void TargetData::init(const std::string &TargetDescription) {    setAlignment(VECTOR_ALIGN,    8,  8, 64);  // v2i32    setAlignment(VECTOR_ALIGN,   16, 16, 128); // v16i8, v8i16, v4i32, ...    setAlignment(AGGREGATE_ALIGN, 0,  8,  0);  // struct, union, class, ... -   +  setAlignment(STACK_ALIGN,     0,  8,  0);  // objects on the stack +    while (!temp.empty()) {      std::string token = getToken(temp, "-");      std::string arg0 = getToken(token, ":"); @@ -204,10 +205,16 @@ void TargetData::init(const std::string &TargetDescription) {      case 'i':      case 'v':      case 'f': -    case 'a': { -      AlignTypeEnum align_type =  -        (*p == 'i' ? INTEGER_ALIGN : (*p == 'f' ? FLOAT_ALIGN : -           (*p == 'v' ? VECTOR_ALIGN : AGGREGATE_ALIGN))); +    case 'a': +    case 's': { +      AlignTypeEnum align_type; +      switch(*p) { +        case 'i': align_type = INTEGER_ALIGN; break; +        case 'v': align_type = VECTOR_ALIGN; break; +        case 'f': align_type = FLOAT_ALIGN; break; +        case 'a': align_type = AGGREGATE_ALIGN; break; +        case 's': align_type = STACK_ALIGN; break; +      }        uint32_t size = (uint32_t) atoi(++p);        unsigned char abi_align = atoi(getToken(token, ":").c_str()) / 8;        unsigned char pref_align = atoi(getToken(token, ":").c_str()) / 8; @@ -529,6 +536,14 @@ unsigned char TargetData::getABITypeAlignment(const Type *Ty) const {    return getAlignment(Ty, true);  } +unsigned char TargetData::getCallFrameTypeAlignment(const Type *Ty) const { +  for (unsigned i = 0, e = Alignments.size(); i != e; ++i) +    if (Alignments[i].AlignType == STACK_ALIGN) +      return Alignments[i].ABIAlign; + +  return getABITypeAlignment(Ty); +} +  unsigned char TargetData::getPrefTypeAlignment(const Type *Ty) const {    return getAlignment(Ty, false);  } diff --git a/llvm/lib/Target/X86/X86Subtarget.h b/llvm/lib/Target/X86/X86Subtarget.h index 493c801f8ce..d939bc00c54 100644 --- a/llvm/lib/Target/X86/X86Subtarget.h +++ b/llvm/lib/Target/X86/X86Subtarget.h @@ -146,7 +146,7 @@ public:    std::string getDataLayout() const {      const char *p;      if (is64Bit()) -      p = "e-p:64:64-f64:64:64-i64:64:64-f80:128:128"; +      p = "e-p:64:64-s:64-f64:64:64-i64:64:64-f80:128:128";      else {        if (isTargetDarwin())          p = "e-p:32:32-f64:32:64-i64:32:64-f80:128:128"; diff --git a/llvm/test/CodeGen/X86/byval3.ll b/llvm/test/CodeGen/X86/byval3.ll new file mode 100644 index 00000000000..f4942869687 --- /dev/null +++ b/llvm/test/CodeGen/X86/byval3.ll @@ -0,0 +1,25 @@ +; RUN: llvm-as < %s | llc -march=x86-64 | grep rep.movsl | count 2 + +%struct.s = type { i32, i32, i32, i32, i32, i32 } + +define void @g(i32 %a1, i32 %a2, i32 %a3, i32 %a4, i32 %a5, i32 %a6) { +entry: +        %d = alloca %struct.s, align 16 +        %tmp = getelementptr %struct.s* %d, i32 0, i32 0 +        store i32 %a1, i32* %tmp, align 16 +        %tmp2 = getelementptr %struct.s* %d, i32 0, i32 1 +        store i32 %a2, i32* %tmp2, align 16 +        %tmp4 = getelementptr %struct.s* %d, i32 0, i32 2 +        store i32 %a3, i32* %tmp4, align 16 +        %tmp6 = getelementptr %struct.s* %d, i32 0, i32 3 +        store i32 %a4, i32* %tmp6, align 16 +        %tmp8 = getelementptr %struct.s* %d, i32 0, i32 4 +        store i32 %a5, i32* %tmp8, align 16 +        %tmp10 = getelementptr %struct.s* %d, i32 0, i32 5 +        store i32 %a6, i32* %tmp10, align 16 +        call void @f( %struct.s* %d byval) +        call void @f( %struct.s* %d byval) +        ret void +} + +declare void @f(%struct.s* byval)  | 

