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]

Fix PR middle-end/14470 (take #2)


My fix for this PR:

http://gcc.gnu.org/ml/gcc-patches/2004-03/msg00768.html

had a (semi-)unexpected side-effect: disabling the POST_INC optimization for 
move targets in certain cases.  Thanks to Richard Earnshaw for spotting this 
with the help of CSiBE.

The attached patch fixes the problem.  Bootstrapped/regtested (3.4 branch) on 
sparc-sun-solaris2.8, sparc64-sun-solaris2.9 and i586-redhat-linux-gnu.

Approved by Mark, applied to mainline and 3.4 branch.

Gaby, do you want it on the 3.3 branch too?


2004-03-22  Eric Botcazou  <ebotcazou@libertysurf.fr>

	PR middle-end/14470
	* expr.c (mark_queue): New function.
	(emit_insns_enqueued_after_mark): New function replacing
	emit_queue.  Clear the body of emitted queued insns.
	(emit_queue): Call emit_insns_enqueued_after_mark.
	(store_expr): Mark the increment queue on entry.  Emit
	only the incrementations queued when expanding the source.


--
Eric Botcazou
Index: expr.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/expr.c,v
retrieving revision 1.615.4.9
diff -c -p -r1.615.4.9 expr.c
*** expr.c	13 Mar 2004 18:26:23 -0000	1.615.4.9
--- expr.c	21 Mar 2004 11:44:37 -0000
*************** queued_subexp_p (rtx x)
*** 474,486 ****
      }
  }
  
! /* Perform all the pending incrementations.  */
  
! void
! emit_queue (void)
  {
    rtx p;
!   while ((p = pending_chain))
      {
        rtx body = QUEUED_BODY (p);
  
--- 474,503 ----
      }
  }
  
! /* Retrieve a mark on the queue.  */
!   
! static rtx
! mark_queue (void)
! {
!   return pending_chain;
! }
  
! /* Perform all the pending incrementations that have been enqueued
!    after MARK was retrieved.  If MARK is null, perform all the
!    pending incrementations.  */
! 
! static void
! emit_insns_enqueued_after_mark (rtx mark)
  {
    rtx p;
! 
!   /* The marked incrementation may have been emitted in the meantime
!      through a call to emit_queue.  In this case, the mark is not valid
!      anymore so do nothing.  */
!   if (mark && ! QUEUED_BODY (mark))
!     return;
! 
!   while ((p = pending_chain) != mark)
      {
        rtx body = QUEUED_BODY (p);
  
*************** emit_queue (void)
*** 507,515 ****
--- 524,541 ----
  	  break;
  	}
  
+       QUEUED_BODY (p) = 0;
        pending_chain = QUEUED_NEXT (p);
      }
  }
+ 
+ /* Perform all the pending incrementations.  */
+ 
+ void
+ emit_queue (void)
+ {
+   emit_insns_enqueued_after_mark (NULL_RTX);
+ }
  
  /* Copy data from FROM to TO, where the machine modes are not the same.
     Both modes may be integer, or both may be floating.
*************** store_expr (tree exp, rtx target, int wa
*** 4010,4015 ****
--- 4036,4042 ----
  {
    rtx temp;
    rtx alt_rtl = NULL_RTX;
+   rtx mark = mark_queue ();
    int dont_return_target = 0;
    int dont_store_target = 0;
  
*************** store_expr (tree exp, rtx target, int wa
*** 4221,4227 ****
  			  temp, TREE_UNSIGNED (TREE_TYPE (exp)));
  
    /* If value was not generated in the target, store it there.
!      Convert the value to TARGET's type first if necessary.
       If TEMP and TARGET compare equal according to rtx_equal_p, but
       one or both of them are volatile memory refs, we have to distinguish
       two cases:
--- 4248,4258 ----
  			  temp, TREE_UNSIGNED (TREE_TYPE (exp)));
  
    /* If value was not generated in the target, store it there.
!      Convert the value to TARGET's type first if necessary and emit the
!      pending incrementations that have been queued when expanding EXP.
!      Note that we cannot emit the whole queue blindly because this will
!      effectively disable the POST_INC optimization later.
! 
       If TEMP and TARGET compare equal according to rtx_equal_p, but
       one or both of them are volatile memory refs, we have to distinguish
       two cases:
*************** store_expr (tree exp, rtx target, int wa
*** 4249,4255 ****
  	 bit-initialized.  */
        && expr_size (exp) != const0_rtx)
      {
!       emit_queue();
        target = protect_from_queue (target, 1);
        temp = protect_from_queue (temp, 0);
        if (GET_MODE (temp) != GET_MODE (target)
--- 4280,4286 ----
  	 bit-initialized.  */
        && expr_size (exp) != const0_rtx)
      {
!       emit_insns_enqueued_after_mark (mark);
        target = protect_from_queue (target, 1);
        temp = protect_from_queue (temp, 0);
        if (GET_MODE (temp) != GET_MODE (target)

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