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]

[tree-ssa] Computed/nonlocal goto handling fixes


Hi,
this patch adds missing predicate to recognize nonlocal_goto and unifies
the is_computed_goto and simple_goto_p.
It also ensures that we create edge from entry block into nonlocal goto
reciver that is needed to avoid them from being deleted (fixes one of
tescases in testsuite).

Bootstrapped/regtested i386, OK?
Honza
2003-11-06  Jan Hubicka  <jh@suse.cz>

	* gimple-low.c (simple_goto_p): Move to...
	* tree-cfg.c: (simple_goto_p): ... here;
	(nonlocal_goto_p): New.
	(is_computed_goto): Rename to ...
	(computed_goto_p): ... this; make global.
	(factor_computed_gotos, make_blocks):  Update calls.
	(make_ctrl_stmt_edges): Add edge for nonlocal labels; use new functions.
	* tree-flow.h (is_coputed_goto): Kill.
	(nonlocal_goto_p, simple_goto_p, computed_goto_p): Declare.
	* tree-ssa-ccp (visit_stmt): Update.
Index: gimple-low.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/Attic/gimple-low.c,v
retrieving revision 1.1.4.6
diff -c -3 -p -r1.1.4.6 gimple-low.c
*** gimple-low.c	5 Nov 2003 13:39:23 -0000	1.1.4.6
--- gimple-low.c	6 Nov 2003 16:07:57 -0000
*************** lower_bind_expr (tree_stmt_iterator *tsi
*** 195,212 ****
    tsi_delink (tsi);
  }
  
- /* Checks whether EXPR is a simple local goto.  */
- 
- static bool
- simple_goto_p (tree expr)
- {
-   return  (TREE_CODE (expr) == GOTO_EXPR
- 	   && TREE_CODE (GOTO_DESTINATION (expr)) == LABEL_DECL
- 	   && ! NONLOCAL_LABEL (GOTO_DESTINATION (expr))
- 	   && (decl_function_context (GOTO_DESTINATION (expr))
- 	       == current_function_decl));
- }
- 
  /* Lowers a cond_expr TSI.  DATA is passed through the recursion.  */
  
  static void
--- 195,200 ----
Index: tree-cfg.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/Attic/tree-cfg.c,v
retrieving revision 1.1.4.194
diff -c -3 -p -r1.1.4.194 tree-cfg.c
*** tree-cfg.c	5 Nov 2003 16:28:06 -0000	1.1.4.194
--- tree-cfg.c	6 Nov 2003 16:07:58 -0000
*************** factor_computed_gotos (void)
*** 271,277 ****
  	continue;
  
        /* If the last statement is a compted goto, factor it.  */
