-
Notifications
You must be signed in to change notification settings - Fork 107
Overflow in len function
-
Affected Components : builtin
-
Operating System : Linux
-
Python Versions : 2.6.x, 2.7.x, 3.1.x, 3.2.x
-
Reproducible : Yes
class A(object):
def __len__(self):
return 100 ** 100
class B(object):
def __len__(self):
return 2L
class C:
def __len__(self):
return 100 ** 100
class D:
def __len__(self):
return 2L
try:
len(A())
print """OK: 'class A(object)' with 'return 100 ** 100' - len calculated"""
except Exception as e:
print """KO: 'class A(object)' with 'return 100 ** 100' - len raise Error: """ + repr(e,)
try:
len(B())
print """OK: 'class B(object)' with 'return 2L' - len calculated"""
except Exception as e:
print """KO: class B(object) with return 2L - len raise Error: """ + repr(e,)
try:
len(C())
print """OK: 'class C' with 'return 100 ** 100' - len calculated"""
except Exception as e:
print """KO: 'class C' with 'return 100 ** 100' - len raise Error: """ + repr(e,)
try:
len(D())
print """OK: 'class C' with 'return 2L' - len calculated"""
except Exception as e:
print """KO: 'class C' with 'return 2L' - len raise Error: """ + repr(e,)
To reproduce the problem copy the source code
in a file and execute the script using the following command syntax:
$ python -OOBRtt test.py
Alternatively you can open python in interactive mode:
$ python -OOBRtt <press enter>
Then copy the lines of code into the interpreter.
The source code tets the ability of python to check the length of an object.
When the source code is executed
$ python -OOBRttu test.py
we have the same results both python 2.6.x and 2.7.x as follow:
KO: 'class A(object)' with 'return 100 ** 100'
Error: OverflowError('long int too large to convert to int',)
OK: 'class B(object)' with 'return 2L' - len calculated
KO: 'class C' with 'return 100 ** 100'
Error: TypeError('__len__() should return an int',)
KO: 'class C' with 'return 2L'
Error: TypeError('__len__() should return an int',)
in this case the len()
function in python does not check for the legth of the object and does not use "python int objects" (unlimited) and this can cause an Overflow
error as the object may contain the actual .length
property.
The reason of this is beacuse len(obj)
is implemented using PyObject_Size(), which in turn it stores the result into a Py_ssize_t, and this object is limited to sys.maxsize (2**31-1
for 32bit or 2**63-1
for 64bit systems).
And when the length of the object is bigger then the maximum size of an integer object in python, the type of the object changes to long.
Even this condition is not checked in the core libraries therefore an unexpected TypeError
is generated.
We are not aware on any easy solution other than writing a custom library to handle the described cases.
[Python built-in functions][01] [01]:https://docs.python.org/2/library/functions.html
[Python Classes][02] [02]:https://docs.python.org/2/tutorial/classes.html
[Python bug 12159][03] [03]:http://bugs.python.org/issue12159
[Python bug 15718][04] [04]:http://bugs.python.org/issue15718
[Python bug 21444][05] [05]:http://bugs.python.org/issue21444
Main site: pythonsecurity.org
OWASP Page: owasp.org/index.php/OWASP_Python_Security_Project