Background: We're implementing a dynamic library in C++ that extends the functionality of a C program. For one of the main structs used in the C program, we would like to add our own library specific fields. Currently when we need a new field, we ask nicely that the developers of the C program add a field for us and we end up having a massive casting mess. I was wondering if we could instead do the following:
Header file of main program:
#ifdef __cplusplus
extern "C" {
#endif
/* ... */
typedef struct ImportantStruct {
/* Definitions */
} ImportantStruct
/* ... */
#ifdef __cplusplus
}
#endif
Our Header File:
//...
class ObjectType : public ImportantStruct {
// Our extra fields
}
//...
I guess I have two questions:
1) Is this even legal?
2) What problems does this create when the C program tries to use the struct part of the object?
Since the ImportantStruct
is a POD structure (automatically it has standard layout), and since ObjectType doesn't have other base types and if it doesn't have virtual methods, it also has a standard layout. Therefore it can be used as a struct in C.
1) Is this even legal?
Yes, it is.
2) What problems does this create when the C program tries to use the struct part of the object?
If your c function doesn't try to over-write it, you are safe. You can overwrite it like this :
void foo( struct ImportantStruct *s )
{
memset( s,0, sizeof(*s) );
}
If it does, then it depends on what is in ImportantStruct, and whether there are padded bytes.
Structure like this :
typedef struct {
int a;
char b;
} ImportantStruct;
might have padded bytes removed when made base class.
Anyway, I would use composition, and avoid any kind of problems. But you have to make sure it is the first member, and that the ObjectType has standard layout.