aschwaighofer created this revision.

The layout must be compatible with the input layout, offsets are defined in
terms of offsets within a packed struct which are computed in terms of the alloc
size of a type.

Using the store size we would insert padding for the following type for example:

struct {

  int3 v;
  long long l;

} __attribute((packed))

On x86-64 int3 is padded to int4 alignment. The swiftcc type would be
<{ <3 x float>, [4 x i8], i64 }> which is not compatible with <{ <3 x float>, 
i64 }>.

The latter has i64 at offset 16 and the former at offset 20.

rdar://32618125


https://reviews.llvm.org/D34454

Files:
  lib/CodeGen/SwiftCallingConv.cpp
  test/CodeGen/64bit-swiftcall.c
  test/CodeGen/windows-swiftcall.c

Index: test/CodeGen/windows-swiftcall.c
===================================================================
--- test/CodeGen/windows-swiftcall.c
+++ test/CodeGen/windows-swiftcall.c
@@ -455,4 +455,4 @@
   int3 v __attribute__((packed));
 } misaligned_int3;
 TEST(misaligned_int3)
-// CHECK-LABEL: define swiftcc void @take_misaligned_int3(i64, i64)
+// CHECK-LABEL: define swiftcc void @take_misaligned_int3(i64, i64, i32)
Index: test/CodeGen/64bit-swiftcall.c
===================================================================
--- test/CodeGen/64bit-swiftcall.c
+++ test/CodeGen/64bit-swiftcall.c
@@ -1,4 +1,5 @@
 // RUN: %clang_cc1 -triple x86_64-apple-darwin10 -target-cpu core2 -emit-llvm -o - %s | FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -target-cpu core2 -emit-llvm -o - %s | FileCheck %s --check-prefix=X86-64
 // RUN: %clang_cc1 -triple arm64-apple-ios9 -target-cpu cyclone -emit-llvm -o - %s | FileCheck %s
 // RUN: %clang_cc1 -triple arm64-apple-ios9 -target-cpu cyclone -emit-llvm -o - %s | FileCheck %s --check-prefix=ARM64
 
@@ -463,7 +464,7 @@
   int3 v __attribute__((packed));
 } misaligned_int3;
 TEST(misaligned_int3)
-// CHECK-LABEL: define swiftcc void @take_misaligned_int3(i64, i64)
+// CHECK-LABEL: define swiftcc void @take_misaligned_int3(i64, i64, i32)
 
 typedef struct {
   float f0;
@@ -1014,3 +1015,19 @@
 TEST(struct_v1f3)
 // ARM64-LABEL: define swiftcc { <2 x float>, float } @return_struct_v1f3()
 // ARM64-LABEL: define swiftcc void @take_struct_v1f3(<2 x float>, float)
+
+typedef struct {
+  int3 vect;
+  unsigned long long val;
+} __attribute__((packed)) padded_alloc_size_vector;
+TEST(padded_alloc_size_vector)
+// X86-64-LABEL: take_padded_alloc_size_vector(<3 x i32>, i64)
+// ARM64-LABEL: take_padded_alloc_size_vector(<2 x i32>, i32, i64)
+
+typedef union {
+  float f1;
+  float3 fv2;
+} union_hom_fp_partial2;
+TEST(union_hom_fp_partial2)
+// X86-64-LABEL: take_union_hom_fp_partial2(i64, i64)
+// ARM64-LABEL: take_union_hom_fp_partial2(i64, float)
Index: lib/CodeGen/SwiftCallingConv.cpp
===================================================================
--- lib/CodeGen/SwiftCallingConv.cpp
+++ lib/CodeGen/SwiftCallingConv.cpp
@@ -57,6 +57,10 @@
   return CharUnits::fromQuantity(CGM.getDataLayout().getTypeStoreSize(type));
 }
 
