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] Fix PRs 33691, 33694 and 33696


This fixes a bunch of type-checking problems in fold-const.c.  More to
come.

Bootstrapped and tested on x86_64-unknown-linux-gnu, applied to mainline.

Richard.

2007-10-08  Richard Guenther  <rguenther@suse.de>

	PR middle-end/33691
	PR middle-end/33694
	PR middle-end/33696
	* fold-const.c (fold_binary): Use the correct types when
	folding (A | CST1) & CST2 to (A & CST2) | (CST1 & CST2).
	(fold_binary): Use the correct types when folding
	(-A) - B to (-B) - A.
	(fold_unary): Use the correct types when folding ~(X).

	* gcc.dg/pr33691.c: New testcase.

Index: fold-const.c
===================================================================
*** fold-const.c	(revision 129036)
--- fold-const.c	(working copy)
*************** fold_unary (enum tree_code code, tree ty
*** 8374,8383 ****
        if (TREE_CODE (arg0) == INTEGER_CST)
          return fold_not_const (arg0, type);
        else if (TREE_CODE (arg0) == BIT_NOT_EXPR)
! 	return TREE_OPERAND (arg0, 0);
        /* Convert ~ (-A) to A - 1.  */
        else if (INTEGRAL_TYPE_P (type) && TREE_CODE (arg0) == NEGATE_EXPR)
! 	return fold_build2 (MINUS_EXPR, type, TREE_OPERAND (arg0, 0),
  			    build_int_cst (type, 1));
        /* Convert ~ (A - 1) or ~ (A + -1) to -A.  */
        else if (INTEGRAL_TYPE_P (type)
--- 8374,8384 ----
        if (TREE_CODE (arg0) == INTEGER_CST)
          return fold_not_const (arg0, type);
        else if (TREE_CODE (arg0) == BIT_NOT_EXPR)
! 	return TREE_OPERAND (op0, 0);
        /* Convert ~ (-A) to A - 1.  */
        else if (INTEGRAL_TYPE_P (type) && TREE_CODE (arg0) == NEGATE_EXPR)
! 	return fold_build2 (MINUS_EXPR, type,
! 			    fold_convert (type, TREE_OPERAND (arg0, 0)),
  			    build_int_cst (type, 1));
        /* Convert ~ (A - 1) or ~ (A + -1) to -A.  */
        else if (INTEGRAL_TYPE_P (type)
*************** fold_unary (enum tree_code code, tree ty
*** 8385,8391 ****
  		    && integer_onep (TREE_OPERAND (arg0, 1)))
  		   || (TREE_CODE (arg0) == PLUS_EXPR
  		       && integer_all_onesp (TREE_OPERAND (arg0, 1)))))
! 	return fold_build1 (NEGATE_EXPR, type, TREE_OPERAND (arg0, 0));
        /* Convert ~(X ^ Y) to ~X ^ Y or X ^ ~Y if ~X or ~Y simplify.  */
        else if (TREE_CODE (arg0) == BIT_XOR_EXPR
  	       && (tem = fold_unary (BIT_NOT_EXPR, type,
--- 8386,8393 ----
  		    && integer_onep (TREE_OPERAND (arg0, 1)))
  		   || (TREE_CODE (arg0) == PLUS_EXPR
  		       && integer_all_onesp (TREE_OPERAND (arg0, 1)))))
! 	return fold_build1 (NEGATE_EXPR, type,
! 			    fold_convert (type, TREE_OPERAND (arg0, 0)));
        /* Convert ~(X ^ Y) to ~X ^ Y or X ^ ~Y if ~X or ~Y simplify.  */
        else if (TREE_CODE (arg0) == BIT_XOR_EXPR
  	       && (tem = fold_unary (BIT_NOT_EXPR, type,
*************** fold_binary (enum tree_code code, tree t
*** 10126,10140 ****
  	}
        /* A - (-B) -> A + B */
        if (TREE_CODE (arg1) == NEGATE_EXPR)
! 	return fold_build2 (PLUS_EXPR, type, arg0, TREE_OPERAND (arg1, 0));
        /* (-A) - B -> (-B) - A  where B is easily negated and we can swap.  */
        if (TREE_CODE (arg0) == NEGATE_EXPR
  	  && (FLOAT_TYPE_P (type)
  	      || INTEGRAL_TYPE_P (type))
  	  && negate_expr_p (arg1)
  	  && reorder_operands_p (arg0, arg1))
! 	return fold_build2 (MINUS_EXPR, type, negate_expr (arg1),
! 			    TREE_OPERAND (arg0, 0));
        /* Convert -A - 1 to ~A.  */
        if (INTEGRAL_TYPE_P (type)
  	  && TREE_CODE (arg0) == NEGATE_EXPR
--- 10128,10144 ----
  	}
        /* A - (-B) -> A + B */
        if (TREE_CODE (arg1) == NEGATE_EXPR)
! 	return fold_build2 (PLUS_EXPR, type, op0,
! 			    fold_convert (type, TREE_OPERAND (arg1, 0)));
        /* (-A) - B -> (-B) - A  where B is easily negated and we can swap.  */
        if (TREE_CODE (arg0) == NEGATE_EXPR
  	  && (FLOAT_TYPE_P (type)
  	      || INTEGRAL_TYPE_P (type))
  	  && negate_expr_p (arg1)
  	  && reorder_operands_p (arg0, arg1))
! 	return fold_build2 (MINUS_EXPR, type,
! 			    fold_convert (type, negate_expr (arg1)),
! 			    fold_convert (type, TREE_OPERAND (arg0, 0)));
        /* Convert -A - 1 to ~A.  */
        if (INTEGRAL_TYPE_P (type)
  	  && TREE_CODE (arg0) == NEGATE_EXPR
*************** fold_binary (enum tree_code code, tree t
*** 10889,10899 ****
        if (TREE_CODE (arg0) == BIT_IOR_EXPR
  	  && TREE_CODE (arg1) == INTEGER_CST
  	  && TREE_CODE (TREE_OPERAND (arg0, 1)) == INTEGER_CST)
! 	return fold_build2 (BIT_IOR_EXPR, type,
! 			    fold_build2 (BIT_AND_EXPR, type,
! 					 TREE_OPERAND (arg0, 0), arg1),
! 			    fold_build2 (BIT_AND_EXPR, type,
! 					 TREE_OPERAND (arg0, 1), arg1));
  
        /* (X | Y) & Y is (X, Y).  */
        if (TREE_CODE (arg0) == BIT_IOR_EXPR
--- 10893,10908 ----
        if (TREE_CODE (arg0) == BIT_IOR_EXPR
  	  && TREE_CODE (arg1) == INTEGER_CST
  	  && TREE_CODE (TREE_OPERAND (arg0, 1)) == INTEGER_CST)
! 	{
! 	  tree tmp1 = fold_convert (TREE_TYPE (arg0), arg1);
! 	  tree tmp2 = fold_build2 (BIT_AND_EXPR, TREE_TYPE (arg0),
! 				   TREE_OPERAND (arg0, 0), tmp1);
! 	  tree tmp3 = fold_build2 (BIT_AND_EXPR, TREE_TYPE (arg0),
! 				   TREE_OPERAND (arg0, 1), tmp1);
! 	  return fold_convert (type,
! 			       fold_build2 (BIT_IOR_EXPR, TREE_TYPE (arg0),
! 					    tmp2, tmp3));
! 	}
  
        /* (X | Y) & Y is (X, Y).  */
        if (TREE_CODE (arg0) == BIT_IOR_EXPR
Index: testsuite/gcc.dg/pr33691.c
===================================================================
*** testsuite/gcc.dg/pr33691.c	(revision 0)
--- testsuite/gcc.dg/pr33691.c	(revision 0)
***************
*** 0 ****
--- 1,8 ----
+ /* { dg-do compile } */
+ 
+ /* ICEd with type-checking enabled.  */
+ 
+ unsigned int mgaSetTexImages(int i)
+ {
+     return ((i | 0x40) & 0xffffffc0);
+ }
Index: testsuite/gcc.dg/pr33694.c
===================================================================
*** testsuite/gcc.dg/pr33694.c	(revision 0)
--- testsuite/gcc.dg/pr33694.c	(revision 0)
***************
*** 0 ****
--- 1,8 ----
+ /* { dg-do compile } */
+ 
+ /* This used to ICE with type-checking enabled.  */
+ 
+ __SIZE_TYPE__ cnfs_mapcntl(long pagesize)
+ {
+      return ~(__SIZE_TYPE__)(pagesize - 1);
+ }
Index: testsuite/gcc.dg/pr33696.c
===================================================================
*** testsuite/gcc.dg/pr33696.c	(revision 0)
--- testsuite/gcc.dg/pr33696.c	(revision 0)
***************
*** 0 ****
--- 1,13 ----
+ /* { dg-do compile } */
+ 
+ /* This used to ICE with type-checking enabled.  */
+ 
+ typedef unsigned char uint8_t;
+ typedef unsigned int uint_least32_t;
+ extern int foo (long int __off);
+ void write (uint_least32_t chunk_len)
+ {
+      uint8_t tmp[4];
+      foo (-(long)chunk_len - sizeof(tmp));
+ }
+ 


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