This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[PATCH] Cleanup get_object_alignment, drop align parameter


This cleans up get_object_alignment in preparation to make it the
replacement for all the alignment code in set_mem_attributes_minus_bitpos.
It drops the align argument as the two existing callers really want
different behavior.

Bootstrapped and tested on x86_64-unknown-linux-gnu.  I'll apply this
tomorrow if there are no objections.

Thanks,
Richard.

2010-08-09  Richard Guenther  <rguenther@suse.de>

	* tree.h (get_object_alignment): Adjust prototype.
	* builtins.c (get_object_alignment): Return unsigned int,
	drop the align parameter.  Handle MEM_REF, MISALIGNED_INDIRECT_REF
	and TARGET_MEM_REF properly.
	(get_pointer_alignment): Adjust.
	* emit-rtl.c (get_mem_align_offset): Adjust comment.
	(set_mem_attributes_minus_bitpos): Adjust.
	* tree-ssa-ccp.c (get_value_from_alignment): Adjust.

Index: gcc/tree.h
===================================================================
*** gcc/tree.h	(revision 163030)
--- gcc/tree.h	(working copy)
*************** extern bool can_trust_pointer_alignment
*** 5036,5042 ****
  extern int get_pointer_alignment (tree, unsigned int);
  extern bool is_builtin_name (const char *);
  extern bool is_builtin_fn (tree);
! extern int get_object_alignment (tree, unsigned int, unsigned int);
  extern tree fold_call_stmt (gimple, bool);
  extern tree gimple_fold_builtin_snprintf_chk (gimple, tree, enum built_in_function);
  extern tree make_range (tree, int *, tree *, tree *, bool *);
--- 5036,5042 ----
  extern int get_pointer_alignment (tree, unsigned int);
  extern bool is_builtin_name (const char *);
  extern bool is_builtin_fn (tree);
! extern unsigned int get_object_alignment (tree, unsigned int);
  extern tree fold_call_stmt (gimple, bool);
  extern tree gimple_fold_builtin_snprintf_chk (gimple, tree, enum built_in_function);
  extern tree make_range (tree, int *, tree *, tree *, bool *);
Index: gcc/builtins.c
===================================================================
*** gcc/builtins.c	(revision 163030)
--- gcc/builtins.c	(working copy)
*************** called_as_built_in (tree node)
*** 270,347 ****
     Don't return more than MAX_ALIGN no matter what, ALIGN is the inital
     guessed alignment e.g. from type alignment.  */
  
! int
! get_object_alignment (tree exp, unsigned int align, unsigned int max_align)
  {
!   unsigned int inner;
  
!   inner = max_align;
!   if (handled_component_p (exp))
!    {
!       HOST_WIDE_INT bitsize, bitpos;
!       tree offset;
!       enum machine_mode mode;
!       int unsignedp, volatilep;
! 
!       exp = get_inner_reference (exp, &bitsize, &bitpos, &offset,
! 				 &mode, &unsignedp, &volatilep, true);
!       if (bitpos)
! 	inner = MIN (inner, (unsigned) (bitpos & -bitpos));
!       while (offset)
! 	{
! 	  tree next_offset;
! 
! 	  if (TREE_CODE (offset) == PLUS_EXPR)
! 	    {
! 	      next_offset = TREE_OPERAND (offset, 0);
! 	      offset = TREE_OPERAND (offset, 1);
! 	    }
! 	  else
! 	    next_offset = NULL;
! 	  if (host_integerp (offset, 1))
! 	    {
! 	      /* Any overflow in calculating offset_bits won't change
! 		 the alignment.  */
! 	      unsigned offset_bits
! 		= ((unsigned) tree_low_cst (offset, 1) * BITS_PER_UNIT);
! 
! 	      if (offset_bits)
! 		inner = MIN (inner, (offset_bits & -offset_bits));
! 	    }
! 	  else if (TREE_CODE (offset) == MULT_EXPR
! 		   && host_integerp (TREE_OPERAND (offset, 1), 1))
! 	    {
! 	      /* Any overflow in calculating offset_factor won't change
! 		 the alignment.  */
! 	      unsigned offset_factor
! 		= ((unsigned) tree_low_cst (TREE_OPERAND (offset, 1), 1)
! 		   * BITS_PER_UNIT);
! 
! 	      if (offset_factor)
! 		inner = MIN (inner, (offset_factor & -offset_factor));
! 	    }
! 	  else
! 	    {
! 	      inner = MIN (inner, BITS_PER_UNIT);
! 	      break;
! 	    }
! 	  offset = next_offset;
! 	}
!     }
    if (TREE_CODE (exp) == CONST_DECL)
      exp = DECL_INITIAL (exp);
    if (DECL_P (exp)
        && TREE_CODE (exp) != LABEL_DECL)
!     align = MIN (inner, DECL_ALIGN (exp));
! #ifdef CONSTANT_ALIGNMENT
    else if (CONSTANT_CLASS_P (exp))
!     align = MIN (inner, (unsigned)CONSTANT_ALIGNMENT (exp, align));
  #endif
!   else if (TREE_CODE (exp) == VIEW_CONVERT_EXPR
! 	   || TREE_CODE (exp) == INDIRECT_REF)
!     align = MIN (TYPE_ALIGN (TREE_TYPE (exp)), inner);
    else
!     align = MIN (align, inner);
    return MIN (align, max_align);
  }
  
