This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[Ada] Fix ICE on variant component in packed record
- From: Eric Botcazou <ebotcazou at adacore dot com>
- To: gcc-patches at gcc dot gnu dot org
- Date: Sun, 6 Apr 2008 15:41:17 +0200
- Subject: [Ada] Fix ICE on variant component in packed record
This is a regression recently introduced on mainline: a component in a packed
record whose type is a discriminated record type with variable size but with
a component size clause can end up being misaligned, which blows up for an
indirect assignment to this component because its address needs to be passed
to the block copy routine.
Fixed by aligning it again, tested on i586-suse-linux, applied on the
mainline.
2008-04-06 Eric Botcazou <ebotcazou@adacore.com>
* decl.c (is_variable_size): Do not unconditionally return false
on non-strict alignment platforms.
2008-04-06 Eric Botcazou <ebotcazou@adacore.com>
* gnat.dg/pack5.adb: New test.
--
Eric Botcazou
Index: decl.c
===================================================================
--- decl.c (revision 133957)
+++ decl.c (working copy)
@@ -6103,18 +6103,17 @@ is_variable_size (tree type)
{
tree field;
- /* We need not be concerned about this at all if we don't have
- strict alignment. */
- if (!STRICT_ALIGNMENT)
- return false;
- else if (!TREE_CONSTANT (TYPE_SIZE (type)))
+ if (!TREE_CONSTANT (TYPE_SIZE (type)))
return true;
- else if (TREE_CODE (type) == RECORD_TYPE && TYPE_IS_PADDING_P (type)
- && !TREE_CONSTANT (DECL_SIZE (TYPE_FIELDS (type))))
+
+ if (TREE_CODE (type) == RECORD_TYPE
+ && TYPE_IS_PADDING_P (type)
+ && !TREE_CONSTANT (DECL_SIZE (TYPE_FIELDS (type))))
return true;
- else if (TREE_CODE (type) != RECORD_TYPE
- && TREE_CODE (type) != UNION_TYPE
- && TREE_CODE (type) != QUAL_UNION_TYPE)
+
+ if (TREE_CODE (type) != RECORD_TYPE
+ && TREE_CODE (type) != UNION_TYPE
+ && TREE_CODE (type) != QUAL_UNION_TYPE)
return false;
for (field = TYPE_FIELDS (type); field; field = TREE_CHAIN (field))
-- { dg-do compile }
procedure Pack5 is
type Kind is (v1, v2, v3);
type Error (k : Kind := Kind'First) is record
case k is
when v1 =>
null;
when v2 =>
null;
when Others =>
B : Boolean;
end case;
end record;
pragma Pack (Error);
for Error'Size use 16;
No_Error: constant Error := (k => v2);
type R (B : Boolean) is record
E : Error;
end record;
pragma Pack(R);
type Ptr is access R;
C : Ptr := new R (True);
begin
C.E := No_Error;
end;