OSDN Git Service

* decl.c (gnat_to_gnu_entity) <object>: If -gnatd.a and not optimizing
[pf3gnuchains/gcc-fork.git] / gcc / ada / trans.c
index f3dc87d..82aaa99 100644 (file)
@@ -4832,34 +4832,41 @@ gnat_to_gnu (Node_Id gnat_node)
          || CONTAINS_PLACEHOLDER_P (TYPE_SIZE (gnu_result_type))))
     gnu_result = gnat_stabilize_reference (gnu_result, false);
 
-  /* Now convert the result to the proper type.  If the type is void or if
-     we have no result, return error_mark_node to show we have no result.
-     If the type of the result is correct or if we have a label (which doesn't
-     have any well-defined type), return our result.  Also don't do the
-     conversion if the "desired" type involves a PLACEHOLDER_EXPR in its size
-     since those are the cases where the front end may have the type wrong due
-     to "instantiating" the unconstrained record with discriminant values
-     or if this is a FIELD_DECL.  If this is the Name of an assignment
-     statement or a parameter of a procedure call, return what we have since
-     the RHS has to be converted to our type there in that case, unless
-     GNU_RESULT_TYPE has a simpler size.  Similarly, if the two types are
-     record types with the same name and GNU_RESULT_TYPE has BLKmode, don't
-     convert.  This will be the case when we are converting from a packable
-     type to its actual type and we need those conversions to be NOPs in
-     order for assignments into these types to work properly.  Finally,
-     don't convert integral types that are the operand of an unchecked
-     conversion since we need to ignore those conversions (for 'Valid).
-     Otherwise, convert the result to the proper type.  */
+  /* Now convert the result to the result type, unless we are in one of the
+     following cases:
+
+       1. If this is the Name of an assignment statement or a parameter of
+         a procedure call, return the result almost unmodified since the
+         RHS will have to be converted to our type in that case, unless
+         the result type has a simpler size.   Similarly, don't convert
+         integral types that are the operands of an unchecked conversion
+         since we need to ignore those conversions (for 'Valid).
+
+       2. If we have a label (which doesn't have any well-defined type), a
+         field or an error, return the result almost unmodified.  Also don't
+         do the conversion if the result type involves a PLACEHOLDER_EXPR in
+         its size since those are the cases where the front end may have the
+         type wrong due to "instantiating" the unconstrained record with
+         discriminant values.  Similarly, if the two types are record types
+         with the same name and the result type has BLKmode, don't convert.
+         This will be the case when we are converting from a packed version
+         of a type to its original type and we need those conversions to be
+         NOPs in order for assignments into these types to work properly.
+
+       3. If the type is void or if we have no result, return error_mark_node
+         to show we have no result.
+
+       4. Finally, if the type of the result is already correct.  */
 
   if (Present (Parent (gnat_node))
       && ((Nkind (Parent (gnat_node)) == N_Assignment_Statement
           && Name (Parent (gnat_node)) == gnat_node)
          || (Nkind (Parent (gnat_node)) == N_Procedure_Call_Statement
              && Name (Parent (gnat_node)) != gnat_node)
+         || Nkind (Parent (gnat_node)) == N_Parameter_Association
          || (Nkind (Parent (gnat_node)) == N_Unchecked_Type_Conversion
              && !AGGREGATE_TYPE_P (gnu_result_type)
-             && !AGGREGATE_TYPE_P (TREE_TYPE (gnu_result)))
-         || Nkind (Parent (gnat_node)) == N_Parameter_Association)
+             && !AGGREGATE_TYPE_P (TREE_TYPE (gnu_result))))
       && !(TYPE_SIZE (gnu_result_type)
           && TYPE_SIZE (TREE_TYPE (gnu_result))
           && (AGGREGATE_TYPE_P (gnu_result_type)
@@ -4874,16 +4881,14 @@ gnat_to_gnu (Node_Id gnat_node)
           && !(TREE_CODE (gnu_result_type) == RECORD_TYPE
                && TYPE_JUSTIFIED_MODULAR_P (gnu_result_type))))
     {
-      /* In this case remove padding only if the inner object type is the
-        same as gnu_result_type or is of self-referential size (in that later
-        case it must be an object of unconstrained type with a default
-        discriminant).  We want to avoid copying too much data.  */
+      /* Remove padding only if the inner object is of self-referential
+        size: in that case it must be an object of unconstrained type
+        with a default discriminant and we want to avoid copying too
+        much data.  */
       if (TREE_CODE (TREE_TYPE (gnu_result)) == RECORD_TYPE
          && TYPE_IS_PADDING_P (TREE_TYPE (gnu_result))
-         && (TREE_TYPE (TYPE_FIELDS (TREE_TYPE (gnu_result)))
-                         == gnu_result_type
-             || CONTAINS_PLACEHOLDER_P (TYPE_SIZE (TREE_TYPE (TYPE_FIELDS
-                                            (TREE_TYPE (gnu_result)))))))
+         && CONTAINS_PLACEHOLDER_P (TYPE_SIZE (TREE_TYPE (TYPE_FIELDS
+                                    (TREE_TYPE (gnu_result))))))
        gnu_result = convert (TREE_TYPE (TYPE_FIELDS (TREE_TYPE (gnu_result))),
                              gnu_result);
     }
@@ -4901,20 +4906,20 @@ gnat_to_gnu (Node_Id gnat_node)
               && TREE_CODE (TREE_TYPE (gnu_result)) == RECORD_TYPE
               && TYPE_MODE (gnu_result_type) == BLKmode))
     {
-      /* Remove any padding record, but do nothing more in this case.  */
+      /* Remove any padding.  */
       if (TREE_CODE (TREE_TYPE (gnu_result)) == RECORD_TYPE
          && TYPE_IS_PADDING_P (TREE_TYPE (gnu_result)))
        gnu_result = convert (TREE_TYPE (TYPE_FIELDS (TREE_TYPE (gnu_result))),
                              gnu_result);
     }
 
-  else if (gnu_result == error_mark_node
-          || gnu_result_type == void_type_node)
-    gnu_result =  error_mark_node;
+  else if (gnu_result == error_mark_node || gnu_result_type == void_type_node)
+    gnu_result = error_mark_node;
+
   else if (gnu_result_type != TREE_TYPE (gnu_result))
     gnu_result = convert (gnu_result_type, gnu_result);
 
-  /* We don't need any NOP_EXPR or NON_LVALUE_EXPR on GNU_RESULT.  */
+  /* We don't need any NOP_EXPR or NON_LVALUE_EXPR on the result.  */
   while ((TREE_CODE (gnu_result) == NOP_EXPR
          || TREE_CODE (gnu_result) == NON_LVALUE_EXPR)
         && TREE_TYPE (TREE_OPERAND (gnu_result, 0)) == TREE_TYPE (gnu_result))