diff mbox series

Fix ICEs from expand_mul_overflow (PR target/82981)

Message ID 20171120210743.GP14653@tucnak
State New
Headers show
Series Fix ICEs from expand_mul_overflow (PR target/82981) | expand

Commit Message

Jakub Jelinek Nov. 20, 2017, 9:07 p.m. UTC
Hi!

Apparently ARM can do the widening SImode multiply only using a libcall,
so the recently changed expand_mul_overflow ignores it at first, then
sees possibility to use the HImode code, but uses expand_simple_binop
with OPTAB_DIRECT which requires actual HImode optabs, which ARM doesn't
have, it needs to use widening to SImode.

Fixed thusly, bootstrapped/regtested on x86_64-linux and i686-linux, ok for
trunk?

2017-11-20  Jakub Jelinek  <jakub@redhat.com>

	PR target/82981
	* internal-fn.c (expand_mul_overflow): Use OPTAB_WIDEN instead of
	OPTAB_DIRECT in calls to expand_simple_binop.


	Jakub

Comments

Jeff Law Nov. 21, 2017, 3 a.m. UTC | #1
On 11/20/2017 02:07 PM, Jakub Jelinek wrote:
> Hi!
> 
> Apparently ARM can do the widening SImode multiply only using a libcall,
> so the recently changed expand_mul_overflow ignores it at first, then
> sees possibility to use the HImode code, but uses expand_simple_binop
> with OPTAB_DIRECT which requires actual HImode optabs, which ARM doesn't
> have, it needs to use widening to SImode.
> 
> Fixed thusly, bootstrapped/regtested on x86_64-linux and i686-linux, ok for
> trunk?
> 
> 2017-11-20  Jakub Jelinek  <jakub@redhat.com>
> 
> 	PR target/82981
> 	* internal-fn.c (expand_mul_overflow): Use OPTAB_WIDEN instead of
> 	OPTAB_DIRECT in calls to expand_simple_binop.
OK.
jeff
Richard Biener Nov. 21, 2017, 8:14 a.m. UTC | #2
On Mon, 20 Nov 2017, Jakub Jelinek wrote:

> Hi!
> 
> Apparently ARM can do the widening SImode multiply only using a libcall,
> so the recently changed expand_mul_overflow ignores it at first, then
> sees possibility to use the HImode code, but uses expand_simple_binop
> with OPTAB_DIRECT which requires actual HImode optabs, which ARM doesn't
> have, it needs to use widening to SImode.
> 
> Fixed thusly, bootstrapped/regtested on x86_64-linux and i686-linux, ok for
> trunk?

Ok.

RIchard.

