gimple-fold.h (follow_single_use_edges): Declare.
authorRichard Biener <rguenther@suse.de>
Tue, 28 Oct 2014 14:23:27 +0000 (14:23 +0000)
committerRichard Biener <rguenth@gcc.gnu.org>
Tue, 28 Oct 2014 14:23:27 +0000 (14:23 +0000)
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

gcc/ChangeLog
gcc/gimple-fold.c
gcc/gimple-fold.h
gcc/tree-ssa-propagate.c

index 64ed03b87b27cad243637db4f22bbe61fc0fc2b6..00708ed6d5e977a142997d7d82b74e3a694ca525 100644 (file)
@@ -1,3 +1,12 @@
+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>
            Maxim Kuznetsov  <maxim.kuznetsov@intel.com>
            Anna Tikhonova  <anna.tikhonova@intel.com>
index 8c8893032771eb7f9a8f1c096e32d12c940e1bce..d0554f4e54f7ec5a07f62612f16e2738bcec753f 100644 (file)
@@ -65,6 +65,8 @@ along with GCC; see the file COPYING3.  If not see
 #include "output.h"
 #include "tree-eh.h"
 #include "gimple-match.h"
+#include "tree-phinodes.h"
+#include "ssa-iterators.h"
 
 /* Return true when DECL can be referenced from current unit.
    FROM_DECL (if non-null) specify constructor of variable DECL was taken from.
@@ -3241,6 +3243,17 @@ no_follow_ssa_edges (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
    replace the whole statement with a new one.  Returns true iff folding
    makes any changes.
@@ -4371,6 +4384,30 @@ maybe_fold_or_comparisons (enum tree_code code1, tree op1a, tree op1b,
 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);
   switch (gimple_code (stmt))
     {
index 39c53ff3916f343130877d024a2baad0d15a85b8..0cd2899494ebaaaf69e1495b4bad886592d3e96d 100644 (file)
@@ -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,
                                       enum tree_code, tree, 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 (gimple, tree (*) (tree));
 extern tree fold_const_aggregate_ref_1 (tree, tree (*) (tree));
index e5e682629da1cccfdcc6502409c3d83c54d679fa..9f4d3811f2872ac06babd177ba53e3b6e395efb2 100644 (file)
@@ -1150,7 +1150,7 @@ substitute_and_fold_dom_walker::before_dom_children (basic_block bb)
 
       /* If we made a replacement, fold the statement.  */
       if (did_replace)
-       fold_stmt (&i);
+       fold_stmt (&i, follow_single_use_edges);
 
       /* Now cleanup.  */
       if (did_replace)