liv2hak
liv2hak

Reputation: 14970

Strange behaviour when using pointers

I have a file with some binary data as follows.

aa 55 aa 55 aa 55 aa 55 aa 55 aa 55 aa 55 aa 55         
aa 55 aa 55 36 65 fb 5f 1e 92 d8 1b 55 f7 fb 5f         
1e 92 d8 1b

I want to extract the values 55 36 65 fb 5f 1e.

If I use the following code.

temp_1 = (data_ptr[offset]);
val = temp_1 << 40;

temp_1 = (data_ptr[offset + 1]);
val |= temp_1 << 32;

temp_1 = (data_ptr[offset + 2]);
val |= temp_1 << 24;

temp_1 = (data_ptr[ts_offset + 3]);
val |= temp_1 << 16;

temp_1 = (data_ptr[ts_offset + 4]);
val |= temp_1 << 8;

temp_1 = (data_ptr[ts_offset + 5]);
val |= temp << 0;

printf("read value %"PRIx64" \n",val);

The outupt of this printf is

3665fb5f1e92

Now I also try to calculate the same value using a single 64-bit ptr cast operation.

val = *(uint64_t*)(data_ptr + ts_offset);
printf("read value %"PRIx64" \n",val);

The output of the above code is

1bd8921e5ffb6536 

If you check the least significant 48-bits here 921e5ffb6536

It is the inverted compared to the first result.I am using a normal intel processor.Why is this behaviour? Is this expected.

Upvotes: 0

Views: 72

Answers (2)

chux
chux

Reputation: 153338

The behavior is expected.

The byte order of an integer is saved in memory varies. From least significant byte to most (Little endian) or most significant byte to least. (Big endian).

Google "endian" for tons of info or read "Guliver Travel's".

Upvotes: 1

Mats Petersson
Mats Petersson

Reputation: 129314

In your code that shifts the value, you are reading the highest byte from the lowest address (bits 40-47 from offset 0). I'm guessing your second case is running on a x86 machine, thus reading the lowest byte from the lowest address (because that's how x86 is defined, as is MANY other processors, they are called "little-endian" machines).

If you want the bytes in that particular order, on a little-endian machine, you will have to get bytes one by one and shift (if you wanted a whole 64-bit value, it may have been possible to use a byteswap instruction on x86, but I doubt it's enough value in that when you then need to "undo" that by shifting and masking the 16 bits you didn't actually need).

Upvotes: 2

Related Questions