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]

[COMMITTED] Fix 70240


As discussed in the PR, the fix for 68215 was a bit too aggressive and caused this one. There's a simple alternate fix, first suggested by Richi in 68714, that cures both.

Thus I apply one patch and revert another, in order, so that nothing breaks in between yet keeps the two commits separate.

Tested on i686 and x86_64 linux.
Committed as approved in the PR,


r~
	PR middle-end/70240
	PR middle-end/68215
	PR tree-opt/68714
	* gimplify.c (gimplify_expr) [VEC_COND_EXPR]: Gimplify the
	first operand as is_gimple_condexpr.

diff --git a/gcc/gimplify.c b/gcc/gimplify.c
index 84ce46e..f3e5c39 100644
--- a/gcc/gimplify.c
+++ b/gcc/gimplify.c
@@ -10799,8 +10799,23 @@ gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
 	    goto expr_2;
 	  }
 
-	case FMA_EXPR:
 	case VEC_COND_EXPR:
+	  {
+	    enum gimplify_status r0, r1, r2;
+
+	    r0 = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
+				post_p, is_gimple_condexpr, fb_rvalue);
+	    r1 = gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p,
+				post_p, is_gimple_val, fb_rvalue);
+	    r2 = gimplify_expr (&TREE_OPERAND (*expr_p, 2), pre_p,
+				post_p, is_gimple_val, fb_rvalue);
+
+	    ret = MIN (MIN (r0, r1), r2);
+	    recalculate_side_effects (*expr_p);
+	  }
+	  break;
+
+	case FMA_EXPR:
 	case VEC_PERM_EXPR:
 	  /* Classified as tcc_expression.  */
 	  goto expr_3;
-- 
2.1.0

	PR middle-end/70240
	PR middle-end/68215
	Revert r231575
	2015-12-11  Eric Botcazou  <ebotcazou@adacore.com>
	* tree-vect-generic.c (tree_vec_extract): Remove GSI parameter.
	Do not gimplify the result.
	(do_unop): Adjust call to tree_vec_extract.
	(do_binop): Likewise.
	(do_compare): Likewise.
	(do_plus_minus): Likewise.
	(do_negate): Likewise.
	(expand_vector_condition): Likewise.
	(do_cond): Likewise.

diff --git a/gcc/tree-vect-generic.c b/gcc/tree-vect-generic.c
index fd3dc43..cb15a95 100644
--- a/gcc/tree-vect-generic.c
+++ b/gcc/tree-vect-generic.c
@@ -103,7 +103,8 @@ typedef tree (*elem_op_func) (gimple_stmt_iterator *,
 			      tree);
 
 static inline tree
-tree_vec_extract (tree type, tree t, tree bitsize, tree bitpos)
+tree_vec_extract (gimple_stmt_iterator *gsi, tree type,
+		  tree t, tree bitsize, tree bitpos)
 {
   if (TREE_CODE (t) == SSA_NAME)
     {
@@ -114,21 +115,22 @@ tree_vec_extract (tree type, tree t, tree bitsize, tree bitpos)
 		  && gimple_assign_rhs_code (def_stmt) == CONSTRUCTOR)))
 	t = gimple_assign_rhs1 (def_stmt);
     }
-
   if (bitpos)
     {
       if (TREE_CODE (type) == BOOLEAN_TYPE)
 	{
 	  tree itype
 	    = build_nonstandard_integer_type (tree_to_uhwi (bitsize), 0);
-	  tree field = fold_build3 (BIT_FIELD_REF, itype, t, bitsize, bitpos);
-	  return fold_build2 (NE_EXPR, type, field, build_zero_cst (itype));
+	  tree field = gimplify_build3 (gsi, BIT_FIELD_REF, itype, t,
+					bitsize, bitpos);
+	  return gimplify_build2 (gsi, NE_EXPR, type, field,
+				  build_zero_cst (itype));
 	}
- 
-      return fold_build3 (BIT_FIELD_REF, type, t, bitsize, bitpos);
+      else
+	return gimplify_build3 (gsi, BIT_FIELD_REF, type, t, bitsize, bitpos);
     }
-
-  return fold_build1 (VIEW_CONVERT_EXPR, type, t);
+  else
+    return gimplify_build1 (gsi, VIEW_CONVERT_EXPR, type, t);
 }
 
 static tree
@@ -136,7 +138,7 @@ do_unop (gimple_stmt_iterator *gsi, tree inner_type, tree a,
 	 tree b ATTRIBUTE_UNUSED, tree bitpos, tree bitsize,
 	 enum tree_code code, tree type ATTRIBUTE_UNUSED)
 {
-  a = tree_vec_extract (inner_type, a, bitsize, bitpos);
+  a = tree_vec_extract (gsi, inner_type, a, bitsize, bitpos);
   return gimplify_build1 (gsi, code, inner_type, a);
 }
 
@@ -146,9 +148,9 @@ do_binop (gimple_stmt_iterator *gsi, tree inner_type, tree a, tree b,
 	  tree type ATTRIBUTE_UNUSED)
 {
   if (TREE_CODE (TREE_TYPE (a)) == VECTOR_TYPE)
-    a = tree_vec_extract (inner_type, a, bitsize, bitpos);
+    a = tree_vec_extract (gsi, inner_type, a, bitsize, bitpos);
   if (TREE_CODE (TREE_TYPE (b)) == VECTOR_TYPE)
-    b = tree_vec_extract (inner_type, b, bitsize, bitpos);
+    b = tree_vec_extract (gsi, inner_type, b, bitsize, bitpos);
   return gimplify_build2 (gsi, code, inner_type, a, b);
 }
 
@@ -167,8 +169,8 @@ do_compare (gimple_stmt_iterator *gsi, tree inner_type, tree a, tree b,
   tree cst_true = build_all_ones_cst (stype);
   tree cmp;
 
-  a = tree_vec_extract (inner_type, a, bitsize, bitpos);
-  b = tree_vec_extract (inner_type, b, bitsize, bitpos);
+  a = tree_vec_extract (gsi, inner_type, a, bitsize, bitpos);
+  b = tree_vec_extract (gsi, inner_type, b, bitsize, bitpos);
 
   cmp = build2 (code, boolean_type_node, a, b);
   return gimplify_build3 (gsi, COND_EXPR, stype, cmp, cst_true, cst_false);
@@ -200,8 +202,8 @@ do_plus_minus (gimple_stmt_iterator *gsi, tree word_type, tree a, tree b,
   low_bits = build_replicated_const (word_type, inner_type, max >> 1);
   high_bits = build_replicated_const (word_type, inner_type, max & ~(max >> 1));
 
-  a = tree_vec_extract (word_type, a, bitsize, bitpos);
-  b = tree_vec_extract (word_type, b, bitsize, bitpos);
+  a = tree_vec_extract (gsi, word_type, a, bitsize, bitpos);
+  b = tree_vec_extract (gsi, word_type, b, bitsize, bitpos);
 
   signs = gimplify_build2 (gsi, BIT_XOR_EXPR, word_type, a, b);
   b_low = gimplify_build2 (gsi, BIT_AND_EXPR, word_type, b, low_bits);
@@ -233,7 +235,7 @@ do_negate (gimple_stmt_iterator *gsi, tree word_type, tree b,
   low_bits = build_replicated_const (word_type, inner_type, max >> 1);
   high_bits = build_replicated_const (word_type, inner_type, max & ~(max >> 1));
 
-  b = tree_vec_extract (word_type, b, bitsize, bitpos);
+  b = tree_vec_extract (gsi, word_type, b, bitsize, bitpos);
 
   b_low = gimplify_build2 (gsi, BIT_AND_EXPR, word_type, b, low_bits);
   signs = gimplify_build1 (gsi, BIT_NOT_EXPR, word_type, b);
@@ -889,16 +891,16 @@ expand_vector_condition (gimple_stmt_iterator *gsi)
        i++, index = int_const_binop (PLUS_EXPR, index, width))
     {
       tree aa, result;
-      tree bb = tree_vec_extract (inner_type, b, width, index);
-      tree cc = tree_vec_extract (inner_type, c, width, index);
+      tree bb = tree_vec_extract (gsi, inner_type, b, width, index);
+      tree cc = tree_vec_extract (gsi, inner_type, c, width, index);
       if (a_is_comparison)
 	{
-	  tree aa1 = tree_vec_extract (comp_inner_type, a1, width, index);
-	  tree aa2 = tree_vec_extract (comp_inner_type, a2, width, index);
+	  tree aa1 = tree_vec_extract (gsi, comp_inner_type, a1, width, index);
+	  tree aa2 = tree_vec_extract (gsi, comp_inner_type, a2, width, index);
 	  aa = build2 (TREE_CODE (a), cond_type, aa1, aa2);
 	}
       else
-	aa = tree_vec_extract (cond_type, a, width, index);
+	aa = tree_vec_extract (gsi, cond_type, a, width, index);
       result = gimplify_build3 (gsi, COND_EXPR, inner_type, aa, bb, cc);
       constructor_elt ce = {NULL_TREE, result};
       v->quick_push (ce);
@@ -1448,9 +1450,9 @@ do_cond (gimple_stmt_iterator *gsi, tree inner_type, tree a, tree b,
 	 tree type ATTRIBUTE_UNUSED)
 {
   if (TREE_CODE (TREE_TYPE (a)) == VECTOR_TYPE)
-    a = tree_vec_extract (inner_type, a, bitsize, bitpos);
+    a = tree_vec_extract (gsi, inner_type, a, bitsize, bitpos);
   if (TREE_CODE (TREE_TYPE (b)) == VECTOR_TYPE)
-    b = tree_vec_extract (inner_type, b, bitsize, bitpos);
+    b = tree_vec_extract (gsi, inner_type, b, bitsize, bitpos);
   tree cond = gimple_assign_rhs1 (gsi_stmt (*gsi));
   return gimplify_build3 (gsi, code, inner_type, unshare_expr (cond), a, b);
 }
-- 
2.1.0

	PR middle-end/70240
	* gcc.c-torture/compile/pr70240.c: New.

diff --git a/gcc/testsuite/gcc.c-torture/compile/pr70240.c b/gcc/testsuite/gcc.c-torture/compile/pr70240.c
new file mode 100644
index 0000000..830d4dd
--- /dev/null
+++ b/gcc/testsuite/gcc.c-torture/compile/pr70240.c
@@ -0,0 +1,26 @@
+typedef short v16hi __attribute__ ((vector_size (32)));
+typedef int v8si __attribute__ ((vector_size (32)));
+typedef long long v4di __attribute__ ((vector_size (32)));
+
+int
+foo(int u16_0, int u32_0, int u64_0, int u16_1, int u32_1, int u64_1, v16hi v32u16_0, v8si v32u32_0, v4di v32u64_0, v16hi v32u16_1, v8si v32u32_1, v4di v32u64_1)
+{
+  do {
+    v32u16_1 += (v16hi){ v32u32_1[7], ~v32u32_1[3], 0, v32u64_0[0]};
+    u32_0 = (u32_0 << 31) | (u32_0 >> ~v32u32_0[1]);
+    u64_0 += 1;
+    v32u64_0[2] <<= v32u64_0[2] & 63;
+    u16_1 = (u16_1 >> (v32u16_0[11] & 15)) | (u16_1 << (-v32u16_0[11] & 15));
+    v32u16_0 -= ~v32u16_1;
+    v32u32_1[5] += u32_1;
+    if (v32u32_1[3] >= 0) {
+      u64_1 -= ~v32u64_1[1];
+      v32u16_1 += (v16hi){ -u64_1, ~u32_0, ~u16_1, v32u32_1[1], 0, ~v32u16_1[2], ~v32u64_1[2], ~v32u32_0[7]};
+    }
+    v32u64_1 += (v4di){0, 0, ~v32u32_0[5]};
+    v32u32_1 *= (v8si){0, ~v32u32_1[6]};
+    v32u64_0[3] &= 0x1234;
+    v32u64_0 += (v4di){v32u32_1[6]};
+  } while (u16_0 < 0x1234);
+  return u64_0 + u16_1;
+}
-- 
2.1.0


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