The codebase at work contains some code that looks roughly like this:
#define DATA_LENGTH 64
u_int32 SmartKey::SerialNumber()
{
unsigned char data[DATA_LENGTH];
// ... initialized data buffer
return *(u_int32*)data;
}
This code works correctly, but GCC gives the following warning:
warning: dereferencing pointer ‘serialNumber’ does break strict-aliasing rules
Can someone explain this warning? Is this code potentially dangerous? How can it be improved?
Update
With thanks to James McNellis’ answer I came up with the following utility function:
template<class T, class Data>
T BinaryCast(const Data & inData)
{
T ret;
std::copy(&inData[0], &inData[0] + sizeof(ret), reinterpret_cast<char*>(&ret));
return ret;
}
u_int32 SmartKey::SerialNumber()
{
unsigned char data[DATA_LENGTH];
// ... initialized data buffer
return BinaryCast<u_int32>(data);
}
Feel free to suggest improvements!
The warning is because you are violating the strict aliasing rule.
One way to do it correctly would be to copy the bytes from the
databuffer into au_int32object and return that object:This solution works because in C++ it is permitted to access any type of object as an array of
char.(
std::copy()is in<algorithm>)