Skip to content

Commit 3668cb3

Browse files
committed
BUG: work round int overflow in size calculation
Omar pointed out the integer overflow in calculating the image size of an image of size > 4GB, on a 32-bit platform.
1 parent ad95b4e commit 3668cb3

File tree

2 files changed

+23
-1
lines changed

2 files changed

+23
-1
lines changed

nibabel/tests/test_utils.py

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1227,3 +1227,21 @@ def assert_rt(data,
12271227
slope = slope,
12281228
post_clips = post_clips,
12291229
nan_fill = nan_fill)
1230+
1231+
1232+
def test_array_from_file_overflow():
1233+
# Test for int overflow in size calculation in array_from_file
1234+
shape = (1500,) * 6
1235+
class NoStringIO: # Null file-like for forcing error
1236+
def seek(self, n_bytes):
1237+
pass
1238+
def read(self, n_bytes):
1239+
return b''
1240+
try:
1241+
array_from_file(shape, np.int8, NoStringIO())
1242+
except IOError as err:
1243+
message = str(err)
1244+
assert_equal(message,
1245+
'Expected {0} bytes, got {1} bytes from {2}\n'
1246+
' - could the file be damaged?'.format(
1247+
11390625000000000000, 0, 'object'))

nibabel/volumeutils.py

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,9 @@
1414
import gzip
1515
import bz2
1616
from os.path import exists, splitext
17+
from operator import mul
18+
19+
from .externals.six.moves import reduce
1720

1821
import numpy as np
1922

@@ -504,7 +507,8 @@ def array_from_file(shape, in_dtype, infile, offset=0, order='F', mmap=True):
504507
pass
505508
if len(shape) == 0:
506509
return np.array([])
507-
n_bytes = int(np.prod(shape) * in_dtype.itemsize)
510+
# Use reduce and mul to work round integer overflow on 32-bit platforms
511+
n_bytes = reduce(mul, shape) * in_dtype.itemsize
508512
if n_bytes == 0:
509513
return np.array([])
510514
# Read data from file

0 commit comments

Comments
 (0)