!       if (is_computed_goto (last))
  	{
  	  tree assignment;
  	  block_stmt_iterator bsi = bsi_last (bb);
--- 271,277 ----
  	continue;
  
        /* If the last statement is a compted goto, factor it.  */
!       if (computed_goto_p (last))
  	{
  	  tree assignment;
  	  block_stmt_iterator bsi = bsi_last (bb);
*************** make_blocks (tree *first_p, basic_block 
*** 441,447 ****
  	 codes.  */
        append_stmt_to_bb (stmt_p, bb);
  
!       if (is_computed_goto (*stmt_p))
  	found_computed_goto = true;
  
        /* All BIND_EXPRs except for the outermost one are lowered already.  */
--- 441,447 ----
  	 codes.  */
        append_stmt_to_bb (stmt_p, bb);
  
!       if (computed_goto_p (*stmt_p))
  	found_computed_goto = true;
  
        /* All BIND_EXPRs except for the outermost one are lowered already.  */
*************** static void
*** 577,588 ****
--- 578,594 ----
  make_ctrl_stmt_edges (basic_block bb)
  {
    tree last = last_stmt (bb);
+   tree first = first_stmt (bb);
  
  #if defined ENABLE_CHECKING
    if (last == NULL_TREE)
      abort();
  #endif
  
+   if (TREE_CODE (first) == LABEL_EXPR
+       && NONLOCAL_LABEL (LABEL_EXPR_LABEL (first)))
+     make_edge (ENTRY_BLOCK_PTR, bb, EDGE_ABNORMAL);
+ 
    switch (TREE_CODE (last))
      {
      case GOTO_EXPR:
*************** make_ctrl_stmt_edges (basic_block bb)
*** 590,600 ****
  
        /* If this is potentially a nonlocal goto, then this should also
  	 create an edge to the exit block.   */
!       if ((TREE_CODE (GOTO_DESTINATION (last)) == LABEL_DECL
! 	   && (decl_function_context (GOTO_DESTINATION (last))
! 	       != current_function_decl))
! 	  || (TREE_CODE (GOTO_DESTINATION (last)) != LABEL_DECL
! 	      && DECL_CONTEXT (current_function_decl)))
  	make_edge (bb, EXIT_BLOCK_PTR, EDGE_ABNORMAL);
        break;
  
--- 596,602 ----
  
        /* If this is potentially a nonlocal goto, then this should also
  	 create an edge to the exit block.   */
!       if (nonlocal_goto_p (last))
  	make_edge (bb, EXIT_BLOCK_PTR, EDGE_ABNORMAL);
        break;
  
*************** make_goto_expr_edges (basic_block bb)
*** 761,767 ****
        for_call = 0;
  
        /* A GOTO to a local label creates normal edges.  */
!       if (TREE_CODE (dest) == LABEL_DECL && ! NONLOCAL_LABEL (dest))
  	{
  	  make_edge (bb, label_to_block (dest), 0);
  	  return;
--- 763,769 ----
        for_call = 0;
  
        /* A GOTO to a local label creates normal edges.  */
!       if (simple_goto_p (goto_t))
  	{
  	  make_edge (bb, label_to_block (dest), 0);
  	  return;
*************** call_expr_flags (tree t)
*** 2408,2419 ****
  /* Return true if T is a computed goto.  */
  
  bool
! is_computed_goto (tree t)
  {
    return (TREE_CODE (t) == GOTO_EXPR
            && TREE_CODE (GOTO_DESTINATION (t)) != LABEL_DECL);
  }
  
  
  /* Return true if T should start a new basic block.  PREV_T is the
     statement preceding T.  It is used when T is a label or a case label.
--- 2417,2450 ----
  /* Return true if T is a computed goto.  */
  
  bool
! computed_goto_p (tree t)
  {
    return (TREE_CODE (t) == GOTO_EXPR
            && TREE_CODE (GOTO_DESTINATION (t)) != LABEL_DECL);
  }
  
+ /* Return true when GOTO is an non-local goto.  */
+ bool
+ nonlocal_goto_p (tree stmt)
+ {
+  return ((TREE_CODE (GOTO_DESTINATION (stmt)) == LABEL_DECL
+ 	   && (decl_function_context (GOTO_DESTINATION (stmt))
+ 	       != current_function_decl))
+ 	  || (TREE_CODE (GOTO_DESTINATION (stmt)) != LABEL_DECL
+ 	      && DECL_CONTEXT (current_function_decl)));
+ }
+ 
+ /* Checks whether EXPR is a simple local goto.  */
+ 
+ bool
+ simple_goto_p (tree expr)
+ {
+   return  (TREE_CODE (expr) == GOTO_EXPR
+ 	   && TREE_CODE (GOTO_DESTINATION (expr)) == LABEL_DECL
+ 	   && ! NONLOCAL_LABEL (GOTO_DESTINATION (expr))
+ 	   && (decl_function_context (GOTO_DESTINATION (expr))
+ 	       == current_function_decl));
+ }
  
  /* Return true if T should start a new basic block.  PREV_T is the
     statement preceding T.  It is used when T is a label or a case label.
Index: tree-flow.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/Attic/tree-flow.h,v
retrieving revision 1.1.4.141
diff -c -3 -p -r1.1.4.141 tree-flow.h
*** tree-flow.h	5 Nov 2003 13:39:23 -0000	1.1.4.141
--- tree-flow.h	6 Nov 2003 16:07:58 -0000
*************** extern void build_tree_cfg (tree *);
*** 430,436 ****
  extern void delete_tree_cfg (void);
  extern bool is_ctrl_stmt (tree);
  extern bool is_ctrl_altering_stmt (tree);
! extern bool is_computed_goto (tree);
  extern void tree_dump_bb (basic_block, FILE *, int);
  extern void debug_tree_bb (basic_block);
  extern basic_block debug_tree_bb_n (int);
--- 430,438 ----
  extern void delete_tree_cfg (void);
  extern bool is_ctrl_stmt (tree);
  extern bool is_ctrl_altering_stmt (tree);
! extern bool computed_goto_p (tree);
! extern bool nonlocal_goto_p (tree);
! extern bool simple_goto_p (tree);
  extern void tree_dump_bb (basic_block, FILE *, int);
  extern void debug_tree_bb (basic_block);
  extern basic_block debug_tree_bb_n (int);
Index: tree-ssa-ccp.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/Attic/tree-ssa-ccp.c,v
retrieving revision 1.1.2.106
diff -c -3 -p -r1.1.2.106 tree-ssa-ccp.c
*** tree-ssa-ccp.c	5 Nov 2003 13:39:23 -0000	1.1.2.106
--- tree-ssa-ccp.c	6 Nov 2003 16:07:58 -0000
*************** visit_stmt (tree stmt)
*** 608,614 ****
  
        /* If STMT is a computed goto, then mark all the output edges
  	 executable.  */
!       if (is_computed_goto (stmt))
  	add_outgoing_control_edges (bb_for_stmt (stmt));
      }
  
--- 608,614 ----
  
        /* If STMT is a computed goto, then mark all the output edges
  	 executable.  */
!       if (computed_goto_p (stmt))
  	add_outgoing_control_edges (bb_for_stmt (stmt));
      }
  


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