views:

272

answers:

2

I'm reading in a binary file into a list and parsing the binary data. I'm using unpack() to extract certain parts of the data as primitive data types, and I want to edit that data and insert it back into the original list of bytes. Using pack_into() would make it easy, except that I'm using Python 2.4, and pack_into() wasn't introduced until 2.5

Does anyone know of a good way to go about serializing the data this way so that I can accomplish essentially the same functionality as pack_into()?

+1  A: 

Do you mean editing data in a buffer object? Documentation on manipulating those at all from Python directly is fairly scarce.

If you just want to edit bytes in a string, it's simple enough, though; struct.pack_into is new to 2.5, but struct.pack isn't:

import struct
s = open("file").read()
ofs = 1024
fmt = "Ih"
size = struct.calcsize(fmt)

before, data, after = s[0:ofs], s[ofs:ofs+size], s[ofs+size:]
values = list(struct.unpack(fmt, data))
values[0] += 5
values[1] /= 2
data = struct.pack(fmt, *values)
s = "".join([before, data, after])
Glenn Maynard
+2  A: 

Have you looked at the bitstring module? It's designed to make the construction, parsing and modification of binary data easier than using the struct and array modules directly.

It's especially made for working at the bit level, but will work with bytes just as well. It will also work with Python 2.4.

from bitstring import BitString
s = BitString(filename='somefile')

# replace byte range with new values
# The step of '8' signifies byte rather than bit indicies.
s[10:15:8] = '0x001122'

# Search and replace byte value with two bytes
s.replace('0xcc', '0xddee', bytealigned=True)

# Different interpretations of the data are available through properties
if s[5:7:8].int > 1000:
    s[5:7:8] = 1000

# Use the bytes property to get back to a Python string
open('newfile', 'wb').write(s.bytes)

The underlying data stored in the BitString is just an array object, but with a comprehensive set of functions and special methods to make it simple to modify and interpret.

Scott Griffiths
Thanks for this!
Jeff L