6
\$\begingroup\$

I am working on a program to decode MMS PDU files. They are binary files and I am reading them byte by byte and decoding each header value as I come to it.

One header value is the Date, and it's represented as follows (in hex):

85 04 57 E2 A2 49

0x85 is the "Date" header, 0x04 is the data length (4 bytes) and the 4 following bytes represent the date (timestamp).

I have code to read those 4 bytes and return it to me as a bytearray:

bytearray(b'W\xe2\xa2I')

Apparently \x57 is a W and \x49 is an I.

In order to parse this as a date, I need to convert it to an int. These bytes represent the timestamp 1474470473 (or 0x57E2A249).

I have code to convert this byte array into an int, but there has got be a better way to do it than the way I came up with.

timestamp = int(''.join(map(hex, byte_range)).replace('0x', ''), 16)
value = datetime.fromtimestamp(timestamp)

That is, I am converting every byte to a string (like "0x57"), joining them together, removing the "0x"s, then reading that string as a base 16 value. This works, but it seems a little too convoluted.

I then realized that I could replace the join/map with binascii.hexlify, so now my code is:

timestamp = int(binascii.hexlify(byte_range), 16)
value = datetime.fromtimestamp(timestamp)

Like I said, this code works, but I just feel there's a better way to do this than to convert the bytearray into a string and then parse that string back as a base-16 int.

\$\endgroup\$

1 Answer 1

7
\$\begingroup\$

To decode binary data, use struct.unpack().

>>> import struct
>>> byte_range = bytearray(b'\x85W\xe2\xa2I')
>>> date_header, timestamp = struct.unpack('>BL', byte_range)
>>> date_header
133
>>> timestamp
1474470473
\$\endgroup\$
1
  • \$\begingroup\$ unpack seems to be exactly what I want. I've never really known how to use it, unfortunately. timestamp = struct.unpack('>L', byte_range) gives me the value I expect. \$\endgroup\$
    – gen_Eric
    Sep 30, 2016 at 17:06

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.