diff -r 92c20f8b297f -r d7d98c4479ab degal/lib/EXIF.py --- a/degal/lib/EXIF.py Thu Jun 11 22:50:44 2009 +0300 +++ b/degal/lib/EXIF.py Thu Jun 11 23:24:48 2009 +0300 @@ -81,7 +81,7 @@ # # ----- See 'changes.txt' file for all contributors and changes ----- # # - +import mmap # Don't throw an exception when given an out of range character. def make_string(seq): @@ -1240,20 +1240,27 @@ class EXIF_header: def __init__(self, file, endian, offset, fake_exif, strict, debug=0): self.file = file + self.mmap = mmap.mmap(file.fileno(), 0, access=mmap.ACCESS_READ) self.endian = endian self.offset = offset self.fake_exif = fake_exif self.strict = strict self.debug = debug self.tags = {} + + def pread(self, reloffset, length): + """Read bytes from self.file at relative offset """ + + offset = self.offset + reloffset + + return self.mmap[offset:offset + length] # convert slice to integer, based on sign and endian flags # usually this offset is assumed to be relative to the beginning of the # start of the EXIF information. For some cameras that use relative tags, # this offset may be relative to some other starting point. def s2n(self, offset, length, signed=0): - self.file.seek(self.offset+offset) - slice=self.file.read(length) + slice=self.pread(offset, length) if self.endian == 'I': val=s2n_intel(slice) else: @@ -1349,8 +1356,7 @@ # XXX investigate # sometimes gets too big to fit in int value if count != 0 and count < (2**31): - self.file.seek(self.offset + offset) - values = self.file.read(count) + values = self.pread(offset, count) #print values # Drop any garbage after a null. values = values.split('\x00', 1)[0] @@ -1426,8 +1432,7 @@ else: tiff = 'II*\x00\x08\x00\x00\x00' # ... plus thumbnail IFD data plus a null "next IFD" pointer - self.file.seek(self.offset+thumb_ifd) - tiff += self.file.read(entries*12+2)+'\x00\x00\x00\x00' + tiff += self.pread(thumb_ifd, entries*12+2)+'\x00\x00\x00\x00' # fix up large value offset pointers into data area for i in range(entries): @@ -1454,8 +1459,7 @@ strip_off = newoff strip_len = 4 # get original data and store it - self.file.seek(self.offset + oldoff) - tiff += self.file.read(count * typelen) + tiff += self.pread(oldoff, count * typelen) # add pixel strips and update strip offset info old_offsets = self.tags['Thumbnail StripOffsets'].values @@ -1466,8 +1470,7 @@ tiff = tiff[:strip_off] + offset + tiff[strip_off + strip_len:] strip_off += strip_len # add pixel strip to end - self.file.seek(self.offset + old_offsets[i]) - tiff += self.file.read(old_counts[i]) + tiff += self.pread(old_offsets[i], old_counts[i]) self.tags['TIFFThumbnail'] = tiff