+static CharUnits getTypeAllocSize(CodeGenModule &CGM, llvm::Type *type) {
+  return CharUnits::fromQuantity(CGM.getDataLayout().getTypeAllocSize(type));
+}
+
 void SwiftAggLowering::addTypedData(QualType type, CharUnits begin) {
   // Deal with various aggregate types as special cases:
 
@@ -189,24 +193,24 @@
 
 void SwiftAggLowering::addTypedData(llvm::Type *type, CharUnits begin) {
   assert(type && "didn't provide type for typed data");
-  addTypedData(type, begin, begin + getTypeStoreSize(CGM, type));
+  addTypedData(type, begin, begin + getTypeAllocSize(CGM, type));
 }
 
 void SwiftAggLowering::addTypedData(llvm::Type *type,
                                     CharUnits begin, CharUnits end) {
   assert(type && "didn't provide type for typed data");
-  assert(getTypeStoreSize(CGM, type) == end - begin);
+  assert(getTypeAllocSize(CGM, type) == end - begin);
 
   // Legalize vector types.
   if (auto vecTy = dyn_cast<llvm::VectorType>(type)) {
     SmallVector<llvm::Type*, 4> componentTys;
-    legalizeVectorType(CGM, end - begin, vecTy, componentTys);
+    legalizeVectorType(CGM, getTypeStoreSize(CGM, type), vecTy, componentTys);
     assert(componentTys.size() >= 1);
 
     // Walk the initial components.
     for (size_t i = 0, e = componentTys.size(); i != e - 1; ++i) {
       llvm::Type *componentTy = componentTys[i];
-      auto componentSize = getTypeStoreSize(CGM, componentTy);
+      auto componentSize = getTypeAllocSize(CGM, componentTy);
       assert(componentSize < end - begin);
       addLegalTypedData(componentTy, begin, begin + componentSize);
       begin += componentSize;
@@ -236,14 +240,15 @@
       auto eltTy = split.first;
       auto numElts = split.second;
 
-      auto eltSize = (end - begin) / numElts;
-      assert(eltSize == getTypeStoreSize(CGM, eltTy));
-      for (size_t i = 0, e = numElts; i != e; ++i) {
-        addLegalTypedData(eltTy, begin, begin + eltSize);
-        begin += eltSize;
+      auto eltSize = getTypeAllocSize(CGM, eltTy);
+      if (eltSize * numElts == end - begin) {
+        for (size_t i = 0, e = numElts; i != e; ++i) {
+          addLegalTypedData(eltTy, begin, begin + eltSize);
+          begin += eltSize;
+        }
+        assert(begin == end);
+        return;
       }
-      assert(begin == end);
-      return;
     }
 
     return addOpaqueData(begin, end);
@@ -318,12 +323,13 @@
   if (auto vecTy = dyn_cast_or_null<llvm::VectorType>(type)) {
     auto eltTy = vecTy->getElementType();
     CharUnits eltSize = (end - begin) / vecTy->getNumElements();
-    assert(eltSize == getTypeStoreSize(CGM, eltTy));
-    for (unsigned i = 0, e = vecTy->getNumElements(); i != e; ++i) {
-      addEntry(eltTy, begin, begin + eltSize);
-      begin += eltSize;
-    }
-    assert(begin == end);
+    if (eltSize == getTypeAllocSize(CGM, eltTy)) {
+      for (unsigned i = 0, e = vecTy->getNumElements(); i != e; ++i) {
+        addEntry(eltTy, begin, begin + eltSize);
+        begin += eltSize;
+      }
+      assert(begin == end);
+    } else { addOpaqueData(begin, end); }
     return;
   }
 
@@ -382,7 +388,7 @@
   auto split = splitLegalVectorType(CGM, Entries[index].getWidth(), vecTy);
 
   auto eltTy = split.first;
-  CharUnits eltSize = getTypeStoreSize(CGM, eltTy);
+  CharUnits eltSize = getTypeAllocSize(CGM, eltTy);
   auto numElts = split.second;
   Entries.insert(Entries.begin() + index + 1, numElts - 1, StorageEntry());
 
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to