The program - some sort of old-school network messaging:
// Common header for all network messages.
struct __attribute__((packed)) MsgHeader {
uint32_t msgType;
};
// One of network messages.
struct __attribute__((packed)) Msg1 {
MsgHeader header;
uint32_t field1;
};
// Network receive buffer.
uint8_t rxBuffer[MAX_MSG_SIZE];
// Receive handler. The received message is already in the rxBuffer.
void onRxMessage() {
// Detect message type
if ( ((const MsgHeader*)rxBuffer)->msgType == MESSAGE1 ) { // Breaks strict-aliasing!
// Process Msg1 message.
const Msg1* msg1 = (const Msg1*)rxBuffer;
if ( msg1->field1 == 0 ) { // Breaks strict-aliasing!
// Some code here;
}
return;
}
// Process other message types.
}
This code violates strict-aliasing in modern GCC (and falls down to unspecified behaviour in modern C++). What is the correct way to solve the problem (to make the code that doesn't throw the "strict-aliasing" warning)?
P.S. If rxBuffer is defined as:
union __attribute__((packed)) {
uint8_t[MAX_MSG_SIZE] rawData;
} rxBuffer;
and then I cast &rxBuffer to other pointers it doesn't cause any warnings. But is it safe, right and portable way?