stmt.c (expand_return): Return if optimize_tail_recursion succeeded.

Jim Wilson wilson@cygnus.com
Fri Feb 12 13:37:00 GMT 1999


I have checked in the following patch.

This fixes a problem where the cygwin compiler was calling abort while
compiling readline.  This was accidentally introduced Jan 8 when Jeff Law
created the new function optimize_tail_recursion.  A return statement in
expand_return was lost when that happened.

Simplified testcase (maybe this should be put in the testsuite?):

sub (int i)
{
  if (i == 0)
    return 0;
  else
    return sub (({int j; j = i - 1; j;}));
}

Patch:

Fri Feb 12 13:06:28 1999  Jim Wilson  <wilson@cygnus.com>

	* stmt.c (expand_return): Return if optimize_tail_recursion succeeded.
	(optimize_tail_recursion): Change return type from void to int.
	Add return statements.
	* tree.h (optimize_tail_recursion): Change prototype to match.

Index: stmt.c
===================================================================
RCS file: /cvs/cvsfiles/devo/gcc/stmt.c,v
retrieving revision 1.160
diff -p -r1.160 stmt.c
*** stmt.c	1999/01/24 15:28:41	1.160
--- stmt.c	1999/02/12 21:08:35
*************** expand_return (retval)
*** 2575,2581 ****
      }
  
    /* Attempt to optimize the call if it is tail recursive.  */
!   optimize_tail_recursion (retval_rhs, last_insn);
  
  #ifdef HAVE_return
    /* This optimization is safe if there are local cleanups
--- 2575,2582 ----
      }
  
    /* Attempt to optimize the call if it is tail recursive.  */
!   if (optimize_tail_recursion (retval_rhs, last_insn))
!     return;
  
  #ifdef HAVE_return
    /* This optimization is safe if there are local cleanups
*************** drop_through_at_end_p ()
*** 2783,2794 ****
  
  /* Test CALL_EXPR to determine if it is a potential tail recursion call
     and emit code to optimize the tail recursion.  LAST_INSN indicates where
!    to place the jump to the tail recursion label.
  
     This is only used by expand_return, but expand_call is expected to
     use it soon.  */
  
! void
  optimize_tail_recursion (call_expr, last_insn)
       tree call_expr;
       rtx last_insn;
--- 2784,2796 ----
  
  /* Test CALL_EXPR to determine if it is a potential tail recursion call
     and emit code to optimize the tail recursion.  LAST_INSN indicates where
!    to place the jump to the tail recursion label.  Return TRUE if the
!    call was optimized into a goto.
  
     This is only used by expand_return, but expand_call is expected to
     use it soon.  */
  
! int
  optimize_tail_recursion (call_expr, last_insn)
       tree call_expr;
       rtx last_insn;
*************** optimize_tail_recursion (call_expr, last
*** 2817,2823 ****
--- 2819,2828 ----
        emit_queue ();
        expand_goto_internal (NULL_TREE, tail_recursion_label, last_insn);
        emit_barrier ();
+       return 1;
      }
+ 
+   return 0;
  }
  
  /* Emit code to alter this function's formal parms for a tail-recursive call.
Index: tree.h
===================================================================
RCS file: /cvs/cvsfiles/devo/gcc/tree.h,v
retrieving revision 1.176
diff -p -r1.176 tree.h
*** tree.h	1999/02/05 19:49:28	1.176
--- tree.h	1999/02/12 21:08:35
*************** extern int expand_exit_something		PROTO(
*** 1935,1941 ****
  
  extern void expand_null_return			PROTO((void));
  extern void expand_return			PROTO((tree));
! extern void optimize_tail_recursion		PROTO((tree, struct rtx_def *));
  extern void expand_start_bindings		PROTO((int));
  extern void expand_end_bindings			PROTO((tree, int, int));
  extern void start_cleanup_deferral		PROTO((void));
--- 1935,1941 ----
  
  extern void expand_null_return			PROTO((void));
  extern void expand_return			PROTO((tree));
! extern int optimize_tail_recursion		PROTO((tree, struct rtx_def *));
  extern void expand_start_bindings		PROTO((int));
  extern void expand_end_bindings			PROTO((tree, int, int));
  extern void start_cleanup_deferral		PROTO((void));


More information about the Gcc-patches mailing list