Repository navigation
Memory exhaustion via crafted zip file #156002
Copy link
Copy link
Closed
Labels
3.10 (EOL)end of lifeend of life3.11only security fixesonly security fixes3.12only security fixesonly security fixes3.13only security fixesonly security fixes3.14bugs and security fixesbugs and security fixes3.15bugs and security fixesbugs and security fixes3.16new features, bugs and security fixesnew features, bugs and security fixesstdlibStandard Library Python modules in the Lib/ directoryStandard Library Python modules in the Lib/ directorytype-securityA security issueA security issue
Description
As reported by @tonghuaroot:
zipfile.ZipExtFile._read1() bounds the output of each decompress() call for DEFLATE members (it passes a max_length to zlib), but for bzip2 / LZMA / Zstandard members it called self._decompressor.decompress(data) with no bound. A whole compressed chunk was therefore expanded into a single allocation before the data = data[:self._left] clip ran.
Linked PRs
- gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard #156003
- [3.15] gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (GH-156003) #156362
- [3.14] gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (GH-156003) (GH-156362) #156737
- [3.13] gh-156002: Bound zipfile decompression for bzip2/LZMA (GH-156003) (GH-156362) #156738
- [3.12] gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (GH-156003) (GH-156362) #156739
- [3.11] gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (GH-156003) (GH-156362) #156740
- [3.10] gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (GH-156003) (GH-156362) #156741
- gh-156002: Keep reading through third-party zipfile decompressors #157180
- [3.15] gh-156002: Keep reading through monkey-patched zipfile decompressors (GH-157180) #157268
- [3.14] gh-156002: Keep reading through monkey-patched zipfile decompressors (GH-157180) (GH-157268) #157557
Reactions are currently unavailable
Metadata
Metadata
Assignees
Labels
3.10 (EOL)end of lifeend of life3.11only security fixesonly security fixes3.12only security fixesonly security fixes3.13only security fixesonly security fixes3.14bugs and security fixesbugs and security fixes3.15bugs and security fixesbugs and security fixes3.16new features, bugs and security fixesnew features, bugs and security fixesstdlibStandard Library Python modules in the Lib/ directoryStandard Library Python modules in the Lib/ directorytype-securityA security issueA security issue
Projects
- StatusShow more project fieldsDone
Activity
gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (GH-1…
pythongh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (…
[3.15] gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (
rasmusfaber commentedon Sep 3, 2026
Please note that this change and its backports breaks zipfile-deflate64, zipfile-zstd etc.
It changes what
ZipExtFile._read1()requires of a non-deflate decompressor: previously it was enough to register a third-party decompressor through_get_decompressor(), now you need adecompress(data, max_length)method and aneeds_input/_needs_inputattribute.I realize that
_get_decompressor()is private, but this seems to be the standard method to extend zipfile, and this seems like a lot of breakage for a low severity issue (CVSS 2.1).It should be pretty easy to fix the vulnerability for the stdlib decompressors and leave the third-party decompressors alone.
def _decompressor_needs_input(decompressor): # bz2/zstd expose the stdlib decompressor's public needs_input; the LZMA # wrapper keeps it private (_needs_input) to avoid adding public API. needs_input = getattr(decompressor, "needs_input", None) - return decompressor._needs_input if needs_input is None else needs_input + if needs_input is None: + return getattr(decompressor, "_needs_input", None) + return needs_inputHappy to open a PR if you want.
[3.14] gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (
7 remaining items
pythongh-156002: Keep reading through monkey-patched zipfile decompre…
pythongh-156002: Keep reading through monkey-patched zipfile decompre…
pythongh-156002: Keep reading through monkey-patched zipfile decompre…
pythongh-156002: Keep reading through monkey-patched zipfile decompre…
Update python314 to version 3.14.7 / rev 40 via SR 1379535
Update python311 to version 3.11.16 / rev 74 via SR 1379773
[3.13] gh-156002: Bound zipfile decompression for bzip2/LZMA (GH-156003…
[3.12] gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (
[3.10] gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (
[3.11] gh-156002: Bound zipfile decompression for bzip2/LZMA/Zstandard (
Update python313 to version 3.13.15 / rev 46 via SR 1381538
Update python310 to version 3.10.21 / rev 83 via SR 1381747
Update python312 to version 3.12.14 / rev 54 via SR 1381748