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]

Re: 2.95 compiler bug with optimization level > 0...


> Cool, that worked!  I can't tell you how grateful we(AMD-K7) are!!!!
> Assuming b) might be the problem, what "common misunderstanding
> about C" are you referring to?  Please include as much detail as you
> can.

People often assume that, in C, you can cast 'an address' to any type
you want and access it. This is incorrect; ISO C (i.e. ANSI C) is more
strict here. Basically, it disallows constructs like

float x;

void foo(long * y)
{
  *y = 0;
}

int main()
{
  foo((int*)&x);
}

The rule in ANSI C is simple: You must not access an object of some
type through a pointer of a different type (for exact rules, see ISO C
99, 6.5/7). In the case above, the access through y has undefined
behaviour, since a float object is access as a long object.

By the same pattern, the following code has undefined behaviour:

short foo()
{
  short x[2];
  x[0] = 1;
  *(int*)x = 0;
  return x[0];
}

Because this has undefined behaviour, the compiler can now make an
interesting optimization: If two pointers have different types, they
cannot possibly refer to the same object. So writing through a pointer
will not modify objects of a different type. As a result, the code
does not need to reload a value from memory when it could not have
changed.

egcs 1.1 already had this optimization as an option. With gcc 2.95, it
was turned on by default. Unfortunately, there is a lot of C code out
there that relies on the aliasing to work, so that this decision was
reverted for gcc 2.95.2.

Hope this helps,
Martin


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