--- 270,402 ----
     Don't return more than MAX_ALIGN no matter what, ALIGN is the inital
     guessed alignment e.g. from type alignment.  */
  
! unsigned int
! get_object_alignment (tree exp, unsigned int max_align)
  {
!   HOST_WIDE_INT bitsize, bitpos;
!   tree offset;
!   enum machine_mode mode;
!   int unsignedp, volatilep;
!   unsigned int align, inner;
  
!   /* Get the innermost object and the constant (bitpos) and possibly
!      variable (offset) offset of the access.  */
!   exp = get_inner_reference (exp, &bitsize, &bitpos, &offset,
! 			     &mode, &unsignedp, &volatilep, true);
! 
!   /* Extract alignment information from the innermost object and
!      possibly adjust bitpos and offset.  */
    if (TREE_CODE (exp) == CONST_DECL)
      exp = DECL_INITIAL (exp);
    if (DECL_P (exp)
        && TREE_CODE (exp) != LABEL_DECL)
!     align = DECL_ALIGN (exp);
    else if (CONSTANT_CLASS_P (exp))
!     {
!       align = TYPE_ALIGN (TREE_TYPE (exp));
! #ifdef CONSTANT_ALIGNMENT
!       align = (unsigned)CONSTANT_ALIGNMENT (exp, align);
  #endif
!     }
!   else if (TREE_CODE (exp) == VIEW_CONVERT_EXPR)
!     align = TYPE_ALIGN (TREE_TYPE (exp));
!   else if (TREE_CODE (exp) == INDIRECT_REF)
!     align = TYPE_ALIGN (TREE_TYPE (exp));
!   else if (TREE_CODE (exp) == MISALIGNED_INDIRECT_REF)
!     {
!       tree op1 = TREE_OPERAND (exp, 1);
!       align = integer_zerop (op1) ? BITS_PER_UNIT : TREE_INT_CST_LOW (op1);
!     }
!   else if (TREE_CODE (exp) == MEM_REF)
!     {
!       tree addr = TREE_OPERAND (exp, 0);
!       if (TREE_CODE (addr) == BIT_AND_EXPR
! 	  && TREE_CODE (TREE_OPERAND (addr, 1)) == INTEGER_CST)
! 	{
! 	  align = (TREE_INT_CST_LOW (TREE_OPERAND (addr, 1))
! 		    & -TREE_INT_CST_LOW (TREE_OPERAND (addr, 1)));
! 	  align *= BITS_PER_UNIT;
! 	  addr = TREE_OPERAND (addr, 0);
! 	}
!       else
! 	align = BITS_PER_UNIT;
!       if (TREE_CODE (addr) == ADDR_EXPR)
! 	align = MAX (align, get_object_alignment (TREE_OPERAND (addr, 0),
! 						  max_align));
!       bitpos += mem_ref_offset (exp).low * BITS_PER_UNIT;
!     }
!   else if (TREE_CODE (exp) == TARGET_MEM_REF
! 	   && TMR_SYMBOL (exp))
!     {
!       align = get_object_alignment (TMR_SYMBOL (exp), max_align);
!       if (TMR_OFFSET (exp))
!         bitpos += TREE_INT_CST_LOW (TMR_OFFSET (exp)) * BITS_PER_UNIT;
!       if (TMR_INDEX (exp) && TMR_STEP (exp))
! 	{
! 	  unsigned HOST_WIDE_INT step = TREE_INT_CST_LOW (TMR_STEP (exp));
! 	  align = MIN (align, (step & -step) * BITS_PER_UNIT);
! 	}
!       else if (TMR_INDEX (exp))
! 	align = BITS_PER_UNIT;
!     }
    else
!     align = BITS_PER_UNIT;
! 
!   /* If there is a non-constant offset part extract the maximum
!      alignment that can prevail.  */
!   inner = max_align;
!   while (offset)
!     {
!       tree next_offset;
! 
!       if (TREE_CODE (offset) == PLUS_EXPR)
! 	{
! 	  next_offset = TREE_OPERAND (offset, 0);
! 	  offset = TREE_OPERAND (offset, 1);
! 	}
!       else
! 	next_offset = NULL;
!       if (host_integerp (offset, 1))
! 	{
! 	  /* Any overflow in calculating offset_bits won't change
! 	     the alignment.  */
! 	  unsigned offset_bits
! 	    = ((unsigned) tree_low_cst (offset, 1) * BITS_PER_UNIT);
! 
! 	  if (offset_bits)
! 	    inner = MIN (inner, (offset_bits & -offset_bits));
! 	}
!       else if (TREE_CODE (offset) == MULT_EXPR
! 	       && host_integerp (TREE_OPERAND (offset, 1), 1))
! 	{
! 	  /* Any overflow in calculating offset_factor won't change
! 	     the alignment.  */
! 	  unsigned offset_factor
! 	    = ((unsigned) tree_low_cst (TREE_OPERAND (offset, 1), 1)
! 	       * BITS_PER_UNIT);
! 
! 	  if (offset_factor)
! 	    inner = MIN (inner, (offset_factor & -offset_factor));
! 	}
!       else
! 	{
! 	  inner = MIN (inner, BITS_PER_UNIT);
! 	  break;
! 	}
!       offset = next_offset;
!     }
! 
!   /* Alignment is innermost object alignment adjusted by the constant
!      and non-constant offset parts.  */
!   align = MIN (align, inner);
!   bitpos = bitpos & (align - 1);
! 
!   /* align and bitpos now specify known low bits of the pointer.
!      ptr & (align - 1) == bitpos.  */
! 
!   if (bitpos != 0)
!     align = (bitpos & -bitpos);
! 
    return MIN (align, max_align);
  }
  
