Mercurial > cpython-lru_cache-weakref
diff Python/compile.c @ 17637:8ff76cf30a8c legacy-trunk
Fix 2.1 nested scopes crash reported by Evan Simpson
The new test case demonstrates the bug. Be more careful in
symtable_resolve_free() to add a var to cells or frees only if it
won't be added under some other rule.
XXX Add new assertion that will catch this bug.
| author | Jeremy Hylton <jeremy@alum.mit.edu> |
|---|---|
| date | Fri, 27 Apr 2001 02:29:40 +0000 |
| parents | 32e7d0898eab |
| children | e3f0fd38c24b |
line wrap: on
line diff
--- a/Python/compile.c Fri Apr 27 02:25:33 2001 +0000 +++ b/Python/compile.c Fri Apr 27 02:29:40 2001 +0000 @@ -4057,7 +4057,7 @@ } static int -symtable_resolve_free(struct compiling *c, PyObject *name, +symtable_resolve_free(struct compiling *c, PyObject *name, int flags, struct symbol_info *si) { PyObject *dict, *v; @@ -4067,11 +4067,19 @@ cell var). If it occurs in a class, then the class has a method and a free variable with the same name. */ - if (c->c_symtable->st_cur->ste_type == TYPE_FUNCTION) { + /* If it isn't declared locally, it can't be a cell. */ + if (!(flags & (DEF_LOCAL | DEF_PARAM))) + return 0; v = PyInt_FromLong(si->si_ncells++); dict = c->c_cellvars; } else { + /* If it is free anyway, then there is no need to do + anything here. + */ + if (is_free(flags ^ DEF_FREE_CLASS) + || flags == DEF_FREE_CLASS) + return 0; v = PyInt_FromLong(si->si_nfrees++); dict = c->c_freevars; } @@ -4357,10 +4365,7 @@ variables or declared global. */ if (flags & (DEF_FREE | DEF_FREE_CLASS)) { - if ((ste->ste_type == TYPE_CLASS - && flags != DEF_FREE_CLASS) - || (flags & (DEF_LOCAL | DEF_PARAM))) - symtable_resolve_free(c, name, &si); + symtable_resolve_free(c, name, flags, &si); } if (flags & DEF_STAR) { @@ -4420,6 +4425,15 @@ } } + /* + fprintf(stderr, + "cells %d: %s\n" + "frees %d: %s\n", + si.si_ncells, PyObject_REPR(c->c_cellvars), + si.si_nfrees, PyObject_REPR(c->c_freevars)); + */ + assert(PyDict_Size(c->c_freevars) == si.si_nfrees); + if (si.si_ncells > 1) { /* one cell is always in order */ if (symtable_cellvar_offsets(&c->c_cellvars, c->c_argcount, c->c_varnames, c->c_flags) < 0)
