OSDN Git Service

* config/h8300/h8300.md (a peephole2): Remove useless code.
[pf3gnuchains/gcc-fork.git] / gcc / stor-layout.c
index 0dd8fc6..6caaf5f 100644 (file)
@@ -1,6 +1,6 @@
 /* C-compiler utilities for types and variables storage layout
    Copyright (C) 1987, 1988, 1992, 1993, 1994, 1995, 1996, 1996, 1998,
-   1999, 2000, 2001, 2002 Free Software Foundation, Inc.
+   1999, 2000, 2001, 2002, 2003 Free Software Foundation, Inc.
 
 This file is part of GCC.
 
@@ -62,9 +62,11 @@ static int reference_types_internal = 0;
 static void finalize_record_size       PARAMS ((record_layout_info));
 static void finalize_type_size         PARAMS ((tree));
 static void place_union_field          PARAMS ((record_layout_info, tree));
+#if defined (PCC_BITFIELD_TYPE_MATTERS) || defined (BITFIELD_NBYTES_LIMITED)
 static int excess_unit_span            PARAMS ((HOST_WIDE_INT, HOST_WIDE_INT,
                                                HOST_WIDE_INT, HOST_WIDE_INT,
                                                tree));
+#endif
 static unsigned int update_alignment_for_field
                                         PARAMS ((record_layout_info, tree, 
                                                 unsigned int));
@@ -155,6 +157,8 @@ tree
 variable_size (size)
      tree size;
 {
+  tree save;
+
   /* If the language-processor is to take responsibility for variable-sized
      items (e.g., languages which have elaboration procedures like Ada),
      just return SIZE unchanged.  Likewise for self-referential sizes and
@@ -164,7 +168,12 @@ variable_size (size)
       || contains_placeholder_p (size))
     return size;
 
-  size = save_expr (size);
+  if (TREE_CODE (size) == MINUS_EXPR && integer_onep (TREE_OPERAND (size, 1)))
+    /* If this is the upper bound of a C array, leave the minus 1 outside
+       the SAVE_EXPR so it can be folded away.  */
+    TREE_OPERAND (size, 0) = save = save_expr (TREE_OPERAND (size, 0));
+  else
+    size = save = save_expr (size);
 
   /* If an array with a variable number of elements is declared, and
      the elements require destruction, we will emit a cleanup for the
@@ -174,8 +183,8 @@ variable_size (size)
      `unsaved', i.e., all SAVE_EXPRs are recalculated.  However, we do
      not wish to do that here; the array-size is the same in both
      places.  */
-  if (TREE_CODE (size) == SAVE_EXPR)
-    SAVE_EXPR_PERSISTENT_P (size) = 1;
+  if (TREE_CODE (save) == SAVE_EXPR)
+    SAVE_EXPR_PERSISTENT_P (save) = 1;
 
   if ((*lang_hooks.decls.global_bindings_p) ())
     {
@@ -188,16 +197,13 @@ variable_size (size)
     }
 
   if (immediate_size_expand)
-    /* NULL_RTX is not defined; neither is the rtx type.
-       Also, we would like to pass const0_rtx here, but don't have it.  */
-    expand_expr (size, expand_expr (integer_zero_node, NULL_RTX, VOIDmode, 0),
-                VOIDmode, 0);
+    expand_expr (save, const0_rtx, VOIDmode, 0);
   else if (cfun != 0 && cfun->x_dont_save_pending_sizes_p)
     /* The front-end doesn't want us to keep a list of the expressions
        that determine sizes for variable size objects.  */
     ;
   else
-    put_pending_size (size);
+    put_pending_size (save);
 
   return size;
 }
@@ -303,6 +309,29 @@ int_mode_for_mode (mode)
   return mode;
 }
 
+/* Return the alignment of MODE. This will be bounded by 1 and
+   BIGGEST_ALIGNMENT.  */
+
+unsigned int
+get_mode_alignment (mode)
+     enum machine_mode mode;
+{
+  unsigned int alignment;
+
+  if (GET_MODE_CLASS (mode) == MODE_COMPLEX_FLOAT
+      || GET_MODE_CLASS (mode) == MODE_COMPLEX_INT)
+    alignment = GET_MODE_UNIT_SIZE (mode);
+  else
+    alignment = GET_MODE_SIZE (mode);
+
+  /* Extract the LSB of the size.  */
+  alignment = alignment & -alignment;
+  alignment *= BITS_PER_UNIT;
+
+  alignment = MIN (BIGGEST_ALIGNMENT, MAX (1, alignment));
+  return alignment;
+}
+
 /* Return the value of VALUE, rounded up to a multiple of DIVISOR.
    This can only be applied to objects of a sizetype.  */
 
@@ -509,7 +538,7 @@ start_record_layout (t)
 #ifdef STRUCTURE_SIZE_BOUNDARY
   /* Packed structures don't need to have minimum size.  */
   if (! TYPE_PACKED (t))
-    rli->record_align = MAX (rli->record_align, STRUCTURE_SIZE_BOUNDARY);
+    rli->record_align = MAX (rli->record_align, (unsigned) STRUCTURE_SIZE_BOUNDARY);
 #endif
 
   rli->offset = size_zero_node;