*************** get_pointer_alignment (tree exp, unsigne
*** 407,413 ****
  
  	case ADDR_EXPR:
  	  /* See what we are pointing at and look at its alignment.  */
! 	  return get_object_alignment (TREE_OPERAND (exp, 0), align, max_align);
  
  	default:
  	  return align;
--- 462,468 ----
  
  	case ADDR_EXPR:
  	  /* See what we are pointing at and look at its alignment.  */
! 	  return get_object_alignment (TREE_OPERAND (exp, 0), max_align);
  
  	default:
  	  return align;
Index: gcc/emit-rtl.c
===================================================================
*** gcc/emit-rtl.c	(revision 163030)
--- gcc/emit-rtl.c	(working copy)
*************** get_mem_align_offset (rtx mem, unsigned
*** 1459,1465 ****
    /* This function can't use
       if (!MEM_EXPR (mem) || !MEM_OFFSET (mem)
  	 || !CONST_INT_P (MEM_OFFSET (mem))
! 	 || (get_object_alignment (MEM_EXPR (mem), MEM_ALIGN (mem), align)
  	     < align))
         return -1;
       else
--- 1459,1466 ----
    /* This function can't use
       if (!MEM_EXPR (mem) || !MEM_OFFSET (mem)
  	 || !CONST_INT_P (MEM_OFFSET (mem))
! 	 || (MAX (MEM_ALIGN (mem),
! 	          get_object_alignment (MEM_EXPR (mem), align))
  	     < align))
         return -1;
       else
*************** set_mem_attributes_minus_bitpos (rtx ref
*** 1796,1803 ****
  
        if (!align_computed && !INDIRECT_REF_P (t))
  	{
! 	  unsigned int obj_align
! 	    = get_object_alignment (t, align, BIGGEST_ALIGNMENT);
  	  align = MAX (align, obj_align);
  	}
      }
--- 1797,1803 ----
  
        if (!align_computed && !INDIRECT_REF_P (t))
  	{
! 	  unsigned int obj_align = get_object_alignment (t, BIGGEST_ALIGNMENT);
  	  align = MAX (align, obj_align);
  	}
      }
Index: gcc/tree-ssa-ccp.c
===================================================================
*** gcc/tree-ssa-ccp.c	(revision 163030)
--- gcc/tree-ssa-ccp.c	(working copy)
*************** get_value_from_alignment (tree expr)
*** 515,522 ****
      val = bit_value_binop (PLUS_EXPR, TREE_TYPE (expr),
  			   TREE_OPERAND (base, 0), TREE_OPERAND (base, 1));
    else if (base
! 	   && ((align = get_object_alignment (base, BITS_PER_UNIT,
! 					      BIGGEST_ALIGNMENT))
  		> BITS_PER_UNIT))
      {
        val.lattice_val = CONSTANT;
--- 515,521 ----
      val = bit_value_binop (PLUS_EXPR, TREE_TYPE (expr),
  			   TREE_OPERAND (base, 0), TREE_OPERAND (base, 1));
    else if (base
! 	   && ((align = get_object_alignment (base, BIGGEST_ALIGNMENT))
  		> BITS_PER_UNIT))
      {
        val.lattice_val = CONSTANT;


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]