One option is to have a header (call it header1.h
) that defines (probably one of many other similar definitions):
typedef struct Command_Line Command_Line;
This specifies that there is a type struct Command_Line
and an alias for it, Command_Line
.
You can now modify the header that defines the structure type details like this:
#include "header1.h"
struct Command_Line
{
char *label;
char *command_name;
enum command_enum command_name_enum;
};
You can also modify the header that declares the function to include header1.h
:
#include "header1.h"
int redefine_command(Command_Line *, char *, int);
(I don't really like anonymous types in function signatures — I'd rather have the parameters named like int redefine_command(Command_Line *cmd, char *new_text, int options);
so reading the declaration gives an indication of the meaning (compared with, say, int new_len
). It's especially important when there are multiple arguments with the same type.)
From C11 onwards, you can repeat a typedef
§6.7 Declarations):
- a typedef name may be redefined to denote the same type as it currently does, provided that type is not a variably modified type;
You might then avoid the separate header1.h
header. However, the header1.h
gives you an opaque type, which can be useful. You can pass pointers to the type between functions, but you can't access the data inside an opaque type because the compiler has no information about the internals of the type. (If it does have the information, it is no longer an opaque type.)
You can also do as chqrlie suggests and use struct Command_Line
in the function declaration. The Linux kernel coding rules actually forbid the use of typedef
for structure or union types. I think that typedef
names have their uses.
Note that the structure tag is optional unless the structure contains pointers to values of its own type, hence:
/* Valid */
typedef struct
{
char *label;
char *command_name;
enum command_enum command_name_enum;
} Command_Line;
This type can only be referenced via Command_Line
(so the function would have to be declared and defined when the structure definition is visible).
The structure tag is needed in these examples:
/* Invalid - List *next does not refer to the List type being defined */
typedef struct
{
void *data;
size_t size;
List *next;
} List;
/* Valid */
typedef struct List
{
void *data;
size_t size;
struct List *next;
} List;
/* Valid */
typedef struct List List;
struct List
{
void *data;
size_t size;
List *next;
};