OSDN Git Service

* Makefile.in (tree-chrec.o): Depends on SCEV_H.
authorspop <spop@138bc75d-0d04-0410-961f-82ee72b054a4>
Fri, 9 Sep 2005 10:56:41 +0000 (10:56 +0000)
committerspop <spop@138bc75d-0d04-0410-961f-82ee72b054a4>
Fri, 9 Sep 2005 10:56:41 +0000 (10:56 +0000)
* tree-chrec.c: Include tree-scalar-evolution.h.
(chrec_convert): Instantiate the base and step before calling
scev_probably_wraps_p that would fail on parametric evolutions.
Collect all the fails into a single section failed_to_convert,
print a diagnostic, and return chrec_dont_know instead of calling
fold_convert.
* tree-scalar-evolution.c (loop_closed_phi_def): New.
(instantiate_parameters_1): Avoid instantiation of loop closed ssa
phi nodes.
(scev_const_prop): Don't replace the definition of a loop closed ssa
phi node by itself, or by another loop closed ssa phi node.
* tree-ssa-loop-niter.c (scev_probably_wraps_p, convert_step): Check
that base and step are defined.

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

gcc/ChangeLog
gcc/Makefile.in
gcc/tree-chrec.c
gcc/tree-scalar-evolution.c
gcc/tree-ssa-loop-niter.c

index 7ec894c..e9295e6 100644 (file)
@@ -1,3 +1,20 @@
+2005-09-09  Sebastian Pop  <pop@cri.ensmp.fr>
+
+       * Makefile.in (tree-chrec.o): Depends on SCEV_H.
+       * tree-chrec.c: Include tree-scalar-evolution.h.
+       (chrec_convert): Instantiate the base and step before calling
+       scev_probably_wraps_p that would fail on parametric evolutions.
+       Collect all the fails into a single section failed_to_convert,
+       print a diagnostic, and return chrec_dont_know instead of calling
+       fold_convert.
+       * tree-scalar-evolution.c (loop_closed_phi_def): New.
+       (instantiate_parameters_1): Avoid instantiation of loop closed ssa
+       phi nodes.
+       (scev_const_prop): Don't replace the definition of a loop closed ssa
+       phi node by itself, or by another loop closed ssa phi node.
+       * tree-ssa-loop-niter.c (scev_probably_wraps_p, convert_step): Check
+       that base and step are defined.
+
 2005-09-09  Richard Guenther  <rguenther@suse.de>
 
        PR c++/23624
index 69e482d..3ed7186 100644 (file)
@@ -1944,7 +1944,7 @@ tree-browser.o : tree-browser.c tree-browser.def $(CONFIG_H) $(SYSTEM_H) \
    $(TREE_H) tree-inline.h $(DIAGNOSTIC_H) $(HASHTAB_H) \
    $(TM_H) coretypes.h
 tree-chrec.o: tree-chrec.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) \
-   $(GGC_H) $(TREE_H) real.h tree-chrec.h tree-pass.h $(PARAMS_H) \
+   $(GGC_H) $(TREE_H) real.h $(SCEV_H) tree-pass.h $(PARAMS_H) \
    $(DIAGNOSTIC_H) $(VARRAY_H) $(CFGLOOP_H) $(TREE_FLOW_H)
 tree-scalar-evolution.o: tree-scalar-evolution.c $(CONFIG_H) $(SYSTEM_H) \
    coretypes.h $(TM_H) $(GGC_H) $(TREE_H) real.h $(RTL_H) \
index 8dae916..3324c8b 100644 (file)
@@ -38,6 +38,7 @@ Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
 #include "tree-chrec.h"
 #include "tree-pass.h"
 #include "params.h"
+#include "tree-scalar-evolution.h"
 
 \f
 
