]> granicus.if.org Git - python/commitdiff
bpo-30068: add missing iter(self) in _io._IOBase.readlines when hint is present ...
authorXiang Zhang <angwerzx@126.com>
Sat, 15 Apr 2017 05:18:22 +0000 (13:18 +0800)
committerGitHub <noreply@github.com>
Sat, 15 Apr 2017 05:18:22 +0000 (13:18 +0800)
Lib/test/test_io.py
Misc/NEWS
Modules/_io/iobase.c

index 3d4da46113927bab843592f951e2762b08dae960..fb91a2dbca410460434e3388f394eea81ae901d0 100644 (file)
@@ -2933,6 +2933,7 @@ class MiscIOTest(unittest.TestCase):
                 self.assertRaises(ValueError, f.readinto, bytearray(1024))
             self.assertRaises(ValueError, f.readline)
             self.assertRaises(ValueError, f.readlines)
+            self.assertRaises(ValueError, f.readlines, 1)
             self.assertRaises(ValueError, f.seek, 0)
             self.assertRaises(ValueError, f.tell)
             self.assertRaises(ValueError, f.truncate)
index acd20159bc93ae37b70a9f90d87ee300b66093e0..5f1b64bf769f550a68e444c97d15d6cfdb5c102f 100644 (file)
--- a/Misc/NEWS
+++ b/Misc/NEWS
@@ -42,6 +42,9 @@ Extension Modules
 Library
 -------
 
+- bpo-30068: _io._IOBase.readlines will check if it's closed first when
+  hint is present.
+
 - bpo-27863: Fixed multiple crashes in ElementTree caused by race conditions
   and wrong types.
 
@@ -12349,4 +12352,3 @@ Mac
 ----
 
 **(For information about older versions, consult the HISTORY file.)**
-
index 2fec7e87e23beeecb9790f9c556b3ad3ca159456..066dc8edad6adbb70e7fe99a5eaedaa7eef115d7 100644 (file)
@@ -1,9 +1,9 @@
 /*
     An implementation of the I/O abstract base classes hierarchy
     as defined by PEP 3116 - "New I/O"
-    
+
     Classes defined here: IOBase, RawIOBase.
-    
+
     Written by Amaury Forgeot d'Arc and Antoine Pitrou
 */
 
@@ -19,7 +19,7 @@
 
 typedef struct {
     PyObject_HEAD
-    
+
     PyObject *dict;
     PyObject *weakreflist;
 } iobase;
@@ -590,7 +590,7 @@ static PyObject *
 iobase_readlines(PyObject *self, PyObject *args)
 {
     Py_ssize_t hint = -1, length = 0;
-    PyObject *result;
+    PyObject *result, *it = NULL;
 
     if (!PyArg_ParseTuple(args, "|O&:readlines", &_PyIO_ConvertSsize_t, &hint)) {
         return NULL;
@@ -606,19 +606,22 @@ iobase_readlines(PyObject *self, PyObject *args)
            probably be removed here. */
         PyObject *ret = PyObject_CallMethod(result, "extend", "O", self);
         if (ret == NULL) {
-            Py_DECREF(result);
-            return NULL;
+            goto error;
         }
         Py_DECREF(ret);
         return result;
     }
 
+    it = PyObject_GetIter(self);
+    if (it == NULL) {
+        goto error;
+    }
+
     while (1) {
-        PyObject *line = PyIter_Next(self);
+        PyObject *line = PyIter_Next(it);
         if (line == NULL) {
             if (PyErr_Occurred()) {
-                Py_DECREF(result);
-                return NULL;
+                goto error;
             }
             else
                 break; /* StopIteration raised */
@@ -626,8 +629,7 @@ iobase_readlines(PyObject *self, PyObject *args)
 
         if (PyList_Append(result, line) < 0) {
             Py_DECREF(line);
-            Py_DECREF(result);
-            return NULL;
+            goto error;
         }
         length += PyObject_Size(line);
         Py_DECREF(line);
@@ -635,7 +637,14 @@ iobase_readlines(PyObject *self, PyObject *args)
         if (length > hint)
             break;
     }
+
+    Py_DECREF(it);
     return result;
+
+ error:
+    Py_XDECREF(it);
+    Py_DECREF(result);
+    return NULL;
 }
 
 static PyObject *
@@ -823,7 +832,7 @@ rawiobase_readall(PyObject *self, PyObject *args)
     int r;
     PyObject *chunks = PyList_New(0);
     PyObject *result;
-    
+
     if (chunks == NULL)
         return NULL;