3

I have arduino uno. I am trying to send and receive serial data from arduino to python. I have usb to uart converter. I have connected its tx to rx of Arduino and rx to tx of Arduino and gnd is connected to gnd. I have connected this usb to my laptop where I have written below python script:

import serial

ser = serial.Serial(port='COM6')

res = ser.read(10) print(bytes.hex(res)) data = b"\x7E\x7E\xAA\x03\xAB\x77" ser.write(data)

ser.close()

In above code, I am first reading the serial data, once the data is received, I sent out some hex packets. Below is the Arduino code:

void setup() 
{
  Serial.begin(9600);
}

void loop() { const byte message[] = {0xAA, 0xBB, 0x06, 0x00, 0x00, 0x00, 0x01, 0x01, 0x03, 0x03 };

Serial.write(message, sizeof message); Serial.println("data sent"); delay(1000);

char buffer[6]; if (Serial.available() > 0) { int size = Serial.readBytesUntil('\x77', buffer, 6); for (int i = 0 ; i < size ; i++) { Serial.println(buffer[i], HEX); } } }

In above code, I am first sending out the hex packets (which is received fine on python side) and then it waits for serial data. Once serial data is available to read, it reads it unitll \x77 and prints out all data. This is received on serial console of Arduino:

enter image description here

You will notice that it has received the data but there are some extra FF being received. Why have we recived these FF. Also in the python code, we know we are sending data of length 6 so accordingly we have defined char buffer[6] in arduino but what if we have to receive data which we do not what length it will be. Please help. Thanks

S Andrew
  • 183
  • 9

1 Answers1

4

The effect that you see is type promotion, in the C++ standard called "integral promotion", which happens implicitly. Values of type char are cast to int. Commonly, and in your case too, the char is by default signed.

The values 0xAA and 0xAB have a set most significant bit, which commonly designates a negative value in two's complement. This holds true for your case. And so these negative values are cast to the same negative values, but in full width of an int. In your case, an int has 32 bits.

Hex 0xAA as (by default signed) char is -86 decimal. And -86 decimal as (by definition signed) int is 0xFFFFFFAA hex.

Printed as hex, all bits are shown. So you see all these FF.

The solution is to mask only the interesting lower 8 bits:

    {
      Serial.println(buffer[i] & 0xFF, HEX);
    }
the busybee
  • 2,408
  • 9
  • 18