#include <stdint.h>
#include <stdio.h>
int main(){
uint64_t number = 0;
for (uint8_t i = 0; i<4; i++){
number |= 0xFF<<(8*i);
printf("%032lb %lu\n",number,number);
}
return 0;
}
I wrote this function to debug my study project and i can't understand why i am getting this output:
00000000000000000000000011111111 255
00000000000000001111111111111111 65535
00000000111111111111111111111111 16777215
1111111111111111111111111111111111111111111111111111111111111111 18446744073709551615
Because i was expecting:
00000000000000000000000011111111 255
00000000000000001111111111111111 65535
00000000111111111111111111111111 16777215
11111111111111111111111111111111 4294967295
Integer constants ("literals") like 0xFF
have a type too. Hex literals are generally of type int
, unless they can only fit in an unsigned int
.
This means that at the last lap of your loop, you invoke undefined behavior (anything can happen) by doing 0xFF << 24
. This is shifting data into the sign bit of the int
0xFF.
One possible (not guaranteed) outcome of that undefined behavior is that the sign bit will get set and then later when converted to uint64_t
, the operand gets sign extended from 0xFF00000 = -16777216 into 0xFFFFFFFFFF00000. And when you bitwise OR everything together you end up with "all ones".
Solution: always make sure the left operand of shifts is an unsigned type of the same size as int
or larger. In this case change to 0xFFu
to enforce unsigned int
.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With