0

I have declared macros like this:

#define F_MASK_4_BIT 0xF
#define GET_F_4BIT_MASK(F, P) (((F) & (F_MASK_4_BIT << (P * 4))) >> (4 * P))

using macro like this:

uint8_t Feature = GET_F_4BIT_MASK(E, P);

Where E is uint64_t datatype P is uint8_t datatype

Which gives warning by Prefast: C6297: Arithmetic overflow: 32-bit value is shifted, then cast to 64-bit value. Results might not be an expected value.

How to fix this?

  • What is `FEATURE_MASK_4_BIT`. What is your platform/compiler etc. Please provide [mcve]. – Jabberwocky Mar 08 '19 at 11:06
  • A static code analyzer can only tell you that this code *might* misbehave, it cannot guarantee that it actually does. Right-shifting a signed value is unspecified, consider at least 0xFU to ensure the shift has defined behavior. A bit less insulting than 0xFULL. The days that macaroni like this was still useful are long gone btw, do favor a function and leave it up to the optimizer to inline it. – Hans Passant Mar 08 '19 at 11:39

1 Answers1

0

It's pretty self-explaining. If P has any value larger than 7 (7*4=28, max is 31), the F_MASK_4_BIT << (P * 4) will overflow. Because F_MASK_4_BIT is a integer constant of type int.

Fix this by using an appropriate type for the integer constant:

#define F_MASK_4_BIT 0xFull
Lundin
  • 195,001
  • 40
  • 254
  • 396
  • 2
    (Mandatory boring jokes about the mask being Full will follow...) – Lundin Mar 08 '19 at 11:27
  • I thought about writing similar answer but I had doubts. Won't it cause the same message if `F` is replaced by a 32 bit value? – Gerhardh Mar 08 '19 at 12:27
  • @Gerhardh What do you mean? `ull` = 64 bit. – Lundin Mar 08 '19 at 12:29
  • Yes. The OP does `64bit & 32bit`. Your suggested fix changes this to `64bit & 64bit.` If the macro is used with a first parameter that only is 32 bits long, the replaced expression becomes `32bit & 64bit` as the right side is still `ull` and the shifted bits could end up in the higher 32 bits. But I don't know how clever that tool is. – Gerhardh Mar 08 '19 at 12:34
  • @Gerhardh I don't understand what you are talking about. The shift has nothing to do with the left operand of &. – Lundin Mar 08 '19 at 18:27