OSDN Git Service

2012-04-03 Richard Guenther <rguenther@suse.de>
authorrguenth <rguenth@138bc75d-0d04-0410-961f-82ee72b054a4>
Tue, 3 Apr 2012 11:55:24 +0000 (11:55 +0000)
committerrguenth <rguenth@138bc75d-0d04-0410-961f-82ee72b054a4>
Tue, 3 Apr 2012 11:55:24 +0000 (11:55 +0000)
Backport from mainline
2012-03-06  Richard Guenther  <rguenther@suse.de>

PR middle-end/52493
* tree-ssa-alias.c (ptr_derefs_may_alias_p): Robustify.

* gcc.dg/torture/pr52493.c: New testcase.

2012-03-23  Richard Guenther  <rguenther@suse.de>

PR tree-optimization/52678
* tree-vectorizer.h (struct _stmt_vec_info): Add
loop_phi_evolution_part member.
(STMT_VINFO_LOOP_PHI_EVOLUTION_PART): New define.
* tree-vect-loop.c (vect_analyze_scalar_cycles_1): Initialize
STMT_VINFO_LOOP_PHI_EVOLUTION_PART.
* tree-vect-loop-manip.c (vect_update_ivs_after_vectorizer):
Use the cached evolution part and the PHI nodes value from
the loop preheader edge instead of re-analyzing the evolution.

* gfortran.dg/pr52678.f: New testcase.

2012-03-26  Richard Guenther  <rguenther@suse.de>

PR tree-optimization/52701
* tree-vect-loop.c (vect_analyze_scalar_cycles_1): Always
compute and set the evolution part of PHI nodes.

* gfortran.dg/pr52701.f90: New testcase.

2012-03-30  Richard Guenther  <rguenther@suse.de>

PR tree-optimization/52754
* tree-ssa-forwprop.c (forward_propagate_addr_expr_1): Only
propagate arbitrary addresses into really plain dereferences.

* gcc.target/i386/pr52754.c: New testcase.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/branches/gcc-4_7-branch@186105 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/ChangeLog
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/torture/pr52493.c [new file with mode: 0644]
gcc/testsuite/gcc.target/i386/pr52754.c [new file with mode: 0644]
gcc/testsuite/gfortran.dg/pr52678.f [new file with mode: 0644]
gcc/testsuite/gfortran.dg/pr52701.f90 [new file with mode: 0644]
gcc/tree-ssa-alias.c
gcc/tree-ssa-forwprop.c
gcc/tree-vect-loop-manip.c
gcc/tree-vect-loop.c
gcc/tree-vectorizer.h

index b452488..18a2741 100644 (file)
@@ -1,3 +1,35 @@
+2012-04-03  Richard Guenther  <rguenther@suse.de>
+
+       Backport from mainline
+       2012-03-06  Richard Guenther  <rguenther@suse.de>
+
+       PR middle-end/52493
+       * tree-ssa-alias.c (ptr_derefs_may_alias_p): Robustify.
+
+       2012-03-23  Richard Guenther  <rguenther@suse.de>
+
+       PR tree-optimization/52678
+       * tree-vectorizer.h (struct _stmt_vec_info): Add
+       loop_phi_evolution_part member.
+       (STMT_VINFO_LOOP_PHI_EVOLUTION_PART): New define.
+       * tree-vect-loop.c (vect_analyze_scalar_cycles_1): Initialize
+       STMT_VINFO_LOOP_PHI_EVOLUTION_PART.
+       * tree-vect-loop-manip.c (vect_update_ivs_after_vectorizer):
+       Use the cached evolution part and the PHI nodes value from
+       the loop preheader edge instead of re-analyzing the evolution.
+
+       2012-03-26  Richard Guenther  <rguenther@suse.de>
+
+       PR tree-optimization/52701
+       * tree-vect-loop.c (vect_analyze_scalar_cycles_1): Always
+       compute and set the evolution part of PHI nodes.
+
+       2012-03-30  Richard Guenther  <rguenther@suse.de>
+
+       PR tree-optimization/52754
+       * tree-ssa-forwprop.c (forward_propagate_addr_expr_1): Only
+       propagate arbitrary addresses into really plain dereferences.
+
 2012-04-03  Jakub Jelinek  <jakub@redhat.com>
 
        PR tree-optimization/52835
