trans.c (Attribute_to_gnu): Strip conversions between original and packable version...
authorEric Botcazou <ebotcazou@adacore.com>
Wed, 16 Sep 2009 15:02:25 +0000 (15:02 +0000)
committerEric Botcazou <ebotcazou@gcc.gnu.org>
Wed, 16 Sep 2009 15:02:25 +0000 (15:02 +0000)
* gcc-interface/trans.c (Attribute_to_gnu) <Attr_Size>: Strip
conversions between original and packable version of types from
the expression.

From-SVN: r151757

gcc/ada/ChangeLog
gcc/ada/gcc-interface/trans.c
gcc/testsuite/ChangeLog
gcc/testsuite/gnat.dg/alignment9.adb [new file with mode: 0644]

index 485562fb29b8cee0cdabca38ed101e2be3f6a676..dae5c00e6a3d633797e34ee333992d5ecbd9702e 100644 (file)
@@ -1,3 +1,9 @@
+2009-09-16  Eric Botcazou  <ebotcazou@adacore.com>
+
+       * gcc-interface/trans.c (Attribute_to_gnu) <Attr_Size>: Strip
+       conversions between original and packable version of types from
+       the expression.
+
 2009-09-16  Eric Botcazou  <ebotcazou@adacore.com>
 
        * gcc-interface/decl.c (gnat_to_gnu_field): Add DEBUG_INFO_P parameter.
index 5bce21a7063953898d50b81274791db79a76f0be..a90a7a060bc0f154bad56ead3b930ef554d844f8 100644 (file)
@@ -1279,9 +1279,16 @@ Attribute_to_gnu (Node_Id gnat_node, tree *gnu_result_type_p, int attribute)
     case Attr_Max_Size_In_Storage_Elements:
       gnu_expr = gnu_prefix;
 
-      /* Remove NOPs from GNU_EXPR and conversions from GNU_PREFIX.
-        We only use GNU_EXPR to see if a COMPONENT_REF was involved.  */
-      while (TREE_CODE (gnu_expr) == NOP_EXPR)
+      /* Remove NOPs and conversions between original and packable version
+        from GNU_EXPR, and conversions from GNU_PREFIX.  We use GNU_EXPR
+        to see if a COMPONENT_REF was involved.  */
+      while (TREE_CODE (gnu_expr) == NOP_EXPR
+            || (TREE_CODE (gnu_expr) == VIEW_CONVERT_EXPR
+                && TREE_CODE (TREE_TYPE (gnu_expr)) == RECORD_TYPE
+                && TREE_CODE (TREE_TYPE (TREE_OPERAND (gnu_expr, 0)))
+                   == RECORD_TYPE
+                && TYPE_NAME (TREE_TYPE (gnu_expr))
+                   == TYPE_NAME (TREE_TYPE (TREE_OPERAND (gnu_expr, 0)))))
        gnu_expr = TREE_OPERAND (gnu_expr, 0);
 
       gnu_prefix = remove_conversions (gnu_prefix, true);
index ac05fd3a73f499b72f53d835794be9d28dadd9dd..e02dbf90d18a776f559b422c836578ce3727a09f 100644 (file)
@@ -1,3 +1,7 @@
+2009-09-16  Eric Botcazou  <ebotcazou@adacore.com>
+
+       * gnat.dg/alignment9.adb: New test.
+
 2009-09-16  Eric Botcazou  <ebotcazou@adacore.com>
 
        * gnat.dg/discr20.ad[sb]: New test.
diff --git a/gcc/testsuite/gnat.dg/alignment9.adb b/gcc/testsuite/gnat.dg/alignment9.adb
new file mode 100644 (file)
index 0000000..ae7a7f6
--- /dev/null
@@ -0,0 +1,30 @@
+-- { dg-do run }
+-- { dg-options "-gnatws" }
+
+procedure Alignment9 is
+
+  type Kind is (Small, Large);
+  for Kind'Size use 8;
+
+  type Header is
+    record
+      K : Kind;
+      I : Integer;
+    end record;
+
+  for Header use
+    record
+      K at 4 range 0..7;
+      I at 0 range 0..31;
+    end record;
+
+  for Header'Size use 5*8;
+  for Header'Alignment use 1;
+
+  H : Header;
+
+begin
+  if H'Size /= 40 then
+    raise Program_Error;
+  end if;
+end;