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]

[tree-ssa] FIx 20030807-9.c, factor some code


This fixes the additional test recently added to 20030807-9.c and
factors the code to optimize reads from readonly strings into a common
function.  Now if someone wants to add wide character support there's
only one place to change :-)

	* fold-const.c (fold_read_from_constant_string): New function.
	* tree.h (fold_read_from_constant_string): Prototype.
	* expr.c (expand_expr, case INDIRECT_REF):  Use it.
	(expand_expr, case ARRAY_REF): Likewise.  Put checking code
	inside an ENABLE_CHECKING.
	* tree-ssa-ccp.c (fold_stmt): Use fold_read_from_constant_string.
	* tree-ssa-dom.c (simplify_rhs_and_lookup_avail_expr): Likewise.

Index: fold-const.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/fold-const.c,v
retrieving revision 1.213.2.46
diff -c -3 -p -r1.213.2.46 fold-const.c
*** fold-const.c	18 Sep 2003 18:25:20 -0000	1.213.2.46
--- fold-const.c	24 Sep 2003 07:59:40 -0000
*************** nondestructive_fold_unary_to_constant (e
*** 9215,9218 ****
--- 9215,9267 ----
      }
  }
  
+ /* If EXP represents referencing an element in a constant string
+    (either via pointer arithmetic or array indexing), return the
+    tree representing the value accessed, otherwise return NULL.  */
+ 
+ tree
+ fold_read_from_constant_string (tree exp)
+ {
+   if (TREE_CODE (exp) == INDIRECT_REF || TREE_CODE (exp) == ARRAY_REF)
+     {
+       tree exp1 = TREE_OPERAND (exp, 0);
+       tree index;
+       tree string;
+ 
+       if (TREE_CODE (exp) == INDIRECT_REF)
+ 	{
+ 	  string = string_constant (exp1, &index);
+ 	}
+       else
+ 	{
+ 	  tree domain = TYPE_DOMAIN (TREE_TYPE (exp1));
+ 	  tree low_bound = domain ? TYPE_MIN_VALUE (domain) : integer_zero_node;
+ 	  index = convert (sizetype, TREE_OPERAND (exp, 1));
+ 	  
+ 	  /* Optimize the special-case of a zero lower bound.
+ 
+ 	     We convert the low_bound to sizetype to avoid some problems
+ 	     with constant folding.  (E.g. suppose the lower bound is 1,
+ 	     and its mode is QI.  Without the conversion,l (ARRAY
+ 	     +(INDEX-(unsigned char)1)) becomes ((ARRAY+(-(unsigned char)1))
+ 	     +INDEX), which becomes (ARRAY+255+INDEX).  Opps!)  */
+ 	  if (! integer_zerop (low_bound))
+ 	    index = size_diffop (index, convert (sizetype, low_bound));
+ 
+ 	  string = exp1;
+ 	}
+ 
+       if (string
+ 	  && TREE_CODE (string) == STRING_CST
+ 	  && TREE_CODE (index) == INTEGER_CST
+ 	  && compare_tree_int (index, TREE_STRING_LENGTH (string)) < 0
+ 	  && (GET_MODE_CLASS (TYPE_MODE (TREE_TYPE (TREE_TYPE (string))))
+ 	      == MODE_INT)
+ 	  && (GET_MODE_SIZE (TYPE_MODE (TREE_TYPE (TREE_TYPE (string)))) == 1))
+ 	return build_int_2 ((TREE_STRING_POINTER (string)
+ 			     [TREE_INT_CST_LOW (index)]), 0);
+     }
+   return NULL;
+ }
+ 
  #include "gt-fold-const.h"