index b0f25a6..d37fed4 100644 (file)
@@ -1,3 +1,26 @@
+2012-04-03  Richard Guenther  <rguenther@suse.de>
+
+       Backport from mainline
+       2012-03-06  Richard Guenther  <rguenther@suse.de>
+
+       PR middle-end/52493
+       * gcc.dg/torture/pr52493.c: New testcase.
+
+       2012-03-23  Richard Guenther  <rguenther@suse.de>
+
+       PR tree-optimization/52678
+       * gfortran.dg/pr52678.f: New testcase.
+
+       2012-03-26  Richard Guenther  <rguenther@suse.de>
+
+       PR tree-optimization/52701
+       * gfortran.dg/pr52701.f90: New testcase.
+
+       2012-03-30  Richard Guenther  <rguenther@suse.de>
+
+       PR tree-optimization/52754
+       * gcc.target/i386/pr52754.c: New testcase.
+
 2012-04-03  Jakub Jelinek  <jakub@redhat.com>
 
        PR tree-optimization/52835
diff --git a/gcc/testsuite/gcc.dg/torture/pr52493.c b/gcc/testsuite/gcc.dg/torture/pr52493.c
new file mode 100644 (file)
index 0000000..b04ac5c
--- /dev/null
@@ -0,0 +1,38 @@
+/* { dg-do compile } */
+
+struct Time {
+    long int sec;
+    long usec;
+};
+struct Flow {
+    unsigned short iif;
+    struct Time mtime;
+};
+struct NetFlow {
+    unsigned MaxFlows;
+    unsigned HeaderFields;
+    unsigned short *HeaderFormat;
+};
+static struct NetFlow *netflow;
+static struct Time start_time;
+static unsigned char emit_packet[1500];
+inline long int cmpmtime(struct Time *t1, struct Time *t2)
+{
+  return (t1->sec - t2->sec) * 1000 + (t1->usec - t2->usec) / 1000;
+}
+static void fill(int fields, unsigned short *format,
+                 struct Flow *flow, void *p)
+{
+  int i;
+  for (i = 0; i < fields; i++)
+    if (format[i] == 21)
+      {
+       unsigned int __v;
+       __v = cmpmtime(&flow->mtime, &start_time);
+       *((unsigned int *) p) = __v;
+      }
+}
+void emit_thread()
+{
+  fill(netflow->HeaderFields, netflow->HeaderFormat, 0, &emit_packet);
+}
diff --git a/gcc/testsuite/gcc.target/i386/pr52754.c b/gcc/testsuite/gcc.target/i386/pr52754.c
new file mode 100644 (file)
index 0000000..0f2dbff
--- /dev/null
@@ -0,0 +1,33 @@
+/* { dg-do run } */
+/* { dg-options "-O2 -fpredictive-commoning -msse2 -std=c99" } */
+/* { dg-require-effective-target sse2 } */
+
+#include <x86intrin.h>
+
+#include "isa-check.h"
+#include "sse-os-support.h"
+
+int main()
+{
+    const float mem[8] = { 0, 1, 2, 3, 4, 5, 6, 7 };
+
+    unsigned int indexes[8];
+    for (unsigned int i = 0; i < 8; ++i) indexes[i] = i;
+
+    check_isa ();
+
+    if (!sse_os_support ())
+      exit (0);
+
+    __m128 x = _mm_setr_ps(0, 1, 2, 3);
+    for (unsigned int i = 0; i + 4 < 6; ++i) {
+        const unsigned int *ii = &indexes[i];
+        const __m128 tmp = _mm_setr_ps(mem[ii[0]], mem[ii[1]], mem[ii[2]], mem[ii[3]]);
+        if (0xf != _mm_movemask_ps(_mm_cmpeq_ps(tmp, x))) {
+            __builtin_abort();
+        }
+        x = _mm_add_ps(x, _mm_set1_ps(1));
+    }
+
+    return 0;
+}
diff --git a/gcc/testsuite/gfortran.dg/pr52678.f b/gcc/testsuite/gfortran.dg/pr52678.f
new file mode 100644 (file)
index 0000000..8d0cd47
--- /dev/null
@@ -0,0 +1,18 @@
+! { dg-do compile }
+! { dg-options "-O -ftree-vectorize" }
+      SUBROUTINE OpenAD_set_ref_state(DRF, RHOFACF, RHOFACC)
+      real(8) DRF(1 : 15)
+      real(8) RHOFACF(1 : 16)
+      real(8) RHOFACC(1 : 15)
+      integer, dimension(:), allocatable :: oad_it
+      integer :: oad_it_ptr
+      INTEGER(8) OpenAD_Symbol_188
+      INTEGER(4) K
+          OpenAD_Symbol_188 = 0
+          DO K = 2, 15, 1
+            RHOFACF(INT(K)) = ((RHOFACC(K) * DRF(K + (-1)) + RHOFACC(K +
+     + (-1)) * DRF(K)) /(DRF(K) + DRF(K + (-1))))
+            OpenAD_Symbol_188 = (INT(OpenAD_Symbol_188) + INT(1))
+          END DO
+          oad_it(oad_it_ptr) = OpenAD_Symbol_188
+      end subroutine OpenAD_set_ref_state
diff --git a/gcc/testsuite/gfortran.dg/pr52701.f90 b/gcc/testsuite/gfortran.dg/pr52701.f90
new file mode 100644 (file)
index 0000000..5834318
--- /dev/null
@@ -0,0 +1,20 @@
+! { dg-do compile }
+! { dg-options "-O3" }
+function pr52701 (x, z, e, f, g, l)
+  integer a, b, c, d, e, f, g, i, j, l, pr52701
+  double precision x(e), z(e*e)
+  do i = l, f
+    do j = l, i
+      d = 0
+      do a = 1, g
+        c = a - g
+        do b = 1, g
+          d = d + 1
+          c = c + g
+          z(d) = z(d) / (x(i) + x(j) - x(f + a) - x(f + b))
+        end do
+      end do
+    end do
+  end do
+  pr52701 = c
+end
index 54badda..dd90432 100644 (file)
@@ -236,17 +236,6 @@ ptr_derefs_may_alias_p (tree ptr1, tree ptr2)
   STRIP_NOPS (ptr1);
   STRIP_NOPS (ptr2);
 
