Wojtek said:
Wojtek said:
Wojtek Lerch wrote:
[...] GCC, for example, allows FAM
initialization as an extension. [...]
What does sizeof return when applied to the name of such object?
To answer my own question, sizeof does not include the FAM. The
analogy with arrays of unknown size is bogus.
The analogy was supposed to apply to how a compiler determines the size
of an object, and my point was that there are situations where the size
is known only after the initialization has been parsed.
But even that analogy is not very good: in the case of normal arrays,
the initializer determines the *type* of the object, and then the size
follows
from the type in the usual way. In the case of a structure with a FAM,
the type of the object is the struct, and the size of that type does not
include
the array (or at least not necessarily all of it). Since the size of
the object, as reported by sizeof, doesn't include the array either, one
could argue that the array doesn't really belong to the declared object,
but to a
larger unnamed object that contains both the struct and the array.
(That's, BTW, more or less how this extension is explained by GCC
documentation.)
I think the C99 Standard [...]
You do realize that the discussion was not about a standard feature, but
a GCC extension, right?
I wanted to show that according to the C99 Standard (in my interpretation),
it doesn't have to be an extension. I'm sorry if i slightly missed the
intention of this thread.
[...] makes no difference between non-subobjects and
subobjects. It just says
"Each brace-enclosed initializer list has an associated current object.
When no designations are present, subobjects of the current object are
initialized in order according to the type of the current object [...]"
Um... It says "subobjects" right there, and doesn't mention
non-subobjects. Is that not a difference?
It says "subobjects ... are initialized ..." here, and in the following text
it says "If an array of unknown size is initialized...". These two
paragraphs fit perfectly together, I think.
Does it? What is the type of the FAM before and after the initializer?
I'm not really sure how I should interpret this wording. The meaning that is
compatible with my reading is: The effective type of the object is an array
type with that many initializers.
That does not, in my reading, necessarily mean that any expression refering
to it (like, a member access) actually has that type too. The aliasing rules
allow an object whose effective type is "T[N]" be accessed by an lvalue of
type "T[]".
Right. But does that mean that an object declared using the GCC
extension is bigger than its type, or does it mean that the declared
object is the size of its type but is a subobject of a bigger, unnamed
object that the compiler allocates to accommodate for the initialized
FAM? The documentation is not completely clear on that, and of course
C99 is silent on the matter.
In the following the object referenced is also larger than the effective
type of a sub-portion of it (at least twice as large, actually).
int *p = malloc(sizeof *p * 2);
*p = 0; // modify the first half only
In the case of "int[]" vs "int[N]", the "int[]" doesn't make any assumption
on the type of the object referenced, and doesn't need to do that either: As
long as you don't invoke sizeof on it, you can perfectly well use such an
expression to modify array elements.
I *think* that any object of size N bytes is also N*(N+1)/2 objects, each
being different because the start address or size of them is different. What
object is addressed depends on the lvalue you use (which in turn determines
the address and effective type, i.e size). Not sure what object is accessed
by an "T[]" expression though - I could imagine that the size-N object is
addressed. Tho if you have any insights, please lemme hear!