As part of answering another question, I came across a piece of code like this, which gcc compiles without complaint.
typedef struct {
struct xyz *z;
} x
Well... All I can say is that your previous assumption was incorrect. Every time you use a struct X
construct (by itself, or as a part of larger declaration), it is interpreted as a declaration of a struct type with a struct tag X
. It could be a re-declaration of a previously declared struct type. Or, it can be a very first declaration of a new struct type. The new tag is declared in scope in which it appears. In your specific example it happens to be a file scope (since C language has no "class scope", as it would be in C++).
The more interesting example of this behavior is when the declaration appears in function prototype:
void foo(struct X *p); // assuming `struct X` has not been declared before
In this case the new struct X
declaration has function-prototype scope, which ends at the end of the prototype. If you declare a file-scope struct X
later
struct X;
and try to pass a pointer of struct X
type to the above function, the compiler will give you a diagnostics about non-matching pointer type
struct X *p = 0;
foo(p); // different pointer types for argument and parameter
This also immediately means that in the following declarations
void foo(struct X *p);
void bar(struct X *p);
void baz(struct X *p);
each struct X
declaration is a declaration of a different type, each local to its own function prototype scope.
But if you pre-declare struct X
as in
struct X;
void foo(struct X *p);
void bar(struct X *p);
void baz(struct X *p);
all struct X
references in all function prototype will refer to the same previosly declared struct X
type.