Commit f56e675d by Tomas Bily Committed by Tomas Bily

re PR tree-optimization/38385 (ICE with -O2 -ftree-loop-distribution)

        PR middlend/38385
        * tree-loop-distribution.c (prop_phis): New function.
        (generate_builtin): Call prop_phis.
        * testsuite/gcc.dg/tree-ssa/pr38385.c: New file.

From-SVN: r143291
parent c2152239
2009-01-12 Tomas Bily <tbily@suse.cz>
PR middlend/38385
* tree-loop-distribution.c (prop_phis): New function.
(generate_builtin): Call prop_phis.
* testsuite/gcc.dg/tree-ssa/pr38385.c: New file.
2009-01-12 Jakub Jelinek <jakub@redhat.com> 2009-01-12 Jakub Jelinek <jakub@redhat.com>
PR tree-optimization/38807 PR tree-optimization/38807
......
/* { dg-do compile } */
/* { dg-options "-O2 -ftree-loop-distribution" } */
struct rtx_def
{
int a;
};
typedef struct rtx_def *rtx;
struct rd {
int alternative_enabled_p[100];
rtx operand[100];
int n_operands;
};
rtx this_insn;
int n_reloads;
int n_replacements;
int n_earlyclobbers;
int replace_reloads;
int hard_regs_live_known;
short* static_reload_reg_p;
struct rd recog_data;
int
find_reloads (rtx insn, int replace, int ind_levels, int live_known,
short *reload_reg_p)
{
int i, j;
int noperands = replace;
int no_input_reloads = 0;
int n_alternatives = replace;
char this_alternative_match_win[30];
char this_alternative_win[30];
char this_alternative_earlyclobber[30];
int this_alternative_matches[30];
int goal_alternative[30];
int this_alternative_number;
char goal_alternative_match_win[30];
char goal_alternative_win[30];
int best;
int operand_mode[30];
int retval = 0;
for (this_alternative_number = 0;
this_alternative_number < n_alternatives;
this_alternative_number++)
{
int losers = 0;
int bad = 0;
if (!recog_data.alternative_enabled_p[this_alternative_number])
{
int i;
for (i = 0; i < recog_data.n_operands; i++)
;
continue;
}
for (i = 0; i < noperands; i++)
if (this_alternative_earlyclobber[i]
&& (this_alternative_win[i] || this_alternative_match_win[i]))
{
if (j != noperands)
{
losers++;
for (j = 0; j < noperands; j++)
if (this_alternative_matches[j] == i
&& this_alternative_match_win[j])
{
this_alternative_win[j] = 0;
this_alternative_match_win[j] = 0;
losers++;
}
}
}
if (losers == 0)
{
for (i = 0; i < noperands; i++)
{
goal_alternative_win[i] = 0;
goal_alternative_match_win[i] = 0;
}
goto finish;
}
if (! bad && best > losers)
{
for (i = 0; i < noperands; i++)
{
goal_alternative[i] = 0;
goal_alternative_win[i] = 0;
}
}
}
finish:
for (i = 0; i < noperands; i++)
if (! goal_alternative_win[i])
{
rtx op = recog_data.operand[i];
int mode = operand_mode[i];
if (((ix86_preferred_reload_class ((op), (goal_alternative[i])) == 2)
|| no_input_reloads)
&& mode != 0)
{}
}
return retval;
}
...@@ -331,6 +331,38 @@ generate_memset_zero (gimple stmt, tree op0, tree nb_iter, ...@@ -331,6 +331,38 @@ generate_memset_zero (gimple stmt, tree op0, tree nb_iter,
return res; return res;
} }
/* Propagate phis in BB b to their uses and remove them. */
static void
prop_phis (basic_block b)
{
gimple_stmt_iterator psi;
gimple_seq phis = phi_nodes (b);
for (psi = gsi_start (phis); !gsi_end_p (psi); )
{
gimple phi = gsi_stmt (psi);
tree def = gimple_phi_result (phi), use = gimple_phi_arg_def (phi, 0);
gcc_assert (gimple_phi_num_args (phi) == 1);
if (!is_gimple_reg (def))
{
imm_use_iterator iter;
use_operand_p use_p;
gimple stmt;
FOR_EACH_IMM_USE_STMT (stmt, iter, def)
FOR_EACH_IMM_USE_ON_STMT (use_p, iter)
SET_USE (use_p, use);
}
else
replace_uses_by (def, use);
remove_phi_node (&psi, true);
}
}
/* Tries to generate a builtin function for the instructions of LOOP /* Tries to generate a builtin function for the instructions of LOOP
pointed to by the bits set in PARTITION. Returns true when the pointed to by the bits set in PARTITION. Returns true when the
operation succeeded. */ operation succeeded. */
...@@ -400,6 +432,7 @@ generate_builtin (struct loop *loop, bitmap partition, bool copy_p) ...@@ -400,6 +432,7 @@ generate_builtin (struct loop *loop, bitmap partition, bool copy_p)
unsigned nbbs = loop->num_nodes; unsigned nbbs = loop->num_nodes;
basic_block src = loop_preheader_edge (loop)->src; basic_block src = loop_preheader_edge (loop)->src;
basic_block dest = single_exit (loop)->dest; basic_block dest = single_exit (loop)->dest;
prop_phis (dest);
make_edge (src, dest, EDGE_FALLTHRU); make_edge (src, dest, EDGE_FALLTHRU);
set_immediate_dominator (CDI_DOMINATORS, dest, src); set_immediate_dominator (CDI_DOMINATORS, dest, src);
cancel_loop_tree (loop); cancel_loop_tree (loop);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment