This fragment of code:
#include <stdio.h>
int main() {
int a = 130;
char *ptr;
ptr = (char *)&a;
printf("%d ",*ptr);
return 0;
}
doesn't have undefined or unspecified behaviour, besides the quite obscure possibility that 130
would somehow happen to be trap value when accessed as (implicitly signed) char
, but there are many possible outcomes:
- output is
-126
on a little-endian platform where char is signed and the representation is 2's complement
- output is something else on an architecture that uses sign-and-magnitude or one's complement for the negative numbers.
- output is
130
on a little-endian platform where char is unsigned.
- output is
0
on a big-endian platform where char is signed or unsigned
- output could be
0
on a middle-endian platform. Or it could be -126
or 130
or something else if int
is represented by one, two bytes
- there are platforms where
sizeof(int)
is 1. It might be that all addressable primitive values have sizeof
1 - these wouldn't then have any endianness at all.
Some of these are obscure, but both little- and big-endian computers do exist widely, and on ARM processors the char
s are unsigned
by default.
To not complicate things too much, the endianess detection ought to be done using unsigned
types.
The union
test works if you use fixed-size types
union {
uint32_t the_int;
uint8_t fragments[4];
}
You wouldn't test the endianness of your computer at runtime! The code has to be compiled for one and one endianness only so you can do it at compile-time anyway. The actual endianness checks that need to be done at runtime concern only data structures read from files or interprocess communication.