tree-cfg.c (make_exit_edges): Use get_call_expr_in.
* tree-cfg.c (make_exit_edges): Use get_call_expr_in. (remove_useless_stmts_1, is_ctrl_altering_stmt): Likewise. (tree_block_ends_with_call_p, need_fake_edge_p): Likewise. * tree-eh.c (lower_eh_constructs_1): Likewise. * tree-sra.c (sra_walk_modify_expr): Likewise. * tree-ssa-dce.c (mark_stmt_if_obviously_necessary): Likewise. (eliminate_unnecessary_stmts): Likewise. * tree-ssa-dse.c (dse_optimize_stmt): Likewise. * tree-tailcall.c (optimize_tail_call): Likewise. * tree-ssa-ccp.c (get_rhs, set_rhs): Reorg to use switch. From-SVN: r84298
This commit is contained in:
parent
c618c6ec7e
commit
cd7097527e
@ -1,3 +1,16 @@
|
||||
2004-07-08 Richard Henderson <rth@redhat.com>
|
||||
|
||||
* tree-cfg.c (make_exit_edges): Use get_call_expr_in.
|
||||
(remove_useless_stmts_1, is_ctrl_altering_stmt): Likewise.
|
||||
(tree_block_ends_with_call_p, need_fake_edge_p): Likewise.
|
||||
* tree-eh.c (lower_eh_constructs_1): Likewise.
|
||||
* tree-sra.c (sra_walk_modify_expr): Likewise.
|
||||
* tree-ssa-dce.c (mark_stmt_if_obviously_necessary): Likewise.
|
||||
(eliminate_unnecessary_stmts): Likewise.
|
||||
* tree-ssa-dse.c (dse_optimize_stmt): Likewise.
|
||||
* tree-tailcall.c (optimize_tail_call): Likewise.
|
||||
* tree-ssa-ccp.c (get_rhs, set_rhs): Reorg to use switch.
|
||||
|
||||
2004-07-08 Paolo Bonzini <bonzini@gnu.org>
|
||||
Jakub Jelinek <jakub@redhat.com>
|
||||
|
||||
|
@ -510,7 +510,7 @@ make_ctrl_stmt_edges (basic_block bb)
|
||||
static void
|
||||
make_exit_edges (basic_block bb)
|
||||
{
|
||||
tree last = last_stmt (bb);
|
||||
tree last = last_stmt (bb), op;
|
||||
|
||||
if (last == NULL_TREE)
|
||||
abort ();
|
||||
@ -550,8 +550,8 @@ make_exit_edges (basic_block bb)
|
||||
/* A MODIFY_EXPR may have a CALL_EXPR on its RHS and the CALL_EXPR
|
||||
may have an abnormal edge. Search the RHS for this case and
|
||||
create any required edges. */
|
||||
if (TREE_CODE (TREE_OPERAND (last, 1)) == CALL_EXPR
|
||||
&& TREE_SIDE_EFFECTS (TREE_OPERAND (last, 1))
|
||||
op = get_call_expr_in (last);
|
||||
if (op && TREE_SIDE_EFFECTS (op)
|
||||
&& current_function_has_nonlocal_label)
|
||||
make_goto_expr_edges (bb);
|
||||
|
||||
@ -1520,7 +1520,7 @@ clear_special_calls (void)
|
||||
static void
|
||||
remove_useless_stmts_1 (tree *tp, struct rus_data *data)
|
||||
{
|
||||
tree t = *tp;
|
||||
tree t = *tp, op;
|
||||
|
||||
switch (TREE_CODE (t))
|
||||
{
|
||||
@ -1566,10 +1566,11 @@ remove_useless_stmts_1 (tree *tp, struct rus_data *data)
|
||||
case MODIFY_EXPR:
|
||||
data->last_goto = NULL;
|
||||
fold_stmt (tp);
|
||||
if (TREE_CODE (TREE_OPERAND (t, 1)) == CALL_EXPR)
|
||||
op = get_call_expr_in (t);
|
||||
if (op)
|
||||
{
|
||||
update_call_expr_flags (TREE_OPERAND (t, 1));
|
||||
notice_special_calls (TREE_OPERAND (t, 1));
|
||||
update_call_expr_flags (op);
|
||||
notice_special_calls (op);
|
||||
}
|
||||
if (tree_could_throw_p (t))
|
||||
data->may_throw = true;
|
||||
@ -2478,37 +2479,24 @@ is_ctrl_stmt (tree t)
|
||||
bool
|
||||
is_ctrl_altering_stmt (tree t)
|
||||
{
|
||||
tree call = t;
|
||||
tree call;
|
||||
|
||||
#if defined ENABLE_CHECKING
|
||||
if (t == NULL)
|
||||
abort ();
|
||||
#endif
|
||||
|
||||
switch (TREE_CODE (t))
|
||||
call = get_call_expr_in (t);
|
||||
if (call)
|
||||
{
|
||||
case MODIFY_EXPR:
|
||||
/* A MODIFY_EXPR with a rhs of a call has the characteristics
|
||||
of the call. */
|
||||
call = TREE_OPERAND (t, 1);
|
||||
if (TREE_CODE (call) != CALL_EXPR)
|
||||
break;
|
||||
/* FALLTHRU */
|
||||
|
||||
case CALL_EXPR:
|
||||
/* A non-pure/const CALL_EXPR alters flow control if the current
|
||||
function has nonlocal labels. */
|
||||
if (TREE_SIDE_EFFECTS (t)
|
||||
&& current_function_has_nonlocal_label)
|
||||
if (TREE_SIDE_EFFECTS (call) && current_function_has_nonlocal_label)
|
||||
return true;
|
||||
|
||||
/* A CALL_EXPR also alters control flow if it does not return. */
|
||||
if (call_expr_flags (call) & (ECF_NORETURN | ECF_LONGJMP))
|
||||
return true;
|
||||
break;
|
||||
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
|
||||
/* If a statement can throw, it alters control flow. */
|
||||
@ -4509,15 +4497,7 @@ static bool
|
||||
tree_block_ends_with_call_p (basic_block bb)
|
||||
{
|
||||
block_stmt_iterator bsi = bsi_last (bb);
|
||||
tree t = tsi_stmt (bsi.tsi);
|
||||
|
||||
if (TREE_CODE (t) == RETURN_EXPR && TREE_OPERAND (t, 0))
|
||||
t = TREE_OPERAND (t, 0);
|
||||
|
||||
if (TREE_CODE (t) == MODIFY_EXPR)
|
||||
t = TREE_OPERAND (t, 1);
|
||||
|
||||
return TREE_CODE (t) == CALL_EXPR;
|
||||
return get_call_expr_in (bsi_stmt (bsi)) != NULL;
|
||||
}
|
||||
|
||||
|
||||
@ -4538,11 +4518,7 @@ tree_block_ends_with_condjump_p (basic_block bb)
|
||||
static bool
|
||||
need_fake_edge_p (tree t)
|
||||
{
|
||||
if (TREE_CODE (t) == RETURN_EXPR && TREE_OPERAND (t, 0))
|
||||
t = TREE_OPERAND (t, 0);
|
||||
|
||||
if (TREE_CODE (t) == MODIFY_EXPR)
|
||||
t = TREE_OPERAND (t, 1);
|
||||
tree call;
|
||||
|
||||
/* NORETURN and LONGJMP calls already have an edge to exit.
|
||||
CONST, PURE and ALWAYS_RETURN calls do not need one.
|
||||
@ -4551,9 +4527,10 @@ need_fake_edge_p (tree t)
|
||||
figured out from the RTL in mark_constant_function, and
|
||||
the counter incrementation code from -fprofile-arcs
|
||||
leads to different results from -fbranch-probabilities. */
|
||||
if (TREE_CODE (t) == CALL_EXPR
|
||||
&& !(call_expr_flags (t) &
|
||||
(ECF_NORETURN | ECF_LONGJMP | ECF_ALWAYS_RETURN)))
|
||||
call = get_call_expr_in (t);
|
||||
if (call
|
||||
&& !(call_expr_flags (call) &
|
||||
(ECF_NORETURN | ECF_LONGJMP | ECF_ALWAYS_RETURN)))
|
||||
return true;
|
||||
|
||||
if (TREE_CODE (t) == ASM_EXPR
|
||||
|
@ -1552,14 +1552,17 @@ lower_eh_constructs_1 (struct leh_state *state, tree *tp)
|
||||
/* Look for things that can throw exceptions, and record them. */
|
||||
if (state->cur_region && tree_could_throw_p (t))
|
||||
{
|
||||
tree op;
|
||||
|
||||
record_stmt_eh_region (state->cur_region, t);
|
||||
note_eh_region_may_contain_throw (state->cur_region);
|
||||
|
||||
/* ??? For the benefit of calls.c, converting all this to rtl,
|
||||
we need to record the call expression, not just the outer
|
||||
modify statement. */
|
||||
if (TREE_CODE (TREE_OPERAND (t, 1)) == CALL_EXPR)
|
||||
record_stmt_eh_region (state->cur_region, TREE_OPERAND (t, 1));
|
||||
op = get_call_expr_in (t);
|
||||
if (op)
|
||||
record_stmt_eh_region (state->cur_region, op);
|
||||
}
|
||||
break;
|
||||
|
||||
|
@ -811,10 +811,14 @@ sra_walk_modify_expr (tree expr, block_stmt_iterator *bsi,
|
||||
else
|
||||
fns->use (rhs_elt, &TREE_OPERAND (expr, 1), bsi, false);
|
||||
}
|
||||
else if (TREE_CODE (rhs) == CALL_EXPR)
|
||||
sra_walk_call_expr (rhs, bsi, fns);
|
||||
else
|
||||
sra_walk_expr (&TREE_OPERAND (expr, 1), bsi, false, fns);
|
||||
{
|
||||
tree call = get_call_expr_in (rhs);
|
||||
if (call)
|
||||
sra_walk_call_expr (call, bsi, fns);
|
||||
else
|
||||
sra_walk_expr (&TREE_OPERAND (expr, 1), bsi, false, fns);
|
||||
}
|
||||
}
|
||||
|
||||
/* Entry point to the walk functions. Search the entire function,
|
||||
|
@ -2106,27 +2106,30 @@ get_rhs (tree stmt)
|
||||
{
|
||||
enum tree_code code = TREE_CODE (stmt);
|
||||
|
||||
if (code == MODIFY_EXPR)
|
||||
return TREE_OPERAND (stmt, 1);
|
||||
if (code == COND_EXPR)
|
||||
return COND_EXPR_COND (stmt);
|
||||
else if (code == SWITCH_EXPR)
|
||||
return SWITCH_COND (stmt);
|
||||
else if (code == RETURN_EXPR)
|
||||
switch (code)
|
||||
{
|
||||
if (!TREE_OPERAND (stmt, 0))
|
||||
return NULL_TREE;
|
||||
if (TREE_CODE (TREE_OPERAND (stmt, 0)) == MODIFY_EXPR)
|
||||
return TREE_OPERAND (TREE_OPERAND (stmt, 0), 1);
|
||||
case RETURN_EXPR:
|
||||
stmt = TREE_OPERAND (stmt, 0);
|
||||
if (stmt)
|
||||
return get_rhs (stmt);
|
||||
else
|
||||
return TREE_OPERAND (stmt, 0);
|
||||
return NULL;
|
||||
|
||||
case MODIFY_EXPR:
|
||||
return TREE_OPERAND (stmt, 1);
|
||||
|
||||
case COND_EXPR:
|
||||
return COND_EXPR_COND (stmt);
|
||||
case SWITCH_EXPR:
|
||||
return SWITCH_COND (stmt);
|
||||
case GOTO_EXPR:
|
||||
return GOTO_DESTINATION (stmt);
|
||||
case LABEL_EXPR:
|
||||
return LABEL_EXPR_LABEL (stmt);
|
||||
|
||||
default:
|
||||
return stmt;
|
||||
}
|
||||
else if (code == GOTO_EXPR)
|
||||
return GOTO_DESTINATION (stmt);
|
||||
else if (code == LABEL_EXPR)
|
||||
return LABEL_EXPR_LABEL (stmt);
|
||||
else
|
||||
return stmt;
|
||||
}
|
||||
|
||||
|
||||
@ -2135,8 +2138,9 @@ get_rhs (tree stmt)
|
||||
static bool
|
||||
set_rhs (tree *stmt_p, tree expr)
|
||||
{
|
||||
tree stmt = *stmt_p;
|
||||
tree stmt = *stmt_p, op;
|
||||
enum tree_code code = TREE_CODE (expr);
|
||||
stmt_ann_t ann;
|
||||
|
||||
/* Verify the constant folded result is valid gimple. */
|
||||
if (TREE_CODE_CLASS (code) == '2')
|
||||
@ -2151,30 +2155,39 @@ set_rhs (tree *stmt_p, tree expr)
|
||||
return false;
|
||||
}
|
||||
|
||||
code = TREE_CODE (stmt);
|
||||
if (code == MODIFY_EXPR)
|
||||
TREE_OPERAND (stmt, 1) = expr;
|
||||
else if (code == COND_EXPR)
|
||||
COND_EXPR_COND (stmt) = expr;
|
||||
else if (code == SWITCH_EXPR)
|
||||
SWITCH_COND (stmt) = expr;
|
||||
else if (code == RETURN_EXPR)
|
||||
{
|
||||
if (TREE_OPERAND (stmt, 0)
|
||||
&& TREE_CODE (TREE_OPERAND (stmt, 0)) == MODIFY_EXPR)
|
||||
TREE_OPERAND (TREE_OPERAND (stmt, 0), 1) = expr;
|
||||
else
|
||||
TREE_OPERAND (stmt, 0) = expr;
|
||||
}
|
||||
else if (code == GOTO_EXPR)
|
||||
GOTO_DESTINATION (stmt) = expr;
|
||||
else if (code == LABEL_EXPR)
|
||||
LABEL_EXPR_LABEL (stmt) = expr;
|
||||
else
|
||||
switch (TREE_CODE (stmt))
|
||||
{
|
||||
case RETURN_EXPR:
|
||||
op = TREE_OPERAND (stmt, 0);
|
||||
if (TREE_CODE (op) != MODIFY_EXPR)
|
||||
{
|
||||
TREE_OPERAND (stmt, 0) = expr;
|
||||
break;
|
||||
}
|
||||
stmt = op;
|
||||
/* FALLTHRU */
|
||||
|
||||
case MODIFY_EXPR:
|
||||
TREE_OPERAND (stmt, 1) = expr;
|
||||
break;
|
||||
|
||||
case COND_EXPR:
|
||||
COND_EXPR_COND (stmt) = expr;
|
||||
break;
|
||||
case SWITCH_EXPR:
|
||||
SWITCH_COND (stmt) = expr;
|
||||
break;
|
||||
case GOTO_EXPR:
|
||||
GOTO_DESTINATION (stmt) = expr;
|
||||
break;
|
||||
case LABEL_EXPR:
|
||||
LABEL_EXPR_LABEL (stmt) = expr;
|
||||
break;
|
||||
|
||||
default:
|
||||
/* Replace the whole statement with EXPR. If EXPR has no side
|
||||
effects, then replace *STMT_P with an empty statement. */
|
||||
stmt_ann_t ann = stmt_ann (stmt);
|
||||
ann = stmt_ann (stmt);
|
||||
*stmt_p = TREE_SIDE_EFFECTS (expr) ? expr : build_empty_stmt ();
|
||||
(*stmt_p)->common.ann = (tree_ann_t) ann;
|
||||
|
||||
@ -2211,6 +2224,7 @@ set_rhs (tree *stmt_p, tree expr)
|
||||
SSA_NAME_DEF_STMT (var) = *stmt_p;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
return true;
|
||||
|
@ -290,6 +290,7 @@ mark_stmt_if_obviously_necessary (tree stmt, bool aggressive)
|
||||
v_must_def_optype v_must_defs;
|
||||
stmt_ann_t ann;
|
||||
size_t i;
|
||||
tree op;
|
||||
|
||||
/* Statements that are implicitly live. Most function calls, asm and return
|
||||
statements are required. Labels and BIND_EXPR nodes are kept because
|
||||
@ -319,8 +320,8 @@ mark_stmt_if_obviously_necessary (tree stmt, bool aggressive)
|
||||
return;
|
||||
|
||||
case MODIFY_EXPR:
|
||||
if (TREE_CODE (TREE_OPERAND (stmt, 1)) == CALL_EXPR
|
||||
&& TREE_SIDE_EFFECTS (TREE_OPERAND (stmt, 1)))
|
||||
op = get_call_expr_in (stmt);
|
||||
if (op && TREE_SIDE_EFFECTS (op))
|
||||
{
|
||||
mark_stmt_necessary (stmt, true);
|
||||
return;
|
||||
@ -638,11 +639,9 @@ eliminate_unnecessary_stmts (void)
|
||||
remove_dead_stmt (&i, bb);
|
||||
else
|
||||
{
|
||||
if (TREE_CODE (t) == CALL_EXPR)
|
||||
notice_special_calls (t);
|
||||
else if (TREE_CODE (t) == MODIFY_EXPR
|
||||
&& TREE_CODE (TREE_OPERAND (t, 1)) == CALL_EXPR)
|
||||
notice_special_calls (TREE_OPERAND (t, 1));
|
||||
tree call = get_call_expr_in (t);
|
||||
if (call)
|
||||
notice_special_calls (call);
|
||||
bsi_next (&i);
|
||||
}
|
||||
}
|
||||
|
@ -244,10 +244,11 @@ dse_optimize_stmt (struct dom_walk_data *walk_data,
|
||||
if (NUM_V_MAY_DEFS (v_may_defs) == 0)
|
||||
return;
|
||||
|
||||
/* We know we have virtual definitions. If this is a MODIFY_EXPR, then
|
||||
record it into our table. */
|
||||
if (TREE_CODE (stmt) == MODIFY_EXPR
|
||||
&& TREE_CODE (TREE_OPERAND (stmt, 1)) != CALL_EXPR)
|
||||
/* We know we have virtual definitions. If this is a MODIFY_EXPR that's
|
||||
not also a function call, then record it into our table. */
|
||||
if (get_call_expr_in (stmt))
|
||||
return;
|
||||
if (TREE_CODE (stmt) == MODIFY_EXPR)
|
||||
{
|
||||
dataflow_t df = get_immediate_uses (stmt);
|
||||
unsigned int num_uses = num_immediate_uses (df);
|
||||
|
@ -757,10 +757,7 @@ optimize_tail_call (struct tailcall *t, bool opt_tailcalls)
|
||||
{
|
||||
tree stmt = bsi_stmt (t->call_bsi);
|
||||
|
||||
if (TREE_CODE (stmt) == MODIFY_EXPR)
|
||||
stmt = TREE_OPERAND (stmt, 1);
|
||||
if (TREE_CODE (stmt) != CALL_EXPR)
|
||||
abort ();
|
||||
stmt = get_call_expr_in (stmt);
|
||||
CALL_EXPR_TAILCALL (stmt) = 1;
|
||||
if (dump_file && (dump_flags & TDF_DETAILS))
|
||||
{
|
||||
|
Loading…
Reference in New Issue
Block a user