[PATCH v14 03/19] vect: Refactor check_load_store_for_partial_vectors

Christopher Bazley <[email protected]>
Newsgroups gmane.comp.gcc.patches
Message-ID <[email protected]>
Moved existing code to determine the partial vector style for a load or
store into a new function that will be reused for BB SLP with predicated
tails.

Instead of reusing the existing enum vect_partial_vector_style, a new
enum type has been defined to represent the return value of the new
function because the new function only tells its caller whether a mask or
length can be used to limit the amount of data loaded or stored; it
cannot tell what variety of masks will be generated (or whether mask
generation will succeed).

gcc/ChangeLog:

	* tree-vect-stmts.cc (vect_get_load_store_partial_vector_style):
	Define a new function to get the partial vectors style supported
	by the target.
	(check_load_store_for_partial_vectors): Use the new function in
	place of existing custom code to do the same thing.
---
 gcc/tree-vect-stmts.cc | 79 +++++++++++++++++++++++++++++++++++-------
 1 file changed, 66 insertions(+), 13 deletions(-)

diff --git a/gcc/tree-vect-stmts.cc b/gcc/tree-vect-stmts.cc
index e76778c8b94..0b92b5bdf7a 100644
--- a/gcc/tree-vect-stmts.cc
+++ b/gcc/tree-vect-stmts.cc
@@ -1386,6 +1386,63 @@ vectorizable_internal_function (combined_fn cfn, tree fndecl,
 static tree permute_vec_elements (vec_info *, tree, tree, tree, stmt_vec_info,
 				  gimple_stmt_iterator *);
 
+enum vect_load_store_partial_vector_style {
+  vect_load_store_partial_vectors_none,
+  vect_load_store_partial_vectors_mask,
+  vect_load_store_partial_vectors_len
+};
+
+/* If target supports vector load/store (determined by IS_LOAD) with length for
+   VECTYPE, return VECT_LOAD_STORE_PARTIAL_VECTORS_LEN; otherwise, if it
+   supports vector masked load/store for mode for VECTYPE, return
+   VECT_LOAD_STORE_PARTIAL_VECTORS_MASK; otherwise, return
+   VECT_LOAD_STORE_PARTIAL_VECTORS_NONE.  If load/store with length or mask is
+   supported and ELSVALS is not null, store the possible else values in the
+   vector it points to.  Unless FACTOR is null, *FACTOR is set to the number of
+   separate subelements that each element of VECTYPE should be split into.
+   (This is always 1 except in the case of VECT_LOAD_STORE_PARTIAL_VECTORS_LEN
+   when the machine mode of VECTYPE can only be supported by using a length in
+   bytes instead of a length in lanes.)
+ */
+static enum vect_load_store_partial_vector_style
+vect_get_load_store_partial_vector_style (tree vectype, bool is_load,
+					  unsigned *factor = nullptr,
+					  vec<int> *elsvals = nullptr)
+{
+  machine_mode vecmode = TYPE_MODE (vectype);
+
+  /* TYPE_MODE tries to map vector modes that are unsupported by the target to
+     same-sized scalar modes, so reject scalar modes here.  */
+  if (VECTOR_MODE_P (vecmode))
+    {
+      machine_mode mask_mode, vmode;
+      if (get_len_load_store_mode (vecmode, is_load, nullptr, elsvals)
+	    .exists (&vmode))
+	{
+	  if (factor)
+	    *factor = (vecmode == vmode) ? 1 : GET_MODE_UNIT_SIZE (vecmode);
+	  return vect_load_store_partial_vectors_len;
+	}
+
+      if (factor)
+	*factor = 1;
+
+      if (targetm.vectorize.get_mask_mode (vecmode).exists (&mask_mode)
+	  && can_vec_mask_load_store_p (vecmode, mask_mode, is_load, NULL,
+					elsvals))
+	{
+	  return vect_load_store_partial_vectors_mask;
+	}
+    }
+
+  if (dump_enabled_p ())
+    dump_printf_loc (MSG_NOTE, vect_location,
+		     "the target doesn't have the appropriate partial"
+		     " vectorization %s for vector data type %T.\n",
+		     is_load ? "load" : "store", vectype);
+  return vect_load_store_partial_vectors_none;
+}
+
 /* Check whether a load or store statement in the loop described by
    LOOP_VINFO is possible in a loop using partial vectors.  This is
    testing whether the vectorizer pass has the appropriate support,
@@ -1548,28 +1605,24 @@ check_load_store_for_partial_vectors (loop_vec_info loop_vinfo, tree vectype,
 
   poly_uint64 nunits = TYPE_VECTOR_SUBPARTS (vectype);
   poly_uint64 vf = LOOP_VINFO_VECT_FACTOR (loop_vinfo);
-  machine_mode mask_mode;
-  machine_mode vmode;
-  bool using_partial_vectors_p = false;
-  if (get_len_load_store_mode
-      (vecmode, is_load, nullptr, elsvals).exists (&vmode))
+  unsigned factor;
+  vect_load_store_partial_vector_style partial_vector_style
+    = vect_get_load_store_partial_vector_style (vectype, is_load, &factor,
+						elsvals);
+
+  if (partial_vector_style == vect_load_store_partial_vectors_len)
     {
       nvectors = group_memory_nvectors (group_size * vf, nunits);
-      unsigned factor = (vecmode == vmode) ? 1 : GET_MODE_UNIT_SIZE (vecmode);
       vect_record_len (loop_vinfo, nvectors, vectype, factor);
-      using_partial_vectors_p = true;
     }
-  else if (targetm.vectorize.get_mask_mode (vecmode).exists (&mask_mode)
-	   && can_vec_mask_load_store_p (vecmode, mask_mode, is_load, NULL,
-					 elsvals))
+  else if (partial_vector_style == vect_load_store_partial_vectors_mask)
     {
       nvectors = group_memory_nvectors (group_size * vf, nunits);
       vect_record_mask (loop_vinfo, nvectors, vectype, scalar_mask);
-      using_partial_vectors_p = true;
     }
-
-  if (!using_partial_vectors_p)
+  else
     {
+      gcc_assert (partial_vector_style == vect_load_store_partial_vectors_none);
       if (dump_enabled_p ())
 	dump_printf_loc (MSG_MISSED_OPTIMIZATION, vect_location,
 			 "can't operate on partial vectors because the"
-- 
2.43.0
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.