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]

[PATCH][1/3] Refactor SIMD lane handling in vect_find_stmt_data_reference


This is a prerequesite for sharing dataref and dependence analysis
results between different vector size vectorization attempts.

Bootstrapped on x86_64-unknown-linux-gnu (with 2/3 included),
testing in progress.

Richard.

>From 9b406b12269d2a0fe86591df862c2ffd0197df37 Mon Sep 17 00:00:00 2001
From: Richard Guenther <rguenther@suse.de>
Date: Fri, 22 Jun 2018 11:33:34 +0200
Subject: [PATCH] do-not-modify-drs-for-simd-lane

2018-06-22  Richard Biener  <rguenther@suse.de>

	* tree-vect-data-refs.c (vect_find_stmt_data_reference): Modify
	DR for SIMD lane accesses here and mark DR with (void *)-1 aux.
	(vect_analyze_data_refs): Remove similar code from here and
	simplify accordingly.

diff --git a/gcc/tree-vect-data-refs.c b/gcc/tree-vect-data-refs.c
index 1ac37bf5001..bd71735585e 100644
--- a/gcc/tree-vect-data-refs.c
+++ b/gcc/tree-vect-data-refs.c
@@ -4030,6 +4030,70 @@ vect_find_stmt_data_reference (loop_p loop, gimple *stmt,
       return false;
     }
 
+  /* Check whether this may be a SIMD lane access and adjust the
+     DR to make it easier for us to handle it.  */
+  if (loop
+      && loop->simduid
+      && (!DR_BASE_ADDRESS (dr)
+	  || !DR_OFFSET (dr)
+	  || !DR_INIT (dr)
+	  || !DR_STEP (dr)))
+    {
+      struct data_reference *newdr
+	= create_data_ref (NULL, loop_containing_stmt (stmt), DR_REF (dr), stmt,
+			   DR_IS_READ (dr), DR_IS_CONDITIONAL_IN_STMT (dr));
+      if (DR_BASE_ADDRESS (newdr)
+	  && DR_OFFSET (newdr)
+	  && DR_INIT (newdr)
+	  && DR_STEP (newdr)
+	  && integer_zerop (DR_STEP (newdr)))
+	{
+	  tree off = DR_OFFSET (newdr);
+	  STRIP_NOPS (off);
+	  if (TREE_CODE (DR_INIT (newdr)) == INTEGER_CST
+	      && TREE_CODE (off) == MULT_EXPR
+	      && tree_fits_uhwi_p (TREE_OPERAND (off, 1)))
+	    {
+	      tree step = TREE_OPERAND (off, 1);
+	      off = TREE_OPERAND (off, 0);
+	      STRIP_NOPS (off);
+	      if (CONVERT_EXPR_P (off)
+		  && (TYPE_PRECISION (TREE_TYPE (TREE_OPERAND (off, 0)))
+		      < TYPE_PRECISION (TREE_TYPE (off))))
+		off = TREE_OPERAND (off, 0);
+	      if (TREE_CODE (off) == SSA_NAME)
+		{
+		  gimple *def = SSA_NAME_DEF_STMT (off);
+		  tree reft = TREE_TYPE (DR_REF (newdr));
+		  if (is_gimple_call (def)
+		      && gimple_call_internal_p (def)
+		      && (gimple_call_internal_fn (def) == IFN_GOMP_SIMD_LANE))
+		    {
+		      tree arg = gimple_call_arg (def, 0);
+		      gcc_assert (TREE_CODE (arg) == SSA_NAME);
+		      arg = SSA_NAME_VAR (arg);
+		      if (arg == loop->simduid
+			  /* For now.  */
+			  && tree_int_cst_equal (TYPE_SIZE_UNIT (reft), step))
+			{
+			  DR_OFFSET (newdr) = ssize_int (0);
+			  DR_STEP (newdr) = step;
+			  DR_OFFSET_ALIGNMENT (newdr) = BIGGEST_ALIGNMENT;
+			  DR_STEP_ALIGNMENT (newdr)
+			    = highest_pow2_factor (step);
+			  /* Mark as simd-lane access.  */
+			  newdr->aux = (void *)-1;
+			  free_data_ref (dr);
+			  datarefs->safe_push (newdr);
+			  return true;
+			}
+		    }
+		}
+	    }
+	}
+      free_data_ref (newdr);
+    }
+
   datarefs->safe_push (dr);
   return true;
 }
@@ -4071,7 +4135,6 @@ vect_analyze_data_refs (vec_info *vinfo, poly_uint64 *min_vf)
       gimple *stmt;
       stmt_vec_info stmt_info;
       enum { SG_NONE, GATHER, SCATTER } gatherscatter = SG_NONE;
-      bool simd_lane_access = false;
       poly_uint64 vf;
 
       gcc_assert (DR_REF (dr));
@@ -4092,76 +4155,13 @@ vect_analyze_data_refs (vec_info *vinfo, poly_uint64 *min_vf)
 	      && !TREE_THIS_VOLATILE (DR_REF (dr))
 	      && (targetm.vectorize.builtin_scatter != NULL
 		  || supports_vec_scatter_store_p ());
-	  bool maybe_simd_lane_access
-	    = is_a <loop_vec_info> (vinfo) && loop->simduid;
 