@@ -715,17 +744,18 @@ update_alignment_for_field (rli, field, known_align)
       && DECL_BIT_FIELD_TYPE (field)
       && ! integer_zerop (TYPE_SIZE (type)))
     {
-      /* For these machines, a zero-length field does not
-        affect the alignment of the structure as a whole.
-        It does, however, affect the alignment of the next field
-        within the structure.  */
-      if (! integer_zerop (DECL_SIZE (field)))
-       rli->record_align = MAX (rli->record_align, desired_align);
-      else if (! DECL_PACKED (field))
-       desired_align = TYPE_ALIGN (type);
-
-      /* A named bit field of declared type `int'
-        forces the entire structure to have `int' alignment.  */
+      /* A zero-length bit-field affects the alignment of the next
+        field.  */
+      if (!DECL_PACKED (field) && integer_zerop (DECL_SIZE (field)))
+       {
+         desired_align = TYPE_ALIGN (type);
+#ifdef ADJUST_FIELD_ALIGN
+         desired_align = ADJUST_FIELD_ALIGN (field, desired_align);
+#endif
+       }
+
+      /* Named bit-fields cause the entire structure to have the
+        alignment implied by their type.  */
       if (DECL_NAME (field) != 0)
        {
          unsigned int type_align = TYPE_ALIGN (type);
@@ -740,7 +770,14 @@ update_alignment_for_field (rli, field, known_align)
          else if (DECL_PACKED (field))
            type_align = MIN (type_align, BITS_PER_UNIT);
 
+         /* The alignment of the record is increased to the maximum
+            of the current alignment, the alignment indicated on the
+            field (i.e., the alignment specified by an __aligned__
+            attribute), and the alignment indicated by the type of
+            the field.  */
+         rli->record_align = MAX (rli->record_align, desired_align);
          rli->record_align = MAX (rli->record_align, type_align);
+
          rli->unpadded_align = MAX (rli->unpadded_align, DECL_ALIGN (field));
          if (warn_packed)
            rli->unpacked_align = MAX (rli->unpacked_align, TYPE_ALIGN (type));
@@ -783,6 +820,7 @@ place_union_field (rli, field)
                               DECL_SIZE_UNIT (field), rli->offset));
 }
 
+#if defined (PCC_BITFIELD_TYPE_MATTERS) || defined (BITFIELD_NBYTES_LIMITED)
 /* A bitfield of SIZE with a required access alignment of ALIGN is allocated
    at BYTE_OFFSET / BIT_OFFSET.  Return nonzero if the field would span more
    units of alignment than the underlying TYPE.  */
@@ -800,6 +838,7 @@ excess_unit_span (byte_offset, bit_offset, size, align, type)
          > ((unsigned HOST_WIDE_INT) tree_low_cst (TYPE_SIZE (type), 1)
             / align));
 }
+#endif
 
 /* RLI contains information about the layout of a RECORD_TYPE.  FIELD
    is a FIELD_DECL to be added after those fields already present in
@@ -993,10 +1032,10 @@ place_field (rli, field)
        used in the record, and any additional adjacent long bitfields are
        packed into the same chunk of 32 bits. However, if the size
        changes, a new field of that size is allocated.)  In an unpacked
-       record, this is the same as using alignment, but not eqivalent
+       record, this is the same as using alignment, but not equivalent
        when packing.
 
-     Note: for compatability, we use the type size, not the type alignment
+     Note: for compatibility, we use the type size, not the type alignment
      to determine alignment, since that matches the documentation */
 
   if ((* targetm.ms_bitfield_layout_p) (rli->t)
@@ -1095,7 +1134,7 @@ place_field (rli, field)
                      TYPE_SIZE (TREE_TYPE (prev_saved)))
               : !integer_zerop (DECL_SIZE (field)) ))
        {
-         unsigned int type_align = 8;  /* Never below 8 for compatability */
+         unsigned int type_align = 8;  /* Never below 8 for compatibility */
 
          /* (When not a bitfield), we could be seeing a flex array (with
             no DECL_SIZE).  Since we won't be using remaining_in_alignment
@@ -1189,7 +1228,7 @@ place_field (rli, field)
 
 /* Assuming that all the fields have been laid out, this function uses
    RLI to compute the final TYPE_SIZE, TYPE_ALIGN, etc. for the type
-   inidicated by RLI.  */
+   indicated by RLI.  */
 
 static void
 finalize_record_size (rli)
@@ -1219,15 +1258,7 @@ finalize_record_size (rli)
     unpadded_size_unit
       = size_binop (PLUS_EXPR, unpadded_size_unit, size_one_node);
 
-  /* Record the un-rounded size in the binfo node.  But first we check
-     the size of TYPE_BINFO to make sure that BINFO_SIZE is available.  */
-  if (TYPE_BINFO (rli->t) && TREE_VEC_LENGTH (TYPE_BINFO (rli->t)) > 6)
-    {
-      TYPE_BINFO_SIZE (rli->t) = unpadded_size;
-      TYPE_BINFO_SIZE_UNIT (rli->t) = unpadded_size_unit;
-    }
-
-    /* Round the size up to be a multiple of the required alignment */
+  /* Round the size up to be a multiple of the required alignment */
 #ifdef ROUND_TYPE_SIZE
   TYPE_SIZE (rli->t) = ROUND_TYPE_SIZE (rli->t, unpadded_size,
                                        TYPE_ALIGN (rli->t));