-  /* Anything we do not explicilty handle aliases.  */
-  if ((TREE_CODE (ptr1) != SSA_NAME
-       && TREE_CODE (ptr1) != ADDR_EXPR
-       && TREE_CODE (ptr1) != POINTER_PLUS_EXPR)
-      || (TREE_CODE (ptr2) != SSA_NAME
-         && TREE_CODE (ptr2) != ADDR_EXPR
-         && TREE_CODE (ptr2) != POINTER_PLUS_EXPR)
-      || !POINTER_TYPE_P (TREE_TYPE (ptr1))
-      || !POINTER_TYPE_P (TREE_TYPE (ptr2)))
-    return true;
-
   /* Disregard pointer offsetting.  */
   if (TREE_CODE (ptr1) == POINTER_PLUS_EXPR)
     {
@@ -275,7 +264,7 @@ ptr_derefs_may_alias_p (tree ptr1, tree ptr2)
       if (base
          && (TREE_CODE (base) == MEM_REF
              || TREE_CODE (base) == TARGET_MEM_REF))
-       ptr1 = TREE_OPERAND (base, 0);
+       return ptr_derefs_may_alias_p (TREE_OPERAND (base, 0), ptr2);
       else if (base
               && DECL_P (base))
        return ptr_deref_may_alias_decl_p (ptr2, base);
@@ -288,7 +277,7 @@ ptr_derefs_may_alias_p (tree ptr1, tree ptr2)
       if (base
          && (TREE_CODE (base) == MEM_REF
              || TREE_CODE (base) == TARGET_MEM_REF))
-       ptr2 = TREE_OPERAND (base, 0);
+       return ptr_derefs_may_alias_p (ptr1, TREE_OPERAND (base, 0));
       else if (base
               && DECL_P (base))
        return ptr_deref_may_alias_decl_p (ptr1, base);
@@ -296,6 +285,13 @@ ptr_derefs_may_alias_p (tree ptr1, tree ptr2)
        return true;
     }
 
+  /* From here we require SSA name pointers.  Anything else aliases.  */
+  if (TREE_CODE (ptr1) != SSA_NAME
+      || TREE_CODE (ptr2) != SSA_NAME
+      || !POINTER_TYPE_P (TREE_TYPE (ptr1))
+      || !POINTER_TYPE_P (TREE_TYPE (ptr2)))
+    return true;
+
   /* We may end up with two empty points-to solutions for two same pointers.
      In this case we still want to say both pointers alias, so shortcut
      that here.  */
