1

I have read the related questions to this Lint warning about the suspicious truncation, but here it is a purely C case.

The following line is where the Warning #647 pops up:

pCont->sig -= (signed int64_t)((sub2 << 8)/pCont->freq + 1);

where pCont->sig is also 64 bit signed (type signed int64_t), and both sub2 and freq are 32 bit unsigned. All this is compiled with armcc.

Already tried, without success, to cast the 1 to unsigned 32 bit, but the problem persists.

Any idea on what I might try, or what is going wrong here?

cafce25
  • 15,907
  • 4
  • 25
  • 31
titus.andronicus
  • 517
  • 1
  • 7
  • 19
  • 2
    Unrelated to your problem, but `int64_t` is already defined to be `signed`, you don't need to specify `signed` again when using it. See e.g. [this fixed-width integer reference](http://en.cppreference.com/w/c/types/integer). – Some programmer dude Aug 24 '16 at 07:29
  • 2
    Do you need: `((int64_t)sub2 << 8) / pCont->freq + 1`? – Jonathan Leffler Aug 24 '16 at 07:34
  • 1
    The basic questions you have to answer for yourself: "why are you using a signed type to store the value when it can never be negative?" And "why are you storing it as a 63-bit value when the expression can never produce more than 32 valid bits?" And it won't hurt to think about "What happens when sub2 is too large and the value overflows?" Only after you can say "I meant to do that!" can you suppress the warning. – Hans Passant Aug 24 '16 at 07:54

1 Answers1

4

From this reference about the warning

For example:

(long) (n << 8)

might elicit this message if n is unsigned int, whereas

(long) n << 8

would not. In the first case, the shift is done at int precision and the high order 8 bits are lost even though there is a subsequent conversion to a type that might hold all the bits. In the second case, the shifted bits are retained.

This seems to fit your case exactly and also show you how to fix it.

Some programmer dude
  • 400,186
  • 35
  • 402
  • 621