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

--- Comment #12 from Martin Uecker <muecker at gwdg dot de> ---

The C standard says "However, when a . (or -> ) operator has a left operand
that is (a pointer to) a structure with a flexible array member and the right
operand names that member, it behaves as if that member were replaced with the
longest array (with the same element type) that would not make the structure
larger than the object being accessed;" 

This would imply that also for GCC not all elements can be accessed in the
following structure without invoking UB. For x86_64 'x' has 11 bytes (for clang
9) but a struct with replacement array actually needs 12.

struct foo { int a; short b; char t[]; } x = { .t = { 1, 2, 3 } }; 
// x has 11 bytes

struct bar { int a; short b; char t[3]; }; // 12 bytes


One can argue that this does not matter for an extension and maybe the C
standard should not be read in this way as itself also contains an example
using the sizeof() + n * sizeof() rule which implies that this amount of
storage is enough for n elements.

But the question is what programmers should use when using memcpy of statically
initialized structs which have a FAM?   sizeof() + n * sizeof() works for GCC
but not for clang.  sizeof(struct bar) works for neither.  One can use
MAX(sizeof(struct foo, offsetof(struct foo, t) + n * sizeof(char)) but I have
not seen anybody use it.

Reply via email to