Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Creating xor checksum of all bytes in hex string In Python

Tags:

python

xor

While attempting to communicate with an audio processing device called BSS London Blu-80, I discovered I have to send a checksum created by Xoring the message. An example message being sent would be:

0x8d 0x1e 0x19 0x1b 0x83 0x00 0x01 0x01 0x00 0x00 0x00 0x4b 0x00 0x00 0xc2

With 0xc2 being the correct checksum for that message.

"The checksum is a single-byte exclusive or(xor) of all the bytes in the message body."

The message body is that above minus the checksum.

The code I attempt however:

packet = '0x8d 0x1e 0x19 0x1b 0x83 0x00 0x01 0x01 0x00 0x00 0x00 0x4b 0x00 0x00'
xor = 0
i = 0
while i < len(packet):
    xor = xor ^ ord(packet[i])
    i += 1

>>print xor
46
>>print hex(xor)
'0x2e'

I'm obviously doing something wrong here, and not fully understanding this. Any help will be GREATLY appreciated.

Thanks!

like image 496
Nicholas Avatar asked Oct 22 '14 22:10

Nicholas


1 Answers

You have declared packet as the printable representation of the message:

packet = '0x8d 0x1e 0x19 0x1b 0x83 0x00 0x01 0x01 0x00 0x00 0x00 0x4b 0x00 0x00'

so your current message is not [0x8d, 0x1e, ..., 0x00], but ['0', 'x', '8', 'd', ..., '0'] instead. So, first step is fixing it:

packet = '0x8d 0x1e 0x19 0x1b 0x83 0x00 0x01 0x01 0x00 0x00 0x00 0x4b 0x00 0x00'
packet = [chr(int(x, 16)) for x in packet.split(' ')]

Or, you could consider encoding it "right" from the beginning:

packet = '\x8d\x1e\x19\x1b\x83\x00\x01\x01\x00\x00\x00\x4b\x00\x00'

At this point, we can xor, member by member:

checksum = 0
for el in packet:
    checksum ^= ord(el)

print checksum, hex(checksum), chr(checksum)

the checksum I get is 0x59, not 0xc2, which means that either you have calculated the wrong one or the original message is not the one you supplied.

like image 176
Stefano Sanfilippo Avatar answered Oct 14 '22 17:10

Stefano Sanfilippo