Revert "Issue #29094: Offsets in a ZIP file created with extern file object and modes" (#1467)
This reverts commit 0f4ed2cdc6e7887153c481f4c7298bc35e219d84 (though, the tests are retained) and the followup 58ab4b57da2e5db7ff9b9940dd21bbbe4d804957.
See discussion on bpo-29094.
diff --git a/Lib/zipfile.py b/Lib/zipfile.py
index cc9f2e6..3ab66ce 100644
--- a/Lib/zipfile.py
+++ b/Lib/zipfile.py
@@ -772,7 +772,6 @@
# set the modified flag so central directory gets written
# even if no files are added to the archive
self._didModify = True
- self._start_disk = 0
elif key == 'a':
try:
# See if file is a zip file
@@ -786,7 +785,6 @@
# set the modified flag so central directory gets written
# even if no files are added to the archive
self._didModify = True
- self._start_disk = self.fp.tell()
else:
raise RuntimeError('Mode must be "r", "w" or "a"')
except:
@@ -817,18 +815,17 @@
offset_cd = endrec[_ECD_OFFSET] # offset of central directory
self._comment = endrec[_ECD_COMMENT] # archive comment
- # self._start_disk: Position of the start of ZIP archive
- # It is zero, unless ZIP was concatenated to another file
- self._start_disk = endrec[_ECD_LOCATION] - size_cd - offset_cd
+ # "concat" is zero, unless zip was concatenated to another file
+ concat = endrec[_ECD_LOCATION] - size_cd - offset_cd
if endrec[_ECD_SIGNATURE] == stringEndArchive64:
# If Zip64 extension structures are present, account for them
- self._start_disk -= (sizeEndCentDir64 + sizeEndCentDir64Locator)
+ concat -= (sizeEndCentDir64 + sizeEndCentDir64Locator)
if self.debug > 2:
- inferred = self._start_disk + offset_cd
- print "given, inferred, offset", offset_cd, inferred, self._start_disk
+ inferred = concat + offset_cd
+ print "given, inferred, offset", offset_cd, inferred, concat
# self.start_dir: Position of start of central directory
- self.start_dir = offset_cd + self._start_disk
+ self.start_dir = offset_cd + concat
fp.seek(self.start_dir, 0)
data = fp.read(size_cd)
fp = cStringIO.StringIO(data)
@@ -858,7 +855,7 @@
t>>11, (t>>5)&0x3F, (t&0x1F) * 2 )
x._decodeExtra()
- x.header_offset = x.header_offset + self._start_disk
+ x.header_offset = x.header_offset + concat
x.filename = x._decodeFilename()
self.filelist.append(x)
self.NameToInfo[x.filename] = x
@@ -1201,7 +1198,7 @@
raise RuntimeError('Compressed size larger than uncompressed size')
# Seek backwards and write file header (which will now include
# correct CRC and file sizes)
- position = self.fp.tell() # Preserve current position in file
+ position = self.fp.tell() # Preserve current position in file
self.fp.seek(zinfo.header_offset, 0)
self.fp.write(zinfo.FileHeader(zip64))
self.fp.seek(position, 0)
@@ -1287,10 +1284,11 @@
file_size = zinfo.file_size
compress_size = zinfo.compress_size
- header_offset = zinfo.header_offset - self._start_disk
- if header_offset > ZIP64_LIMIT:
- extra.append(header_offset)
+ if zinfo.header_offset > ZIP64_LIMIT:
+ extra.append(zinfo.header_offset)
header_offset = 0xffffffffL
+ else:
+ header_offset = zinfo.header_offset
extra_data = zinfo.extra
if extra:
@@ -1334,7 +1332,7 @@
# Write end-of-zip-archive record
centDirCount = len(self.filelist)
centDirSize = pos2 - pos1
- centDirOffset = pos1 - self._start_disk
+ centDirOffset = pos1
requires_zip64 = None
if centDirCount > ZIP_FILECOUNT_LIMIT:
requires_zip64 = "Files count"
diff --git a/Misc/NEWS b/Misc/NEWS
index d8ca14a..01f4fef 100644
--- a/Misc/NEWS
+++ b/Misc/NEWS
@@ -42,6 +42,8 @@
Library
-------
+- Revert bpo-26293 for zipfile breakage. See also bpo-29094.
+
- bpo-30070: Fixed leaks and crashes in errors handling in the parser module.
- bpo-30061: Fixed crashes in IOBase methods next() and readlines() when
@@ -91,9 +93,6 @@
leading dots could match related hostnames again (e.g. .b.c matches a.b.c).
Patch by Milan Oberkirch.
-- Issue #29094: Offsets in a ZIP file created with extern file object and mode
- "w" now are relative to the start of the file.
-
- Issue #13051: Fixed recursion errors in large or resized
curses.textpad.Textbox. Based on patch by Tycho Andersen.