I'm working with an SDS011 particular sensor through its serial interface. The spec sheet (http://inovafitness.com/upload/file/20150311/14261262164716.pdf) indicates that the second to last byte of a serial packet is a checksum equal to sum of all the data bytes.
I am using pyserial to read and interpret the serial data. Here's a snippet of the code:
import serial
def read_sensor(port):
while True:
header = port.read(2)
if header == b'\xAA\xC0':
data = port.read(6)
checksum = port.read()
tail = port.read()
if tail == b'\xAB':
return header + data + checksum + tail
port = serial.Serial(port=MY_PORT)
packet = read_sensor(port)
data_sum = sum(packet[2:8])
checksum = packet[8]
if data_sum == checksum:
print('Ok')
else:
print('Error')
However, I haven't got a single packet whose checksum hasn't been an error. Is there anything I could be potentially doing wrong?
2 Answers 2
Generally, a checksum byte is computed using 8-bit arithmetic, with overflow ignored.
The Python sum function uses arithmetic of indefinite precision (eg, 32- or 64-bit words for small values, with additional words for larger numbers).
Try comparing checksum
to data_sum % 256
. If that doesn't fix the problem, print out some of the data packets and checksum values so that you can use a calculator to test different combinations.
-
data_sum % 256 fixed it. I thought it was strange that data_sum values were greater than a byte. Should've just checked the first byte!user1569339– user15693392016年04月16日 03:31:18 +00:00Commented Apr 16, 2016 at 3:31
I assume MY_PORT
stands for COMxx
. Since you set no timeout, it means port.read()
will block till it gets the number of bytes requested. I suggest you add a print()
to display the bytes returned, if any.
To get the sum, use data_sum = sum(packet[2:8]) & 0xff
to ensure you only get a byte. Also add port.reset_input_buffer()
right before you call read_sensor()
, to flush the input buffer.
It would also be a good idea to take at least 3 consecutive readings from the sensor in case of any errors in the first reading right after opening the port. Dont forget to add a port.close()
at the end of your code.