I said that wrong. In the macro you suggested,
#define array_offsetof(type, member, index) (size_t)(offsetof(type,
member) + sizeof(((type *)NULL)->##member[0]) * index)
your use of ## is not, in itself, a syntax error.
However, it is guaranteed to result in a syntax
error. Think for a moment about what ->##member
is supposed to do. It is supposed to first
replace "member" with the reprocessing tokens
Of the corresponding macro argument. Then it's
supposed to take the reprocessing token that
immediately precedes the ## (which is "->" in
this case), and the one that immediately
follows it (which, in this case, will normally
be the identifier for a member of the struct),
and concatenate them together to form a single
preprocessing token.
Now, why would you tell it to do that? The
character sequence "->member_identifier"
doesn't match any of the permitted forms for a
single preprocessing token. There's nothing
that you could pass as the second argument that
would result in a valid preprocessing token
after that concatenation. That sequence of
characters would normally be parsed as two
separate tokens, "->" and "member_identifier",
which would work fine. However, such parsing is
already complete by the time ## operators are
evaluated. What ## puts together will never
again be taken apart. If it doesn't already have
the correct form to qualify as a single
preprocessing token, the behavior is simply
undefined.
I suspect you had a subtly different concept of
what ## does, a concept that makes it not merely
harmless in this context, but actually necessary
for some reason. There is no such reason - with
the ## removed, that macro would do precisely
what I believe you wanted it to do.