BitShift question

Hello Everybody,

I do have the following sketch that converts three bytes into a long using bit shifts.
What really puzzles me is that thios code is working on an ESP32 but the same code produces a different result on an Arduino 168.

byte RFAdress = 100;
byte BatteryLevel = 95;
byte SensorValue =67;
unsigned long Telegram;

Telegram = RFAdress + (BatteryLevel << 8) + (SensorValue << 16);

The first 8 bits of Telegram should be 100 (0110 0100)
The next 8 bits should be 95 (0101 1111)
And the last 8 bits should be 67 (0100 0011)

The overall result on the ESP is
4415332 (= ‭0100 0011 0101 1111 0110 0100‬)
On the arduino, I get
24420 (= 0101 1111 0110 0100)

It seems for me that the unsigned long has only 2 byte instead of 4 byte.

Am I doing anything wrong here?

Your values to be bit shifted are typed as bytes, and you are bit shifting them left to oblivion i.e. into numbers larger than the type can hold.

Integer promotion (Google this term) with the bit shift has created size for BatteryLevel <<8 with the Arduino as there are 16 bit integers. SensorValue needs to be cast as an unsigned long before the shift.

Telegram = RFAdress + (BatteryLevel << 8) + ((unsigned int)SensorValue << 16);

EDIT: Correction based on PaulS’s correction of my hasty post

Telegram = RFAdress + (BatteryLevel << 8) + ((unsigned long)SensorValue << 16);

With the ESP32 integer promotion must be to a 32 bit integer so the uncast bit shifting works as intended.

SensorValue needs to be cast as an unsigned long before the shift.

That comment is correct. The code that follows does not match the comment, though.

BatteryLevel also needs to be cast.Both should be cast to unsigned long, not unsigned int.

Thank you both for the quick reply.
Casting to unsigned long works now.


Casting to unsigned long works now.

Your code will be more portable if you cast to "uint32_t"