This is the mail archive of the gcc-bugs@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]

optimization/6162: gcc 3.0.4: certain i386 asm reloader ice



>Number:         6162
>Category:       optimization
>Synopsis:       gcc 3.0.4: certain i386 asm reloader ice
>Confidential:   no
>Severity:       serious
>Priority:       low
>Responsible:    unassigned
>State:          open
>Class:          ice-on-legal-code
>Submitter-Id:   net
>Arrival-Date:   Wed Apr 03 16:26:00 PST 2002
>Closed-Date:
>Last-Modified:
>Originator:     
>Release:        3.0.4 (Debian testing/unstable)
>Organization:
>Environment:
System: Linux blah 2.2.15 #1 Tue Apr 25 17:13:48 EST 2000 i586 unknown
Architecture: i586
	<machine, os, target, libraries (multiple lines)>
host: i386-pc-linux-gnu
build: i386-pc-linux-gnu
target: i386-pc-linux-gnu
configured with: ../src/configure -v --enable-languages=c,c++,java,f77,proto,objc --prefix=/usr --infodir=/share/info --mandir=/share/man --enable-shared --with-gnu-as --with-gnu-ld --with-system-zlib --enable-long-long --enable-nls --without-included-gettext --disable-checking --enable-threads=posix --enable-java-gc=boehm --with-cpp-install-dir=bin --enable-objc-gc i386-linux

>Description:
On i386, a certain slightly convoluted combination of variables and
asm blocks provokes an ICE from gcc under "-O -fomit-frame-pointer".

>How-To-Repeat:
The file foo.c below (which has been through the preprocessor
already), compiled with

	gcc-3.0 -O -fomit-frame-pointer -c foo.c

produces