index 20821ef..308a579 100644 (file)
@@ -905,6 +905,7 @@ forward_propagate_addr_expr_1 (tree name, tree def_rhs,
          that of the pointed-to type of the address we can put the
         dereferenced address on the LHS preserving the original alias-type.  */
       else if (gimple_assign_lhs (use_stmt) == lhs
+              && integer_zerop (TREE_OPERAND (lhs, 1))
               && useless_type_conversion_p
                    (TREE_TYPE (TREE_OPERAND (def_rhs, 0)),
                     TREE_TYPE (gimple_assign_rhs1 (use_stmt))))
@@ -917,9 +918,8 @@ forward_propagate_addr_expr_1 (tree name, tree def_rhs,
          if (TREE_CODE (*def_rhs_basep) == MEM_REF)
            {
              new_base = TREE_OPERAND (*def_rhs_basep, 0);
-             new_offset
-               = int_const_binop (PLUS_EXPR, TREE_OPERAND (lhs, 1),
-                                  TREE_OPERAND (*def_rhs_basep, 1));
+             new_offset = fold_convert (TREE_TYPE (TREE_OPERAND (lhs, 1)),
+                                        TREE_OPERAND (*def_rhs_basep, 1));
            }
          else
            {
@@ -989,6 +989,7 @@ forward_propagate_addr_expr_1 (tree name, tree def_rhs,
          that of the pointed-to type of the address we can put the
         dereferenced address on the RHS preserving the original alias-type.  */
       else if (gimple_assign_rhs1 (use_stmt) == rhs
+              && integer_zerop (TREE_OPERAND (rhs, 1))
               && useless_type_conversion_p
                    (TREE_TYPE (gimple_assign_lhs (use_stmt)),
                     TREE_TYPE (TREE_OPERAND (def_rhs, 0))))
@@ -1001,9 +1002,8 @@ forward_propagate_addr_expr_1 (tree name, tree def_rhs,
          if (TREE_CODE (*def_rhs_basep) == MEM_REF)
            {
              new_base = TREE_OPERAND (*def_rhs_basep, 0);
-             new_offset
-               = int_const_binop (PLUS_EXPR, TREE_OPERAND (rhs, 1),
-                                  TREE_OPERAND (*def_rhs_basep, 1));
+             new_offset = fold_convert (TREE_TYPE (TREE_OPERAND (rhs, 1)),
+                                        TREE_OPERAND (*def_rhs_basep, 1));
            }
          else
            {
index 70c4f89..b7db6c2 100644 (file)
@@ -1797,13 +1797,12 @@ vect_update_ivs_after_vectorizer (loop_vec_info loop_vinfo, tree niters,
        !gsi_end_p (gsi) && !gsi_end_p (gsi1);
        gsi_next (&gsi), gsi_next (&gsi1))
     {
-      tree access_fn = NULL;
-      tree evolution_part;
       tree init_expr;
       tree step_expr, off;
       tree type;
       tree var, ni, ni_name;
       gimple_stmt_iterator last_gsi;
+      stmt_vec_info stmt_info;
 
       phi = gsi_stmt (gsi);
       phi1 = gsi_stmt (gsi1);
@@ -1822,45 +1821,34 @@ vect_update_ivs_after_vectorizer (loop_vec_info loop_vinfo, tree niters,
        }
 
       /* Skip reduction phis.  */
-      if (STMT_VINFO_DEF_TYPE (vinfo_for_stmt (phi)) == vect_reduction_def)
+      stmt_info = vinfo_for_stmt (phi);
+      if (STMT_VINFO_DEF_TYPE (stmt_info) == vect_reduction_def)
         {
           if (vect_print_dump_info (REPORT_DETAILS))
             fprintf (vect_dump, "reduc phi. skip.");
           continue;
         }
 
-      access_fn = analyze_scalar_evolution (loop, PHI_RESULT (phi));
-      gcc_assert (access_fn);
-      /* We can end up with an access_fn like
-           (short int) {(short unsigned int) i_49, +, 1}_1
-        for further analysis we need to strip the outer cast but we
-        need to preserve the original type.  */
-      type = TREE_TYPE (access_fn);
-      STRIP_NOPS (access_fn);
-      evolution_part =
-        unshare_expr (evolution_part_in_loop_num (access_fn, loop->num));
-      gcc_assert (evolution_part != NULL_TREE);
+      type = TREE_TYPE (gimple_phi_result (phi));
+      step_expr = STMT_VINFO_LOOP_PHI_EVOLUTION_PART (stmt_info);
+      step_expr = unshare_expr (step_expr);
 
       /* FORNOW: We do not support IVs whose evolution function is a polynomial
          of degree >= 2 or exponential.  */
-      gcc_assert (!tree_is_chrec (evolution_part));
+      gcc_assert (!tree_is_chrec (step_expr));
 
-      step_expr = evolution_part;
-      init_expr = unshare_expr (initial_condition_in_loop_num (access_fn,
-                                                              loop->num));
-      init_expr = fold_convert (type, init_expr);
+      init_expr = PHI_ARG_DEF_FROM_EDGE (phi, loop_preheader_edge (loop));
 
       off = fold_build2 (MULT_EXPR, TREE_TYPE (step_expr),
                         fold_convert (TREE_TYPE (step_expr), niters),
                         step_expr);
-      if (POINTER_TYPE_P (TREE_TYPE (init_expr)))
+      if (POINTER_TYPE_P (type))
        ni = fold_build_pointer_plus (init_expr, off);
       else
-       ni = fold_build2 (PLUS_EXPR, TREE_TYPE (init_expr),
-                         init_expr,
-                         fold_convert (TREE_TYPE (init_expr), off));
+       ni = fold_build2 (PLUS_EXPR, type,
+                         init_expr, fold_convert (type, off));
 
-      var = create_tmp_var (TREE_TYPE (init_expr), "tmp");
+      var = create_tmp_var (type, "tmp");
       add_referenced_var (var);
 
       last_gsi = gsi_last_bb (exit_bb);
index 7f42a7d..1d0818c 100644 (file)
@@ -565,11 +565,15 @@ vect_analyze_scalar_cycles_1 (loop_vec_info loop_vinfo, struct loop *loop)
       /* Analyze the evolution function.  */
       access_fn = analyze_scalar_evolution (loop, def);
       if (access_fn)
-       STRIP_NOPS (access_fn);
-      if (access_fn && vect_print_dump_info (REPORT_DETAILS))
        {
-         fprintf (vect_dump, "Access function of PHI: ");
-         print_generic_expr (vect_dump, access_fn, TDF_SLIM);
+         STRIP_NOPS (access_fn);
+         if (vect_print_dump_info (REPORT_DETAILS))
+           {
+             fprintf (vect_dump, "Access function of PHI: ");
+             print_generic_expr (vect_dump, access_fn, TDF_SLIM);
+           }
+         STMT_VINFO_LOOP_PHI_EVOLUTION_PART (stmt_vinfo)
+           = evolution_part_in_loop_num (access_fn, loop->num);
        }
 
       if (!access_fn
@@ -579,6 +583,8 @@ vect_analyze_scalar_cycles_1 (loop_vec_info loop_vinfo, struct loop *loop)
          continue;
        }
 
+      gcc_assert (STMT_VINFO_LOOP_PHI_EVOLUTION_PART (stmt_vinfo) != NULL_TREE);
+
       if (vect_print_dump_info (REPORT_DETAILS))
        fprintf (vect_dump, "Detected induction.");
       STMT_VINFO_DEF_TYPE (stmt_vinfo) = vect_induction_def;
index 35420ba..aa58f60 100644 (file)
@@ -476,6 +476,13 @@ typedef struct _stmt_vec_info {
   tree dr_step;
   tree dr_aligned_to;
 
+  /* For loop PHI nodes, the evolution part of it.  This makes sure
+     this information is still available in vect_update_ivs_after_vectorizer
+     where we may not be able to re-analyze the PHI nodes evolution as
+     peeling for the prologue loop can make it unanalyzable.  The evolution
+     part is still correct though.  */
+  tree loop_phi_evolution_part;
+
   /* Used for various bookkeeping purposes, generally holding a pointer to
      some other stmt S that is in some way "related" to this stmt.
      Current use of this field is:
@@ -572,6 +579,7 @@ typedef struct _stmt_vec_info {
 #define STMT_VINFO_GROUP_SAME_DR_STMT(S)   (S)->same_dr_stmt
 #define STMT_VINFO_GROUP_READ_WRITE_DEPENDENCE(S)  (S)->read_write_dep
 #define STMT_VINFO_STRIDED_ACCESS(S)      ((S)->first_element != NULL && (S)->data_ref_info)
+#define STMT_VINFO_LOOP_PHI_EVOLUTION_PART(S) (S)->loop_phi_evolution_part
 
 #define GROUP_FIRST_ELEMENT(S)          (S)->first_element
 #define GROUP_NEXT_ELEMENT(S)           (S)->next_element