diff options
author | Bin Cheng <bin.cheng@arm.com> | 2011-12-23 05:43:09 +0000 |
---|---|---|
committer | Joey Ye <jye2@gcc.gnu.org> | 2011-12-23 05:43:09 +0000 |
commit | 2b9ed3bc10e02c3430fa6393b604095cb4bd943a (patch) | |
tree | dcbbdbfe25be1bb7cb6bb32976e61c401d6ec529 | |
parent | 994182df2760962dc90ab4f2eace2de84c669133 (diff) | |
download | gcc-2b9ed3bc10e02c3430fa6393b604095cb4bd943a.zip gcc-2b9ed3bc10e02c3430fa6393b604095cb4bd943a.tar.gz gcc-2b9ed3bc10e02c3430fa6393b604095cb4bd943a.tar.bz2 |
re PR tree-optimization/43491 (Unnecessary temporary for global register variable)
2011-12-22 Bin Cheng <bin.cheng@arm.com>
Richard Guenther <rguenther@suse.de>
PR tree-optimization/43491
* tree-ssa-pre.c (eliminate): Don't replace global register
variable when it is the RHS of a single assign.
testsuite:
* gcc.dg/tree-ssa/pr43491.c: New test.
Co-Authored-By: Richard Guenther <rguenther@suse.de>
From-SVN: r182650
-rw-r--r-- | gcc/ChangeLog | 7 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 5 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/tree-ssa/pr43491.c | 42 | ||||
-rw-r--r-- | gcc/tree-ssa-pre.c | 35 |
4 files changed, 77 insertions, 12 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 8b6fc68..d739d2e 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,10 @@ +2011-12-22 Bin Cheng <bin.cheng@arm.com> + Richard Guenther <rguenther@suse.de> + + PR tree-optimization/43491 + * tree-ssa-pre.c (eliminate): Don't replace global register + variable when it is the RHS of a single assign. + 2011-12-22 Joey Ye <joey.ye@arm.com> * toplev.c (process_options): Fix typo. diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 540d28b..0594a96 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2011-12-22 Bin Cheng <bin.cheng@arm.com> + + PR tree-optimization/43491 + * gcc.dg/tree-ssa/pr43491.c: New test. + 2011-12-22 John David Anglin <dave.anglin@nrc-cnrc.gc.ca> PR testsuite/50722 diff --git a/gcc/testsuite/gcc.dg/tree-ssa/pr43491.c b/gcc/testsuite/gcc.dg/tree-ssa/pr43491.c new file mode 100644 index 0000000..2473400 --- /dev/null +++ b/gcc/testsuite/gcc.dg/tree-ssa/pr43491.c @@ -0,0 +1,42 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -fdump-tree-pre-stats" } */ + +#define REGISTER register + +#if defined __arm__ +# define REG1 asm("r4") +#elif defined __i386__ +# define REG1 asm("ebx") +#elif defined __mips__ +# define REG1 asm("s0") +#elif defined __x86_64__ +# define REG1 asm("rbp") +#else +# undef REGISTER +# define REGISTER +# define REG1 +#endif + +REGISTER long data_0 REG1; +long data_3; + +long foo(long data, long v) +{ + long i; + long t, u; + + if (data) + i = data_0 + data_3; + else { + v = 2; + i = 5; + } + t = data_0 + data_3; + u = i; + return v * t * u; +} +/* We should not eliminate global register variable when it is the RHS of + a single assignment. */ +/* { dg-final { scan-tree-dump-times "Eliminated: 2" 1 "pre" { target { arm-*-* i?86-*-* mips*-*-* x86_64-*-* } } } } */ +/* { dg-final { scan-tree-dump-times "Eliminated: 3" 1 "pre" { target { ! { arm-*-* i?86-*-* mips*-*-* x86_64-*-* } } } } } */ +/* { dg-final { cleanup-tree-dump "pre" } } */ diff --git a/gcc/tree-ssa-pre.c b/gcc/tree-ssa-pre.c index 557b56a..6e86024 100644 --- a/gcc/tree-ssa-pre.c +++ b/gcc/tree-ssa-pre.c @@ -4161,28 +4161,40 @@ eliminate (void) { for (gsi = gsi_start_bb (b); !gsi_end_p (gsi); gsi_next (&gsi)) { + tree lhs = NULL_TREE; + tree rhs = NULL_TREE; + stmt = gsi_stmt (gsi); + if (gimple_has_lhs (stmt)) + lhs = gimple_get_lhs (stmt); + + if (gimple_assign_single_p (stmt)) + rhs = gimple_assign_rhs1 (stmt); + /* Lookup the RHS of the expression, see if we have an available computation for it. If so, replace the RHS with - the available computation. */ + the available computation. + + See PR43491. + We don't replace global register variable when it is a the RHS of + a single assign. We do replace local register variable since gcc + does not guarantee local variable will be allocated in register. */ if (gimple_has_lhs (stmt) - && TREE_CODE (gimple_get_lhs (stmt)) == SSA_NAME + && TREE_CODE (lhs) == SSA_NAME && !gimple_assign_ssa_name_copy_p (stmt) && (!gimple_assign_single_p (stmt) - || !is_gimple_min_invariant (gimple_assign_rhs1 (stmt))) + || (!is_gimple_min_invariant (rhs) + && (gimple_assign_rhs_code (stmt) != VAR_DECL + || !is_global_var (rhs) + || !DECL_HARD_REGISTER (rhs)))) && !gimple_has_volatile_ops (stmt) - && !has_zero_uses (gimple_get_lhs (stmt))) + && !has_zero_uses (lhs)) { - tree lhs = gimple_get_lhs (stmt); - tree rhs = NULL_TREE; tree sprime = NULL; pre_expr lhsexpr = get_or_alloc_expr_for_name (lhs); pre_expr sprimeexpr; - if (gimple_assign_single_p (stmt)) - rhs = gimple_assign_rhs1 (stmt); - sprimeexpr = bitmap_find_leader (AVAIL_OUT (b), get_expr_value_id (lhsexpr), NULL); @@ -4298,10 +4310,9 @@ eliminate (void) dead. */ else if (gimple_assign_single_p (stmt) && !is_gimple_reg (gimple_assign_lhs (stmt)) - && (TREE_CODE (gimple_assign_rhs1 (stmt)) == SSA_NAME - || is_gimple_min_invariant (gimple_assign_rhs1 (stmt)))) + && (TREE_CODE (rhs) == SSA_NAME + || is_gimple_min_invariant (rhs))) { - tree rhs = gimple_assign_rhs1 (stmt); tree val; val = vn_reference_lookup (gimple_assign_lhs (stmt), gimple_vuse (stmt), VN_WALK, NULL); |