@@ -1120,8 +1121,12 @@ chrec_convert (tree type, tree chrec, tree at_stmt)
 
   if (evolution_function_is_affine_p (chrec))
     {
-      tree step;
+      tree base, step;
       bool dummy;
+      struct loop *loop = current_loops->parray[CHREC_VARIABLE (chrec)];
+
+      base = instantiate_parameters (loop, CHREC_LEFT (chrec));
+      step = instantiate_parameters (loop, CHREC_RIGHT (chrec));
 
       /* Avoid conversion of (signed char) {(uchar)1, +, (uchar)1}_x
         when it is not possible to prove that the scev does not wrap.
@@ -1130,16 +1135,32 @@ chrec_convert (tree type, tree chrec, tree at_stmt)
         1, 2, ..., 127, -128, ...  The result should not be
         {(schar)1, +, (schar)1}_x, but instead, we should keep the
         conversion: (schar) {(uchar)1, +, (uchar)1}_x.  */
-      if (scev_probably_wraps_p (type, CHREC_LEFT (chrec), CHREC_RIGHT (chrec),
-                                at_stmt,
-                                current_loops->parray[CHREC_VARIABLE (chrec)],
+      if (scev_probably_wraps_p (type, base, step, at_stmt, loop,
                                 &dummy, &dummy))
-       return fold_convert (type, chrec);
+       goto failed_to_convert;
 
-      step = convert_step (current_loops->parray[CHREC_VARIABLE (chrec)], type,
-                          CHREC_LEFT (chrec), CHREC_RIGHT (chrec), at_stmt);
+      step = convert_step (loop, type, base, step, at_stmt);
       if (!step)
-       return fold_convert (type, chrec);
+       {
+       failed_to_convert:;
+         if (dump_file && (dump_flags & TDF_DETAILS))
+           {
+             fprintf (dump_file, "(failed conversion:");
+             fprintf (dump_file, "\n  type: ");
+             print_generic_expr (dump_file, type, 0);
+             fprintf (dump_file, "\n  base: ");
+             print_generic_expr (dump_file, base, 0);
+             fprintf (dump_file, "\n  step: ");
+             print_generic_expr (dump_file, step, 0);
+             fprintf (dump_file, "\n  estimated_nb_iterations: ");
+             print_generic_expr (dump_file, loop->estimated_nb_iterations, 0);
+             fprintf (dump_file, "\n)\n");
+           }
+
+         /* Directly convert to "don't know": no worth dealing with
+            difficult cases.  */
+         return chrec_dont_know;
+       }
 
       return build_polynomial_chrec (CHREC_VARIABLE (chrec),
                                     chrec_convert (type, CHREC_LEFT (chrec),
index e749047..235edcd 100644 (file)
@@ -1928,6 +1928,32 @@ set_instantiated_value (htab_t cache, tree version, tree val)
   info->chrec = val;
 }
 
+/* Return the closed_loop_phi node for VAR.  If there is none, return
+   NULL_TREE.  */
+
+static tree
+loop_closed_phi_def (tree var)
+{
+  struct loop *loop;
+  edge exit;
+  tree phi;
+
+  if (var == NULL_TREE
+      || TREE_CODE (var) != SSA_NAME)
+    return NULL_TREE;
+
+  loop = loop_containing_stmt (SSA_NAME_DEF_STMT (var));
+  exit = loop->single_exit;
+  if (!exit)
+    return NULL_TREE;
+
+  for (phi = phi_nodes (exit->dest); phi; phi = PHI_CHAIN (phi))
+    if (PHI_ARG_DEF_FROM_EDGE (phi, exit) == var)
+      return PHI_RESULT (phi);
+
+  return NULL_TREE;
+}
+
 /* Analyze all the parameters of the chrec that were left under a symbolic form,
    with respect to LOOP.  CHREC is the chrec to instantiate.  If
    ALLOW_SUPERLOOP_CHRECS is true, replacing loop invariants with
@@ -1993,9 +2019,26 @@ instantiate_parameters_1 (struct loop *loop, tree chrec,
         result again.  */
       bitmap_set_bit (already_instantiated, SSA_NAME_VERSION (chrec));
       res = analyze_scalar_evolution (def_loop, chrec);
-      if (res != chrec_dont_know)
+
+      /* Don't instantiate loop-closed-ssa phi nodes.  */
+      if (TREE_CODE (res) == SSA_NAME
+         && (loop_containing_stmt (SSA_NAME_DEF_STMT (res)) == NULL
+             || (loop_containing_stmt (SSA_NAME_DEF_STMT (res))->depth
+                 > def_loop->depth)))
+       {
+         if (res == chrec)
+           res = loop_closed_phi_def (chrec);
+         else
+           res = chrec;
+
+         if (res == NULL_TREE)
+           res = chrec_dont_know;
+       }
+
+      else if (res != chrec_dont_know)
        res = instantiate_parameters_1 (loop, res, allow_superloop_chrecs,
                                        cache);
+
       bitmap_clear_bit (already_instantiated, SSA_NAME_VERSION (chrec));
 
       /* Store the correct value to the cache.  */
@@ -2652,7 +2695,8 @@ scev_const_prop (void)
            continue;
 
          /* Replace the uses of the name.  */
-         replace_uses_by (name, ev);
+         if (name != ev)
+           replace_uses_by (name, ev);
 
          if (!ssa_names_to_remove)
            ssa_names_to_remove = BITMAP_ALLOC (NULL);
@@ -2712,7 +2756,13 @@ scev_const_prop (void)
 
          def = analyze_scalar_evolution_in_loop (ex_loop, ex_loop, def);
          if (!tree_does_not_contain_chrecs (def)
-             || chrec_contains_symbols_defined_in_loop (def, loop->num))
+             || chrec_contains_symbols_defined_in_loop (def, loop->num)
+             || def == PHI_RESULT (phi)
+             || (TREE_CODE (def) == SSA_NAME
+                 && loop_containing_stmt (SSA_NAME_DEF_STMT (def))
+                 && loop_containing_stmt (phi)
+                 && loop_containing_stmt (SSA_NAME_DEF_STMT (def))
+                 == loop_containing_stmt (phi)))
            continue;
 
          /* If computing the expression is expensive, let it remain in
index 3ee27f4..b866418 100644 (file)
@@ -1857,7 +1857,9 @@ scev_probably_wraps_p (tree type, tree base, tree step,
        }
     }
 
-  if (TREE_CODE (base) == REAL_CST
+  if (chrec_contains_undetermined (base)
+      || chrec_contains_undetermined (step)
+      || TREE_CODE (base) == REAL_CST
       || TREE_CODE (step) == REAL_CST)
     {
       *unknown_max = true;
@@ -1978,7 +1980,13 @@ tree
 convert_step (struct loop *loop, tree new_type, tree base, tree step,
              tree at_stmt)
 {
-  tree base_type = TREE_TYPE (base);
+  tree base_type;
+
+  if (chrec_contains_undetermined (base)
+      || chrec_contains_undetermined (step))
+    return NULL_TREE;
+
+  base_type = TREE_TYPE (base);
 
   /* When not using wrapping arithmetic, signed types don't wrap.  */
   if (!flag_wrapv && !TYPE_UNSIGNED (base_type))