Is the following code legal in C++?
int get_i(int idx) { ... }
float transform(int i) { ... }
void use(float f) { ... }
static_assert(sizeof(int) == sizeof(float));
void* buffer = std::malloc(n * sizeof(int));
int* i_buffer = reinterpret_cast<int*>(buffer);
float* f_buffer = reinterpret_cast<float*>(buffer);
// Fill int values into the buffer
for(int idx = 0; idx < n; ++idx)
i_buffer[idx] = get_i(idx);
// Transform int value to float value, and overwrite
// (maybe violates strict aliassing rule?)
for(int idx = 0; idx < n; ++idx)
f_buffer[idx] = transform(i_buffer[idx]);
for(int idx = 0; idx < n; ++idx)
use(f_buffer[idx]);
The second step reads the buffer value as an int
, and then writes a float
in its place. It never accesses the memory through i_buffer
again afterwards, so there is no type aliasing when reading.
However the assignment f_buffer[idx] =
writes a float
object into an int
object, which is UB.
Is there a way to make the compiler consider this to mean that the lifetime of the int
should end, and a float
object should be constructed in its place, so that there is no type aliassing?