From: Serhiy Storchaka Date: Wed, 12 Feb 2014 08:52:07 +0000 (+0200) Subject: Issue #17671: Fixed a crash when use non-initialized io.BufferedRWPair. X-Git-Tag: v2.7.7rc1~179 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=1d19f97eedb69096933917e35e18c49003bd9e39;p=python Issue #17671: Fixed a crash when use non-initialized io.BufferedRWPair. Based on patch by Stephen Tu. --- diff --git a/Lib/test/test_io.py b/Lib/test/test_io.py index bc59af399d..936dbed64a 100644 --- a/Lib/test/test_io.py +++ b/Lib/test/test_io.py @@ -793,6 +793,16 @@ class BufferedReaderTest(unittest.TestCase, CommonBufferedTests): bufio.__init__(rawio) self.assertEqual(b"abc", bufio.read()) + def test_uninitialized(self): + bufio = self.tp.__new__(self.tp) + del bufio + bufio = self.tp.__new__(self.tp) + self.assertRaisesRegexp((ValueError, AttributeError), + 'uninitialized|has no attribute', + bufio.read, 0) + bufio.__init__(self.MockRawIO()) + self.assertEqual(bufio.read(0), b'') + def test_read(self): for arg in (None, 7): rawio = self.MockRawIO((b"abc", b"d", b"efg")) @@ -1029,6 +1039,16 @@ class BufferedWriterTest(unittest.TestCase, CommonBufferedTests): bufio.flush() self.assertEqual(b"".join(rawio._write_stack), b"abcghi") + def test_uninitialized(self): + bufio = self.tp.__new__(self.tp) + del bufio + bufio = self.tp.__new__(self.tp) + self.assertRaisesRegexp((ValueError, AttributeError), + 'uninitialized|has no attribute', + bufio.write, b'') + bufio.__init__(self.MockRawIO()) + self.assertEqual(bufio.write(b''), 0) + def test_detach_flush(self): raw = self.MockRawIO() buf = self.tp(raw) @@ -1313,6 +1333,20 @@ class BufferedRWPairTest(unittest.TestCase): pair = self.tp(self.MockRawIO(), self.MockRawIO()) self.assertFalse(pair.closed) + def test_uninitialized(self): + pair = self.tp.__new__(self.tp) + del pair + pair = self.tp.__new__(self.tp) + self.assertRaisesRegexp((ValueError, AttributeError), + 'uninitialized|has no attribute', + pair.read, 0) + self.assertRaisesRegexp((ValueError, AttributeError), + 'uninitialized|has no attribute', + pair.write, b'') + pair.__init__(self.MockRawIO(), self.MockRawIO()) + self.assertEqual(pair.read(0), b'') + self.assertEqual(pair.write(b''), 0) + def test_detach(self): pair = self.tp(self.MockRawIO(), self.MockRawIO()) self.assertRaises(self.UnsupportedOperation, pair.detach) @@ -1440,6 +1474,10 @@ class BufferedRandomTest(BufferedReaderTest, BufferedWriterTest): BufferedReaderTest.test_constructor(self) BufferedWriterTest.test_constructor(self) + def test_uninitialized(self): + BufferedReaderTest.test_uninitialized(self) + BufferedWriterTest.test_uninitialized(self) + def test_read_and_write(self): raw = self.MockRawIO((b"asdf", b"ghjk")) rw = self.tp(raw, 8) diff --git a/Misc/NEWS b/Misc/NEWS index d2ef384d0b..a823fa7692 100644 --- a/Misc/NEWS +++ b/Misc/NEWS @@ -44,6 +44,9 @@ Core and Builtins Library ------- +- Issue #17671: Fixed a crash when use non-initialized io.BufferedRWPair. + Based on patch by Stephen Tu. + - Issue #20594: Avoid name clash with the libc function posix_close. - Issue #19856: shutil.move() failed to move a directory to other directory diff --git a/Modules/_io/bufferedio.c b/Modules/_io/bufferedio.c index 411755c1ed..758edf4208 100644 --- a/Modules/_io/bufferedio.c +++ b/Modules/_io/bufferedio.c @@ -2129,9 +2129,14 @@ bufferedrwpair_dealloc(rwpair *self) static PyObject * _forward_call(buffered *self, const char *name, PyObject *args) { - PyObject *func = PyObject_GetAttrString((PyObject *)self, name); - PyObject *ret; + PyObject *func, *ret; + if (self == NULL) { + PyErr_SetString(PyExc_ValueError, + "I/O operation on uninitialized object"); + return NULL; + } + func = PyObject_GetAttrString((PyObject *)self, name); if (func == NULL) { PyErr_SetString(PyExc_AttributeError, name); return NULL;