For example, is this code valid, or does it invoke undefined behavior by violating the aliasing rules?
int x;
struct s { int i; } y;
x = 1;
y = *(struct s *)&x;
printf("%d\n", y.i);
My interest is in using a technique based on this to develop a portable method for performing aliased reads.
Update: here is the intended usage case, a little bit different, but it should be valid if and only if the above is valid:
static inline uint32_t read32(const unsigned char *p)
{
struct a { char r[4]; };
union b { struct a r; uint32_t x; } tmp;
tmp.r = *(struct a *)p;
return tmp.x;
}
GCC, as desired, compiles this to a single 32-bit load, and it seems to avoid the aliasing issues that could happen if p
actually points to a type other than char
. In other words, it seems to act as a portable replacement for the GNU C __attribute__((__may_alias__))
attribute. But I'm uncertain whether it's really well-defined...