aboutsummaryrefslogtreecommitdiff
path: root/gcc/ada/gcc-interface/trans.c
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/ada/gcc-interface/trans.c')
-rw-r--r--gcc/ada/gcc-interface/trans.c76
1 files changed, 36 insertions, 40 deletions
diff --git a/gcc/ada/gcc-interface/trans.c b/gcc/ada/gcc-interface/trans.c
index 860e0dc..cd6626f 100644
--- a/gcc/ada/gcc-interface/trans.c
+++ b/gcc/ada/gcc-interface/trans.c
@@ -1415,14 +1415,14 @@ Attribute_to_gnu (Node_Id gnat_node, tree *gnu_result_type_p, int attribute)
case Attr_Pool_Address:
{
- tree gnu_obj_type;
tree gnu_ptr = gnu_prefix;
+ tree gnu_obj_type;
gnu_result_type = get_unpadded_type (Etype (gnat_node));
- /* If this is an unconstrained array, we know the object has been
- allocated with the template in front of the object. So compute
- the template address. */
+ /* If this is fat pointer, the object must have been allocated with the
+ template in front of the array. So compute the template address; do
+ it by converting to a thin pointer. */
if (TYPE_IS_FAT_POINTER_P (TREE_TYPE (gnu_ptr)))
gnu_ptr
= convert (build_pointer_type
@@ -1431,16 +1431,15 @@ Attribute_to_gnu (Node_Id gnat_node, tree *gnu_result_type_p, int attribute)
gnu_ptr);
gnu_obj_type = TREE_TYPE (TREE_TYPE (gnu_ptr));
- if (TREE_CODE (gnu_obj_type) == RECORD_TYPE
- && TYPE_CONTAINS_TEMPLATE_P (gnu_obj_type))
- {
- tree gnu_char_ptr_type
- = build_pointer_type (unsigned_char_type_node);
- tree gnu_pos = byte_position (TYPE_FIELDS (gnu_obj_type));
- gnu_ptr = convert (gnu_char_ptr_type, gnu_ptr);
- gnu_ptr = build_binary_op (POINTER_PLUS_EXPR, gnu_char_ptr_type,
- gnu_ptr, gnu_pos);
- }
+
+ /* If this is a thin pointer, the object must have been allocated with
+ the template in front of the array. So compute the template address
+ and return it. */
+ if (TYPE_IS_THIN_POINTER_P (TREE_TYPE (gnu_ptr)))
+ gnu_ptr
+ = build_binary_op (POINTER_PLUS_EXPR, TREE_TYPE (gnu_ptr),
+ gnu_ptr,
+ byte_position (TYPE_FIELDS (gnu_obj_type)));
gnu_result = convert (gnu_result_type, gnu_ptr);
}
@@ -6593,23 +6592,20 @@ gnat_to_gnu (Node_Id gnat_node)
{
tree gnu_ptr = gnat_to_gnu (Expression (gnat_node));
tree gnu_ptr_type = TREE_TYPE (gnu_ptr);
- tree gnu_obj_type;
- tree gnu_actual_obj_type = 0;
- tree gnu_obj_size;
-
- /* If this is a thin pointer, we must dereference it to create
- a fat pointer, then go back below to a thin pointer. The
- reason for this is that we need a fat pointer someplace in
- order to properly compute the size. */
+ tree gnu_obj_type, gnu_actual_obj_type;
+
+ /* If this is a thin pointer, we must first dereference it to create
+ a fat pointer, then go back below to a thin pointer. The reason
+ for this is that we need to have a fat pointer someplace in order
+ to properly compute the size. */
if (TYPE_IS_THIN_POINTER_P (TREE_TYPE (gnu_ptr)))
gnu_ptr = build_unary_op (ADDR_EXPR, NULL_TREE,
build_unary_op (INDIRECT_REF, NULL_TREE,
gnu_ptr));
- /* If this is an unconstrained array, we know the object must
- have been allocated with the template in front of the object.
- So pass the template address, but get the total size. Do this
- by converting to a thin pointer. */
+ /* If this is a fat pointer, the object must have been allocated with
+ the template in front of the array. So pass the template address,
+ and get the total size; do it by converting to a thin pointer. */
if (TYPE_IS_FAT_POINTER_P (TREE_TYPE (gnu_ptr)))
gnu_ptr
= convert (build_pointer_type
@@ -6619,6 +6615,17 @@ gnat_to_gnu (Node_Id gnat_node)
gnu_obj_type = TREE_TYPE (TREE_TYPE (gnu_ptr));
+ /* If this is a thin pointer, the object must have been allocated with
+ the template in front of the array. So pass the template address,
+ and get the total size. */
+ if (TYPE_IS_THIN_POINTER_P (TREE_TYPE (gnu_ptr)))
+ gnu_ptr
+ = build_binary_op (POINTER_PLUS_EXPR, TREE_TYPE (gnu_ptr),
+ gnu_ptr,
+ byte_position (TYPE_FIELDS (gnu_obj_type)));
+
+ /* If we have a special dynamic constrained subtype on the node, use
+ it to compute the size; otherwise, use the designated subtype. */
if (Present (Actual_Designated_Subtype (gnat_node)))
{
gnu_actual_obj_type
@@ -6634,21 +6641,10 @@ gnat_to_gnu (Node_Id gnat_node)
else
gnu_actual_obj_type = gnu_obj_type;
- gnu_obj_size = TYPE_SIZE_UNIT (gnu_actual_obj_type);
-
- if (TREE_CODE (gnu_obj_type) == RECORD_TYPE
- && TYPE_CONTAINS_TEMPLATE_P (gnu_obj_type))
- {
- tree gnu_char_ptr_type
- = build_pointer_type (unsigned_char_type_node);
- tree gnu_pos = byte_position (TYPE_FIELDS (gnu_obj_type));
- gnu_ptr = convert (gnu_char_ptr_type, gnu_ptr);
- gnu_ptr = build_binary_op (POINTER_PLUS_EXPR, gnu_char_ptr_type,
- gnu_ptr, gnu_pos);
- }
-
gnu_result
- = build_call_alloc_dealloc (gnu_ptr, gnu_obj_size, gnu_obj_type,
+ = build_call_alloc_dealloc (gnu_ptr,
+ TYPE_SIZE_UNIT (gnu_actual_obj_type),
+ gnu_obj_type,
Procedure_To_Call (gnat_node),
Storage_Pool (gnat_node),
gnat_node);