Commit e9d44ccb authored by Victor Stinner's avatar Victor Stinner

Issue #12175: FileIO.readall() now only reads the file position and size once.

parent 5eb55599
......@@ -161,6 +161,9 @@ Core and Builtins
Library
-------
- Issue #12175: FileIO.readall() now only reads the file position and size
once.
- Issue #12180: Fixed a few remaining errors in test_packaging when no
threading.
......
......@@ -547,14 +547,14 @@ fileio_readinto(fileio *self, PyObject *args)
}
static size_t
new_buffersize(fileio *self, size_t currentsize)
new_buffersize(fileio *self, size_t currentsize
#ifdef HAVE_FSTAT
, off_t pos, off_t end
#endif
)
{
#ifdef HAVE_FSTAT
off_t pos, end;
struct stat st;
if (fstat(self->fd, &st) == 0) {
end = st.st_size;
pos = lseek(self->fd, 0L, SEEK_CUR);
if (end != (off_t)-1) {
/* Files claiming a size smaller than SMALLCHUNK may
actually be streaming pseudo-files. In this case, we
apply the more aggressive algorithm below.
......@@ -579,9 +579,14 @@ new_buffersize(fileio *self, size_t currentsize)
static PyObject *
fileio_readall(fileio *self)
{
#ifdef HAVE_FSTAT
struct stat st;
off_t pos, end;
#endif
PyObject *result;
Py_ssize_t total = 0;
int n;
size_t newsize;
if (self->fd < 0)
return err_closed();
......@@ -592,8 +597,23 @@ fileio_readall(fileio *self)
if (result == NULL)
return NULL;
#ifdef HAVE_FSTAT
#if defined(MS_WIN64) || defined(MS_WINDOWS)
pos = _lseeki64(self->fd, 0L, SEEK_CUR);
#else
pos = lseek(self->fd, 0L, SEEK_CUR);
#endif
if (fstat(self->fd, &st) == 0)
end = st.st_size;
else
end = (off_t)-1;
#endif
while (1) {
size_t newsize = new_buffersize(self, total);
#ifdef HAVE_FSTAT
newsize = new_buffersize(self, total, pos, end);
#else
newsize = new_buffersize(self, total);
#endif
if (newsize > PY_SSIZE_T_MAX || newsize <= 0) {
PyErr_SetString(PyExc_OverflowError,
"unbounded read returned more bytes "
......@@ -632,6 +652,9 @@ fileio_readall(fileio *self)
return NULL;
}
total += n;
#ifdef HAVE_FSTAT
pos += n;
#endif
}
if (PyBytes_GET_SIZE(result) > total) {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment