C++ PATCH: empty non-byte aligned bases

Mark Mitchell mark@codesourcery.com
Sun Mar 26 10:59:00 GMT 2000


Jason says that under some systems we can have empty bases that are
not byte-aligned.  Here's a patch to handle that.

--
Mark Mitchell                   mark@codesourcery.com
CodeSourcery, LLC               http://www.codesourcery.com

2000-03-26  Mark Mitchell  <mark@codesourcery.com>

	* class.c (layout_empty_base): Handle empty bases with non-byte
	alignment.
	(build_base_field): Likewise.
	(layout_virtual_bases): Likewise.

	* class.c (finish_struct_1): Fix typo in this change:
	
	Sat Mar 25 09:12:10 2000  Richard Kenner  <kenner@vlsi1.ultra.nyu.edu>

Index: class.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/cp/class.c,v
retrieving revision 1.279
diff -c -p -r1.279 class.c
*** class.c	2000/03/25 18:34:11	1.279
--- class.c	2000/03/26 18:53:48
*************** layout_nonempty_base_or_field (rli, decl
*** 4267,4274 ****
  }
  
  /* Layout the empty base BINFO.  EOC indicates the byte currently just
!    past the end of the class; BINFO_OFFSETS gives the offsets of the
!    other bases allocated so far.  */
  
  static void
  layout_empty_base (binfo, eoc, binfo_offsets)
--- 4267,4275 ----
  }
  
  /* Layout the empty base BINFO.  EOC indicates the byte currently just
!    past the end of the class, and should be correctly aligned for a
!    class of the type indicated by BINFO; BINFO_OFFSETS gives the
!    offsets of the other bases allocated so far.  */
  
  static void
  layout_empty_base (binfo, eoc, binfo_offsets)
*************** layout_empty_base (binfo, eoc, binfo_off
*** 4276,4292 ****
       tree eoc;
       varray_type binfo_offsets;
  {
    tree basetype = BINFO_TYPE (binfo);
    
    /* This routine should only be used for empty classes.  */
    my_friendly_assert (is_empty_class (basetype), 20000321);
  
-   /* This code assumes that zero-sized classes have one-byte
-      alignment.  There might someday be a system where that's not
-      true.  */
-   my_friendly_assert (TYPE_ALIGN (basetype) == BITS_PER_UNIT, 
- 		      20000314);
- 
    /* This is an empty base class.  We first try to put it at offset
       zero.  */
    if (layout_conflict_p (binfo, binfo_offsets))
--- 4277,4289 ----
       tree eoc;
       varray_type binfo_offsets;
  {
+   tree alignment;
    tree basetype = BINFO_TYPE (binfo);
    
    /* This routine should only be used for empty classes.  */
    my_friendly_assert (is_empty_class (basetype), 20000321);
+   alignment = ssize_int (CLASSTYPE_ALIGN (basetype));
  
    /* This is an empty base class.  We first try to put it at offset
       zero.  */
    if (layout_conflict_p (binfo, binfo_offsets))
*************** layout_empty_base (binfo, eoc, binfo_off
*** 4301,4307 ****
  	    break;
  
  	  /* There's overlap here, too.  Bump along to the next spot.  */
! 	  propagate_binfo_offsets (binfo, ssize_int (1));
  	}
      }
  }
--- 4298,4304 ----
  	    break;
  
  	  /* There's overlap here, too.  Bump along to the next spot.  */
! 	  propagate_binfo_offsets (binfo, alignment);
  	}
      }
  }
*************** build_base_field (rli, binfo, empty_p, b
*** 4360,4366 ****
        layout_nonempty_base_or_field (rli, decl, binfo, *v);
      }
    else
!     layout_empty_base (binfo, rli_size_unit_so_far (rli), *v);
  
    /* Check for inaccessible base classes.  If the same base class
       appears more than once in the hierarchy, but isn't virtual, then
--- 4357,4371 ----
        layout_nonempty_base_or_field (rli, decl, binfo, *v);
      }
    else
!     {
!       unsigned HOST_WIDE_INT eoc;
! 
!       /* On some platforms (ARM), even empty classes will not be
! 	 byte-aligned.  */
!       eoc = tree_low_cst (rli_size_unit_so_far (rli), 0);
!       eoc = CEIL (eoc, DECL_ALIGN (decl)) * DECL_ALIGN (decl);
!       layout_empty_base (binfo, size_int (eoc), *v);
!     }
  
    /* Check for inaccessible base classes.  If the same base class
       appears more than once in the hierarchy, but isn't virtual, then
*************** layout_virtual_bases (t, base_offsets)
*** 4847,4852 ****
--- 4852,4870 ----
  
  	basetype = BINFO_TYPE (vbase);
  
+ 	if (flag_new_abi)
+ 	  desired_align = CLASSTYPE_ALIGN (basetype);
+ 	else
+ 	  /* Under the old ABI, virtual bases were aligned as for the
+ 	     entire base object (including its virtual bases).  That's
+ 	     wasteful, in general.  */
+ 	  desired_align = TYPE_ALIGN (basetype);
+ 	TYPE_ALIGN (t) = MAX (TYPE_ALIGN (t), desired_align);
+ 
+ 	/* Add padding so that we can put the virtual base class at an
+ 	   appropriately aligned offset.  */
+ 	dsize = CEIL (dsize, desired_align) * desired_align;
+ 
  	/* Under the new ABI, we try to squish empty virtual bases in
  	   just like ordinary empty bases.  */
  	if (flag_new_abi && is_empty_class (basetype))
*************** layout_virtual_bases (t, base_offsets)
*** 4855,4872 ****
  			     *base_offsets);
  	else
  	  {
- 	    if (flag_new_abi)
- 	      desired_align = CLASSTYPE_ALIGN (basetype);
- 	    else
- 	      /* Under the old ABI, virtual bases were aligned as for
- 		 the entire base object (including its virtual bases).
- 		 That's wasteful, in general.  */
- 	      desired_align = TYPE_ALIGN (basetype);
- 	    TYPE_ALIGN (t) = MAX (TYPE_ALIGN (t), desired_align);
- 
- 	    /* Add padding so that we can put the virtual base class at an
- 	       appropriately aligned offset.  */
- 	    dsize = CEIL (dsize, desired_align) * desired_align;
  	    /* And compute the offset of the virtual base.  */
  	    propagate_binfo_offsets (vbase, 
  				     ssize_int (CEIL (dsize, BITS_PER_UNIT)));
--- 4873,4878 ----


More information about the Gcc-patches mailing list