|
10 | 10 | import sys |
11 | 11 | import unittest |
12 | 12 | import weakref |
| 13 | + |
13 | 14 | from collections.abc import MutableMapping |
14 | 15 | from test import mapping_tests, support |
15 | 16 | from test.support import import_helper |
@@ -729,6 +730,32 @@ def test_merge_operator(self): |
729 | 730 | with self.assertRaises(ValueError): |
730 | 731 | a |= "BAD" |
731 | 732 |
|
| 733 | + def test_getitem_re_entrant_clear_during_copy(self): |
| 734 | + class Evil(self.OrderedDict): |
| 735 | + def __getitem__(self, key): |
| 736 | + super().clear() |
| 737 | + return None |
| 738 | + |
| 739 | + evil_dict = Evil([(i, i) for i in range(4)]) |
| 740 | + result = evil_dict.copy() |
| 741 | + |
| 742 | + self.assertEqual(len(result), 4) |
| 743 | + |
| 744 | + def test_getitem_re_entrant_modify_during_copy(self): |
| 745 | + class Modifier(self.OrderedDict): |
| 746 | + def __getitem__(self, key): |
| 747 | + self['new_key'] = 'new_value' |
| 748 | + return super().__getitem__(key) |
| 749 | + |
| 750 | + original = Modifier([(1, 'one'), (2, 'two')]) |
| 751 | + result = original.copy() |
| 752 | + |
| 753 | + self.assertIn(1, result) |
| 754 | + self.assertIn(2, result) |
| 755 | + self.assertEqual(result[1], 'one') |
| 756 | + self.assertEqual(result[2], 'two') |
| 757 | + self.assertEqual(result["new_key"], "new_value") |
| 758 | + |
732 | 759 | @support.cpython_only |
733 | 760 | def test_ordered_dict_items_result_gc(self): |
734 | 761 | # bpo-42536: OrderedDict.items's tuple-reuse speed trick breaks the GC's |
|
0 commit comments