> 2017-11-20  Jakub Jelinek  <jakub@redhat.com>
> 
> 	PR target/82981
> 	* internal-fn.c (expand_mul_overflow): Use OPTAB_WIDEN instead of
> 	OPTAB_DIRECT in calls to expand_simple_binop.
> 
> --- gcc/internal-fn.c.jj	2017-11-15 09:54:30.000000000 +0100
> +++ gcc/internal-fn.c	2017-11-20 16:38:55.185145957 +0100
> @@ -1760,7 +1760,7 @@ expand_mul_overflow (location_t loc, tre
>  	      tem = convert_modes (mode, hmode, lopart, 1);
>  	      tem = expand_shift (LSHIFT_EXPR, mode, tem, hprec, NULL_RTX, 1);
>  	      tem = expand_simple_binop (mode, MINUS, loxhi, tem, NULL_RTX,
> -					 1, OPTAB_DIRECT);
> +					 1, OPTAB_WIDEN);
>  	      emit_move_insn (loxhi, tem);
>  
>  	      emit_label (after_hipart_neg);
> @@ -1774,7 +1774,7 @@ expand_mul_overflow (location_t loc, tre
>  					 profile_probability::even ());
>  
>  	      tem = expand_simple_binop (mode, MINUS, loxhi, larger, NULL_RTX,
> -					 1, OPTAB_DIRECT);
> +					 1, OPTAB_WIDEN);
>  	      emit_move_insn (loxhi, tem);
>  
>  	      emit_label (after_lopart_neg);
> @@ -1783,7 +1783,7 @@ expand_mul_overflow (location_t loc, tre
>  	  /* loxhi += (uns) lo0xlo1 >> (bitsize / 2);  */
>  	  tem = expand_shift (RSHIFT_EXPR, mode, lo0xlo1, hprec, NULL_RTX, 1);
>  	  tem = expand_simple_binop (mode, PLUS, loxhi, tem, NULL_RTX,
> -				     1, OPTAB_DIRECT);
> +				     1, OPTAB_WIDEN);
>  	  emit_move_insn (loxhi, tem);
>  
>  	  /* if (loxhi >> (bitsize / 2)
> @@ -1810,7 +1810,7 @@ expand_mul_overflow (location_t loc, tre
>  			       convert_modes (hmode, mode, lo0xlo1, 1), 1);
>  
>  	  tem = expand_simple_binop (mode, IOR, loxhishifted, tem, res,
> -				     1, OPTAB_DIRECT);
> +				     1, OPTAB_WIDEN);
>  	  if (tem != res)
>  	    emit_move_insn (res, tem);
>  	  emit_jump (done_label);
> @@ -1835,7 +1835,7 @@ expand_mul_overflow (location_t loc, tre
>  	      if (!op0_medium_p)
>  		{
>  		  tem = expand_simple_binop (hmode, PLUS, hipart0, const1_rtx,
> -					     NULL_RTX, 1, OPTAB_DIRECT);
> +					     NULL_RTX, 1, OPTAB_WIDEN);
>  		  do_compare_rtx_and_jump (tem, const1_rtx, GTU, true, hmode,
>  					   NULL_RTX, NULL, do_error,
>  					   profile_probability::very_unlikely ());
> @@ -1844,7 +1844,7 @@ expand_mul_overflow (location_t loc, tre
>  	      if (!op1_medium_p)
>  		{
>  		  tem = expand_simple_binop (hmode, PLUS, hipart1, const1_rtx,
> -					     NULL_RTX, 1, OPTAB_DIRECT);
> +					     NULL_RTX, 1, OPTAB_WIDEN);
>  		  do_compare_rtx_and_jump (tem, const1_rtx, GTU, true, hmode,
>  					   NULL_RTX, NULL, do_error,
>  					   profile_probability::very_unlikely ());
> 
> 	Jakub
> 
>
Christophe Lyon Nov. 21, 2017, 9:29 a.m. UTC | #3
On 21 November 2017 at 09:14, Richard Biener <rguenther@suse.de> wrote:
> On Mon, 20 Nov 2017, Jakub Jelinek wrote:
>
>> Hi!
>>
>> Apparently ARM can do the widening SImode multiply only using a libcall,
>> so the recently changed expand_mul_overflow ignores it at first, then
>> sees possibility to use the HImode code, but uses expand_simple_binop
>> with OPTAB_DIRECT which requires actual HImode optabs, which ARM doesn't
>> have, it needs to use widening to SImode.
>>
>> Fixed thusly, bootstrapped/regtested on x86_64-linux and i686-linux, ok for
>> trunk?
>
> Ok.
>

Thanks Jakub, I had run validations with the patch you attached in
bugzilla, and it does fix the problem I reported.

Thanks,

Christophe

> RIchard.
>
>> 2017-11-20  Jakub Jelinek  <jakub@redhat.com>
>>
>>       PR target/82981
>>       * internal-fn.c (expand_mul_overflow): Use OPTAB_WIDEN instead of
>>       OPTAB_DIRECT in calls to expand_simple_binop.
>>
>> --- gcc/internal-fn.c.jj      2017-11-15 09:54:30.000000000 +0100
>> +++ gcc/internal-fn.c 2017-11-20 16:38:55.185145957 +0100
>> @@ -1760,7 +1760,7 @@ expand_mul_overflow (location_t loc, tre
>>             tem = convert_modes (mode, hmode, lopart, 1);
>>             tem = expand_shift (LSHIFT_EXPR, mode, tem, hprec, NULL_RTX, 1);
>>             tem = expand_simple_binop (mode, MINUS, loxhi, tem, NULL_RTX,
>> -                                      1, OPTAB_DIRECT);
>> +                                      1, OPTAB_WIDEN);
>>             emit_move_insn (loxhi, tem);
>>
>>             emit_label (after_hipart_neg);
>> @@ -1774,7 +1774,7 @@ expand_mul_overflow (location_t loc, tre
>>                                        profile_probability::even ());
>>
>>             tem = expand_simple_binop (mode, MINUS, loxhi, larger, NULL_RTX,
>> -                                      1, OPTAB_DIRECT);
>> +                                      1, OPTAB_WIDEN);
>>             emit_move_insn (loxhi, tem);
>>
>>             emit_label (after_lopart_neg);
>> @@ -1783,7 +1783,7 @@ expand_mul_overflow (location_t loc, tre
>>         /* loxhi += (uns) lo0xlo1 >> (bitsize / 2);  */
>>         tem = expand_shift (RSHIFT_EXPR, mode, lo0xlo1, hprec, NULL_RTX, 1);
>>         tem = expand_simple_binop (mode, PLUS, loxhi, tem, NULL_RTX,
>> -                                  1, OPTAB_DIRECT);
>> +                                  1, OPTAB_WIDEN);
>>         emit_move_insn (loxhi, tem);
>>
>>         /* if (loxhi >> (bitsize / 2)
>> @@ -1810,7 +1810,7 @@ expand_mul_overflow (location_t loc, tre
>>                              convert_modes (hmode, mode, lo0xlo1, 1), 1);
>>
>>         tem = expand_simple_binop (mode, IOR, loxhishifted, tem, res,
>> -                                  1, OPTAB_DIRECT);
>> +                                  1, OPTAB_WIDEN);
>>         if (tem != res)
>>           emit_move_insn (res, tem);
>>         emit_jump (done_label);
>> @@ -1835,7 +1835,7 @@ expand_mul_overflow (location_t loc, tre
>>             if (!op0_medium_p)
>>               {
>>                 tem = expand_simple_binop (hmode, PLUS, hipart0, const1_rtx,
>> -                                          NULL_RTX, 1, OPTAB_DIRECT);
>> +                                          NULL_RTX, 1, OPTAB_WIDEN);
>>                 do_compare_rtx_and_jump (tem, const1_rtx, GTU, true, hmode,
>>                                          NULL_RTX, NULL, do_error,
>>                                          profile_probability::very_unlikely ());
>> @@ -1844,7 +1844,7 @@ expand_mul_overflow (location_t loc, tre
>>             if (!op1_medium_p)
>>               {
>>                 tem = expand_simple_binop (hmode, PLUS, hipart1, const1_rtx,
>> -                                          NULL_RTX, 1, OPTAB_DIRECT);
>> +                                          NULL_RTX, 1, OPTAB_WIDEN);
>>                 do_compare_rtx_and_jump (tem, const1_rtx, GTU, true, hmode,
>>                                          NULL_RTX, NULL, do_error,
>>                                          profile_probability::very_unlikely ());
>>
>>       Jakub
>>
>>
>
> --
> Richard Biener <rguenther@suse.de>
> SUSE LINUX GmbH, GF: Felix Imendoerffer, Jane Smithard, Graham Norton, HRB 21284 (AG Nuernberg)
diff mbox series

Patch

--- gcc/internal-fn.c.jj	2017-11-15 09:54:30.000000000 +0100
+++ gcc/internal-fn.c	2017-11-20 16:38:55.185145957 +0100
@@ -1760,7 +1760,7 @@  expand_mul_overflow (location_t loc, tre
 	      tem = convert_modes (mode, hmode, lopart, 1);
 	      tem = expand_shift (LSHIFT_EXPR, mode, tem, hprec, NULL_RTX, 1);
 	      tem = expand_simple_binop (mode, MINUS, loxhi, tem, NULL_RTX,
-					 1, OPTAB_DIRECT);
+					 1, OPTAB_WIDEN);
 	      emit_move_insn (loxhi, tem);
 
 	      emit_label (after_hipart_neg);
@@ -1774,7 +1774,7 @@  expand_mul_overflow (location_t loc, tre
 					 profile_probability::even ());
 
 	      tem = expand_simple_binop (mode, MINUS, loxhi, larger, NULL_RTX,
-					 1, OPTAB_DIRECT);
+					 1, OPTAB_WIDEN);
 	      emit_move_insn (loxhi, tem);
 
 	      emit_label (after_lopart_neg);
@@ -1783,7 +1783,7 @@  expand_mul_overflow (location_t loc, tre
 	  /* loxhi += (uns) lo0xlo1 >> (bitsize / 2);  */
 	  tem = expand_shift (RSHIFT_EXPR, mode, lo0xlo1, hprec, NULL_RTX, 1);
 	  tem = expand_simple_binop (mode, PLUS, loxhi, tem, NULL_RTX,
-				     1, OPTAB_DIRECT);
+				     1, OPTAB_WIDEN);
 	  emit_move_insn (loxhi, tem);
 
 	  /* if (loxhi >> (bitsize / 2)
@@ -1810,7 +1810,7 @@  expand_mul_overflow (location_t loc, tre
 			       convert_modes (hmode, mode, lo0xlo1, 1), 1);
 
 	  tem = expand_simple_binop (mode, IOR, loxhishifted, tem, res,
-				     1, OPTAB_DIRECT);
+				     1, OPTAB_WIDEN);
 	  if (tem != res)
 	    emit_move_insn (res, tem);
 	  emit_jump (done_label);
@@ -1835,7 +1835,7 @@  expand_mul_overflow (location_t loc, tre
 	      if (!op0_medium_p)
 		{
 		  tem = expand_simple_binop (hmode, PLUS, hipart0, const1_rtx,
-					     NULL_RTX, 1, OPTAB_DIRECT);
+					     NULL_RTX, 1, OPTAB_WIDEN);
 		  do_compare_rtx_and_jump (tem, const1_rtx, GTU, true, hmode,
 					   NULL_RTX, NULL, do_error,
 					   profile_probability::very_unlikely ());
@@ -1844,7 +1844,7 @@  expand_mul_overflow (location_t loc, tre
 	      if (!op1_medium_p)
 		{
 		  tem = expand_simple_binop (hmode, PLUS, hipart1, const1_rtx,
-					     NULL_RTX, 1, OPTAB_DIRECT);
+					     NULL_RTX, 1, OPTAB_WIDEN);
 		  do_compare_rtx_and_jump (tem, const1_rtx, GTU, true, hmode,
 					   NULL_RTX, NULL, do_error,
 					   profile_probability::very_unlikely ());