http://gcc.gnu.org/bugzilla/show_bug.cgi?id=52448

             Bug #: 52448
           Summary: [4.4/4.5/4.6/4.7 Regression] cselim broken with calls
    Classification: Unclassified
           Product: gcc
           Version: 4.7.0
            Status: UNCONFIRMED
          Keywords: wrong-code
          Severity: normal
          Priority: P3
         Component: tree-optimization
        AssignedTo: unassig...@gcc.gnu.org
        ReportedBy: ja...@gcc.gnu.org


extern void abort (void);
extern void *malloc (__SIZE_TYPE__);
extern void free (void *);

__attribute__((noinline, noclone)) void
bar (char *x, int y)
{
  if (*x != '\n')
    abort ();
  if (y == 0)
    free (x);
}

__attribute__((noinline, noclone)) void
foo (char *x, int y)
{
  *x = '\n';
  bar (x, y);
  if (y)
    *x = '\0';
}

int
main ()
{
  char *p = malloc (1);
  if (p)
    {
      foo (p, 1);
      if (*p != '\0')
        abort ();
      foo (p, 0);
    }
  return 0;
}

The above testcase is miscompiled, starting with 4.3 with just -O2, before that
(including 3.2) with -O2 -ftree-cselim.  If you run the testcase under
valgrind, it will complain loudly, I could rewrite it (less portably) using
mmap/munmap to show it crash even without valgrind.

I'm afraid we need to invalidate the set of non-trapping MEMs on non-pure/const
calls (perhaps with the exception of selected builtins, e.g. none of the
string/mem builtins should actually unmap/mprotect/free any memory).

Reply via email to