[Bug c/65892] gcc fails to implement N685 aliasing of union members

msebor at gcc dot gnu.org gcc-bugzilla@gcc.gnu.org
Fri Apr 20 17:01:00 GMT 2018


https://gcc.gnu.org/bugzilla/show_bug.cgi?id=65892

--- Comment #34 from Martin Sebor <msebor at gcc dot gnu.org> ---
The questions in N2223 and the other documents are there to provide background
and justification for the proposed changes (the questions come surveys they
sent to various forums).  The proposed words are at the end of each of the
papers referenced from N2223.  I don't have the sense that N2223 covers this
case but it's closely related.

Memcpy and memmove transfer the effective type only to objects with no declared
type (i.e., allocated objects):

  int i = 123;
  void *p = malloc (sizeof i);
  memcpy (p, &i, sizeof i);   // *p's effective type is now int

This standard mentions just memcpy, memmove, and copies via a character type,
so other mechanisms do not transfer the effective type.  (The effective type of
other (typed) storage is that of its declared type.)  Memory is only allowed to
be accessed via an lvalue compatible with its effective type (or char), so
above, what's at p can only accessed as *(int*)p.

I think in the use case below:

   struct { int i; char buf[4]; } s, r;
   *(float *)s.buf = 1.;
   r = s;

the aggregate copy has to be viewed as a recursive copy of each of its members
and copying buf[4] must be viewed as a memcpy,  Char is definitely special (it
can accesses anything with impunity, even indeterminate values).  That said, I
don't think the rules allow char arrays to be treated as allocated storage so
while the store to s.buf via float* may be valid it doesn't change the
effective type of s.buf and so the only way to read the float value stored in
it is to copy it byte-by-byte (i.e., copy the float representation) to an
object whose effective type is float.  Some of the papers that deal with the
effective type rules might touch on this (e.g., DR 236, Clark's N1520


More information about the Gcc-bugs mailing list