mirror of
https://github.com/python/cpython.git
synced 2025-10-21 14:12:27 +00:00
In symtable_update_free_vars() do not modify the dictionary while
iterating over it using PyDict_Next(). This bug fix brought to you by the letters b, c, d, g, h, ... and the reporter Ping.
This commit is contained in:
parent
b258bedb13
commit
d7f393edae
1 changed files with 27 additions and 7 deletions
|
@ -4205,8 +4205,8 @@ PySymtable_Free(struct symtable *st)
|
||||||
static int
|
static int
|
||||||
symtable_update_free_vars(struct symtable *st)
|
symtable_update_free_vars(struct symtable *st)
|
||||||
{
|
{
|
||||||
PyObject *o, *name;
|
int i, j, def;
|
||||||
int i, def;
|
PyObject *o, *name, *list = NULL;
|
||||||
PySymtableEntryObject *child, *ste = st->st_cur;
|
PySymtableEntryObject *child, *ste = st->st_cur;
|
||||||
|
|
||||||
if (ste->ste_type == TYPE_CLASS)
|
if (ste->ste_type == TYPE_CLASS)
|
||||||
|
@ -4216,25 +4216,45 @@ symtable_update_free_vars(struct symtable *st)
|
||||||
for (i = 0; i < PyList_GET_SIZE(ste->ste_children); ++i) {
|
for (i = 0; i < PyList_GET_SIZE(ste->ste_children); ++i) {
|
||||||
int pos = 0;
|
int pos = 0;
|
||||||
|
|
||||||
|
if (list)
|
||||||
|
PyList_SetSlice(list, 0,
|
||||||
|
((PyVarObject*)list)->ob_size, 0);
|
||||||
child = (PySymtableEntryObject *)\
|
child = (PySymtableEntryObject *)\
|
||||||
PyList_GET_ITEM(ste->ste_children, i);
|
PyList_GET_ITEM(ste->ste_children, i);
|
||||||
while (PyDict_Next(child->ste_symbols, &pos, &name, &o)) {
|
while (PyDict_Next(child->ste_symbols, &pos, &name, &o)) {
|
||||||
int v = PyInt_AS_LONG(o);
|
int v = PyInt_AS_LONG(o);
|
||||||
if (!(is_free(v)))
|
if (!(is_free(v)))
|
||||||
continue; /* avoids indentation */
|
continue; /* avoids indentation */
|
||||||
|
if (list == NULL) {
|
||||||
|
list = PyList_New(0);
|
||||||
|
if (list == NULL)
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
ste->ste_child_free = 1;
|
ste->ste_child_free = 1;
|
||||||
|
if (PyList_Append(list, name) < 0) {
|
||||||
|
Py_DECREF(list);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for (j = 0; list && j < PyList_GET_SIZE(list); j++) {
|
||||||
|
name = PyList_GET_ITEM(list, j);
|
||||||
if (ste->ste_nested) {
|
if (ste->ste_nested) {
|
||||||
if (symtable_add_def_o(st, ste->ste_symbols,
|
if (symtable_add_def_o(st, ste->ste_symbols,
|
||||||
name, def) < 0)
|
name, def) < 0) {
|
||||||
return -1;
|
Py_DECREF(list);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
if (symtable_check_global(st, child->ste_id,
|
if (symtable_check_global(st, child->ste_id,
|
||||||
name) < 0)
|
name) < 0) {
|
||||||
return -1;
|
Py_DECREF(list);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Py_XDECREF(list);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue