Tamar Christina <tamar.christ...@arm.com> writes:
>> For variable-sized vectors, I suppose the question is whether the
>> first unequal element is found in the minimum vector length, or whether
>> it only occurs for larger lengths.  In the former case we can fold at
>> compile time, but in the latter case we can't.
>> 
>> So we probably do want the loop for variable-length vectors, up to
>> constant_lower_bound (CONST_VECTOR_NUNITS (...)).
>> 
>
> Doesn't operand_equal already do this? it looks like the VLA handling
> In same_vector_encodings_p rejects vectors that are not the same size,
> which is good enough for this no? since I'm after strict equality.

But what I meant is that for VLA vectors, compile-time equality is
a tristate value: yes, no, or maybe.

E.g.:

   { 0, 0, 0, 0, 0, 0, 0, 0, ... }

is not equal to

   { 0, 0, 1, 1, 1, 1, 1, 1, ... }

if the runtime VL gives more than 2 elements, but they are equal if
the runtime VL gives 2 elements.  In this case, we can't fold EQ to
false at compile time if the minimum length is 2 elements, but we can
if the minimum length is 4 elements.

Similarly:

   { 0, 0, 1, 1, 1, 1, 1, 1, ... }

is only conditionally not equal to:

   { 0, 0, 1, 1, 2, 2, 3, 3, ... }

It isn't the case that every encoded value has to be present in every
runtime vector.  E.g. the series { 0, 1, 2, ... } exists for VNx2DI
(for INDEX Z0.D, #0, #1), even though there is never a "2" element for
the minimum vector length.

Thanks,
Richard

>
>
> Bootstrapped Regtested on aarch64-none-linux-gnu, arm-none-linux-gnueabihf,
> x86_64-pc-linux-gnu -m32, -m64 and no issues.
>
> Ok for master?
>
> Thanks,
> Tamar
>
> gcc/ChangeLog:
>
>       * simplify-rtx.cc (simplify_context::simplify_unary_operation): Try
>       simplifying operand.
>       (simplify_const_relational_operation): Simplify vector EQ and NE.
>       (test_vector_int_const_compare): New.
>       (test_vector_ops): Use it.
>
>
> -- inline copy of patch --
>
> diff --git a/gcc/simplify-rtx.cc b/gcc/simplify-rtx.cc
> index 
> a20a61c5dddbc80b23a9489d925a2c31b2163458..8ba5864efb33ffa5d1ced99f6a7d0c73e12560d5
>  100644
> --- a/gcc/simplify-rtx.cc
> +++ b/gcc/simplify-rtx.cc
> @@ -6354,6 +6354,19 @@ simplify_const_relational_operation (enum rtx_code 
> code,
>       return 0;
>      }
>  
> +  /* Check if the operands are a vector EQ or NE comparison.  */
> +  if (VECTOR_MODE_P (mode)
> +      && INTEGRAL_MODE_P (mode)
> +      && GET_CODE (op0) == CONST_VECTOR
> +      && GET_CODE (op1) == CONST_VECTOR
> +      && (code == EQ || code == NE))
> +    {
> +      if (rtx_equal_p (op0, op1))
> +     return code == EQ ? const_true_rtx : const0_rtx;
> +      else
> +     return code == NE ? const_true_rtx : const0_rtx;
> +    }
> +
>    /* We can't simplify MODE_CC values since we don't know what the
>       actual comparison is.  */
>    if (GET_MODE_CLASS (GET_MODE (op0)) == MODE_CC)
> @@ -8797,6 +8810,34 @@ test_vector_subregs (machine_mode inner_mode)
>    test_vector_subregs_stepped (inner_mode);
>  }
>  
> +/* Verify vector constant comparisons for EQ and NE.  */
> +
> +static void
> +test_vector_int_const_compare (machine_mode mode)
> +{
> +  rtx zeros = CONST0_RTX (mode);
> +  rtx minusone = CONSTM1_RTX (mode);
> +  rtx series_0_1 = gen_const_vec_series (mode, const0_rtx, const1_rtx);
> +  ASSERT_RTX_EQ (const0_rtx,
> +              simplify_const_relational_operation (EQ, mode, zeros,
> +                                                   CONST1_RTX (mode)));
> +  ASSERT_RTX_EQ (const_true_rtx,
> +              simplify_const_relational_operation (EQ, mode, zeros,
> +                                                   CONST0_RTX (mode)));
> +  ASSERT_RTX_EQ (const_true_rtx,
> +              simplify_const_relational_operation (EQ, mode, minusone,
> +                                                   CONSTM1_RTX (mode)));
> +  ASSERT_RTX_EQ (const_true_rtx,
> +              simplify_const_relational_operation (NE, mode, zeros,
> +                                                   CONST1_RTX (mode)));
> +  ASSERT_RTX_EQ (const_true_rtx,
> +              simplify_const_relational_operation (NE, mode, zeros,
> +                                                   series_0_1));
> +  ASSERT_RTX_EQ (const0_rtx,
> +              simplify_const_relational_operation (EQ, mode, zeros,
> +                                                   series_0_1));
> +}
> +
>  /* Verify some simplifications involving vectors.  */
>  
>  static void
> @@ -8814,6 +8855,7 @@ test_vector_ops ()
>           {
>             test_vector_ops_series (mode, scalar_reg);
>             test_vector_subregs (mode);
> +           test_vector_int_const_compare (mode);
>           }
>         test_vec_merge (mode);
>       }

Reply via email to