The warning is as follows:
Wouldn't make more sense to make temp an 8 element array, and place the bytes as needed without all the shifts?
Then cast temp to long long in the return?
What is the endianism of the buffer data (same or different to CPU)? If the same just cast a unit64_t pointer onto byte 0 and read through the pointer.
The warning seems to imply a long long is only
32 bits on your platform.
--Mike
long long has to be at least 64 bits,
endian[n] is type char, which is then promoted to int for the shift.
Presumably int is 32 bits on this platform, which means a shift is valid over range 0 - 31.
You could do
temp += (unsigned long long)endian[n] << whatever
That's what I actually done.
Maybe
unsigned long long data_to_cpu64(char endian[8]) { /* little endian assumed */ return *(unsigned long long *)endian; }
works. See also https://onlinegdb.com/BJVM5D4C4.
The warning seems to imply a long long is only
32 bits on your platform.
No, it doesn't. `long long` is not involved in that shift expression at all. That warning implies that `int` is 32 bits on that platform. This `int` is a result of integral promotion applied to the original `char` value.
works.
Formally, that's a violation of strict aliasing semantics. Today it "works", tomorrow it might stop working.
avr-mike wrote:The warning seems to imply a long long is only
32 bits on your platform.
No, it doesn't. `long long` is not involved in that shift expression at all.
Yeah, MrKendo already corrected my erroneous thinking.
--Mike
skotti wrote:works.
Formally, that's a violation of strict aliasing semantics. Today it "works", tomorrow it might stop working.
I read recently about strict aliasing, and the only valid approach is to use memcpy to copy data from one type to another. So maybe this should work:
unsigned long long data_to_cpu64(char endian[8]) { unsigned long long ll; /* little endian assumed */ memcpy(&ll, endian, sizeof ll); return ll; }
The compiler should be able to optimize that to basically the same machine code as skotti's.
I think you want to cast your endian[4], otherwise it shifts the char 32 bits in an 8 bit char.
You CAN ignore warnings -- at your peril.
My recollection is that unsigned char may alias any object.
If char is unsigned, I expect the rule applies to char.
That said, char should be reserved for text.
The only exception I can think of at the moment
is dealing with legacy code that does it wrong.
Some day your code might be legacy code.