Index: tree.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/tree.h,v
retrieving revision 1.342.2.101
diff -c -3 -p -r1.342.2.101 tree.h
*** tree.h	21 Sep 2003 22:14:28 -0000	1.342.2.101
--- tree.h	24 Sep 2003 07:59:48 -0000
*************** extern tree omit_one_operand (tree, tree
*** 3167,3172 ****
--- 3167,3173 ----
  extern tree invert_truthvalue (tree);
  extern tree nondestructive_fold_unary_to_constant (enum tree_code, tree, 
tree);
  extern tree nondestructive_fold_binary_to_constant (enum tree_code, tree, 
tree, tree);
+ extern tree fold_read_from_constant_string (tree);
  
  /* In builtins.c */
  extern tree fold_builtin (tree);
Index: expr.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/expr.c,v
retrieving revision 1.467.2.49
diff -c -3 -p -r1.467.2.49 expr.c
*** expr.c	22 Sep 2003 16:54:29 -0000	1.467.2.49
--- expr.c	24 Sep 2003 08:00:15 -0000
*************** expand_expr (tree exp, rtx target, enum 
*** 7322,7340 ****
      case INDIRECT_REF:
        {
  	tree exp1 = TREE_OPERAND (exp, 0);
- 	tree index;
- 	tree string = string_constant (exp1, &index);
  
! 	/* Try to optimize reads from const strings.  */
! 	if (string
! 	    && TREE_CODE (string) == STRING_CST
! 	    && TREE_CODE (index) == INTEGER_CST
! 	    && compare_tree_int (index, TREE_STRING_LENGTH (string)) < 0
! 	    && GET_MODE_CLASS (mode) == MODE_INT
! 	    && GET_MODE_SIZE (mode) == 1
! 	    && modifier != EXPAND_WRITE)
! 	  return gen_int_mode (TREE_STRING_POINTER (string)
! 			       [TREE_INT_CST_LOW (index)], mode);
  
  	op0 = expand_expr (exp1, NULL_RTX, VOIDmode, EXPAND_SUM);
  	op0 = memory_address (mode, op0);
--- 7322,7336 ----
      case INDIRECT_REF:
        {
  	tree exp1 = TREE_OPERAND (exp, 0);
  
! 	if (modifier != EXPAND_WRITE)
! 	  {
! 	    tree t;
! 
! 	    t = fold_read_from_constant_string (exp);
! 	    if (t)
! 	      return expand_expr (t, target, tmode, modifier);
! 	  }
  
  	op0 = expand_expr (exp1, NULL_RTX, VOIDmode, EXPAND_SUM);
  	op0 = memory_address (mode, op0);
*************** expand_expr (tree exp, rtx target, enum 
*** 7351,7358 ****
--- 7347,7357 ----
        }
  
      case ARRAY_REF:
+ 
+ #ifdef ENABLE_CHECKING
        if (TREE_CODE (TREE_TYPE (TREE_OPERAND (exp, 0))) != ARRAY_TYPE)
  	abort ();
+ #endif
  
        {
  	tree array = TREE_OPERAND (exp, 0);
*************** expand_expr (tree exp, rtx target, enum 
*** 7379,7392 ****
  
  	if (modifier != EXPAND_CONST_ADDRESS
  	    && modifier != EXPAND_INITIALIZER
! 	    && modifier != EXPAND_MEMORY
! 	    && TREE_CODE (array) == STRING_CST
! 	    && TREE_CODE (index) == INTEGER_CST
! 	    && compare_tree_int (index, TREE_STRING_LENGTH (array)) < 0
! 	    && GET_MODE_CLASS (mode) == MODE_INT
! 	    && GET_MODE_SIZE (mode) == 1)
! 	  return gen_int_mode (TREE_STRING_POINTER (array)
! 			       [TREE_INT_CST_LOW (index)], mode);
  
  	/* If this is a constant index into a constant array,
  	   just get the value from the array.  Handle both the cases when
--- 7378,7390 ----
  
  	if (modifier != EXPAND_CONST_ADDRESS
  	    && modifier != EXPAND_INITIALIZER
! 	    && modifier != EXPAND_MEMORY)
! 	  {
! 	    tree t = fold_read_from_constant_string (exp);
! 
! 	    if (t)
! 	      return expand_expr (t, target, tmode, modifier);
! 	  }
  
  	/* If this is a constant index into a constant array,
  	   just get the value from the array.  Handle both the cases when
Index: tree-ssa-ccp.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/Attic/tree-ssa-ccp.c,v
retrieving revision 1.1.2.94
diff -c -3 -p -r1.1.2.94 tree-ssa-ccp.c
*** tree-ssa-ccp.c	21 Sep 2003 22:14:27 -0000	1.1.2.94
--- tree-ssa-ccp.c	24 Sep 2003 08:00:17 -0000
*************** fold_stmt (tree *stmt_p)
*** 1411,1435 ****
  
        /* Optimize *"foo" into 'f'.  This is done here rather than
           in fold to avoid problems with stuff like &*"foo".  */
!       if (TREE_CODE (rhs) == INDIRECT_REF)
! 	{
! 	  tree exp1 = TREE_OPERAND (rhs, 0);
! 	  tree index;
! 	  tree string = string_constant (exp1, &index);
! 
! 	  if (string
! 	      && TREE_CODE (string) == STRING_CST
! 	      && TREE_CODE (index) == INTEGER_CST
! 	      && compare_tree_int (index, TREE_STRING_LENGTH (string)) < 0
! 	      && TREE_CODE (TREE_TYPE (string)) == ARRAY_TYPE
! 	      && (GET_MODE_CLASS (TYPE_MODE (TREE_TYPE (TREE_TYPE (string))))
! 		  == MODE_INT)
! 	      && (GET_MODE_SIZE (TYPE_MODE (TREE_TYPE (TREE_TYPE (string))))
! 		  == 1))
! 	    result = build_int_2 ((TREE_STRING_POINTER (string)
! 				   [TREE_INT_CST_LOW (index)]), 0);
! 	}
! 	  
  
        /* If we couldn't fold the RHS, hand it over to the generic fold
  	 routines.  */
--- 1411,1418 ----
  
        /* Optimize *"foo" into 'f'.  This is done here rather than
           in fold to avoid problems with stuff like &*"foo".  */
!       if (TREE_CODE (rhs) == INDIRECT_REF || TREE_CODE (rhs) == ARRAY_REF)
! 	result = fold_read_from_constant_string (rhs);
  
        /* If we couldn't fold the RHS, hand it over to the generic fold
  	 routines.  */
Index: tree-ssa-dom.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/Attic/tree-ssa-dom.c,v
retrieving revision 1.1.2.45
diff -c -3 -p -r1.1.2.45 tree-ssa-dom.c
*** tree-ssa-dom.c	23 Sep 2003 13:37:56 -0000	1.1.2.45
--- tree-ssa-dom.c	24 Sep 2003 08:00:23 -0000
*************** simplify_rhs_and_lookup_avail_expr (tree
*** 947,952 ****
--- 947,966 ----
  						     ann, insert);
  	}
      }
+ 
+   /* Optimize *"foo" into 'f'.  This is done here rather than
+      in fold to avoid problems with stuff like &*"foo".  */
+   if (TREE_CODE (rhs) == INDIRECT_REF || TREE_CODE (rhs) == ARRAY_REF)
+     {
+       tree t = fold_read_from_constant_string (rhs);
+ 
+       if (t)
+         result = update_rhs_and_lookup_avail_expr (stmt, t,
+ 						   block_avail_exprs_p,
+ 						   const_and_copies,
+ 						   ann, insert);
+     }
+ 
    return result;
  }
  





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