diff options
author | Miss Islington (bot) <31488909+miss-islington@users.noreply.github.com> | 2018-07-14 03:58:12 (GMT) |
---|---|---|
committer | GitHub <noreply@github.com> | 2018-07-14 03:58:12 (GMT) |
commit | c721472fb83d1f7c7606bcf33ba2d42d6127a764 (patch) | |
tree | 5423358bf1045bb2902ddbf92a772c2689146b35 | |
parent | cf21d0031dd84544d4108765553c2b03dfe726c5 (diff) | |
download | cpython-c721472fb83d1f7c7606bcf33ba2d42d6127a764.zip cpython-c721472fb83d1f7c7606bcf33ba2d42d6127a764.tar.gz cpython-c721472fb83d1f7c7606bcf33ba2d42d6127a764.tar.bz2 |
bpo-34087: Fix buffer overflow in int(s) and similar functions (GH-8274)
`_PyUnicode_TransformDecimalAndSpaceToASCII()` missed trailing NUL char.
It caused buffer overflow in `_Py_string_to_number_with_underscores()`.
This bug is introduced in 9b6c60cb.
(cherry picked from commit 16dfca4d829e45f36e71bf43f83226659ce49315)
Co-authored-by: INADA Naoki <methane@users.noreply.github.com>
-rw-r--r-- | Lib/test/test_complex.py | 3 | ||||
-rw-r--r-- | Lib/test/test_float.py | 3 | ||||
-rw-r--r-- | Lib/test/test_long.py | 4 | ||||
-rw-r--r-- | Misc/NEWS.d/next/Core and Builtins/2018-07-13-22-09-55.bpo-34087.I1Bxfc.rst | 1 | ||||
-rw-r--r-- | Objects/unicodeobject.c | 2 | ||||
-rw-r--r-- | Python/pystrtod.c | 2 |
6 files changed, 15 insertions, 0 deletions
diff --git a/Lib/test/test_complex.py b/Lib/test/test_complex.py index 2d883c5..21c6eae 100644 --- a/Lib/test/test_complex.py +++ b/Lib/test/test_complex.py @@ -345,6 +345,9 @@ class ComplexTest(unittest.TestCase): self.assertEqual(type(complex("1"*500)), complex) # check whitespace processing self.assertEqual(complex('\N{EM SPACE}(\N{EN SPACE}1+1j ) '), 1+1j) + # Invalid unicode string + # See bpo-34087 + self.assertRaises(ValueError, complex, '\u3053\u3093\u306b\u3061\u306f') class EvilExc(Exception): pass diff --git a/Lib/test/test_float.py b/Lib/test/test_float.py index 17174dd..06ea90c 100644 --- a/Lib/test/test_float.py +++ b/Lib/test/test_float.py @@ -60,6 +60,9 @@ class GeneralFloatCases(unittest.TestCase): # extra long strings should not be a problem float(b'.' + b'1'*1000) float('.' + '1'*1000) + # Invalid unicode string + # See bpo-34087 + self.assertRaises(ValueError, float, '\u3053\u3093\u306b\u3061\u306f') def test_underscores(self): for lit in VALID_UNDERSCORE_LITERALS: diff --git a/Lib/test/test_long.py b/Lib/test/test_long.py index cc48259..8472889 100644 --- a/Lib/test/test_long.py +++ b/Lib/test/test_long.py @@ -373,6 +373,10 @@ class LongTest(unittest.TestCase): for base in invalid_bases: self.assertRaises(ValueError, int, '42', base) + # Invalid unicode string + # See bpo-34087 + self.assertRaises(ValueError, int, '\u3053\u3093\u306b\u3061\u306f') + def test_conversion(self): diff --git a/Misc/NEWS.d/next/Core and Builtins/2018-07-13-22-09-55.bpo-34087.I1Bxfc.rst b/Misc/NEWS.d/next/Core and Builtins/2018-07-13-22-09-55.bpo-34087.I1Bxfc.rst new file mode 100644 index 0000000..5147395 --- /dev/null +++ b/Misc/NEWS.d/next/Core and Builtins/2018-07-13-22-09-55.bpo-34087.I1Bxfc.rst @@ -0,0 +1 @@ +Fix buffer overflow while converting unicode to numeric values. diff --git a/Objects/unicodeobject.c b/Objects/unicodeobject.c index d5e7d10..5d605ab 100644 --- a/Objects/unicodeobject.c +++ b/Objects/unicodeobject.c @@ -9076,6 +9076,7 @@ _PyUnicode_TransformDecimalAndSpaceToASCII(PyObject *unicode) int decimal = Py_UNICODE_TODECIMAL(ch); if (decimal < 0) { out[i] = '?'; + out[i+1] = '\0'; _PyUnicode_LENGTH(result) = i + 1; break; } @@ -9083,6 +9084,7 @@ _PyUnicode_TransformDecimalAndSpaceToASCII(PyObject *unicode) } } + assert(_PyUnicode_CheckConsistency(result, 1)); return result; } diff --git a/Python/pystrtod.c b/Python/pystrtod.c index 9bf9363..141a47a 100644 --- a/Python/pystrtod.c +++ b/Python/pystrtod.c @@ -391,6 +391,8 @@ _Py_string_to_number_with_underscores( char *dup, *end; PyObject *result; + assert(s[orig_len] == '\0'); + if (strchr(s, '_') == NULL) { return innerfunc(s, orig_len, arg); } |