This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PATCH] Fix BB vectorization cost model wrt scalar uses


The patch breaks compiling Open MPI with default compilation flags (for that file: -O3 -fno-strict-aliasing):

../../../../../ompi/mca/btl/tcp/btl_tcp_frag.c:100:6: internal compiler error: in operator[], at vec.h:815
 bool mca_btl_tcp_frag_send(mca_btl_tcp_frag_t* frag, int sd)


See PR 57453 for a reduced test case.

Tobias


Richard Biener wrote:
This properly accounts for remaining unvectorized scalar uses of
stmts we vectorize during BB vectorization.  Previously we
happily retained all of the scalar loads and computations, just
optimizing the final stores, alongside the vectorized code.
To account for scalar uses properly the following patch simply
makes the scalar cost cheaper when stmts have to be kept live.

Support for "vectorizing" those by using vector extracts is
currently missing.  It happens quite frequently that CSE
looks through the final scalar global store, re-using the stored
value and thus keeping the whole computation sequence live.

Bootstrap / regtest running on x86_64-unknown-linux-gnu.

Richard.

2013-05-28  Richard Biener  <rguenther@suse.de>

	* tree-vect-slp.c (vect_bb_slp_scalar_cost): New function
	computing scalar cost offsetted by stmts that are kept live
	by scalar uses.
	(vect_bb_vectorization_profitable_p): Use vect_bb_slp_scalar_cost
	for computation of scalar cost.

	* gcc.dg/vect/bb-slp-32.c: New testcase.

Index: gcc/tree-vect-slp.c
===================================================================
*** gcc/tree-vect-slp.c	(revision 199375)
--- gcc/tree-vect-slp.c	(working copy)
*************** vect_slp_analyze_operations (bb_vec_info
*** 1898,1903 ****
--- 1898,1966 ----
     return true;
   }

+
+ /* Compute the scalar cost of the SLP node NODE and its children
+    and return it.  Do not account defs that are marked in LIFE and
+    update LIFE according to uses of NODE.  */
+
+ static unsigned
+ vect_bb_slp_scalar_cost (slp_tree node, vec<bool, va_stack> life)
+ {
+   unsigned scalar_cost = 0;
+   unsigned i;
+   gimple stmt;
+   slp_tree child;
+
+   FOR_EACH_VEC_ELT (SLP_TREE_SCALAR_STMTS (node), i, stmt)
+     {
+       unsigned stmt_cost;
+       ssa_op_iter op_iter;
+       def_operand_p def_p;
+       stmt_vec_info stmt_info;
+
+       if (life[i])
+ 	continue;
+
+       /* If there is a non-vectorized use of the defs then the scalar
+          stmt is kept live in which case we do not account it or any
+ 	 required defs in the SLP children in the scalar cost.  This
+ 	 way we make the vectorization more costly when compared to
+ 	 the scalar cost.  */
+       FOR_EACH_SSA_DEF_OPERAND (def_p, stmt, op_iter, SSA_OP_DEF)
+ 	{
+ 	  imm_use_iterator use_iter;
+ 	  gimple use_stmt;
+ 	  FOR_EACH_IMM_USE_STMT (use_stmt, use_iter, DEF_FROM_PTR (def_p))
+ 	    if (!vinfo_for_stmt (use_stmt)
+ 		|| !STMT_VINFO_VECTORIZABLE (vinfo_for_stmt (use_stmt)))
+ 	      {
+ 		life[i] = true;
+ 		BREAK_FROM_IMM_USE_STMT (use_iter);
+ 	      }
+ 	}
+       if (life[i])
+ 	continue;
+
+       stmt_info = vinfo_for_stmt (stmt);
+       if (STMT_VINFO_DATA_REF (stmt_info))
+         {
+           if (DR_IS_READ (STMT_VINFO_DATA_REF (stmt_info)))
+             stmt_cost = vect_get_stmt_cost (scalar_load);
+           else
+             stmt_cost = vect_get_stmt_cost (scalar_store);
+         }
+       else
+         stmt_cost = vect_get_stmt_cost (scalar_stmt);
+
+       scalar_cost += stmt_cost;
+     }
+
+   FOR_EACH_VEC_ELT (SLP_TREE_CHILDREN (node), i, child)
+     scalar_cost += vect_bb_slp_scalar_cost (child, life);
+
+   return scalar_cost;
+ }
+
   /* Check if vectorization of the basic block is profitable.  */

   static bool
*************** vect_bb_vectorization_profitable_p (bb_v
*** 1931,1956 ****
       }

     /* Calculate scalar cost.  */
!   for (si = gsi_start_bb (bb); !gsi_end_p (si); gsi_next (&si))
       {
!       stmt = gsi_stmt (si);
!       stmt_info = vinfo_for_stmt (stmt);
!
!       if (!stmt_info || !STMT_VINFO_VECTORIZABLE (stmt_info)
!           || !PURE_SLP_STMT (stmt_info))
!         continue;
!
!       if (STMT_VINFO_DATA_REF (stmt_info))
!         {
!           if (DR_IS_READ (STMT_VINFO_DATA_REF (stmt_info)))
!             stmt_cost = vect_get_stmt_cost (scalar_load);
!           else
!             stmt_cost = vect_get_stmt_cost (scalar_store);
!         }
!       else
!         stmt_cost = vect_get_stmt_cost (scalar_stmt);
!
!       scalar_cost += stmt_cost;
       }

     /* Complete the target-specific cost calculation.  */
--- 1994,2007 ----
       }

     /* Calculate scalar cost.  */
!   FOR_EACH_VEC_ELT (slp_instances, i, instance)
       {
!       vec<bool, va_stack> life;
!       vec_stack_alloc (bool, life, SLP_INSTANCE_GROUP_SIZE (instance));
!       life.quick_grow_cleared (SLP_INSTANCE_GROUP_SIZE (instance));
!       scalar_cost += vect_bb_slp_scalar_cost (SLP_INSTANCE_TREE (instance),
! 					      life);
!       life.release ();
       }

     /* Complete the target-specific cost calculation.  */
Index: gcc/testsuite/gcc.dg/vect/bb-slp-32.c
===================================================================
*** gcc/testsuite/gcc.dg/vect/bb-slp-32.c	(revision 0)
--- gcc/testsuite/gcc.dg/vect/bb-slp-32.c	(working copy)
***************
*** 0 ****
--- 1,23 ----
+ /* { dg-do compile } */
+ /* { dg-require-effective-target vect_int } */
+ /* { dg-additional-options "-fvect-cost-model" } */
+
+ void bar (int *);
+ int foo (int *p)
+ {
+   int x[4];
+   int tem0, tem1, tem2, tem3;
+   tem0 = p[0] + 1;
+   x[0] = tem0;
+   tem1 = p[1] + 2;
+   x[1] = tem1;
+   tem2 = p[2] + 3;
+   x[2] = tem2;
+   tem3 = p[3] + 4;
+   x[3] = tem3;
+   bar (x);
+   return tem0 + tem1 + tem2 + tem3;
+ }
+
+ /* { dg-final { scan-tree-dump "vectorization is not profitable" "slp" } } */
+ /* { dg-final { cleanup-tree-dump "slp" } } */


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]