-	  /* If target supports vector gather loads or scatter stores, or if
-	     this might be a SIMD lane access, see if they can't be used.  */
+	  /* If target supports vector gather loads or scatter stores,
+	     see if they can't be used.  */
 	  if (is_a <loop_vec_info> (vinfo)
 	      && !nested_in_vect_loop_p (loop, stmt))
 	    {
-	      if (maybe_simd_lane_access)
-		{
-		  struct data_reference *newdr
-		    = create_data_ref (NULL, loop_containing_stmt (stmt),
-				       DR_REF (dr), stmt, !maybe_scatter,
-				       DR_IS_CONDITIONAL_IN_STMT (dr));
-		  gcc_assert (newdr != NULL && DR_REF (newdr));
-		  if (DR_BASE_ADDRESS (newdr)
-		      && DR_OFFSET (newdr)
-		      && DR_INIT (newdr)
-		      && DR_STEP (newdr)
-		      && integer_zerop (DR_STEP (newdr)))
-		    {
-		      tree off = DR_OFFSET (newdr);
-		      STRIP_NOPS (off);
-		      if (TREE_CODE (DR_INIT (newdr)) == INTEGER_CST
-			  && TREE_CODE (off) == MULT_EXPR
-			  && tree_fits_uhwi_p (TREE_OPERAND (off, 1)))
-			{
-			  tree step = TREE_OPERAND (off, 1);
-			  off = TREE_OPERAND (off, 0);
-			  STRIP_NOPS (off);
-			  if (CONVERT_EXPR_P (off)
-			      && TYPE_PRECISION (TREE_TYPE (TREE_OPERAND (off,
-									  0)))
-			      < TYPE_PRECISION (TREE_TYPE (off)))
-			    off = TREE_OPERAND (off, 0);
-			  if (TREE_CODE (off) == SSA_NAME)
-			    {
-			      gimple *def = SSA_NAME_DEF_STMT (off);
-			      tree reft = TREE_TYPE (DR_REF (newdr));
-			      if (is_gimple_call (def)
-				  && gimple_call_internal_p (def)
-				  && (gimple_call_internal_fn (def)
-				      == IFN_GOMP_SIMD_LANE))
-				{
-				  tree arg = gimple_call_arg (def, 0);
-				  gcc_assert (TREE_CODE (arg) == SSA_NAME);
-				  arg = SSA_NAME_VAR (arg);
-				  if (arg == loop->simduid
-				      /* For now.  */
-				      && tree_int_cst_equal
-				      (TYPE_SIZE_UNIT (reft),
-				       step))
-				    {
-				      DR_OFFSET (newdr) = ssize_int (0);
-				      DR_STEP (newdr) = step;
-				      DR_OFFSET_ALIGNMENT (newdr)
-					  = BIGGEST_ALIGNMENT;
-				      DR_STEP_ALIGNMENT (newdr)
-					  = highest_pow2_factor (step);
-				      dr = newdr;
-				      simd_lane_access = true;
-				    }
-				}
-			    }
-			}
-		    }
-		  if (!simd_lane_access)
-		    free_data_ref (newdr);
-		}
-	      if (!simd_lane_access && (maybe_gather || maybe_scatter))
+	      if (maybe_gather || maybe_scatter)
 		{
 		  if (maybe_gather)
 		    gatherscatter = GATHER;
@@ -4170,7 +4170,7 @@ vect_analyze_data_refs (vec_info *vinfo, poly_uint64 *min_vf)
 		}
 	    }
 
-	  if (gatherscatter == SG_NONE && !simd_lane_access)
+	  if (gatherscatter == SG_NONE)
 	    {
 	      if (dump_enabled_p ())
 		{
@@ -4190,6 +4190,23 @@ vect_analyze_data_refs (vec_info *vinfo, poly_uint64 *min_vf)
 	    }
         }
 
+      /* See if this was detected as SIMD lane access.  */
+      if (dr->aux == (void *)-1)
+	{
+	  if (nested_in_vect_loop_p (loop, stmt))
+	    {
+	      if (dump_enabled_p ())
+		{
+		  dump_printf_loc (MSG_MISSED_OPTIMIZATION, vect_location,
+				   "not vectorized: data ref analysis "
+				   "failed ");
+		  dump_gimple_stmt (MSG_MISSED_OPTIMIZATION, TDF_SLIM, stmt, 0);
+		}
+	      return false;
+	    }
+	  STMT_VINFO_SIMD_LANE_ACCESS_P (stmt_info) = true;
+	}
+
       tree base = get_base_address (DR_REF (dr));
       if (base && VAR_P (base) && DECL_NONALIASED (base))
 	{
@@ -4292,12 +4309,6 @@ vect_analyze_data_refs (vec_info *vinfo, poly_uint64 *min_vf)
 
       gcc_assert (!STMT_VINFO_DATA_REF (stmt_info));
       STMT_VINFO_DATA_REF (stmt_info) = dr;
-      if (simd_lane_access)
-	{
-	  STMT_VINFO_SIMD_LANE_ACCESS_P (stmt_info) = true;
-	  free_data_ref (datarefs[i]);
-	  datarefs[i] = dr;
-	}
 
       /* Set vectype for STMT.  */
       scalar_type = TREE_TYPE (DR_REF (dr));
@@ -4323,12 +4334,6 @@ vect_analyze_data_refs (vec_info *vinfo, poly_uint64 *min_vf)
 	      STMT_VINFO_VECTORIZABLE (stmt_info) = false;
 	      continue;
 	    }
-
-	  if (simd_lane_access)
-	    {
-	      STMT_VINFO_DATA_REF (stmt_info) = NULL;
-	      free_data_ref (dr);
-	    }
 	  return false;
         }
       else


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