Join GitHub today
GitHub is home to over 28 million developers working together to host and review code, manage projects, and build software together.Sign up
Denial of service issue #184
I found denial of service issue from PyPDF2 version 1.24. With fuzzed sample file PyPDF2 ends up using all CPU from one core.
Sample file is located at http://bugs.fi/media/afl/pypdf2/pypdf2-1.24-afl-dos.pdf which is fuzzed with American fuzzy lop and using https://bitbucket.org/jwilk/python-afl project as instrumentation component.
crasher.py (SHA1: a4fcecaa1e49472d45d6b2155cf70d62620b9622)
Execution with Python 2.7.9 using latest Git version (41d90b4):
If you insert the following lines into the
if len(tok) <= 0: # Prevents an infinite loop by raising # an error iff the stream is at the EOF raise PdfStreamError("File ended unexpectedly.")
You should insert the above code so that your
def readObject(stream, pdf): tok = stream.read(1) stream.seek(-1, 1) # reset to start idx = ObjectPrefix.find(tok) if idx == 0: # name object return NameObject.readFromStream(stream, pdf) elif idx == 1: # hexadecimal string OR dictionary peek = stream.read(2) stream.seek(-2, 1) # reset to start if peek == b_('<<'): return DictionaryObject.readFromStream(stream, pdf) else: return readHexStringFromStream(stream) elif idx == 2: # array object return ArrayObject.readFromStream(stream, pdf) elif idx == 3 or idx == 4: # boolean object return BooleanObject.readFromStream(stream) elif idx == 5: # string object return readStringFromStream(stream) elif idx == 6: # null object return NullObject.readFromStream(stream) elif idx == 7: # comment while tok not in (b_('\r'), b_('\n')): tok = stream.read(1) if len(tok) <= 0: # Prevents an infinite loop by raising # an error iff the stream is at the EOF raise PdfStreamError("File ended unexpectedly.") tok = readNonWhitespace(stream) stream.seek(-1, 1) return readObject(stream, pdf) else: # number object OR indirect reference if tok in NumberSigns: # number return NumberObject.readFromStream(stream) peek = stream.read(20) stream.seek(-len(peek), 1) # reset to start if IndirectPattern.match(peek) != None: return IndirectObject.readFromStream(stream, pdf) else: return NumberObject.readFromStream(stream)
Thank you very much for finding this bug, and waiting for us to get back to you.