2012-07-04 Richard Guenther <rguenther@suse.de>
authorrguenth <rguenth@138bc75d-0d04-0410-961f-82ee72b054a4>
Wed, 4 Jul 2012 12:10:40 +0000 (12:10 +0000)
committerrguenth <rguenth@138bc75d-0d04-0410-961f-82ee72b054a4>
Wed, 4 Jul 2012 12:10:40 +0000 (12:10 +0000)
PR tree-optimization/53844
* tree-ssa-dse.c (dse_possible_dead_store_p): Properly handle
the loop virtual PHI.

* g++.dg/tree-ssa/pr53844.C: New testcase.

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

gcc/ChangeLog
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/tree-ssa/pr53844.C [new file with mode: 0644]
gcc/tree-ssa-dse.c

index 27c8cfc..c33c5a5 100644 (file)
@@ -1,5 +1,11 @@
 2012-07-04  Richard Guenther  <rguenther@suse.de>
 
+       PR tree-optimization/53844
+       * tree-ssa-dse.c (dse_possible_dead_store_p): Properly handle
+       the loop virtual PHI.
+
+2012-07-04  Richard Guenther  <rguenther@suse.de>
+
        PR tree-optimization/53849
        * tree-cfg.c (move_stmt_op): Only call add_referenced_var
        for duplicated locals.  Use add_referenced_var_1 to avoid
index 884f66b..3d1fda9 100644 (file)
@@ -1,5 +1,10 @@
 2012-07-04  Richard Guenther  <rguenther@suse.de>
 
+       PR tree-optimization/53844
+       * g++.dg/tree-ssa/pr53844.C: New testcase.
+
+2012-07-04  Richard Guenther  <rguenther@suse.de>
+
        PR tree-optimization/53849
        * gcc.dg/pr53849.c: New testcase.
 
diff --git a/gcc/testsuite/g++.dg/tree-ssa/pr53844.C b/gcc/testsuite/g++.dg/tree-ssa/pr53844.C
new file mode 100644 (file)
index 0000000..0be29d8
--- /dev/null
@@ -0,0 +1,78 @@
+// { dg-do compile }
+// { dg-options "-O2 -fdump-tree-optimized-vops" }
+
+struct VBase;
+
+//Very minimal numeric vector class where Base provides the policy
+template<typename Base=VBase>
+struct Vector : public Base{
+       
+       inline Vector(const Base& b)
+       :Base(b)
+       {
+       }
+
+       //Assignment from any other sort of Vector
+       template<typename Base2>
+       void operator= (const Vector<Base2>& from)
+       {
+               for(int i=0; i<100; i++){
+                       (*this)[i]=from[i];
+               }
+       }
+};
+
+
+//Base class to represent pointer as a Vector
+struct VBase{
+       double * const my_data;
+
+       double& operator[](int i) {
+               return my_data[i];
+       }
+
+       const double& operator[](int i) const {
+               return my_data[i];
+       }
+};
+
+//Base class providing very minimalistic expression template
+template<class B2> struct ScalarMulExpr
+{
+       const int& mul;
+       const Vector<B2>& vec;
+
+       int size() const
+       {
+               return vec.size();
+       }
+
+       double operator[](int i) const
+       {
+               return vec[i]*mul;
+       }
+
+       ScalarMulExpr(const Vector<B2>& vec_, const int& m)
+       :mul(m),vec(vec_)
+       {
+       }
+};
+
+//Allow vector to be multiplied by a scalar
+template<class B2>
+Vector<ScalarMulExpr<B2> > operator*(const Vector<B2>& lhs, const int& rhs)
+{
+       return ScalarMulExpr<B2>(lhs, rhs);
+}
+
+//Test function producing suboptimal asm code
+void test(const Vector<>& in, Vector<>& out, int i)
+{
+       out=in*1*1*1*1*1*1*1*1*1*1*1;
+}
+
+// There should be a single store remaining, inside the loops.  All
+// dead stores to unused temporaries should have been removed.
+
+// { dg-final { scan-tree-dump-times "VDEF" 1 "optimized" } }
+// { dg-final { cleanup-tree-dump "optimized" } }
index 5fdba8c..04cc6ad 100644 (file)
@@ -94,7 +94,7 @@ dse_possible_dead_store_p (gimple stmt, gimple *use_stmt)
   temp = stmt;
   do
     {
-      gimple use_stmt;
+      gimple use_stmt, defvar_def;
       imm_use_iterator ui;
       bool fail = false;
       tree defvar;
@@ -108,6 +108,7 @@ dse_possible_dead_store_p (gimple stmt, gimple *use_stmt)
        defvar = PHI_RESULT (temp);
       else
        defvar = gimple_vdef (temp);
+      defvar_def = temp;
       temp = NULL;
       FOR_EACH_IMM_USE_STMT (use_stmt, ui, defvar)
        {
@@ -139,7 +140,14 @@ dse_possible_dead_store_p (gimple stmt, gimple *use_stmt)
                  fail = true;
                  BREAK_FROM_IMM_USE_STMT (ui);
                }
-             temp = use_stmt;
+             /* Do not consider the PHI as use if it dominates the 
+                stmt defining the virtual operand we are processing,
+                we have processed it already in this case.  */
+             if (gimple_bb (defvar_def) != gimple_bb (use_stmt)
+                 && !dominated_by_p (CDI_DOMINATORS,
+                                     gimple_bb (defvar_def),
+                                     gimple_bb (use_stmt)))
+               temp = use_stmt;
            }
          /* If the statement is a use the store is not dead.  */
          else if (ref_maybe_used_by_stmt_p (use_stmt,