Skip to content

Commit 3fd36fa

Browse files
authored
gh-154709: Fix out-of-bounds access in dict reverse iterator (GH-154721)
1 parent a528a24 commit 3fd36fa

3 files changed

Lines changed: 27 additions & 1 deletion

File tree

Lib/test/test_dict.py

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1403,6 +1403,27 @@ def __init__(self, x, y):
14031403
self.assertEqual(list(reversed(A(1, 0).__dict__)), ['x'])
14041404
self.assertEqual(list(reversed(A(0, 1).__dict__)), ['y'])
14051405

1406+
def test_reversed_dict_after_clear_and_restore(self):
1407+
d = {}
1408+
for i in range(1000):
1409+
d[f"k{i}"] = i
1410+
1411+
for i in range(1, 1000):
1412+
del d[f"k{i}"]
1413+
1414+
iterators = (
1415+
reversed(d),
1416+
reversed(d.keys()),
1417+
reversed(d.values()),
1418+
reversed(d.items()),
1419+
)
1420+
1421+
d.clear()
1422+
d["k0"] = 0
1423+
1424+
for it in iterators:
1425+
self.assertEqual(list(it), [])
1426+
14061427
def test_dict_copy_order(self):
14071428
# bpo-34320
14081429
od = collections.OrderedDict([('a', 1), ('b', 2)])
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
Fix an out-of-bounds access in reverse dictionary iterators when the
2+
underlying dictionary is cleared and modified after the iterator is created.

Objects/dictobject.c

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6276,9 +6276,12 @@ dictreviter_iter_lock_held(PyDictObject *d, PyObject *self)
62766276
int index = get_index_from_order(d, i);
62776277
key = LOAD_SHARED_KEY(DK_UNICODE_ENTRIES(k)[index].me_key);
62786278
value = d->ma_values->values[index];
6279-
assert (value != NULL);
6279+
assert(value != NULL);
62806280
}
62816281
else {
6282+
if (i >= k->dk_nentries) {
6283+
goto fail;
6284+
}
62826285
if (DK_IS_UNICODE(k)) {
62836286
PyDictUnicodeEntry *entry_ptr = &DK_UNICODE_ENTRIES(k)[i];
62846287
while (entry_ptr->me_value == NULL) {

0 commit comments

Comments
 (0)