can I ignore the following warning

Go To Last Post
12 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0


The warning is as follows:

 

This topic has a solution.
Last Edited: Fri. May 24, 2019 - 03:07 PM
This reply has been marked as the solution. 
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

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?

 

 

Click Link: Get Free Stock: Retire early! PM for strategy

share.robinhood.com/jamesc3274

 

 

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 2

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.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

The warning seems to imply a long long is only

32 bits on your platform.

 

--Mike

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

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

 

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

That's what I actually done.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

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.

In the beginning was the Word, and the Word was with God, and the Word was God.

Last Edited: Tue. Jun 4, 2019 - 10:02 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

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. 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.

 

skotti wrote:
works.

 

Formally, that's a violation of strict aliasing semantics. Today it "works", tomorrow it might stop working.

Last Edited: Fri. May 24, 2019 - 11:05 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

AndreyT wrote:

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

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

AndreyT wrote:

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.

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

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.

The largest known prime number: 282589933-1

In my humble opinion, I'm always right. 

Last Edited: Sat. May 25, 2019 - 07:32 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

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.

"SCSI is NOT magic. There are *fundamental technical
reasons* why it is necessary to sacrifice a young
goat to your SCSI chain now and then." -- John Woods