Eric Botcazou <ebotca...@adacore.com> writes:
>> Thanks, and to Bernd for the review.  I went ahead and applied it to trunk.
>
> Thanks.  We need something for the 4.8 branch as well, probably the 
> builtins.c 
> hunk and the reversion of the cse.c/cselib.c/dse.c changes to the 4.7 state.

OK, how about this?  It looks like the builtins.c and stmt.c stuff wasn't
merged until 4.9, and at this stage it seemed safer to just add the same
use/clobber sequence to both places.

Tested on x86_64-linux-gnu.  OK to install?

Thanks,
Richard


gcc/
        * builtins.c (expand_builtin_setjmp_receiver): Emit a use of
        the hard frame pointer.  Synchronize commentary with mainline.
        * cse.c (cse_insn): Only check for volatile asms.
        * cselib.c (cselib_process_insn): Likewise.
        * dse.c (scan_insn): Likewise.
        * stmt.c (expand_nl_goto_receiver): Emit a use and a clobber of
        the hard frame pointer.

Index: gcc/builtins.c
===================================================================
--- gcc/builtins.c      2014-03-12 18:24:02.919132339 +0000
+++ gcc/builtins.c      2014-03-12 18:24:17.679262346 +0000
@@ -905,9 +905,24 @@ expand_builtin_setjmp_receiver (rtx rece
   if (! HAVE_nonlocal_goto)
 #endif
     {
+      /* First adjust our frame pointer to its actual value.  It was
+        previously set to the start of the virtual area corresponding to
+        the stacked variables when we branched here and now needs to be
+        adjusted to the actual hardware fp value.
+
+        Assignments to virtual registers are converted by
+        instantiate_virtual_regs into the corresponding assignment
+        to the underlying register (fp in this case) that makes
+        the original assignment true.
+        So the following insn will actually be decrementing fp by
+        STARTING_FRAME_OFFSET.  */
       emit_move_insn (virtual_stack_vars_rtx, hard_frame_pointer_rtx);
-      /* This might change the hard frame pointer in ways that aren't
-        apparent to early optimization passes, so force a clobber.  */
+
+      /* Restoring the frame pointer also modifies the hard frame pointer.
+        Mark it used (so that the previous assignment remains live once
+        the frame pointer is eliminated) and clobbered (to represent the
+        implicit update from the assignment).  */
+      emit_use (hard_frame_pointer_rtx);
       emit_clobber (hard_frame_pointer_rtx);
     }
 
@@ -948,8 +963,7 @@ expand_builtin_setjmp_receiver (rtx rece
 
   /* We must not allow the code we just generated to be reordered by
      scheduling.  Specifically, the update of the frame pointer must
-     happen immediately, not later.  Similarly, we must block
-     (frame-related) register values to be used across this code.  */
+     happen immediately, not later.  */
   emit_insn (gen_blockage ());
 }
 
Index: gcc/cse.c
===================================================================
--- gcc/cse.c   2014-03-12 18:24:02.919132339 +0000
+++ gcc/cse.c   2014-03-12 18:24:17.680262355 +0000
@@ -5659,9 +5659,10 @@ cse_insn (rtx insn)
          invalidate (XEXP (dest, 0), GET_MODE (dest));
       }
 
-  /* A volatile ASM or an UNSPEC_VOLATILE invalidates everything.  */
+  /* A volatile ASM invalidates everything.  */
   if (NONJUMP_INSN_P (insn)
-      && volatile_insn_p (PATTERN (insn)))
+      && GET_CODE (PATTERN (insn)) == ASM_OPERANDS
+      && MEM_VOLATILE_P (PATTERN (insn)))
     flush_hash_table ();
 
   /* Don't cse over a call to setjmp; on some machines (eg VAX)
Index: gcc/cselib.c
===================================================================
--- gcc/cselib.c        2014-03-12 18:24:02.919132339 +0000
+++ gcc/cselib.c        2014-03-12 18:24:17.681262364 +0000
@@ -2623,12 +2623,13 @@ cselib_process_insn (rtx insn)
 
   cselib_current_insn = insn;
 
-  /* Forget everything at a CODE_LABEL, a volatile insn, or a setjmp.  */
+  /* Forget everything at a CODE_LABEL, a volatile asm, or a setjmp.  */
   if ((LABEL_P (insn)
        || (CALL_P (insn)
           && find_reg_note (insn, REG_SETJMP, NULL))
        || (NONJUMP_INSN_P (insn)
-          && volatile_insn_p (PATTERN (insn))))
+          && GET_CODE (PATTERN (insn)) == ASM_OPERANDS
+          && MEM_VOLATILE_P (PATTERN (insn))))
       && !cselib_preserve_constants)
     {
       cselib_reset_table (next_uid);
Index: gcc/dse.c
===================================================================
--- gcc/dse.c   2014-03-12 18:24:02.919132339 +0000
+++ gcc/dse.c   2014-03-12 18:24:17.681262364 +0000
@@ -2518,7 +2518,8 @@ scan_insn (bb_info_t bb_info, rtx insn)
   /* Cselib clears the table for this case, so we have to essentially
      do the same.  */
   if (NONJUMP_INSN_P (insn)
-      && volatile_insn_p (PATTERN (insn)))
+      && GET_CODE (PATTERN (insn)) == ASM_OPERANDS
+      && MEM_VOLATILE_P (PATTERN (insn)))
     {
       add_wild_read (bb_info);
       insn_info->cannot_delete = true;
Index: gcc/stmt.c
===================================================================
--- gcc/stmt.c  2014-03-12 18:24:15.789245708 +0000
+++ gcc/stmt.c  2014-03-12 18:24:24.062318544 +0000
@@ -1602,18 +1602,27 @@ expand_nl_goto_receiver (void)
 #ifdef HAVE_nonlocal_goto
   if (! HAVE_nonlocal_goto)
 #endif
-    /* First adjust our frame pointer to its actual value.  It was
-       previously set to the start of the virtual area corresponding to
-       the stacked variables when we branched here and now needs to be
-       adjusted to the actual hardware fp value.
+    {
+      /* First adjust our frame pointer to its actual value.  It was
+        previously set to the start of the virtual area corresponding to
+        the stacked variables when we branched here and now needs to be
+        adjusted to the actual hardware fp value.
 
-       Assignments are to virtual registers are converted by
-       instantiate_virtual_regs into the corresponding assignment
-       to the underlying register (fp in this case) that makes
-       the original assignment true.
-       So the following insn will actually be
-       decrementing fp by STARTING_FRAME_OFFSET.  */
-    emit_move_insn (virtual_stack_vars_rtx, hard_frame_pointer_rtx);
+        Assignments to virtual registers are converted by
+        instantiate_virtual_regs into the corresponding assignment
+        to the underlying register (fp in this case) that makes
+        the original assignment true.
+        So the following insn will actually be decrementing fp by
+        STARTING_FRAME_OFFSET.  */
+      emit_move_insn (virtual_stack_vars_rtx, hard_frame_pointer_rtx);
+
+      /* Restoring the frame pointer also modifies the hard frame pointer.
+        Mark it used (so that the previous assignment remains live once
+        the frame pointer is eliminated) and clobbered (to represent the
+        implicit update from the assignment).  */
+      emit_use (hard_frame_pointer_rtx);
+      emit_clobber (hard_frame_pointer_rtx);
+    }
 
 #if !HARD_FRAME_POINTER_IS_ARG_POINTER
   if (fixed_regs[ARG_POINTER_REGNUM])

Reply via email to