foo.c: In function `__gmpn_divrem_1':
foo.c:219: Unrecognizable insn:
(insn 399 662 401 (parallel[ 
            (set (reg/v:SI 6 ebp [89])
                (asm_operands:SI ("addl %5,%1
	adcl %3,%0") ("=r") 0[ 
                        (mem:SI (plus:SI (reg/f:SI 7 esp)
                                (const_int 48 [0x30])) 0)
                        (reg/v:SI 6 ebp [93])
                        (reg/v:SI 2 ecx [90])
                        (reg/v:SI 4 esi [78])
                    ] 
                    [ 
                        (asm_input:SI ("%0"))
                        (asm_input:SI ("g"))
                        (asm_input:SI ("%1"))
                        (asm_input:SI ("g"))
                    ]  ("foo.c") 172))
            (set (reg/v:SI 2 ecx [90])
                (asm_operands:SI ("addl %5,%1
	adcl %3,%0") ("=&r") 1[ 
                        (mem:SI (plus:SI (reg/f:SI 7 esp)
                                (const_int 48 [0x30])) 0)
                        (reg/v:SI 6 ebp [93])
                        (reg/v:SI 2 ecx [90])
                        (reg/v:SI 4 esi [78])
                    ] 
                    [ 
                        (asm_input:SI ("%0"))
                        (asm_input:SI ("g"))
                        (asm_input:SI ("%1"))
                        (asm_input:SI ("g"))
                    ]  ("foo.c") 172))
            (clobber (reg:QI 19 dirflag))
            (clobber (reg:QI 18 fpsr))
            (clobber (reg:QI 17 flags))
        ] ) -1 (insn_list 390 (insn_list 390 (nil)))
    (nil))
foo.c:219: Internal compiler error in reload_cse_simplify_operands, at reload1.c:8364



For what it's worth, this was an experimental GMP division routine,
but only a work-in-progress version, so the code isn't supposed to
work or do anything useful, but I think it's syntactically correct
(since it seems to compile fine if either of -O or
-fomit-frame-pointer is omitted).




--=-=-=
Content-Type: text/x-csrc
Content-Disposition: attachment; filename=foo.c


typedef unsigned * mp_ptr;
typedef const unsigned * mp_srcptr;


void __gmpn_tdiv_qr (mp_ptr, mp_ptr, long, mp_srcptr, long, mp_srcptr, long);

void __gmp_assert_fail (const char *filename, int linenum, const char *expr)
     __attribute__ ((noreturn));



unsigned
__gmpn_divrem_1 (mp_ptr qp, long xsize,
                 mp_srcptr ap, long size, unsigned d)
{
  long total_size;
  long i;
  unsigned dinvh, dinvl;
  unsigned r;

  do {
    if (!(xsize >= 0))
      __gmp_assert_fail ("divrem_1_two_ice.c", 179, "xsize >= 0");
  } while (0);

  do {
    if (!(size >= 0))
      __gmp_assert_fail ("divrem_1_two_ice.c", 180, "size >= 0");
  } while (0);

  do {
    if (!(d != 0))
      __gmp_assert_fail ("divrem_1_two_ice.c", 181, "d != 0");
  } while (0);

  do {
    if (!(((qp+xsize) == (ap) || ! ((qp+xsize) + (size) > (ap) && (ap) + (size) > (qp+xsize)))))
      __gmp_assert_fail ("divrem_1_two_ice.c", 183, "((qp+xsize) == (ap) || ! ((qp+xsize) + (size) > (ap) && (ap) + (size) > (qp+xsize)))");
  } while (0);

  total_size = size + xsize;
  if (total_size == 0)
    return 0;
  qp += (total_size - 1);
  if ((d & ((~ (unsigned) 0) ^ ((~ (unsigned) 0) >> 1))) != 0)
    {
      do {
        unsigned a[4];
        unsigned q[3];
        unsigned d_array[2];
        unsigned r_dummy[2];

        do {
          if (!(((d) & ((~ (unsigned) 0) ^ ((~ (unsigned) 0) >> 1))) != 0))
            __gmp_assert_fail ("divrem_1_two_ice.c", 193, "((d) & ((~ (unsigned) 0) ^ ((~ (unsigned) 0) >> 1))) != 0");
        } while (0);

        a[0] = (~ (unsigned) 0);
        a[1] = (~ (unsigned) 0);
        a[2] = (~ (unsigned) 0);
        a[3] = (~ (unsigned) 0);
        d_array[0] = 0L;
        d_array[1] = d;
        __gmpn_tdiv_qr (q, r_dummy, (long) 0, a, (long) 4, d_array, (long) 2);
        do {
          if (!(q[2] == 1))
            __gmp_assert_fail ("divrem_1_two_ice.c", 193, "q[2] == 1");
        } while (0);
        dinvl = q[0];
        dinvh = q[1];
      } while (0);

      i = size-1;
      r = 0;
      if (i > 0)
        {
          r = ap[i];
          if (r < d)
            i--;
        }

      while (i >= 1)
        {

          do {
            unsigned _n2h = (r);
            unsigned _n2l = (ap[i]);
            unsigned _n10h = (ap[i-1]);
            unsigned _d = (d);
            unsigned _n1, _nadjh, _sumh, _suml, _q1h, _q1l, _mask, _r;
            unsigned _x3, _x2, _x1, _x0;

            _n1 = _n10h >> ((8*4) - 1);

            _nadjh = _n10h + (-_n1 & _d);

            __asm__ ("subl %5,%1\n\tsbbl %3,%0"
                     : "=r" ((unsigned)(_sumh)), "=&r" ((unsigned)(_suml))
                     : "0" ((unsigned)(_n2h)), "g" ((unsigned)(0)),
                       "1" ((unsigned)(_n2l)), "g" ((unsigned)(_n1)));
            do {
              unsigned _xh = (dinvh);
              unsigned _xl = (dinvl);
              unsigned _yh = (_sumh);
              unsigned _yl = (_suml);
              unsigned _mh, _ml;

              __asm__ ("mull %3"
                       : "=a" (_x0), "=d" (_x1)
                       : "%0" ((unsigned)(_xl)),
                         "rm" ((unsigned)(_yl)));

              __asm__ ("mull %3"
                       : "=a" (_x2), "=d" (_x3)
                       : "%0" ((unsigned)(_xh)), "rm" ((unsigned)(_yh)));

              __asm__ ("mull %3"
                       : "=a" (_ml), "=d" (_mh)
                       : "%0" ((unsigned)(_xh)), "rm" ((unsigned)(_yl)));

              do {
                unsigned _c1, _s0;

                __asm__ ("addl %5,%1\n\tadcl %3,%0"
                         : "=r" ((unsigned)(_c1)), "=&r" ((unsigned)(_s0))
                         : "%0" ((unsigned)(0)), "g" ((unsigned)(0)),
                           "%1" ((unsigned)(_x1)), "g" ((unsigned)(_ml)));

                __asm__ ("addl %5,%1\n\tadcl %3,%0"
                         : "=r" ((unsigned)(_x3)), "=&r" ((unsigned)(_x2))
                         : "%0" ((unsigned)(_x3)), "g" ((unsigned)(0)),
                           "%1" ((unsigned)(_x2)), "g" ((unsigned)(_mh)));

                __asm__ ("addl %5,%1\n\tadcl %3,%0"
                         : "=r" ((unsigned)(_x3)), "=&r" ((unsigned)(_x2))
                         : "%0" ((unsigned)(_x3)), "g" ((unsigned)(0)),
                           "%1" ((unsigned)(_x2)), "g" ((unsigned)(_c1)));

                (_x1) = _s0;

              } while (0);

              __asm__ ("mull %3"
                       : "=a" (_ml), "=d" (_mh)
                       : "%0" ((unsigned)(_xl)), "rm" ((unsigned)(_yh)));

              do {
                unsigned _c1, _s0;

                __asm__ ("addl %5,%1\n\tadcl %3,%0"
                         : "=r" ((unsigned)(_c1)), "=&r" ((unsigned)(_s0))
                         : "%0" ((unsigned)(0)), "g" ((unsigned)(0)),
                           "%1" ((unsigned)(_x1)), "g" ((unsigned)(_ml)));

                __asm__ ("addl %5,%1\n\tadcl %3,%0"
                         : "=r" ((unsigned)(_x3)), "=&r" ((unsigned)(_x2))
                         : "%0" ((unsigned)(_x3)), "g" ((unsigned)(0)),
                           "%1" ((unsigned)(_x2)), "g" ((unsigned)(_mh)));

                __asm__ ("addl %5,%1\n\tadcl %3,%0"
                         : "=r" ((unsigned)(_x3)), "=&r" ((unsigned)(_x2))
                         : "%0" ((unsigned)(_x3)), "g" ((unsigned)(0)),
                           "%1" ((unsigned)(_x2)), "g" ((unsigned)(_c1)));

                (_x1) = _s0;

              } while (0);

            } while (0);

            __asm__ ("addl %5,%1\n\tadcl %3,%0"
                     : "=r"  ((unsigned) (_q1h)),
                       "=&r" ((unsigned) (_q1l))
                     : "%0"  ((unsigned) (_n2h)),
                       "g"   ((unsigned) (_x3)),
                       "%1"  ((unsigned) (_n2l)),
                       "g"   ((unsigned) (_x2)));

            __asm__ ("addl %5,%1\n\tadcl %3,%0"
                     : "=r" ((unsigned)(_q1h)), "=&r" ((unsigned)(_q1l))
                     : "%0" ((unsigned)(_q1h)), "g" ((unsigned)(0)),
                       "%1" ((unsigned)(_q1l)), "g" ((unsigned)(1)));

            __asm__ ("mull %3"
                     : "=a" (_x1), "=d" (_x2)
                     : "%0" ((unsigned)(_q1l)), "rm" ((unsigned)(_d)));

            _x2 += _q1h * _d;

            __asm__ ("subl %5,%1\n\tsbbl %3,%0"
                     : "=r" ((unsigned)(_mask)), "=&r" ((unsigned)(_r))
                     : "0" ((unsigned)(_n2l)), "g" ((unsigned)(_x2)),
                       "1" ((unsigned)(_n10h)), "g" ((unsigned)(_x1)));

            do {
              if (!(_mask == 0 || _mask == (~ (unsigned) 0)))
                __gmp_assert_fail ("divrem_1_two_ice.c", 243, "_mask == 0 || _mask == (~ (unsigned) 0)");
            } while (0);

            (r) = _r + (_mask & _d);

            __asm__ ("subl %5,%1\n\tsbbl %3,%0"
                     : "=r" ((unsigned)(qp[0])), "=&r" ((unsigned)(qp[-1]))
                     : "0" ((unsigned)(_q1h)), "g" ((unsigned)(0)),
                       "1" ((unsigned)(_q1l)), "g" ((unsigned)(-_mask)));

          } while (0);

          qp -= 2;
          i -= 2;
        }
    }
  else
    {
      r = 0;
    }
  return r;
}

--=-=-=--
>Fix:
>Release-Note:
>Audit-Trail:
>Unformatted:
 --=-=-=
 


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