|
18 | 18 | import textwrap |
19 | 19 | import threading |
20 | 20 | import unittest |
| 21 | +from _codecs import _unregister_error as _codecs_unregister_error |
21 | 22 |
|
22 | 23 | import test.support |
23 | 24 | from test import support |
@@ -2195,6 +2196,30 @@ def delslice(): |
2195 | 2196 | self.assertRaises(BufferError, delslice) |
2196 | 2197 | self.assertEqual(b, orig) |
2197 | 2198 |
|
| 2199 | + def test_decode_resize_forbidden(self): |
| 2200 | + # The storage is pinned while it is decoded, so an error handler |
| 2201 | + # cannot resize the bytearray. |
| 2202 | + b = bytearray(b'ab\xffcd') |
| 2203 | + errors = 'test.bytearray_decode_resize' |
| 2204 | + def handler(exc): |
| 2205 | + self.assertRaises(BufferError, b.clear) |
| 2206 | + self.assertRaises(BufferError, b.append, 0) |
| 2207 | + return ('?', exc.end) |
| 2208 | + self.addCleanup(_codecs_unregister_error, errors) |
| 2209 | + codecs.register_error(errors, handler) |
| 2210 | + for encoding in 'utf-8', 'utf-8-sig': |
| 2211 | + with self.subTest(encoding=encoding): |
| 2212 | + self.assertEqual(b.decode(encoding, errors), 'ab?cd') |
| 2213 | + self.assertEqual(b, b'ab\xffcd') |
| 2214 | + |
| 2215 | + def test_decode_subclass_buffer(self): |
| 2216 | + # decode() decodes the buffer that the object exports. |
| 2217 | + class B(bytearray): |
| 2218 | + def __buffer__(self, flags): |
| 2219 | + return memoryview(b'other') |
| 2220 | + self.assertEqual(B(b'mine').decode(), 'other') |
| 2221 | + self.assertEqual(B(b'mine').decode('latin-1'), 'other') |
| 2222 | + |
2198 | 2223 | @test.support.cpython_only |
2199 | 2224 | def test_obsolete_write_lock(self): |
2200 | 2225 | _testcapi = import_helper.import_module('_testcapi') |
|
0 commit comments