diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 0108a0d3a7b3..acdfadb50eba 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,10 @@ +2012-08-13 Richard Guenther + + PR tree-optimization/54200 + * tree-ssa-copyrename.c (rename_ssa_copies): Do not add + PHI results to another partition if not all PHI arguments + have the same partition. + 2012-08-12 Jan Hubicka * tree-pass.h (write_summary, write_optimization_summary): Remove diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index a9df8b75264a..f09347af0d75 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,9 @@ +2012-08-13 Richard Guenther + + PR tree-optimization/54200 + * gcc.dg/guality/pr54200.c: New testcase. + * gcc.dg/tree-ssa/slsr-8.c: Adjust. + 2012-08-12 Oleg Endo * gcc.target/sh/prefetch.c: Add -m3* to inclusion list. diff --git a/gcc/testsuite/gcc.dg/guality/pr54200.c b/gcc/testsuite/gcc.dg/guality/pr54200.c new file mode 100644 index 000000000000..9b171876401c --- /dev/null +++ b/gcc/testsuite/gcc.dg/guality/pr54200.c @@ -0,0 +1,28 @@ +/* PR tree-optimization/54200 */ +/* { dg-do run } */ +/* { dg-options "-g -fno-var-tracking-assignments" } */ + +int o __attribute__((used)); + +void bar (void) { o = 2; } + +int __attribute__((noinline,noclone)) +foo (int z, int x, int b) +{ + if (x == 1) + { + bar (); + return z; + } + else + { + int a = (x + z) + b; + return a; /* { dg-final { gdb-test 20 "z" "3" } } */ + } +} + +int main () +{ + foo (3, 2, 1); + return 0; +} diff --git a/gcc/testsuite/gcc.dg/tree-ssa/slsr-8.c b/gcc/testsuite/gcc.dg/tree-ssa/slsr-8.c index b03c52c33603..c2e9b615568d 100644 --- a/gcc/testsuite/gcc.dg/tree-ssa/slsr-8.c +++ b/gcc/testsuite/gcc.dg/tree-ssa/slsr-8.c @@ -17,7 +17,7 @@ f (int s, int *c) return x1 ? x2 : x3; } -/* There are 2 ' * ' instances in the decls (since "int * x3;" is - optimized out), 1 parm, 2 in the code. */ -/* { dg-final { scan-tree-dump-times " \\* " 5 "optimized" } } */ +/* There are 4 ' * ' instances in the decls (since "int * iftmp.0;" is + added), 1 parm, 2 in the code. */ +/* { dg-final { scan-tree-dump-times " \\* " 7 "optimized" } } */ /* { dg-final { cleanup-tree-dump "optimized" } } */ diff --git a/gcc/tree-ssa-copyrename.c b/gcc/tree-ssa-copyrename.c index 82f8c64fe1c7..387e67bce6e9 100644 --- a/gcc/tree-ssa-copyrename.c +++ b/gcc/tree-ssa-copyrename.c @@ -348,15 +348,53 @@ rename_ssa_copies (void) res = gimple_phi_result (phi); /* Do not process virtual SSA_NAMES. */ - if (!is_gimple_reg (res)) + if (virtual_operand_p (res)) continue; - for (i = 0; i < gimple_phi_num_args (phi); i++) - { - tree arg = gimple_phi_arg (phi, i)->def; - if (TREE_CODE (arg) == SSA_NAME) - updated |= copy_rename_partition_coalesce (map, res, arg, debug); - } + /* Make sure to only use the same partition for an argument + as the result but never the other way around. */ + if (SSA_NAME_VAR (res) + && !DECL_IGNORED_P (SSA_NAME_VAR (res))) + for (i = 0; i < gimple_phi_num_args (phi); i++) + { + tree arg = PHI_ARG_DEF (phi, i); + if (TREE_CODE (arg) == SSA_NAME) + updated |= copy_rename_partition_coalesce (map, res, arg, + debug); + } + /* Else if all arguments are in the same partition try to merge + it with the result. */ + else + { + int all_p_same = -1; + int p = -1; + for (i = 0; i < gimple_phi_num_args (phi); i++) + { + tree arg = PHI_ARG_DEF (phi, i); + if (TREE_CODE (arg) != SSA_NAME) + { + all_p_same = 0; + break; + } + else if (all_p_same == -1) + { + p = partition_find (map->var_partition, + SSA_NAME_VERSION (arg)); + all_p_same = 1; + } + else if (all_p_same == 1 + && p != partition_find (map->var_partition, + SSA_NAME_VERSION (arg))) + { + all_p_same = 0; + break; + } + } + if (all_p_same == 1) + updated |= copy_rename_partition_coalesce (map, res, + PHI_ARG_DEF (phi, 0), + debug); + } } }