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]

[3.4] Backport fix for PR middle-end/17813


Hello,

Jakub asked me to backport the fix for PR middle-end/17813 to the 3.4 branch.  
He found a testcase that used to pass with GCC 3.3.4 but fails with 3.4.4pre.
I didn't analyze the problem on the 3.4 branch, I of course fully trust him on 
this.

Bootstrapped/regtested on i586-mandrake-linux-gnu.  OK for 3.4 branch?

Jakub, would you mind checking that I put the right options in the testcase?


2004-11-19 ?Eric Botcazou ?<ebotcazou@libertysurf.fr>

	Backport from mainline:
	2004-10-18  Eric Botcazou  <ebotcazou@libertysurf.fr>
	              Roger Sayle  <roger@eyesopen.com>

	PR middle-end/17813
	* dojump.c (discard_pending_stack_adjust): New function.
	(clear_pending_stack_adjust): Call it.
	* expr.h (discard_pending_stack_adjust): Declare it.
	* explow.c (emit_stack_save): Emit pending stack adjustments
	before saving the stack pointer.
	(emit_stack_restore): Discard pending stack adjustments before
	restoring the stack pointer.


2004-11-19  Jakub Jelinek <jakub@redhat.com>

	* gcc.dg/setjmp-2.c: New test.


-- 
Eric Botcazou
Index: dojump.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/dojump.c,v
retrieving revision 1.29
diff -u -p -r1.29 dojump.c
--- dojump.c	8 Sep 2004 07:47:45 -0000	1.29
+++ dojump.c	18 Oct 2004 18:48:23 -0000
@@ -50,6 +50,15 @@ init_pending_stack_adjust (void)
   pending_stack_adjust = 0;
 }
 
+/* Discard any pending stack adjustment.  This avoid relying on the
+   RTL optimizers to remove useless adjustments when we know the
+   stack pointer value is dead.  */
+void discard_pending_stack_adjust (void)
+{
+  stack_pointer_delta -= pending_stack_adjust;
+  pending_stack_adjust = 0;
+}
+
 /* When exiting from function, if safe, clear out any pending stack adjust
    so the adjustment won't get done.
 
@@ -64,10 +73,7 @@ clear_pending_stack_adjust (void)
       && EXIT_IGNORE_STACK
       && ! (DECL_INLINE (current_function_decl) && ! flag_no_inline)
       && ! flag_inline_functions)
-    {
-      stack_pointer_delta -= pending_stack_adjust,
-      pending_stack_adjust = 0;
-    }
+    discard_pending_stack_adjust ();
 }
 
 /* Pop any previously-pushed arguments that have not been popped yet.  */
Index: explow.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/explow.c,v
retrieving revision 1.139
diff -u -p -r1.139 explow.c
--- explow.c	8 Sep 2004 08:05:13 -0000	1.139
+++ explow.c	18 Oct 2004 18:48:33 -0000
@@ -965,6 +965,7 @@ emit_stack_save (enum save_level save_le
       rtx seq;
 
       start_sequence ();
+      do_pending_stack_adjust ();
       /* We must validize inside the sequence, to ensure that any instructions
 	 created by the validize call also get moved to the right place.  */
       if (sa != 0)
@@ -976,6 +977,7 @@ emit_stack_save (enum save_level save_le
     }
   else
     {
+      do_pending_stack_adjust ();
       if (sa != 0)
 	sa = validize_mem (sa);
       emit_insn (fcn (sa, stack_pointer_rtx));
@@ -1032,6 +1034,8 @@ emit_stack_restore (enum save_level save
 		    gen_rtx_MEM (BLKmode, stack_pointer_rtx)));
     }
 
+  discard_pending_stack_adjust ();
+
   if (after)
     {
       rtx seq;
Index: expr.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/expr.h,v
retrieving revision 1.171
diff -u -p -r1.171 expr.h
--- expr.h	8 Sep 2004 18:44:56 -0000	1.171
+++ expr.h	18 Oct 2004 18:48:36 -0000
@@ -499,6 +499,9 @@ extern void expand_var (tree);
    arguments waiting to be popped.  */
 extern void init_pending_stack_adjust (void);
 
+/* Discard any pending stack adjustment.  */
+extern void discard_pending_stack_adjust (void);
+
 /* When exiting from function, if safe, clear out any pending stack adjust
    so the adjustment won't get done.  */
 extern void clear_pending_stack_adjust (void);
/* PR middle-end/17813 */
/* Contributed by Jakub Jelinek <jakub@redhat.com> */
/* { dg-do run { target i?86-*-linux* x86_64-*-linux* } } */
/* { dg-options "-O -fomit-frame-pointer -march=i386" { target i?86-*-linux* } } */
/* { dg-options "-O -fomit-frame-pointer -m32 -march=i386" { target x86_64-*-linux* } } */

#include <setjmp.h>
#include <signal.h>
#include <stdlib.h>

static jmp_buf segv_jmpbuf;

static void segv_handler(int seg)
{
   __builtin_longjmp(segv_jmpbuf, 1);
}

static int is_addressable(void *p, size_t size)
{
   volatile char * volatile cp = (volatile char *)p;
   volatile int ret;
   struct sigaction sa, origsa;
   sigset_t mask;
   
   sa.sa_handler = segv_handler;
   sa.sa_flags = 0;
   sigfillset(&sa.sa_mask);
   sigaction(SIGSEGV, &sa, &origsa);
   sigprocmask(SIG_SETMASK, NULL, &mask);

   if (__builtin_setjmp(segv_jmpbuf) == 0) {
      while(size--)
	 *cp++;
      ret = 1;
    } else
      ret = 0;

   sigaction(SIGSEGV, &origsa, NULL);
   sigprocmask(SIG_SETMASK, &mask, NULL);

   return ret;
}

int main(int argc, char **argv)
{
   is_addressable(0x0, 1);
   return 0;
}

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