diff mbox series

middle-end: [PR middle-end/116926] Allow widening optabs for vec-mode -> scalar-mode

Message ID 20241010152452.1205387-1-victor.donascimento@arm.com
State New
Headers show
Series middle-end: [PR middle-end/116926] Allow widening optabs for vec-mode -> scalar-mode | expand

Commit Message

Victor Do Nascimento Oct. 10, 2024, 3:24 p.m. UTC
The recent refactoring of the dot_prod optab to convert-type exposed a
limitation in how `find_widening_optab_handler_and_mode' is currently
implemented, owing to the fact that, while the function expects the

  GET_MODE_CLASS (from_mode) == GET_MODE_CLASS (to_mode)

condition to hold, the c6x backend implements a dot product from V2HI
to SI, which triggers an ICE.

Consequently, this patch adds some logic to allow widening optabs
which accumulate vector elements to a single scalar.

Regression tested on x86_64 and aarch64 with no new regressions.
Fixes failing unit tests on c6x, as validated for the tic6x-unknown-elf
target.

Ok for master?

gcc/ChangeLog:

	PR middle-end/116926
	* optabs-query.cc (find_widening_optab_handler_and_mode): Add
	handling of vector -> scalar optab handling.
---
 gcc/optabs-query.cc | 13 +++++++++++++
 1 file changed, 13 insertions(+)

Comments

Richard Biener Oct. 11, 2024, 7:28 a.m. UTC | #1
On Thu, Oct 10, 2024 at 5:25 PM Victor Do Nascimento
<victor.donascimento@arm.com> wrote:
>
> The recent refactoring of the dot_prod optab to convert-type exposed a
> limitation in how `find_widening_optab_handler_and_mode' is currently
> implemented, owing to the fact that, while the function expects the
>
>   GET_MODE_CLASS (from_mode) == GET_MODE_CLASS (to_mode)
>
> condition to hold, the c6x backend implements a dot product from V2HI
> to SI, which triggers an ICE.
>
> Consequently, this patch adds some logic to allow widening optabs
> which accumulate vector elements to a single scalar.
>
> Regression tested on x86_64 and aarch64 with no new regressions.
> Fixes failing unit tests on c6x, as validated for the tic6x-unknown-elf
> target.
>
> Ok for master?
>
> gcc/ChangeLog:
>
>         PR middle-end/116926
>         * optabs-query.cc (find_widening_optab_handler_and_mode): Add
>         handling of vector -> scalar optab handling.
> ---
>  gcc/optabs-query.cc | 13 +++++++++++++
>  1 file changed, 13 insertions(+)
>
> diff --git a/gcc/optabs-query.cc b/gcc/optabs-query.cc
> index c3134d6a2ce..8a9092ffec7 100644
> --- a/gcc/optabs-query.cc
> +++ b/gcc/optabs-query.cc
> @@ -485,6 +485,19 @@ find_widening_optab_handler_and_mode (optab op, machine_mode to_mode,
>        if (GET_MODE_CLASS (limit_mode) == MODE_PARTIAL_INT)
>         limit_mode = GET_MODE_WIDER_MODE (limit_mode).require ();
>      }
> +  else if (GET_MODE_CLASS (from_mode) != GET_MODE_CLASS (to_mode))
> +    {
> +      gcc_checking_assert (VECTOR_MODE_P (from_mode)
> +                          && !VECTOR_MODE_P (to_mode)
> +                          && GET_MODE_INNER (from_mode) < to_mode);
> +      enum insn_code handler = convert_optab_handler (op, to_mode, from_mode);
> +      if (handler != CODE_FOR_nothing)
> +       {
> +         if (found_mode)
> +           *found_mode = from_mode;
> +         return handler;
> +       }

   else if (is_a <scalar_int_mode> (to_mode))
     {
        gcc_checking_assert (VECTOR_MODE_P (from_mode)
                                            && GET_MODE_INNER
(from_mode) < to_mode);
        limit_mode = from_mode;
     }
   else
...

would also work?

Thanks,
Richard.

> +    }
>    else
>      gcc_checking_assert (GET_MODE_CLASS (from_mode) == GET_MODE_CLASS (to_mode)
>                          && from_mode < to_mode);
> --
> 2.34.1
>
Victor Do Nascimento Oct. 11, 2024, 3:55 p.m. UTC | #2
On 10/11/24 08:28, Richard Biener wrote:
> On Thu, Oct 10, 2024 at 5:25 PM Victor Do Nascimento
> <victor.donascimento@arm.com> wrote:
>>
>> The recent refactoring of the dot_prod optab to convert-type exposed a
>> limitation in how `find_widening_optab_handler_and_mode' is currently
>> implemented, owing to the fact that, while the function expects the
>>
>>    GET_MODE_CLASS (from_mode) == GET_MODE_CLASS (to_mode)
>>
>> condition to hold, the c6x backend implements a dot product from V2HI
>> to SI, which triggers an ICE.
>>
>> Consequently, this patch adds some logic to allow widening optabs
>> which accumulate vector elements to a single scalar.
>>
>> Regression tested on x86_64 and aarch64 with no new regressions.
>> Fixes failing unit tests on c6x, as validated for the tic6x-unknown-elf
>> target.
>>
>> Ok for master?
>>
>> gcc/ChangeLog:
>>
>>          PR middle-end/116926
>>          * optabs-query.cc (find_widening_optab_handler_and_mode): Add
>>          handling of vector -> scalar optab handling.
>> ---
>>   gcc/optabs-query.cc | 13 +++++++++++++
>>   1 file changed, 13 insertions(+)
>>
>> diff --git a/gcc/optabs-query.cc b/gcc/optabs-query.cc
>> index c3134d6a2ce..8a9092ffec7 100644
>> --- a/gcc/optabs-query.cc
>> +++ b/gcc/optabs-query.cc
>> @@ -485,6 +485,19 @@ find_widening_optab_handler_and_mode (optab op, machine_mode to_mode,
>>         if (GET_MODE_CLASS (limit_mode) == MODE_PARTIAL_INT)
>>          limit_mode = GET_MODE_WIDER_MODE (limit_mode).require ();
>>       }
>> +  else if (GET_MODE_CLASS (from_mode) != GET_MODE_CLASS (to_mode))
>> +    {
>> +      gcc_checking_assert (VECTOR_MODE_P (from_mode)
>> +                          && !VECTOR_MODE_P (to_mode)
>> +                          && GET_MODE_INNER (from_mode) < to_mode);
>> +      enum insn_code handler = convert_optab_handler (op, to_mode, from_mode);
>> +      if (handler != CODE_FOR_nothing)
>> +       {
>> +         if (found_mode)
>> +           *found_mode = from_mode;
>> +         return handler;
>> +       }
> 
>     else if (is_a <scalar_int_mode> (to_mode))
>       {
>          gcc_checking_assert (VECTOR_MODE_P (from_mode)
>                                              && GET_MODE_INNER
> (from_mode) < to_mode);
>          limit_mode = from_mode;
>       }
>     else
> ...
> 
> would also work?

You're absolutely right, much better.

Patch resubmitted.

Many thanks,
Victor.

> Thanks,
> Richard.
> 
>> +    }
>>     else
>>       gcc_checking_assert (GET_MODE_CLASS (from_mode) == GET_MODE_CLASS (to_mode)
>>                           && from_mode < to_mode);
>> --
>> 2.34.1
>>
diff mbox series

Patch

diff --git a/gcc/optabs-query.cc b/gcc/optabs-query.cc
index c3134d6a2ce..8a9092ffec7 100644
--- a/gcc/optabs-query.cc
+++ b/gcc/optabs-query.cc
@@ -485,6 +485,19 @@  find_widening_optab_handler_and_mode (optab op, machine_mode to_mode,
       if (GET_MODE_CLASS (limit_mode) == MODE_PARTIAL_INT)
 	limit_mode = GET_MODE_WIDER_MODE (limit_mode).require ();
     }
+  else if (GET_MODE_CLASS (from_mode) != GET_MODE_CLASS (to_mode))
+    {
+      gcc_checking_assert (VECTOR_MODE_P (from_mode)
+			   && !VECTOR_MODE_P (to_mode)
+			   && GET_MODE_INNER (from_mode) < to_mode);
+      enum insn_code handler = convert_optab_handler (op, to_mode, from_mode);
+      if (handler != CODE_FOR_nothing)
+	{
+	  if (found_mode)
+	    *found_mode = from_mode;
+	  return handler;
+	}
+    }
   else
     gcc_checking_assert (GET_MODE_CLASS (from_mode) == GET_MODE_CLASS (to_mode)
 			 && from_mode < to_mode);