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]

Re: ICE in simplify_plus_minus when called from loop.c



Richard Henderson wrote:

>I suppose the only question is whether we want to do the sort of
>brute-force search that simplify_plus_minus does on arbitrary
>numbers of arguments.  If we don't think that number will ever
>be REALLY big, then changing simplify_plus_minus would be best.

Well, if I understand the consec_sets_giv logic correctly,
the add_val that gets computed there can become arbitrarily
complex, depending on the source code.

So it would be at least theoretically possible to construct
test cases that cause any given fixed limit to be exceeded ...

>Otherwise, we change simplify_gen_binary to support failure in
>simplify_plus_minus and just call gen_rtx_PLUS.

The following patch does basically what you suggest here, and it
solves my test case.  If this is a correct solution, is it OK
to check it in (trunk and branch)?

I've bootstrapped and regtested on s390-ibm-linux and s390x-ibm-linux
(on the branch only at the moment).

Bye,
Ulrich

ChangeLog:

     * gcc/simplify-rtx.c (simplify_plus_minus): Do not abort,
     but simply fail if the expression is too complex to simplify.
     (simplify_gen_binary): Handle simplify_plus_minus failures.


Index: gcc/simplify-rtx.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/simplify-rtx.c,v
retrieving revision 1.94
diff -c -p -r1.94 simplify-rtx.c
*** simplify-rtx.c  2002/02/21 23:06:15  1.94
--- simplify-rtx.c  2002/03/06 20:23:21
*************** simplify_gen_binary (code, mode, op0, op
*** 145,153 ****
       the operation.  */

    if (code == PLUS || code == MINUS)
!     return simplify_plus_minus (code, mode, op0, op1, 1);
!   else
!     return gen_rtx_fmt_ee (code, mode, op0, op1);
  }

  /* If X is a MEM referencing the constant pool, return the real value.
--- 145,157 ----
       the operation.  */

    if (code == PLUS || code == MINUS)
!     {
!       tem = simplify_plus_minus (code, mode, op0, op1, 1);
!       if (tem)
!    return tem;
!     }
!
!   return gen_rtx_fmt_ee (code, mode, op0, op1);
  }

  /* If X is a MEM referencing the constant pool, return the real value.
*************** simplify_binary_operation (code, mode, o
*** 1725,1731 ****
     we rebuild the operation.

     If FORCE is true, then always generate the rtx.  This is used to
!    canonicalize stuff emitted from simplify_gen_binary.  */

  struct simplify_plus_minus_op_data
  {
--- 1729,1737 ----
     we rebuild the operation.

     If FORCE is true, then always generate the rtx.  This is used to
!    canonicalize stuff emitted from simplify_gen_binary.  Note that this
!    can still fail if the rtx is too complex.  It won't fail just because
!    the result is not 'simpler' than the input, however.  */

  struct simplify_plus_minus_op_data
  {
*************** simplify_plus_minus (code, mode, op0, op
*** 1784,1794 ****
         case PLUS:
         case MINUS:
           if (n_ops == 7)
!         {
!           if (force)
!             abort ();
!           return NULL_RTX;
!         }

           ops[n_ops].op = XEXP (this_op, 1);
           ops[n_ops].neg = (this_code == MINUS) ^ this_neg;
--- 1790,1796 ----
         case PLUS:
         case MINUS:
           if (n_ops == 7)
!         return NULL_RTX;

           ops[n_ops].op = XEXP (this_op, 1);
           ops[n_ops].neg = (this_code == MINUS) ^ this_neg;




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