Home > OS >  In C or C , is memory layout of uint64_t guaranteed to be the same as uint32_t[2] ? Can one be cast
In C or C , is memory layout of uint64_t guaranteed to be the same as uint32_t[2] ? Can one be cast

Time:12-20

In C or C , is memory layout of uint64_t guaranteed to be the same as uint32_t[2] ? Can I cast one to the other and have them always work as expected? Does it depend upon if the CPU is 32bit or 64bit or is it compiler implementation dependent?

CodePudding user response:

In C or C , is memory layout of uint64_t guaranteed to be the same as uint32_t[2] ?

No. Endianess.

Can one be cast as the other?

Maybe, maybe not, in C. A pointer to an array of 2 uint32_t may not be aligned to uint64_t. When the resulting pointer is not properly aligned, it's undefined behavior. https://port70.net/~nsz/c/c11/n1570.html#6.3.2.3p7

Yes in C . https://eel.is/c draft/expr#reinterpret.cast-7

Can I cast one to the other and have them always work as expected?

No. Possibly, you can cast, but you can't access the data with the handle after casting. It would be a strict alias violation.

Does it depend upon if the CPU is 32bit or 64bit

Not really.

or is it compiler implementation dependent?

Because the behavior would be undefined, it's very much compiler dependent.

CodePudding user response:

At least since C 20 there are no special integer values in C (as opposed to, I think, C, where they in theory still exist), and hence all bit combinations of two adjacent uint32 objects form a valid 64 bit integer bit sequence.

Casting a pointer is still disallowed because of aliasing and potentially alignment issues, but in C 20 you can use std::bit_cast() to obtain a bit-wise copy of the original: uint32_t arr[2] = {}; uint64_t ui64 = std::bit_cast<uint64_t>(arr);. Note that this performs a copy.

As Kamil said, the result may be surprising on a little endian system, but it is valid.

There is an hour-long, medium interesting CppCon talk about type punning by Timur Doumler on youtube. 52 minutes into the talk he calls the inability to interpret bytes as different types "the last hole in the object model of C " and says he'll write a proposal to fix it by introducing an equivalent to alignas, e.g. layoutas(T) that tells the compiler to accept interpretations as T.

  • Related