2008-04-30 Richard Guenther <rguenther@suse.de>
authorrguenth <rguenth@138bc75d-0d04-0410-961f-82ee72b054a4>
Wed, 30 Apr 2008 19:05:12 +0000 (19:05 +0000)
committerrguenth <rguenth@138bc75d-0d04-0410-961f-82ee72b054a4>
Wed, 30 Apr 2008 19:05:12 +0000 (19:05 +0000)
PR tree-optimization/21636
* tree-ssa-ccp.c (ccp_fold): Handle &p->x with p being a
constant address.
(evaluate_stmt): Print the likely value.
(ccp_visit_stmt): Avoid excessive vertical spacing.

* gcc.dg/tree-ssa/ssa-ccp-19.c: New testcase.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@134834 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/ChangeLog
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/tree-ssa/ssa-ccp-19.c [new file with mode: 0644]
gcc/tree-ssa-ccp.c

index 043723e..9df335e 100644 (file)
@@ -1,3 +1,11 @@
+2008-04-30  Richard Guenther  <rguenther@suse.de>
+
+       PR tree-optimization/21636
+       * tree-ssa-ccp.c (ccp_fold): Handle &p->x with p being a
+       constant address.
+       (evaluate_stmt): Print the likely value.
+       (ccp_visit_stmt): Avoid excessive vertical spacing.
+
 2008-04-30  Rafael Espindola  <espindola@google.com>
 
        * builtins.c (fold_call_expr): Return realret.
index 53978cc..410b720 100644 (file)
@@ -1,3 +1,8 @@
+2008-04-30  Richard Guenther  <rguenther@suse.de>
+
+       PR tree-optimization/21636
+       * gcc.dg/tree-ssa/ssa-ccp-19.c: New testcase.
+
 2008-04-30  Thomas Koenig  <tkoenig@gcc.gnu.org>
 
        PR libfortran/35993
diff --git a/gcc/testsuite/gcc.dg/tree-ssa/ssa-ccp-19.c b/gcc/testsuite/gcc.dg/tree-ssa/ssa-ccp-19.c
new file mode 100644 (file)
index 0000000..ab41822
--- /dev/null
@@ -0,0 +1,16 @@
+/* { dg-do compile } */
+/* { dg-options "-O -fdump-tree-ccp1" } */
+
+struct f { int i; };
+int g()
+{
+  struct f a, *a1;
+  int *i;
+  a.i = 1;
+  a1 = &a;
+  i = &a1->i;
+  return *i;  /* This should be turned into a.i */
+}
+
+/* { dg-final { scan-tree-dump "= a.i;" "ccp1" } } */
+/* { dg-final { cleanup-tree-dump "ccp1" } } */
index 6907f0b..c6c7a88 100644 (file)
@@ -975,6 +975,38 @@ ccp_fold (tree stmt)
   else if (kind == tcc_reference)
     return fold_const_aggregate_ref (rhs);
 
+  /* Handle propagating invariant addresses into address operations.
+     The folding we do here matches that in tree-ssa-forwprop.c.  */
+  else if (code == ADDR_EXPR)
+    {
+      tree *base;
+      base = &TREE_OPERAND (rhs, 0);
+      while (handled_component_p (*base))
+       base = &TREE_OPERAND (*base, 0);
+      if (TREE_CODE (*base) == INDIRECT_REF
+         && TREE_CODE (TREE_OPERAND (*base, 0)) == SSA_NAME)
+       {
+         prop_value_t *val = get_value (TREE_OPERAND (*base, 0));
+         if (val->lattice_val == CONSTANT
+             && TREE_CODE (val->value) == ADDR_EXPR
+             && useless_type_conversion_p (TREE_TYPE (TREE_OPERAND (*base, 0)),
+                                           TREE_TYPE (val->value))
+             && useless_type_conversion_p (TREE_TYPE (*base),
+                                           TREE_TYPE (TREE_OPERAND (val->value, 0))))
+           {
+             /* We need to return a new tree, not modify the IL or share
+                parts of it.  So play some tricks to avoid manually
+                building it.  */
+             tree ret, save = *base;
+             *base = TREE_OPERAND (val->value, 0);
+             ret = unshare_expr (rhs);
+             recompute_tree_invariant_for_addr_expr (ret);
+             *base = save;
+             return ret;
+           }
+       }
+    }
+
   /* We may be able to fold away calls to builtin functions if their
      arguments are constants.  */
   else if (code == CALL_EXPR
@@ -1210,6 +1242,25 @@ evaluate_stmt (tree stmt)
 
   fold_undefer_overflow_warnings (is_constant, stmt, 0);
 
+  if (dump_file && (dump_flags & TDF_DETAILS))
+    {
+      fprintf (dump_file, "which is likely ");
+      switch (likelyvalue)
+       {
+       case CONSTANT:
+         fprintf (dump_file, "CONSTANT");
+         break;
+       case UNDEFINED:
+         fprintf (dump_file, "UNDEFINED");
+         break;
+       case VARYING:
+         fprintf (dump_file, "VARYING");
+         break;
+       default:;
+       }
+      fprintf (dump_file, "\n");
+    }
+
   if (is_constant)
     {
       /* The statement produced a constant value.  */
@@ -1378,7 +1429,6 @@ ccp_visit_stmt (tree stmt, edge *taken_edge_p, tree *output_p)
     {
       fprintf (dump_file, "\nVisiting statement:\n");
       print_generic_stmt (dump_file, stmt, dump_flags);
-      fprintf (dump_file, "\n");
     }
 
   if (TREE_CODE (stmt) == GIMPLE_MODIFY_STMT)