Commit 45cc9f96 by Richard Biener Committed by Richard Biener

gimple-fold.h (follow_single_use_edges): Declare.

2014-10-28  Richard Biener  <rguenther@suse.de>

	* gimple-fold.h (follow_single_use_edges): Declare.
	* gimple-fold.c (follow_single_use_edges): New function.
	(gimple_fold_stmt_to_constant_1): Dispatch to gimple_simplify.
	* tree-ssa-propagate.c
	(substitute_and_fold_dom_walker::before_dom_children): Allow
	following single-use edges when folding stmts we propagated into.

From-SVN: r216799
parent 936c0fe4
2014-10-28 Richard Biener <rguenther@suse.de>
* gimple-fold.h (follow_single_use_edges): Declare.
* gimple-fold.c (follow_single_use_edges): New function.
(gimple_fold_stmt_to_constant_1): Dispatch to gimple_simplify.
* tree-ssa-propagate.c
(substitute_and_fold_dom_walker::before_dom_children): Allow
following single-use edges when folding stmts we propagated into.
2014-10-28 Alexander Ivchenko <alexander.ivchenko@intel.com> 2014-10-28 Alexander Ivchenko <alexander.ivchenko@intel.com>
Maxim Kuznetsov <maxim.kuznetsov@intel.com> Maxim Kuznetsov <maxim.kuznetsov@intel.com>
Anna Tikhonova <anna.tikhonova@intel.com> Anna Tikhonova <anna.tikhonova@intel.com>
...@@ -65,6 +65,8 @@ along with GCC; see the file COPYING3. If not see ...@@ -65,6 +65,8 @@ along with GCC; see the file COPYING3. If not see
#include "output.h" #include "output.h"
#include "tree-eh.h" #include "tree-eh.h"
#include "gimple-match.h" #include "gimple-match.h"
#include "tree-phinodes.h"
#include "ssa-iterators.h"
/* Return true when DECL can be referenced from current unit. /* Return true when DECL can be referenced from current unit.
FROM_DECL (if non-null) specify constructor of variable DECL was taken from. FROM_DECL (if non-null) specify constructor of variable DECL was taken from.
...@@ -3241,6 +3243,17 @@ no_follow_ssa_edges (tree) ...@@ -3241,6 +3243,17 @@ no_follow_ssa_edges (tree)
return NULL_TREE; return NULL_TREE;
} }
/* Valueization callback that ends up following single-use SSA edges only. */
tree
follow_single_use_edges (tree val)
{
if (TREE_CODE (val) == SSA_NAME
&& !has_single_use (val))
return NULL_TREE;
return val;
}
/* Fold the statement pointed to by GSI. In some cases, this function may /* Fold the statement pointed to by GSI. In some cases, this function may
replace the whole statement with a new one. Returns true iff folding replace the whole statement with a new one. Returns true iff folding
makes any changes. makes any changes.
...@@ -4371,6 +4384,30 @@ maybe_fold_or_comparisons (enum tree_code code1, tree op1a, tree op1b, ...@@ -4371,6 +4384,30 @@ maybe_fold_or_comparisons (enum tree_code code1, tree op1a, tree op1b,
tree tree
gimple_fold_stmt_to_constant_1 (gimple stmt, tree (*valueize) (tree)) gimple_fold_stmt_to_constant_1 (gimple stmt, tree (*valueize) (tree))
{ {
code_helper rcode;
tree ops[3] = {};
/* ??? The SSA propagators do not correctly deal with following SSA use-def
edges if there are intermediate VARYING defs. For this reason
do not follow SSA edges here even though SCCVN can technically
just deal fine with that. */
if (gimple_simplify (stmt, &rcode, ops, NULL, no_follow_ssa_edges)
&& rcode.is_tree_code ()
&& (TREE_CODE_LENGTH ((tree_code) rcode) == 0
|| ((tree_code) rcode) == ADDR_EXPR)
&& is_gimple_val (ops[0]))
{
tree res = ops[0];
if (dump_file && dump_flags & TDF_DETAILS)
{
fprintf (dump_file, "Match-and-simplified ");
print_gimple_expr (dump_file, stmt, 0, TDF_SLIM);
fprintf (dump_file, " to ");
print_generic_expr (dump_file, res, 0);
fprintf (dump_file, "\n");
}
return res;
}
location_t loc = gimple_location (stmt); location_t loc = gimple_location (stmt);
switch (gimple_code (stmt)) switch (gimple_code (stmt))
{ {
......
...@@ -33,6 +33,7 @@ extern tree maybe_fold_and_comparisons (enum tree_code, tree, tree, ...@@ -33,6 +33,7 @@ extern tree maybe_fold_and_comparisons (enum tree_code, tree, tree,
extern tree maybe_fold_or_comparisons (enum tree_code, tree, tree, extern tree maybe_fold_or_comparisons (enum tree_code, tree, tree,
enum tree_code, tree, tree); enum tree_code, tree, tree);
extern tree no_follow_ssa_edges (tree); extern tree no_follow_ssa_edges (tree);
extern tree follow_single_use_edges (tree);
extern tree gimple_fold_stmt_to_constant_1 (gimple, tree (*) (tree)); extern tree gimple_fold_stmt_to_constant_1 (gimple, tree (*) (tree));
extern tree gimple_fold_stmt_to_constant (gimple, tree (*) (tree)); extern tree gimple_fold_stmt_to_constant (gimple, tree (*) (tree));
extern tree fold_const_aggregate_ref_1 (tree, tree (*) (tree)); extern tree fold_const_aggregate_ref_1 (tree, tree (*) (tree));
......
...@@ -1150,7 +1150,7 @@ substitute_and_fold_dom_walker::before_dom_children (basic_block bb) ...@@ -1150,7 +1150,7 @@ substitute_and_fold_dom_walker::before_dom_children (basic_block bb)
/* If we made a replacement, fold the statement. */ /* If we made a replacement, fold the statement. */
if (did_replace) if (did_replace)
fold_stmt (&i); fold_stmt (&i, follow_single_use_edges);
/* Now cleanup. */ /* Now cleanup. */
if (did_replace) if (did_replace)
......
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