You might want to consider not overlaying structs onto memory buffers. Just read the bytes in a deserialization step instead. Something like:
struct A {
uint8_t aByte;
uint32_t aDWord;
uint16_t aWord;
};
void serialize(FILE* fp, A const& aStruct) {
fwrite(&aStruct.aByte, sizeof(aStruct.aByte), 1, fp);
fwrite(&aStruct.aDWord, sizeof(aStruct.aDWord), 1, fp);
fwrite(&aStruct.aWord, sizeof(aStruct.aWord), 1, fp);
}
void deserialize(FILE* fp, A& aStruct) {
fread(&aStruct.aByte, sizeof(aStruct.aByte), 1, fp);
fread(&aStruct.aDWord, sizeof(aStruct.aDWord), 1, fp);
fread(&aStruct.aWord, sizeof(aStruct.aWord), 1, fp);
}
instead of:
void serialise(FILE* fp, A const& aStruct) {
fwrite(&aStruct, sizeof(aStruct), 1, fp);
}
void deserialise(FILE* fp, A& aStruct) {
fread(&aStruct, sizeof(aStruct), 1, fp);
}
The first example isn't dependent on structure packing rules where the second example is. I would recommend using the one that isn't. Most languages (not sure about C#) give you some way to read and write raw bytes so do all of the serialization/deserialization memberwise instead of a singular memory block and the packing/padding problems go away.