[patch] combine.c: Convert (ne (and (lshiftrt (xor X CST) Y) 1) 0) into (eq (and (lshiftrt X Y) 1) 0). (take 3)

Kazu Hirata kazu@cs.umass.edu
Fri Aug 22 01:06:00 GMT 2003


Hi,

Attached is a patch to have the combiner convert

  (ne (and (lshiftrt (xor X CST) Y) 1) 0)

into

  (eq (and (lshiftrt X Y) 1) 0)

if xor inverts the bit that is extracted.

This will trigger when combining the following sequence:

  (set (reg 2)
       (not (reg 1)))

  (set (reg 3)
       (lshiftrt (reg 2)
                 (const_int 2)))

  (set (reg 4)
       (and (reg 3)
            (const_int 1)))

  (set (pc)
       (if_then_else (eq (cc0)
                         (const_int 0))))

The patch has been revised since take 2.  The difference is that now
simplify_and_const_int() is asked not to share rtx.  For the
justification, see

http://gcc.gnu.org/ml/gcc-patches/2003-07/msg01936.html

Tested on h8300 port.  OK to apply?

Kazu Hirata

2003-08-21  Kazu Hirata  <kazu@cs.umass.edu>

	* combine.c (simplify_comparison): Convert
	(ne (and (lshiftrt (xor X CST) Y) 1) 0) into
	(eq (and (lshiftrt X Y) 1) 0).

Index: combine.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/combine.c,v
retrieving revision 1.377
diff -c -r1.377 combine.c
*** combine.c	31 Jul 2003 18:37:23 -0000	1.377
--- combine.c	21 Aug 2003 14:04:30 -0000
***************
*** 11074,11092 ****
  	    }
  
  	  /* Convert (ne (and (lshiftrt (not X)) 1) 0) to
! 	     (eq (and (lshiftrt X) 1) 0).  */
  	  if (const_op == 0 && equality_comparison_p
  	      && XEXP (op0, 1) == const1_rtx
! 	      && GET_CODE (XEXP (op0, 0)) == LSHIFTRT
! 	      && GET_CODE (XEXP (XEXP (op0, 0), 0)) == NOT)
  	    {
! 	      op0 = simplify_and_const_int
! 		(op0, mode,
! 		 gen_rtx_LSHIFTRT (mode, XEXP (XEXP (XEXP (op0, 0), 0), 0),
! 				   XEXP (XEXP (op0, 0), 1)),
! 		 (HOST_WIDE_INT) 1);
! 	      code = (code == NE ? EQ : NE);
! 	      continue;
  	    }
  	  break;
  
--- 11074,11102 ----
  	    }
  
  	  /* Convert (ne (and (lshiftrt (not X)) 1) 0) to
! 	     (eq (and (lshiftrt X) 1) 0).
! 	     Also handle the case where (not X) is expressed using xor.  */
  	  if (const_op == 0 && equality_comparison_p
  	      && XEXP (op0, 1) == const1_rtx
! 	      && GET_CODE (XEXP (op0, 0)) == LSHIFTRT)
  	    {
! 	      rtx shift_op = XEXP (XEXP (op0, 0), 0);
! 	      rtx shift_count = XEXP (XEXP (op0, 0), 1);
! 
! 	      if (GET_CODE (shift_op) == NOT
! 		  || (GET_CODE (shift_op) == XOR
! 		      && GET_CODE (XEXP (shift_op, 1)) == CONST_INT
! 		      && GET_CODE (shift_count) == CONST_INT
! 		      && (INTVAL (XEXP (shift_op, 1))
! 			  == 1 << INTVAL (shift_count))))
! 		{
! 		  op0 = simplify_and_const_int
! 		    (NULL_RTX, mode,
! 		     gen_rtx_LSHIFTRT (mode, XEXP (shift_op, 0), shift_count),
! 		     (HOST_WIDE_INT) 1);
! 		  code = (code == NE ? EQ : NE);
! 		  continue;
! 		}
  	    }
  	  break;
  



More information about the Gcc-patches mailing list