Commit b38086f0 by Eric Botcazou Committed by Eric Botcazou

decl.c (gnat_to_gnu_entity): In type annotation mode...

	* gcc-interface/decl.c (gnat_to_gnu_entity): In type annotation mode,
	do not adjust the size of a tagged type if there is a representation
	clause on it.  Otherwise, round the adjustment up to the alignment
	of the first field and use the appropriate helper routine.
	(maybe_pad_type): Do not warn in type annotation mode on a tagged type.
	(gnat_to_gnu_field): Do not error out under the same circumstances.
	(annotate_rep): In type annotation mode, do not adjust the offset of
	components of a tagged type with representation clause.  Otherwise,
	round the adjustment up to the alignment of the first field.

From-SVN: r186961
parent bb358f1c
2012-04-30 Eric Botcazou <ebotcazou@adacore.com> 2012-04-30 Eric Botcazou <ebotcazou@adacore.com>
* gcc-interface/decl.c (gnat_to_gnu_entity): In type annotation mode,
do not adjust the size of a tagged type if there is a representation
clause on it. Otherwise, round the adjustment up to the alignment
of the first field and use the appropriate helper routine.
(maybe_pad_type): Do not warn in type annotation mode on a tagged type.
(gnat_to_gnu_field): Do not error out under the same circumstances.
(annotate_rep): In type annotation mode, do not adjust the offset of
components of a tagged type with representation clause. Otherwise,
round the adjustment up to the alignment of the first field.
2012-04-30 Eric Botcazou <ebotcazou@adacore.com>
* gcc-interface/utils.c (finish_record_type): Force the traditional GCC * gcc-interface/utils.c (finish_record_type): Force the traditional GCC
layout for bitfields on the type if it is packed or has a representation layout for bitfields on the type if it is packed or has a representation
clause and an alternate layout is available. clause and an alternate layout is available.
...@@ -14,7 +26,7 @@ ...@@ -14,7 +26,7 @@
(destroy_dummy_type): Likewise. (destroy_dummy_type): Likewise.
* gcc-interface/trans.c (gnat_validate_uc_list): New variable. * gcc-interface/trans.c (gnat_validate_uc_list): New variable.
(gigi): Call validate_unchecked_conversion on gnat_validate_uc_list (gigi): Call validate_unchecked_conversion on gnat_validate_uc_list
after the translation is completed.  Call destroy_gnat_to_gnu and after the translation is completed. Call destroy_gnat_to_gnu and
destroy_dummy_type at the end. destroy_dummy_type at the end.
(Subprogram_Body_to_gnu): Do not call mark_out_of_scope. (Subprogram_Body_to_gnu): Do not call mark_out_of_scope.
(gnat_to_gnu) <N_Block_Statement>: Likewise. (gnat_to_gnu) <N_Block_Statement>: Likewise.
......
...@@ -5027,28 +5027,33 @@ gnat_to_gnu_entity (Entity_Id gnat_entity, tree gnu_expr, int definition) ...@@ -5027,28 +5027,33 @@ gnat_to_gnu_entity (Entity_Id gnat_entity, tree gnu_expr, int definition)
if (CONTAINS_PLACEHOLDER_P (gnu_size)) if (CONTAINS_PLACEHOLDER_P (gnu_size))
gnu_size = max_size (gnu_size, true); gnu_size = max_size (gnu_size, true);
if (type_annotate_only && Is_Tagged_Type (gnat_entity)) /* If we are just annotating types and the type is tagged, the tag
and the parent components are not generated by the front-end so
sizes must be adjusted if there is no representation clause. */
if (type_annotate_only
&& Is_Tagged_Type (gnat_entity)
&& !VOID_TYPE_P (gnu_type)
&& (!TYPE_FIELDS (gnu_type)
|| integer_zerop (bit_position (TYPE_FIELDS (gnu_type)))))
{ {
/* In this mode, the tag and the parent components are not
generated by the front-end so the sizes must be adjusted. */
tree pointer_size = bitsize_int (POINTER_SIZE), offset; tree pointer_size = bitsize_int (POINTER_SIZE), offset;
Uint uint_size; Uint uint_size;
if (Is_Derived_Type (gnat_entity)) if (Is_Derived_Type (gnat_entity))
{ {
offset = UI_To_gnu (Esize (Etype (Base_Type (gnat_entity))), Entity_Id gnat_parent = Etype (Base_Type (gnat_entity));
bitsizetype); offset = UI_To_gnu (Esize (gnat_parent), bitsizetype);
Set_Alignment (gnat_entity, Set_Alignment (gnat_entity, Alignment (gnat_parent));
Alignment (Etype (Base_Type (gnat_entity))));
} }
else else
offset = pointer_size; offset = pointer_size;
if (TYPE_FIELDS (gnu_type))
offset
= round_up (offset, DECL_ALIGN (TYPE_FIELDS (gnu_type)));
gnu_size = size_binop (PLUS_EXPR, gnu_size, offset); gnu_size = size_binop (PLUS_EXPR, gnu_size, offset);
gnu_size = size_binop (MULT_EXPR, pointer_size, gnu_size = round_up (gnu_size, POINTER_SIZE);
size_binop (CEIL_DIV_EXPR,
gnu_size,
pointer_size));
uint_size = annotate_value (gnu_size); uint_size = annotate_value (gnu_size);
Set_Esize (gnat_entity, uint_size); Set_Esize (gnat_entity, uint_size);
Set_RM_Size (gnat_entity, uint_size); Set_RM_Size (gnat_entity, uint_size);
...@@ -6619,7 +6624,9 @@ maybe_pad_type (tree type, tree size, unsigned int align, ...@@ -6619,7 +6624,9 @@ maybe_pad_type (tree type, tree size, unsigned int align,
/* If the size was widened explicitly, maybe give a warning. Take the /* If the size was widened explicitly, maybe give a warning. Take the
original size as the maximum size of the input if there was an original size as the maximum size of the input if there was an
unconstrained record involved and round it up to the specified alignment, unconstrained record involved and round it up to the specified alignment,
if one was specified. */ if one was specified. But don't do it if we are just annotating types
and the type is tagged, since tagged types aren't fully laid out in this
mode. */
if (CONTAINS_PLACEHOLDER_P (orig_size)) if (CONTAINS_PLACEHOLDER_P (orig_size))
orig_size = max_size (orig_size, true); orig_size = max_size (orig_size, true);
...@@ -6635,7 +6642,8 @@ maybe_pad_type (tree type, tree size, unsigned int align, ...@@ -6635,7 +6642,8 @@ maybe_pad_type (tree type, tree size, unsigned int align,
&& TREE_CODE (orig_size) == INTEGER_CST && TREE_CODE (orig_size) == INTEGER_CST
&& (TREE_OVERFLOW (size) && (TREE_OVERFLOW (size)
|| TREE_OVERFLOW (orig_size) || TREE_OVERFLOW (orig_size)
|| tree_int_cst_lt (size, orig_size)))) || tree_int_cst_lt (size, orig_size)))
&& !(type_annotate_only && Is_Tagged_Type (Etype (gnat_entity))))
{ {
Node_Id gnat_error_node = Empty; Node_Id gnat_error_node = Empty;
...@@ -6901,10 +6909,13 @@ gnat_to_gnu_field (Entity_Id gnat_field, tree gnu_record_type, int packed, ...@@ -6901,10 +6909,13 @@ gnat_to_gnu_field (Entity_Id gnat_field, tree gnu_record_type, int packed,
} }
} }
/* If this field needs strict alignment, ensure the record is /* If this field needs strict alignment, check that the record is
sufficiently aligned and that that position and size are sufficiently aligned and that position and size are consistent
consistent with the alignment. */ with the alignment. But don't do it if we are just annotating
if (needs_strict_alignment) types and the field's type is tagged, since tagged types aren't
fully laid out in this mode. */
if (needs_strict_alignment
&& !(type_annotate_only && Is_Tagged_Type (gnat_field_type)))
{ {
TYPE_ALIGN (gnu_record_type) TYPE_ALIGN (gnu_record_type)
= MAX (TYPE_ALIGN (gnu_record_type), TYPE_ALIGN (gnu_field_type)); = MAX (TYPE_ALIGN (gnu_record_type), TYPE_ALIGN (gnu_field_type));
...@@ -7839,12 +7850,16 @@ annotate_rep (Entity_Id gnat_entity, tree gnu_type) ...@@ -7839,12 +7850,16 @@ annotate_rep (Entity_Id gnat_entity, tree gnu_type)
{ {
tree parent_offset; tree parent_offset;
if (type_annotate_only && Is_Tagged_Type (gnat_entity)) /* If we are just annotating types and the type is tagged, the tag
and the parent components are not generated by the front-end so
we need to add the appropriate offset to each component without
representation clause. */
if (type_annotate_only
&& Is_Tagged_Type (gnat_entity)
&& No (Component_Clause (gnat_field)))
{ {
/* In this mode the tag and parent components are not /* For a component appearing in the current extension, the
generated, so we add the appropriate offset to each offset is the size of the parent. */
component. For a component appearing in the current
extension, the offset is the size of the parent. */
if (Is_Derived_Type (gnat_entity) if (Is_Derived_Type (gnat_entity)
&& Original_Record_Component (gnat_field) == gnat_field) && Original_Record_Component (gnat_field) == gnat_field)
parent_offset parent_offset
...@@ -7852,6 +7867,11 @@ annotate_rep (Entity_Id gnat_entity, tree gnu_type) ...@@ -7852,6 +7867,11 @@ annotate_rep (Entity_Id gnat_entity, tree gnu_type)
bitsizetype); bitsizetype);
else else
parent_offset = bitsize_int (POINTER_SIZE); parent_offset = bitsize_int (POINTER_SIZE);
if (TYPE_FIELDS (gnu_type))
parent_offset
= round_up (parent_offset,
DECL_ALIGN (TYPE_FIELDS (gnu_type)));
} }
else else
parent_offset = bitsize_zero_node; parent_offset = bitsize_zero_node;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment