]> granicus.if.org Git - clang/commitdiff
Sema: Fix a subtle i64 -> i32 truncation which broke layout of large structures
authorDaniel Dunbar <daniel@zuster.org>
Tue, 29 Jun 2010 18:34:35 +0000 (18:34 +0000)
committerDaniel Dunbar <daniel@zuster.org>
Tue, 29 Jun 2010 18:34:35 +0000 (18:34 +0000)
with bit-fields.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@107185 91177308-0d34-0410-b5e6-96231b3b80d8

lib/AST/RecordLayoutBuilder.cpp
test/Sema/bitfield-layout.c

index 275daf6bb22b57c62b0f3245a09e96c1426c5a43..88d71ce04287eb01a2ae2b3fea7e0db79b569a9f 100644 (file)
@@ -1296,7 +1296,7 @@ void RecordLayoutBuilder::LayoutBitField(const FieldDecl *D) {
 
   // Check if we need to add padding to give the field the correct alignment.
   if (FieldSize == 0 || (FieldOffset & (FieldAlign-1)) + FieldSize > TypeSize)
-    FieldOffset = (FieldOffset + (FieldAlign-1)) & ~(FieldAlign-1);
+    FieldOffset = llvm::RoundUpToAlignment(FieldOffset, FieldAlign);
 
   // Padding members don't affect overall alignment.
   if (!D->getIdentifier())
index edc44bdefa08e2871d68b400d60655ecebe6eb0e..2655fc70cd4c427bde64cf2062014bb79c1025b1 100644 (file)
@@ -30,3 +30,13 @@ CHECK_ALIGN(struct, e, 1)
 struct f {__attribute((aligned(8))) int x : 30, y : 30, z : 30;};
 CHECK_SIZE(struct, f, 24)
 CHECK_ALIGN(struct, f, 8)
+
+// Large structure (overflows i32, in bits).
+struct s0 {
+  char a[0x32100000];
+  int x:30, y:30;
+};
+
+CHECK_SIZE(struct, s0, 0x32100008)
+CHECK_ALIGN(struct, s0, 4)
+