/src/cpython/Python/symtable.c
Line | Count | Source (jump to first uncovered line) |
1 | | #include "Python.h" |
2 | | #include "pycore_ast.h" // stmt_ty |
3 | | #include "pycore_parser.h" // _PyParser_ASTFromString() |
4 | | #include "pycore_pystate.h" // _PyThreadState_GET() |
5 | | #include "pycore_runtime.h" // _Py_ID() |
6 | | #include "pycore_symtable.h" // PySTEntryObject |
7 | | #include "pycore_unicodeobject.h" // _PyUnicode_EqualToASCIIString |
8 | | |
9 | | #include <stddef.h> // offsetof() |
10 | | |
11 | | |
12 | | // Set this to 1 to dump all symtables to stdout for debugging |
13 | | #define _PY_DUMP_SYMTABLE 0 |
14 | | |
15 | | /* error strings used for warnings */ |
16 | 0 | #define GLOBAL_PARAM \ |
17 | 0 | "name '%U' is parameter and global" |
18 | | |
19 | 0 | #define NONLOCAL_PARAM \ |
20 | 0 | "name '%U' is parameter and nonlocal" |
21 | | |
22 | 0 | #define GLOBAL_AFTER_ASSIGN \ |
23 | 0 | "name '%U' is assigned to before global declaration" |
24 | | |
25 | 0 | #define NONLOCAL_AFTER_ASSIGN \ |
26 | 0 | "name '%U' is assigned to before nonlocal declaration" |
27 | | |
28 | 0 | #define GLOBAL_AFTER_USE \ |
29 | 0 | "name '%U' is used prior to global declaration" |
30 | | |
31 | 0 | #define NONLOCAL_AFTER_USE \ |
32 | 0 | "name '%U' is used prior to nonlocal declaration" |
33 | | |
34 | 0 | #define GLOBAL_ANNOT \ |
35 | 0 | "annotated name '%U' can't be global" |
36 | | |
37 | 0 | #define NONLOCAL_ANNOT \ |
38 | 0 | "annotated name '%U' can't be nonlocal" |
39 | | |
40 | 0 | #define IMPORT_STAR_WARNING "import * only allowed at module level" |
41 | | |
42 | 0 | #define NAMED_EXPR_COMP_IN_CLASS \ |
43 | 0 | "assignment expression within a comprehension cannot be used in a class body" |
44 | | |
45 | 0 | #define NAMED_EXPR_COMP_IN_TYPEVAR_BOUND \ |
46 | 0 | "assignment expression within a comprehension cannot be used in a TypeVar bound" |
47 | | |
48 | 0 | #define NAMED_EXPR_COMP_IN_TYPEALIAS \ |
49 | 0 | "assignment expression within a comprehension cannot be used in a type alias" |
50 | | |
51 | 0 | #define NAMED_EXPR_COMP_IN_TYPEPARAM \ |
52 | 0 | "assignment expression within a comprehension cannot be used within the definition of a generic" |
53 | | |
54 | 0 | #define NAMED_EXPR_COMP_CONFLICT \ |
55 | 0 | "assignment expression cannot rebind comprehension iteration variable '%U'" |
56 | | |
57 | 0 | #define NAMED_EXPR_COMP_INNER_LOOP_CONFLICT \ |
58 | 0 | "comprehension inner loop cannot rebind assignment expression target '%U'" |
59 | | |
60 | 0 | #define NAMED_EXPR_COMP_ITER_EXPR \ |
61 | 0 | "assignment expression cannot be used in a comprehension iterable expression" |
62 | | |
63 | 0 | #define ANNOTATION_NOT_ALLOWED \ |
64 | 0 | "%s cannot be used within an annotation" |
65 | | |
66 | 0 | #define EXPR_NOT_ALLOWED_IN_TYPE_VARIABLE \ |
67 | 0 | "%s cannot be used within %s" |
68 | | |
69 | 0 | #define EXPR_NOT_ALLOWED_IN_TYPE_ALIAS \ |
70 | 0 | "%s cannot be used within a type alias" |
71 | | |
72 | 0 | #define EXPR_NOT_ALLOWED_IN_TYPE_PARAMETERS \ |
73 | 0 | "%s cannot be used within the definition of a generic" |
74 | | |
75 | 0 | #define DUPLICATE_TYPE_PARAM \ |
76 | 0 | "duplicate type parameter '%U'" |
77 | | |
78 | 1 | #define ASYNC_WITH_OUTSIDE_ASYNC_FUNC \ |
79 | 1 | "'async with' outside async function" |
80 | | |
81 | 0 | #define ASYNC_FOR_OUTSIDE_ASYNC_FUNC \ |
82 | 0 | "'async for' outside async function" |
83 | | |
84 | 117k | #define LOCATION(x) SRC_LOCATION_FROM_AST(x) |
85 | | |
86 | | #define SET_ERROR_LOCATION(FNAME, L) \ |
87 | 0 | PyErr_RangedSyntaxLocationObject((FNAME), \ |
88 | 0 | (L).lineno, (L).col_offset + 1, (L).end_lineno, (L).end_col_offset + 1) |
89 | | |
90 | 344 | #define IS_ASYNC_DEF(st) ((st)->st_cur->ste_type == FunctionBlock && (st)->st_cur->ste_coroutine) |
91 | | |
92 | | static PySTEntryObject * |
93 | | ste_new(struct symtable *st, identifier name, _Py_block_ty block, |
94 | | void *key, _Py_SourceLocation loc) |
95 | 10.0k | { |
96 | 10.0k | PySTEntryObject *ste = NULL; |
97 | 10.0k | PyObject *k = NULL; |
98 | | |
99 | 10.0k | k = PyLong_FromVoidPtr(key); |
100 | 10.0k | if (k == NULL) |
101 | 0 | goto fail; |
102 | 10.0k | ste = PyObject_New(PySTEntryObject, &PySTEntry_Type); |
103 | 10.0k | if (ste == NULL) { |
104 | 0 | Py_DECREF(k); |
105 | 0 | goto fail; |
106 | 0 | } |
107 | 10.0k | ste->ste_table = st; |
108 | 10.0k | ste->ste_id = k; /* ste owns reference to k */ |
109 | | |
110 | 10.0k | ste->ste_name = Py_NewRef(name); |
111 | | |
112 | 10.0k | ste->ste_symbols = NULL; |
113 | 10.0k | ste->ste_varnames = NULL; |
114 | 10.0k | ste->ste_children = NULL; |
115 | | |
116 | 10.0k | ste->ste_directives = NULL; |
117 | 10.0k | ste->ste_mangled_names = NULL; |
118 | | |
119 | 10.0k | ste->ste_type = block; |
120 | 10.0k | ste->ste_scope_info = NULL; |
121 | | |
122 | 10.0k | ste->ste_nested = 0; |
123 | 10.0k | ste->ste_varargs = 0; |
124 | 10.0k | ste->ste_varkeywords = 0; |
125 | 10.0k | ste->ste_annotations_used = 0; |
126 | 10.0k | ste->ste_loc = loc; |
127 | | |
128 | 10.0k | if (st->st_cur != NULL && |
129 | 10.0k | (st->st_cur->ste_nested || |
130 | 9.72k | _PyST_IsFunctionLike(st->st_cur))) |
131 | 728 | ste->ste_nested = 1; |
132 | 10.0k | ste->ste_generator = 0; |
133 | 10.0k | ste->ste_coroutine = 0; |
134 | 10.0k | ste->ste_comprehension = NoComprehension; |
135 | 10.0k | ste->ste_returns_value = 0; |
136 | 10.0k | ste->ste_needs_class_closure = 0; |
137 | 10.0k | ste->ste_comp_inlined = 0; |
138 | 10.0k | ste->ste_comp_iter_target = 0; |
139 | 10.0k | ste->ste_can_see_class_scope = 0; |
140 | 10.0k | ste->ste_comp_iter_expr = 0; |
141 | 10.0k | ste->ste_needs_classdict = 0; |
142 | 10.0k | ste->ste_has_conditional_annotations = 0; |
143 | 10.0k | ste->ste_in_conditional_block = 0; |
144 | 10.0k | ste->ste_in_unevaluated_annotation = 0; |
145 | 10.0k | ste->ste_annotation_block = NULL; |
146 | | |
147 | 10.0k | ste->ste_has_docstring = 0; |
148 | | |
149 | 10.0k | ste->ste_method = 0; |
150 | 10.0k | if (st->st_cur != NULL && |
151 | 10.0k | st->st_cur->ste_type == ClassBlock && |
152 | 10.0k | block == FunctionBlock) { |
153 | 2.75k | ste->ste_method = 1; |
154 | 2.75k | } |
155 | | |
156 | 10.0k | ste->ste_symbols = PyDict_New(); |
157 | 10.0k | ste->ste_varnames = PyList_New(0); |
158 | 10.0k | ste->ste_children = PyList_New(0); |
159 | 10.0k | if (ste->ste_symbols == NULL |
160 | 10.0k | || ste->ste_varnames == NULL |
161 | 10.0k | || ste->ste_children == NULL) |
162 | 0 | goto fail; |
163 | | |
164 | 10.0k | if (PyDict_SetItem(st->st_blocks, ste->ste_id, (PyObject *)ste) < 0) |
165 | 0 | goto fail; |
166 | | |
167 | 10.0k | return ste; |
168 | 0 | fail: |
169 | 0 | Py_XDECREF(ste); |
170 | 0 | return NULL; |
171 | 10.0k | } |
172 | | |
173 | | static PyObject * |
174 | | ste_repr(PyObject *op) |
175 | 0 | { |
176 | 0 | PySTEntryObject *ste = (PySTEntryObject *)op; |
177 | 0 | return PyUnicode_FromFormat("<symtable entry %U(%R), line %d>", |
178 | 0 | ste->ste_name, ste->ste_id, ste->ste_loc.lineno); |
179 | 0 | } |
180 | | |
181 | | static void |
182 | | ste_dealloc(PyObject *op) |
183 | 10.0k | { |
184 | 10.0k | PySTEntryObject *ste = (PySTEntryObject *)op; |
185 | 10.0k | ste->ste_table = NULL; |
186 | 10.0k | Py_XDECREF(ste->ste_id); |
187 | 10.0k | Py_XDECREF(ste->ste_name); |
188 | 10.0k | Py_XDECREF(ste->ste_symbols); |
189 | 10.0k | Py_XDECREF(ste->ste_varnames); |
190 | 10.0k | Py_XDECREF(ste->ste_children); |
191 | 10.0k | Py_XDECREF(ste->ste_directives); |
192 | 10.0k | Py_XDECREF(ste->ste_annotation_block); |
193 | 10.0k | Py_XDECREF(ste->ste_mangled_names); |
194 | 10.0k | PyObject_Free(ste); |
195 | 10.0k | } |
196 | | |
197 | | #define OFF(x) offsetof(PySTEntryObject, x) |
198 | | |
199 | | static PyMemberDef ste_memberlist[] = { |
200 | | {"id", _Py_T_OBJECT, OFF(ste_id), Py_READONLY}, |
201 | | {"name", _Py_T_OBJECT, OFF(ste_name), Py_READONLY}, |
202 | | {"symbols", _Py_T_OBJECT, OFF(ste_symbols), Py_READONLY}, |
203 | | {"varnames", _Py_T_OBJECT, OFF(ste_varnames), Py_READONLY}, |
204 | | {"children", _Py_T_OBJECT, OFF(ste_children), Py_READONLY}, |
205 | | {"nested", Py_T_INT, OFF(ste_nested), Py_READONLY}, |
206 | | {"type", Py_T_INT, OFF(ste_type), Py_READONLY}, |
207 | | {"lineno", Py_T_INT, OFF(ste_loc.lineno), Py_READONLY}, |
208 | | {NULL} |
209 | | }; |
210 | | |
211 | | PyTypeObject PySTEntry_Type = { |
212 | | PyVarObject_HEAD_INIT(&PyType_Type, 0) |
213 | | "symtable entry", |
214 | | sizeof(PySTEntryObject), |
215 | | 0, |
216 | | ste_dealloc, /* tp_dealloc */ |
217 | | 0, /* tp_vectorcall_offset */ |
218 | | 0, /* tp_getattr */ |
219 | | 0, /* tp_setattr */ |
220 | | 0, /* tp_as_async */ |
221 | | ste_repr, /* tp_repr */ |
222 | | 0, /* tp_as_number */ |
223 | | 0, /* tp_as_sequence */ |
224 | | 0, /* tp_as_mapping */ |
225 | | 0, /* tp_hash */ |
226 | | 0, /* tp_call */ |
227 | | 0, /* tp_str */ |
228 | | PyObject_GenericGetAttr, /* tp_getattro */ |
229 | | 0, /* tp_setattro */ |
230 | | 0, /* tp_as_buffer */ |
231 | | Py_TPFLAGS_DEFAULT, /* tp_flags */ |
232 | | 0, /* tp_doc */ |
233 | | 0, /* tp_traverse */ |
234 | | 0, /* tp_clear */ |
235 | | 0, /* tp_richcompare */ |
236 | | 0, /* tp_weaklistoffset */ |
237 | | 0, /* tp_iter */ |
238 | | 0, /* tp_iternext */ |
239 | | 0, /* tp_methods */ |
240 | | ste_memberlist, /* tp_members */ |
241 | | 0, /* tp_getset */ |
242 | | 0, /* tp_base */ |
243 | | 0, /* tp_dict */ |
244 | | 0, /* tp_descr_get */ |
245 | | 0, /* tp_descr_set */ |
246 | | 0, /* tp_dictoffset */ |
247 | | 0, /* tp_init */ |
248 | | 0, /* tp_alloc */ |
249 | | 0, /* tp_new */ |
250 | | }; |
251 | | |
252 | | static int symtable_analyze(struct symtable *st); |
253 | | static int symtable_enter_block(struct symtable *st, identifier name, |
254 | | _Py_block_ty block, void *ast, _Py_SourceLocation loc); |
255 | | static int symtable_exit_block(struct symtable *st); |
256 | | static int symtable_visit_stmt(struct symtable *st, stmt_ty s); |
257 | | static int symtable_visit_expr(struct symtable *st, expr_ty s); |
258 | | static int symtable_visit_type_param(struct symtable *st, type_param_ty s); |
259 | | static int symtable_visit_genexp(struct symtable *st, expr_ty s); |
260 | | static int symtable_visit_listcomp(struct symtable *st, expr_ty s); |
261 | | static int symtable_visit_setcomp(struct symtable *st, expr_ty s); |
262 | | static int symtable_visit_dictcomp(struct symtable *st, expr_ty s); |
263 | | static int symtable_visit_arguments(struct symtable *st, arguments_ty); |
264 | | static int symtable_visit_excepthandler(struct symtable *st, excepthandler_ty); |
265 | | static int symtable_visit_alias(struct symtable *st, alias_ty); |
266 | | static int symtable_visit_comprehension(struct symtable *st, comprehension_ty); |
267 | | static int symtable_visit_keyword(struct symtable *st, keyword_ty); |
268 | | static int symtable_visit_params(struct symtable *st, asdl_arg_seq *args); |
269 | | static int symtable_visit_annotation(struct symtable *st, expr_ty annotation, void *key); |
270 | | static int symtable_visit_argannotations(struct symtable *st, asdl_arg_seq *args); |
271 | | static int symtable_implicit_arg(struct symtable *st, int pos); |
272 | | static int symtable_visit_annotations(struct symtable *st, stmt_ty, arguments_ty, expr_ty, |
273 | | struct _symtable_entry *parent_ste); |
274 | | static int symtable_visit_withitem(struct symtable *st, withitem_ty item); |
275 | | static int symtable_visit_match_case(struct symtable *st, match_case_ty m); |
276 | | static int symtable_visit_pattern(struct symtable *st, pattern_ty s); |
277 | | static int symtable_raise_if_annotation_block(struct symtable *st, const char *, expr_ty); |
278 | | static int symtable_raise_if_not_coroutine(struct symtable *st, const char *msg, _Py_SourceLocation loc); |
279 | | static int symtable_raise_if_comprehension_block(struct symtable *st, expr_ty); |
280 | | static int symtable_add_def(struct symtable *st, PyObject *name, int flag, _Py_SourceLocation loc); |
281 | | |
282 | | /* For debugging purposes only */ |
283 | | #if _PY_DUMP_SYMTABLE |
284 | | static void _dump_symtable(PySTEntryObject* ste, PyObject* prefix) |
285 | | { |
286 | | const char *blocktype = ""; |
287 | | switch (ste->ste_type) { |
288 | | case FunctionBlock: blocktype = "FunctionBlock"; break; |
289 | | case ClassBlock: blocktype = "ClassBlock"; break; |
290 | | case ModuleBlock: blocktype = "ModuleBlock"; break; |
291 | | case AnnotationBlock: blocktype = "AnnotationBlock"; break; |
292 | | case TypeVariableBlock: blocktype = "TypeVariableBlock"; break; |
293 | | case TypeAliasBlock: blocktype = "TypeAliasBlock"; break; |
294 | | case TypeParametersBlock: blocktype = "TypeParametersBlock"; break; |
295 | | } |
296 | | const char *comptype = ""; |
297 | | switch (ste->ste_comprehension) { |
298 | | case ListComprehension: comptype = " ListComprehension"; break; |
299 | | case DictComprehension: comptype = " DictComprehension"; break; |
300 | | case SetComprehension: comptype = " SetComprehension"; break; |
301 | | case GeneratorExpression: comptype = " GeneratorExpression"; break; |
302 | | case NoComprehension: break; |
303 | | } |
304 | | PyObject* msg = PyUnicode_FromFormat( |
305 | | ( |
306 | | "%U=== Symtable for %U ===\n" |
307 | | "%U%s%s\n" |
308 | | "%U%s%s%s%s%s%s%s%s%s%s%s\n" |
309 | | "%Ulineno: %d col_offset: %d\n" |
310 | | "%U--- Symbols ---\n" |
311 | | ), |
312 | | prefix, |
313 | | ste->ste_name, |
314 | | prefix, |
315 | | blocktype, |
316 | | comptype, |
317 | | prefix, |
318 | | ste->ste_nested ? " nested" : "", |
319 | | ste->ste_generator ? " generator" : "", |
320 | | ste->ste_coroutine ? " coroutine" : "", |
321 | | ste->ste_varargs ? " varargs" : "", |
322 | | ste->ste_varkeywords ? " varkeywords" : "", |
323 | | ste->ste_returns_value ? " returns_value" : "", |
324 | | ste->ste_needs_class_closure ? " needs_class_closure" : "", |
325 | | ste->ste_needs_classdict ? " needs_classdict" : "", |
326 | | ste->ste_comp_inlined ? " comp_inlined" : "", |
327 | | ste->ste_comp_iter_target ? " comp_iter_target" : "", |
328 | | ste->ste_can_see_class_scope ? " can_see_class_scope" : "", |
329 | | prefix, |
330 | | ste->ste_loc.lineno, |
331 | | ste->ste_loc.col_offset, |
332 | | prefix |
333 | | ); |
334 | | assert(msg != NULL); |
335 | | printf("%s", PyUnicode_AsUTF8(msg)); |
336 | | Py_DECREF(msg); |
337 | | PyObject *name, *value; |
338 | | Py_ssize_t pos = 0; |
339 | | while (PyDict_Next(ste->ste_symbols, &pos, &name, &value)) { |
340 | | int scope = _PyST_GetScope(ste, name); |
341 | | long flags = _PyST_GetSymbol(ste, name); |
342 | | printf("%s %s: ", PyUnicode_AsUTF8(prefix), PyUnicode_AsUTF8(name)); |
343 | | if (flags & DEF_GLOBAL) printf(" DEF_GLOBAL"); |
344 | | if (flags & DEF_LOCAL) printf(" DEF_LOCAL"); |
345 | | if (flags & DEF_PARAM) printf(" DEF_PARAM"); |
346 | | if (flags & DEF_NONLOCAL) printf(" DEF_NONLOCAL"); |
347 | | if (flags & USE) printf(" USE"); |
348 | | if (flags & DEF_FREE_CLASS) printf(" DEF_FREE_CLASS"); |
349 | | if (flags & DEF_IMPORT) printf(" DEF_IMPORT"); |
350 | | if (flags & DEF_ANNOT) printf(" DEF_ANNOT"); |
351 | | if (flags & DEF_COMP_ITER) printf(" DEF_COMP_ITER"); |
352 | | if (flags & DEF_TYPE_PARAM) printf(" DEF_TYPE_PARAM"); |
353 | | if (flags & DEF_COMP_CELL) printf(" DEF_COMP_CELL"); |
354 | | switch (scope) { |
355 | | case LOCAL: printf(" LOCAL"); break; |
356 | | case GLOBAL_EXPLICIT: printf(" GLOBAL_EXPLICIT"); break; |
357 | | case GLOBAL_IMPLICIT: printf(" GLOBAL_IMPLICIT"); break; |
358 | | case FREE: printf(" FREE"); break; |
359 | | case CELL: printf(" CELL"); break; |
360 | | } |
361 | | printf("\n"); |
362 | | } |
363 | | printf("%s--- Children ---\n", PyUnicode_AsUTF8(prefix)); |
364 | | PyObject *new_prefix = PyUnicode_FromFormat(" %U", prefix); |
365 | | assert(new_prefix != NULL); |
366 | | for (Py_ssize_t i = 0; i < PyList_GET_SIZE(ste->ste_children); i++) { |
367 | | PyObject *child = PyList_GetItem(ste->ste_children, i); |
368 | | assert(child != NULL && PySTEntry_Check(child)); |
369 | | _dump_symtable((PySTEntryObject *)child, new_prefix); |
370 | | } |
371 | | Py_DECREF(new_prefix); |
372 | | } |
373 | | |
374 | | static void dump_symtable(PySTEntryObject* ste) |
375 | | { |
376 | | PyObject *empty = Py_GetConstant(Py_CONSTANT_EMPTY_STR); |
377 | | assert(empty != NULL); |
378 | | _dump_symtable(ste, empty); |
379 | | Py_DECREF(empty); |
380 | | } |
381 | | #endif |
382 | | |
383 | 0 | #define DUPLICATE_PARAMETER \ |
384 | 0 | "duplicate parameter '%U' in function definition" |
385 | | |
386 | | static struct symtable * |
387 | | symtable_new(void) |
388 | 307 | { |
389 | 307 | struct symtable *st; |
390 | | |
391 | 307 | st = (struct symtable *)PyMem_Malloc(sizeof(struct symtable)); |
392 | 307 | if (st == NULL) { |
393 | 0 | PyErr_NoMemory(); |
394 | 0 | return NULL; |
395 | 0 | } |
396 | | |
397 | 307 | st->st_filename = NULL; |
398 | 307 | st->st_blocks = NULL; |
399 | | |
400 | 307 | if ((st->st_stack = PyList_New(0)) == NULL) |
401 | 0 | goto fail; |
402 | 307 | if ((st->st_blocks = PyDict_New()) == NULL) |
403 | 0 | goto fail; |
404 | 307 | st->st_cur = NULL; |
405 | 307 | st->st_private = NULL; |
406 | 307 | return st; |
407 | 0 | fail: |
408 | 0 | _PySymtable_Free(st); |
409 | 0 | return NULL; |
410 | 307 | } |
411 | | |
412 | | struct symtable * |
413 | | _PySymtable_Build(mod_ty mod, PyObject *filename, _PyFutureFeatures *future) |
414 | 307 | { |
415 | 307 | struct symtable *st = symtable_new(); |
416 | 307 | asdl_stmt_seq *seq; |
417 | 307 | Py_ssize_t i; |
418 | 307 | PyThreadState *tstate; |
419 | | |
420 | 307 | if (st == NULL) |
421 | 0 | return NULL; |
422 | 307 | if (filename == NULL) { |
423 | 0 | _PySymtable_Free(st); |
424 | 0 | return NULL; |
425 | 0 | } |
426 | 307 | st->st_filename = Py_NewRef(filename); |
427 | 307 | st->st_future = future; |
428 | | |
429 | | /* Setup recursion depth check counters */ |
430 | 307 | tstate = _PyThreadState_GET(); |
431 | 307 | if (!tstate) { |
432 | 0 | _PySymtable_Free(st); |
433 | 0 | return NULL; |
434 | 0 | } |
435 | | |
436 | | /* Make the initial symbol information gathering pass */ |
437 | | |
438 | 307 | _Py_SourceLocation loc0 = {0, 0, 0, 0}; |
439 | 307 | if (!symtable_enter_block(st, &_Py_ID(top), ModuleBlock, (void *)mod, loc0)) { |
440 | 0 | _PySymtable_Free(st); |
441 | 0 | return NULL; |
442 | 0 | } |
443 | | |
444 | 307 | st->st_top = st->st_cur; |
445 | 307 | switch (mod->kind) { |
446 | 264 | case Module_kind: |
447 | 264 | seq = mod->v.Module.body; |
448 | 264 | if (_PyAST_GetDocString(seq)) { |
449 | 174 | st->st_cur->ste_has_docstring = 1; |
450 | 174 | } |
451 | 4.52k | for (i = 0; i < asdl_seq_LEN(seq); i++) |
452 | 4.25k | if (!symtable_visit_stmt(st, |
453 | 4.25k | (stmt_ty)asdl_seq_GET(seq, i))) |
454 | 0 | goto error; |
455 | 264 | break; |
456 | 264 | case Expression_kind: |
457 | 43 | if (!symtable_visit_expr(st, mod->v.Expression.body)) |
458 | 0 | goto error; |
459 | 43 | break; |
460 | 43 | case Interactive_kind: |
461 | 0 | seq = mod->v.Interactive.body; |
462 | 0 | for (i = 0; i < asdl_seq_LEN(seq); i++) |
463 | 0 | if (!symtable_visit_stmt(st, |
464 | 0 | (stmt_ty)asdl_seq_GET(seq, i))) |
465 | 0 | goto error; |
466 | 0 | break; |
467 | 0 | case FunctionType_kind: |
468 | 0 | PyErr_SetString(PyExc_RuntimeError, |
469 | 0 | "this compiler does not handle FunctionTypes"); |
470 | 0 | goto error; |
471 | 307 | } |
472 | 307 | if (!symtable_exit_block(st)) { |
473 | 0 | _PySymtable_Free(st); |
474 | 0 | return NULL; |
475 | 0 | } |
476 | | /* Make the second symbol analysis pass */ |
477 | 307 | if (symtable_analyze(st)) { |
478 | | #if _PY_DUMP_SYMTABLE |
479 | | dump_symtable(st->st_top); |
480 | | #endif |
481 | 307 | return st; |
482 | 307 | } |
483 | 0 | _PySymtable_Free(st); |
484 | 0 | return NULL; |
485 | 0 | error: |
486 | 0 | (void) symtable_exit_block(st); |
487 | 0 | _PySymtable_Free(st); |
488 | 0 | return NULL; |
489 | 307 | } |
490 | | |
491 | | |
492 | | void |
493 | | _PySymtable_Free(struct symtable *st) |
494 | 307 | { |
495 | 307 | Py_XDECREF(st->st_filename); |
496 | 307 | Py_XDECREF(st->st_blocks); |
497 | 307 | Py_XDECREF(st->st_stack); |
498 | 307 | PyMem_Free((void *)st); |
499 | 307 | } |
500 | | |
501 | | PySTEntryObject * |
502 | | _PySymtable_Lookup(struct symtable *st, void *key) |
503 | 6.16k | { |
504 | 6.16k | PyObject *k, *v; |
505 | | |
506 | 6.16k | k = PyLong_FromVoidPtr(key); |
507 | 6.16k | if (k == NULL) |
508 | 0 | return NULL; |
509 | 6.16k | if (PyDict_GetItemRef(st->st_blocks, k, &v) == 0) { |
510 | 0 | PyErr_SetString(PyExc_KeyError, |
511 | 0 | "unknown symbol table entry"); |
512 | 0 | } |
513 | 6.16k | Py_DECREF(k); |
514 | | |
515 | 6.16k | assert(v == NULL || PySTEntry_Check(v)); |
516 | 6.16k | return (PySTEntryObject *)v; |
517 | 6.16k | } |
518 | | |
519 | | int |
520 | | _PySymtable_LookupOptional(struct symtable *st, void *key, |
521 | | PySTEntryObject **out) |
522 | 4.13k | { |
523 | 4.13k | PyObject *k = PyLong_FromVoidPtr(key); |
524 | 4.13k | if (k == NULL) { |
525 | 0 | *out = NULL; |
526 | 0 | return -1; |
527 | 0 | } |
528 | 4.13k | int result = PyDict_GetItemRef(st->st_blocks, k, (PyObject **)out); |
529 | 4.13k | Py_DECREF(k); |
530 | 4.13k | assert(*out == NULL || PySTEntry_Check(*out)); |
531 | 4.13k | return result; |
532 | 4.13k | } |
533 | | |
534 | | long |
535 | | _PyST_GetSymbol(PySTEntryObject *ste, PyObject *name) |
536 | 98.8k | { |
537 | 98.8k | PyObject *v; |
538 | 98.8k | if (PyDict_GetItemRef(ste->ste_symbols, name, &v) < 0) { |
539 | 0 | return -1; |
540 | 0 | } |
541 | 98.8k | if (!v) { |
542 | 13.8k | return 0; |
543 | 13.8k | } |
544 | 84.9k | long symbol = PyLong_AsLong(v); |
545 | 84.9k | Py_DECREF(v); |
546 | 84.9k | if (symbol < 0) { |
547 | 0 | if (!PyErr_Occurred()) { |
548 | 0 | PyErr_SetString(PyExc_SystemError, "invalid symbol"); |
549 | 0 | } |
550 | 0 | return -1; |
551 | 0 | } |
552 | 84.9k | return symbol; |
553 | 84.9k | } |
554 | | |
555 | | int |
556 | | _PyST_GetScope(PySTEntryObject *ste, PyObject *name) |
557 | 88.5k | { |
558 | 88.5k | long symbol = _PyST_GetSymbol(ste, name); |
559 | 88.5k | if (symbol < 0) { |
560 | 0 | return -1; |
561 | 0 | } |
562 | 88.5k | return SYMBOL_TO_SCOPE(symbol); |
563 | 88.5k | } |
564 | | |
565 | | int |
566 | | _PyST_IsFunctionLike(PySTEntryObject *ste) |
567 | 173k | { |
568 | 173k | return ste->ste_type == FunctionBlock |
569 | 173k | || ste->ste_type == AnnotationBlock |
570 | 173k | || ste->ste_type == TypeVariableBlock |
571 | 173k | || ste->ste_type == TypeAliasBlock |
572 | 173k | || ste->ste_type == TypeParametersBlock; |
573 | 173k | } |
574 | | |
575 | | static int |
576 | | error_at_directive(PySTEntryObject *ste, PyObject *name) |
577 | 0 | { |
578 | 0 | Py_ssize_t i; |
579 | 0 | PyObject *data; |
580 | 0 | assert(ste->ste_directives); |
581 | 0 | for (i = 0; i < PyList_GET_SIZE(ste->ste_directives); i++) { |
582 | 0 | data = PyList_GET_ITEM(ste->ste_directives, i); |
583 | 0 | assert(PyTuple_CheckExact(data)); |
584 | 0 | assert(PyUnicode_CheckExact(PyTuple_GET_ITEM(data, 0))); |
585 | 0 | if (PyUnicode_Compare(PyTuple_GET_ITEM(data, 0), name) == 0) { |
586 | 0 | PyErr_RangedSyntaxLocationObject(ste->ste_table->st_filename, |
587 | 0 | PyLong_AsLong(PyTuple_GET_ITEM(data, 1)), |
588 | 0 | PyLong_AsLong(PyTuple_GET_ITEM(data, 2)) + 1, |
589 | 0 | PyLong_AsLong(PyTuple_GET_ITEM(data, 3)), |
590 | 0 | PyLong_AsLong(PyTuple_GET_ITEM(data, 4)) + 1); |
591 | |
|
592 | 0 | return 0; |
593 | 0 | } |
594 | 0 | } |
595 | 0 | PyErr_SetString(PyExc_RuntimeError, |
596 | 0 | "BUG: internal directive bookkeeping broken"); |
597 | 0 | return 0; |
598 | 0 | } |
599 | | |
600 | | |
601 | | /* Analyze raw symbol information to determine scope of each name. |
602 | | |
603 | | The next several functions are helpers for symtable_analyze(), |
604 | | which determines whether a name is local, global, or free. In addition, |
605 | | it determines which local variables are cell variables; they provide |
606 | | bindings that are used for free variables in enclosed blocks. |
607 | | |
608 | | There are also two kinds of global variables, implicit and explicit. An |
609 | | explicit global is declared with the global statement. An implicit |
610 | | global is a free variable for which the compiler has found no binding |
611 | | in an enclosing function scope. The implicit global is either a global |
612 | | or a builtin. Python's module and class blocks use the xxx_NAME opcodes |
613 | | to handle these names to implement slightly odd semantics. In such a |
614 | | block, the name is treated as global until it is assigned to; then it |
615 | | is treated as a local. |
616 | | |
617 | | The symbol table requires two passes to determine the scope of each name. |
618 | | The first pass collects raw facts from the AST via the symtable_visit_* |
619 | | functions: the name is a parameter here, the name is used but not defined |
620 | | here, etc. The second pass analyzes these facts during a pass over the |
621 | | PySTEntryObjects created during pass 1. |
622 | | |
623 | | When a function is entered during the second pass, the parent passes |
624 | | the set of all name bindings visible to its children. These bindings |
625 | | are used to determine if non-local variables are free or implicit globals. |
626 | | Names which are explicitly declared nonlocal must exist in this set of |
627 | | visible names - if they do not, a syntax error is raised. After doing |
628 | | the local analysis, it analyzes each of its child blocks using an |
629 | | updated set of name bindings. |
630 | | |
631 | | The children update the free variable set. If a local variable is added to |
632 | | the free variable set by the child, the variable is marked as a cell. The |
633 | | function object being defined must provide runtime storage for the variable |
634 | | that may outlive the function's frame. Cell variables are removed from the |
635 | | free set before the analyze function returns to its parent. |
636 | | |
637 | | During analysis, the names are: |
638 | | symbols: dict mapping from symbol names to flag values (including offset scope values) |
639 | | scopes: dict mapping from symbol names to scope values (no offset) |
640 | | local: set of all symbol names local to the current scope |
641 | | bound: set of all symbol names local to a containing function scope |
642 | | free: set of all symbol names referenced but not bound in child scopes |
643 | | global: set of all symbol names explicitly declared as global |
644 | | */ |
645 | | |
646 | | #define SET_SCOPE(DICT, NAME, I) \ |
647 | 41.5k | do { \ |
648 | 41.5k | PyObject *o = PyLong_FromLong(I); \ |
649 | 41.5k | if (!o) \ |
650 | 41.5k | return 0; \ |
651 | 41.5k | if (PyDict_SetItem((DICT), (NAME), o) < 0) { \ |
652 | 0 | Py_DECREF(o); \ |
653 | 0 | return 0; \ |
654 | 0 | } \ |
655 | 41.5k | Py_DECREF(o); \ |
656 | 41.5k | } while(0) |
657 | | |
658 | | /* Decide on scope of name, given flags. |
659 | | |
660 | | The namespace dictionaries may be modified to record information |
661 | | about the new name. For example, a new global will add an entry to |
662 | | global. A name that was global can be changed to local. |
663 | | */ |
664 | | |
665 | | static int |
666 | | analyze_name(PySTEntryObject *ste, PyObject *scopes, PyObject *name, long flags, |
667 | | PyObject *bound, PyObject *local, PyObject *free, |
668 | | PyObject *global, PyObject *type_params, PySTEntryObject *class_entry) |
669 | 41.3k | { |
670 | 41.3k | int contains; |
671 | 41.3k | if (flags & DEF_GLOBAL) { |
672 | 72 | if (flags & DEF_NONLOCAL) { |
673 | 0 | PyErr_Format(PyExc_SyntaxError, |
674 | 0 | "name '%U' is nonlocal and global", |
675 | 0 | name); |
676 | 0 | return error_at_directive(ste, name); |
677 | 0 | } |
678 | 72 | SET_SCOPE(scopes, name, GLOBAL_EXPLICIT); |
679 | 72 | if (PySet_Add(global, name) < 0) |
680 | 0 | return 0; |
681 | 72 | if (bound && (PySet_Discard(bound, name) < 0)) |
682 | 0 | return 0; |
683 | 72 | return 1; |
684 | 72 | } |
685 | 41.2k | if (flags & DEF_NONLOCAL) { |
686 | 47 | if (!bound) { |
687 | 0 | PyErr_Format(PyExc_SyntaxError, |
688 | 0 | "nonlocal declaration not allowed at module level"); |
689 | 0 | return error_at_directive(ste, name); |
690 | 0 | } |
691 | 47 | contains = PySet_Contains(bound, name); |
692 | 47 | if (contains < 0) { |
693 | 0 | return 0; |
694 | 0 | } |
695 | 47 | if (!contains) { |
696 | 0 | PyErr_Format(PyExc_SyntaxError, |
697 | 0 | "no binding for nonlocal '%U' found", |
698 | 0 | name); |
699 | |
|
700 | 0 | return error_at_directive(ste, name); |
701 | 0 | } |
702 | 47 | contains = PySet_Contains(type_params, name); |
703 | 47 | if (contains < 0) { |
704 | 0 | return 0; |
705 | 0 | } |
706 | 47 | if (contains) { |
707 | 0 | PyErr_Format(PyExc_SyntaxError, |
708 | 0 | "nonlocal binding not allowed for type parameter '%U'", |
709 | 0 | name); |
710 | 0 | return error_at_directive(ste, name); |
711 | 0 | } |
712 | 47 | SET_SCOPE(scopes, name, FREE); |
713 | 47 | return PySet_Add(free, name) >= 0; |
714 | 47 | } |
715 | 41.2k | if (flags & DEF_BOUND) { |
716 | 27.3k | SET_SCOPE(scopes, name, LOCAL); |
717 | 27.3k | if (PySet_Add(local, name) < 0) |
718 | 0 | return 0; |
719 | 27.3k | if (PySet_Discard(global, name) < 0) |
720 | 0 | return 0; |
721 | 27.3k | if (flags & DEF_TYPE_PARAM) { |
722 | 0 | if (PySet_Add(type_params, name) < 0) |
723 | 0 | return 0; |
724 | 0 | } |
725 | 27.3k | else { |
726 | 27.3k | if (PySet_Discard(type_params, name) < 0) |
727 | 0 | return 0; |
728 | 27.3k | } |
729 | 27.3k | return 1; |
730 | 27.3k | } |
731 | | // If we were passed class_entry (i.e., we're in an ste_can_see_class_scope scope) |
732 | | // and the bound name is in that set, then the name is potentially bound both by |
733 | | // the immediately enclosing class namespace, and also by an outer function namespace. |
734 | | // In that case, we want the runtime name resolution to look at only the class |
735 | | // namespace and the globals (not the namespace providing the bound). |
736 | | // Similarly, if the name is explicitly global in the class namespace (through the |
737 | | // global statement), we want to also treat it as a global in this scope. |
738 | 13.8k | if (class_entry != NULL) { |
739 | 2.76k | long class_flags = _PyST_GetSymbol(class_entry, name); |
740 | 2.76k | if (class_flags < 0) { |
741 | 0 | return 0; |
742 | 0 | } |
743 | 2.76k | if (class_flags & DEF_GLOBAL) { |
744 | 0 | SET_SCOPE(scopes, name, GLOBAL_EXPLICIT); |
745 | 0 | return 1; |
746 | 0 | } |
747 | 2.76k | else if ((class_flags & DEF_BOUND) && !(class_flags & DEF_NONLOCAL)) { |
748 | 0 | SET_SCOPE(scopes, name, GLOBAL_IMPLICIT); |
749 | 0 | return 1; |
750 | 0 | } |
751 | 2.76k | } |
752 | | /* If an enclosing block has a binding for this name, it |
753 | | is a free variable rather than a global variable. |
754 | | Note that having a non-NULL bound implies that the block |
755 | | is nested. |
756 | | */ |
757 | 13.8k | if (bound) { |
758 | 13.4k | contains = PySet_Contains(bound, name); |
759 | 13.4k | if (contains < 0) { |
760 | 0 | return 0; |
761 | 0 | } |
762 | 13.4k | if (contains) { |
763 | 3.53k | SET_SCOPE(scopes, name, FREE); |
764 | 3.53k | return PySet_Add(free, name) >= 0; |
765 | 3.53k | } |
766 | 13.4k | } |
767 | | /* If a parent has a global statement, then call it global |
768 | | explicit? It could also be global implicit. |
769 | | */ |
770 | 10.3k | if (global) { |
771 | 10.3k | contains = PySet_Contains(global, name); |
772 | 10.3k | if (contains < 0) { |
773 | 0 | return 0; |
774 | 0 | } |
775 | 10.3k | if (contains) { |
776 | 37 | SET_SCOPE(scopes, name, GLOBAL_IMPLICIT); |
777 | 37 | return 1; |
778 | 37 | } |
779 | 10.3k | } |
780 | 10.2k | SET_SCOPE(scopes, name, GLOBAL_IMPLICIT); |
781 | 10.2k | return 1; |
782 | 10.2k | } |
783 | | |
784 | | static int |
785 | | is_free_in_any_child(PySTEntryObject *entry, PyObject *key) |
786 | 199 | { |
787 | 199 | for (Py_ssize_t i = 0; i < PyList_GET_SIZE(entry->ste_children); i++) { |
788 | 0 | PySTEntryObject *child_ste = (PySTEntryObject *)PyList_GET_ITEM( |
789 | 0 | entry->ste_children, i); |
790 | 0 | long scope = _PyST_GetScope(child_ste, key); |
791 | 0 | if (scope < 0) { |
792 | 0 | return -1; |
793 | 0 | } |
794 | 0 | if (scope == FREE) { |
795 | 0 | return 1; |
796 | 0 | } |
797 | 0 | } |
798 | 199 | return 0; |
799 | 199 | } |
800 | | |
801 | | static int |
802 | | inline_comprehension(PySTEntryObject *ste, PySTEntryObject *comp, |
803 | | PyObject *scopes, PyObject *comp_free, |
804 | | PyObject *inlined_cells) |
805 | 185 | { |
806 | 185 | PyObject *k, *v; |
807 | 185 | Py_ssize_t pos = 0; |
808 | 185 | int remove_dunder_class = 0; |
809 | | |
810 | 786 | while (PyDict_Next(comp->ste_symbols, &pos, &k, &v)) { |
811 | | // skip comprehension parameter |
812 | 601 | long comp_flags = PyLong_AsLong(v); |
813 | 601 | if (comp_flags == -1 && PyErr_Occurred()) { |
814 | 0 | return 0; |
815 | 0 | } |
816 | 601 | if (comp_flags & DEF_PARAM) { |
817 | 185 | assert(_PyUnicode_EqualToASCIIString(k, ".0")); |
818 | 185 | continue; |
819 | 185 | } |
820 | 416 | int scope = SYMBOL_TO_SCOPE(comp_flags); |
821 | 416 | int only_flags = comp_flags & ((1 << SCOPE_OFFSET) - 1); |
822 | 416 | if (scope == CELL || only_flags & DEF_COMP_CELL) { |
823 | 0 | if (PySet_Add(inlined_cells, k) < 0) { |
824 | 0 | return 0; |
825 | 0 | } |
826 | 0 | } |
827 | 416 | PyObject *existing = PyDict_GetItemWithError(ste->ste_symbols, k); |
828 | 416 | if (existing == NULL && PyErr_Occurred()) { |
829 | 0 | return 0; |
830 | 0 | } |
831 | | // __class__ is never allowed to be free through a class scope (see |
832 | | // drop_class_free) |
833 | 416 | if (scope == FREE && ste->ste_type == ClassBlock && |
834 | 416 | _PyUnicode_EqualToASCIIString(k, "__class__")) { |
835 | 0 | scope = GLOBAL_IMPLICIT; |
836 | 0 | if (PySet_Discard(comp_free, k) < 0) { |
837 | 0 | return 0; |
838 | 0 | } |
839 | 0 | remove_dunder_class = 1; |
840 | 0 | } |
841 | 416 | if (!existing) { |
842 | | // name does not exist in scope, copy from comprehension |
843 | 193 | assert(scope != FREE || PySet_Contains(comp_free, k) == 1); |
844 | 193 | PyObject *v_flags = PyLong_FromLong(only_flags); |
845 | 193 | if (v_flags == NULL) { |
846 | 0 | return 0; |
847 | 0 | } |
848 | 193 | int ok = PyDict_SetItem(ste->ste_symbols, k, v_flags); |
849 | 193 | Py_DECREF(v_flags); |
850 | 193 | if (ok < 0) { |
851 | 0 | return 0; |
852 | 0 | } |
853 | 193 | SET_SCOPE(scopes, k, scope); |
854 | 193 | } |
855 | 223 | else { |
856 | 223 | long flags = PyLong_AsLong(existing); |
857 | 223 | if (flags == -1 && PyErr_Occurred()) { |
858 | 0 | return 0; |
859 | 0 | } |
860 | 223 | if ((flags & DEF_BOUND) && ste->ste_type != ClassBlock) { |
861 | | // free vars in comprehension that are locals in outer scope can |
862 | | // now simply be locals, unless they are free in comp children, |
863 | | // or if the outer scope is a class block |
864 | 199 | int ok = is_free_in_any_child(comp, k); |
865 | 199 | if (ok < 0) { |
866 | 0 | return 0; |
867 | 0 | } |
868 | 199 | if (!ok) { |
869 | 199 | if (PySet_Discard(comp_free, k) < 0) { |
870 | 0 | return 0; |
871 | 0 | } |
872 | 199 | } |
873 | 199 | } |
874 | 223 | } |
875 | 416 | } |
876 | 185 | if (remove_dunder_class && PyDict_DelItemString(comp->ste_symbols, "__class__") < 0) { |
877 | 0 | return 0; |
878 | 0 | } |
879 | 185 | return 1; |
880 | 185 | } |
881 | | |
882 | | #undef SET_SCOPE |
883 | | |
884 | | /* If a name is defined in free and also in locals, then this block |
885 | | provides the binding for the free variable. The name should be |
886 | | marked CELL in this block and removed from the free list. |
887 | | |
888 | | Note that the current block's free variables are included in free. |
889 | | That's safe because no name can be free and local in the same scope. |
890 | | */ |
891 | | |
892 | | static int |
893 | | analyze_cells(PyObject *scopes, PyObject *free, PyObject *inlined_cells) |
894 | 8.70k | { |
895 | 8.70k | PyObject *name, *v, *v_cell; |
896 | 8.70k | int success = 0; |
897 | 8.70k | Py_ssize_t pos = 0; |
898 | | |
899 | 8.70k | v_cell = PyLong_FromLong(CELL); |
900 | 8.70k | if (!v_cell) |
901 | 0 | return 0; |
902 | 41.5k | while (PyDict_Next(scopes, &pos, &name, &v)) { |
903 | 32.7k | long scope = PyLong_AsLong(v); |
904 | 32.7k | if (scope == -1 && PyErr_Occurred()) { |
905 | 0 | goto error; |
906 | 0 | } |
907 | 32.7k | if (scope != LOCAL) |
908 | 13.0k | continue; |
909 | 19.7k | int contains = PySet_Contains(free, name); |
910 | 19.7k | if (contains < 0) { |
911 | 0 | goto error; |
912 | 0 | } |
913 | 19.7k | if (!contains) { |
914 | 19.3k | contains = PySet_Contains(inlined_cells, name); |
915 | 19.3k | if (contains < 0) { |
916 | 0 | goto error; |
917 | 0 | } |
918 | 19.3k | if (!contains) { |
919 | 19.3k | continue; |
920 | 19.3k | } |
921 | 19.3k | } |
922 | | /* Replace LOCAL with CELL for this name, and remove |
923 | | from free. It is safe to replace the value of name |
924 | | in the dict, because it will not cause a resize. |
925 | | */ |
926 | 378 | if (PyDict_SetItem(scopes, name, v_cell) < 0) |
927 | 0 | goto error; |
928 | 378 | if (PySet_Discard(free, name) < 0) |
929 | 0 | goto error; |
930 | 378 | } |
931 | 8.70k | success = 1; |
932 | 8.70k | error: |
933 | 8.70k | Py_DECREF(v_cell); |
934 | 8.70k | return success; |
935 | 8.70k | } |
936 | | |
937 | | static int |
938 | | drop_class_free(PySTEntryObject *ste, PyObject *free) |
939 | 1.02k | { |
940 | 1.02k | int res; |
941 | 1.02k | res = PySet_Discard(free, &_Py_ID(__class__)); |
942 | 1.02k | if (res < 0) |
943 | 0 | return 0; |
944 | 1.02k | if (res) |
945 | 66 | ste->ste_needs_class_closure = 1; |
946 | 1.02k | res = PySet_Discard(free, &_Py_ID(__classdict__)); |
947 | 1.02k | if (res < 0) |
948 | 0 | return 0; |
949 | 1.02k | if (res) |
950 | 595 | ste->ste_needs_classdict = 1; |
951 | 1.02k | res = PySet_Discard(free, &_Py_ID(__conditional_annotations__)); |
952 | 1.02k | if (res < 0) |
953 | 0 | return 0; |
954 | 1.02k | if (res) { |
955 | 0 | ste->ste_has_conditional_annotations = 1; |
956 | 0 | } |
957 | 1.02k | return 1; |
958 | 1.02k | } |
959 | | |
960 | | /* Enter the final scope information into the ste_symbols dict. |
961 | | * |
962 | | * All arguments are dicts. Modifies symbols, others are read-only. |
963 | | */ |
964 | | static int |
965 | | update_symbols(PyObject *symbols, PyObject *scopes, |
966 | | PyObject *bound, PyObject *free, |
967 | | PyObject *inlined_cells, int classflag) |
968 | 10.0k | { |
969 | 10.0k | PyObject *name = NULL, *itr = NULL; |
970 | 10.0k | PyObject *v = NULL, *v_scope = NULL, *v_new = NULL, *v_free = NULL; |
971 | 10.0k | Py_ssize_t pos = 0; |
972 | | |
973 | | /* Update scope information for all symbols in this scope */ |
974 | 51.5k | while (PyDict_Next(symbols, &pos, &name, &v)) { |
975 | 41.5k | long flags = PyLong_AsLong(v); |
976 | 41.5k | if (flags == -1 && PyErr_Occurred()) { |
977 | 0 | return 0; |
978 | 0 | } |
979 | 41.5k | int contains = PySet_Contains(inlined_cells, name); |
980 | 41.5k | if (contains < 0) { |
981 | 0 | return 0; |
982 | 0 | } |
983 | 41.5k | if (contains) { |
984 | 0 | flags |= DEF_COMP_CELL; |
985 | 0 | } |
986 | 41.5k | if (PyDict_GetItemRef(scopes, name, &v_scope) < 0) { |
987 | 0 | return 0; |
988 | 0 | } |
989 | 41.5k | if (!v_scope) { |
990 | 0 | PyErr_SetObject(PyExc_KeyError, name); |
991 | 0 | return 0; |
992 | 0 | } |
993 | 41.5k | long scope = PyLong_AsLong(v_scope); |
994 | 41.5k | Py_DECREF(v_scope); |
995 | 41.5k | if (scope == -1 && PyErr_Occurred()) { |
996 | 0 | return 0; |
997 | 0 | } |
998 | 41.5k | flags |= (scope << SCOPE_OFFSET); |
999 | 41.5k | v_new = PyLong_FromLong(flags); |
1000 | 41.5k | if (!v_new) |
1001 | 0 | return 0; |
1002 | 41.5k | if (PyDict_SetItem(symbols, name, v_new) < 0) { |
1003 | 0 | Py_DECREF(v_new); |
1004 | 0 | return 0; |
1005 | 0 | } |
1006 | 41.5k | Py_DECREF(v_new); |
1007 | 41.5k | } |
1008 | | |
1009 | | /* Record not yet resolved free variables from children (if any) */ |
1010 | 10.0k | v_free = PyLong_FromLong(FREE << SCOPE_OFFSET); |
1011 | 10.0k | if (!v_free) |
1012 | 0 | return 0; |
1013 | | |
1014 | 10.0k | itr = PyObject_GetIter(free); |
1015 | 10.0k | if (itr == NULL) { |
1016 | 0 | Py_DECREF(v_free); |
1017 | 0 | return 0; |
1018 | 0 | } |
1019 | | |
1020 | 10.0k | while ((name = PyIter_Next(itr))) { |
1021 | 26 | v = PyDict_GetItemWithError(symbols, name); |
1022 | | |
1023 | | /* Handle symbol that already exists in this scope */ |
1024 | 26 | if (v) { |
1025 | | /* Handle a free variable in a method of |
1026 | | the class that has the same name as a local |
1027 | | or global in the class scope. |
1028 | | */ |
1029 | 10 | if (classflag) { |
1030 | 0 | long flags = PyLong_AsLong(v); |
1031 | 0 | if (flags == -1 && PyErr_Occurred()) { |
1032 | 0 | goto error; |
1033 | 0 | } |
1034 | 0 | flags |= DEF_FREE_CLASS; |
1035 | 0 | v_new = PyLong_FromLong(flags); |
1036 | 0 | if (!v_new) { |
1037 | 0 | goto error; |
1038 | 0 | } |
1039 | 0 | if (PyDict_SetItem(symbols, name, v_new) < 0) { |
1040 | 0 | Py_DECREF(v_new); |
1041 | 0 | goto error; |
1042 | 0 | } |
1043 | 0 | Py_DECREF(v_new); |
1044 | 0 | } |
1045 | | /* It's a cell, or already free in this scope */ |
1046 | 10 | Py_DECREF(name); |
1047 | 10 | continue; |
1048 | 10 | } |
1049 | 16 | else if (PyErr_Occurred()) { |
1050 | 0 | goto error; |
1051 | 0 | } |
1052 | | /* Handle global symbol */ |
1053 | 16 | if (bound) { |
1054 | 16 | int contains = PySet_Contains(bound, name); |
1055 | 16 | if (contains < 0) { |
1056 | 0 | goto error; |
1057 | 0 | } |
1058 | 16 | if (!contains) { |
1059 | 0 | Py_DECREF(name); |
1060 | 0 | continue; /* it's a global */ |
1061 | 0 | } |
1062 | 16 | } |
1063 | | /* Propagate new free symbol up the lexical stack */ |
1064 | 16 | if (PyDict_SetItem(symbols, name, v_free) < 0) { |
1065 | 0 | goto error; |
1066 | 0 | } |
1067 | 16 | Py_DECREF(name); |
1068 | 16 | } |
1069 | | |
1070 | | /* Check if loop ended because of exception in PyIter_Next */ |
1071 | 10.0k | if (PyErr_Occurred()) { |
1072 | 0 | goto error; |
1073 | 0 | } |
1074 | | |
1075 | 10.0k | Py_DECREF(itr); |
1076 | 10.0k | Py_DECREF(v_free); |
1077 | 10.0k | return 1; |
1078 | 0 | error: |
1079 | 0 | Py_XDECREF(v_free); |
1080 | 0 | Py_XDECREF(itr); |
1081 | 0 | Py_XDECREF(name); |
1082 | 0 | return 0; |
1083 | 10.0k | } |
1084 | | |
1085 | | /* Make final symbol table decisions for block of ste. |
1086 | | |
1087 | | Arguments: |
1088 | | ste -- current symtable entry (input/output) |
1089 | | bound -- set of variables bound in enclosing scopes (input). bound |
1090 | | is NULL for module blocks. |
1091 | | free -- set of free variables in enclosed scopes (output) |
1092 | | globals -- set of declared global variables in enclosing scopes (input) |
1093 | | |
1094 | | The implementation uses two mutually recursive functions, |
1095 | | analyze_block() and analyze_child_block(). analyze_block() is |
1096 | | responsible for analyzing the individual names defined in a block. |
1097 | | analyze_child_block() prepares temporary namespace dictionaries |
1098 | | used to evaluated nested blocks. |
1099 | | |
1100 | | The two functions exist because a child block should see the name |
1101 | | bindings of its enclosing blocks, but those bindings should not |
1102 | | propagate back to a parent block. |
1103 | | */ |
1104 | | |
1105 | | static int |
1106 | | analyze_child_block(PySTEntryObject *entry, PyObject *bound, PyObject *free, |
1107 | | PyObject *global, PyObject *type_params, |
1108 | | PySTEntryObject *class_entry, PyObject **child_free); |
1109 | | |
1110 | | static int |
1111 | | analyze_block(PySTEntryObject *ste, PyObject *bound, PyObject *free, |
1112 | | PyObject *global, PyObject *type_params, |
1113 | | PySTEntryObject *class_entry) |
1114 | 10.0k | { |
1115 | 10.0k | PyObject *name, *v, *local = NULL, *scopes = NULL, *newbound = NULL; |
1116 | 10.0k | PyObject *newglobal = NULL, *newfree = NULL, *inlined_cells = NULL; |
1117 | 10.0k | PyObject *temp; |
1118 | 10.0k | int success = 0; |
1119 | 10.0k | Py_ssize_t i, pos = 0; |
1120 | | |
1121 | 10.0k | local = PySet_New(NULL); /* collect new names bound in block */ |
1122 | 10.0k | if (!local) |
1123 | 0 | goto error; |
1124 | 10.0k | scopes = PyDict_New(); /* collect scopes defined for each name */ |
1125 | 10.0k | if (!scopes) |
1126 | 0 | goto error; |
1127 | | |
1128 | | /* Allocate new global, bound and free variable sets. These |
1129 | | sets hold the names visible in nested blocks. For |
1130 | | ClassBlocks, the bound and global names are initialized |
1131 | | before analyzing names, because class bindings aren't |
1132 | | visible in methods. For other blocks, they are initialized |
1133 | | after names are analyzed. |
1134 | | */ |
1135 | | |
1136 | | /* TODO(jhylton): Package these dicts in a struct so that we |
1137 | | can write reasonable helper functions? |
1138 | | */ |
1139 | 10.0k | newglobal = PySet_New(NULL); |
1140 | 10.0k | if (!newglobal) |
1141 | 0 | goto error; |
1142 | 10.0k | newfree = PySet_New(NULL); |
1143 | 10.0k | if (!newfree) |
1144 | 0 | goto error; |
1145 | 10.0k | newbound = PySet_New(NULL); |
1146 | 10.0k | if (!newbound) |
1147 | 0 | goto error; |
1148 | 10.0k | inlined_cells = PySet_New(NULL); |
1149 | 10.0k | if (!inlined_cells) |
1150 | 0 | goto error; |
1151 | | |
1152 | | /* Class namespace has no effect on names visible in |
1153 | | nested functions, so populate the global and bound |
1154 | | sets to be passed to child blocks before analyzing |
1155 | | this one. |
1156 | | */ |
1157 | 10.0k | if (ste->ste_type == ClassBlock) { |
1158 | | /* Pass down known globals */ |
1159 | 1.02k | temp = PyNumber_InPlaceOr(newglobal, global); |
1160 | 1.02k | if (!temp) |
1161 | 0 | goto error; |
1162 | 1.02k | Py_DECREF(temp); |
1163 | | /* Pass down previously bound symbols */ |
1164 | 1.02k | if (bound) { |
1165 | 1.02k | temp = PyNumber_InPlaceOr(newbound, bound); |
1166 | 1.02k | if (!temp) |
1167 | 0 | goto error; |
1168 | 1.02k | Py_DECREF(temp); |
1169 | 1.02k | } |
1170 | 1.02k | } |
1171 | | |
1172 | 51.3k | while (PyDict_Next(ste->ste_symbols, &pos, &name, &v)) { |
1173 | 41.3k | long flags = PyLong_AsLong(v); |
1174 | 41.3k | if (flags == -1 && PyErr_Occurred()) { |
1175 | 0 | goto error; |
1176 | 0 | } |
1177 | 41.3k | if (!analyze_name(ste, scopes, name, flags, |
1178 | 41.3k | bound, local, free, global, type_params, class_entry)) |
1179 | 0 | goto error; |
1180 | 41.3k | } |
1181 | | |
1182 | | /* Populate global and bound sets to be passed to children. */ |
1183 | 10.0k | if (ste->ste_type != ClassBlock) { |
1184 | | /* Add function locals to bound set */ |
1185 | 9.01k | if (_PyST_IsFunctionLike(ste)) { |
1186 | 8.70k | temp = PyNumber_InPlaceOr(newbound, local); |
1187 | 8.70k | if (!temp) |
1188 | 0 | goto error; |
1189 | 8.70k | Py_DECREF(temp); |
1190 | 8.70k | } |
1191 | | /* Pass down previously bound symbols */ |
1192 | 9.01k | if (bound) { |
1193 | 8.70k | temp = PyNumber_InPlaceOr(newbound, bound); |
1194 | 8.70k | if (!temp) |
1195 | 0 | goto error; |
1196 | 8.70k | Py_DECREF(temp); |
1197 | 8.70k | } |
1198 | | /* Pass down known globals */ |
1199 | 9.01k | temp = PyNumber_InPlaceOr(newglobal, global); |
1200 | 9.01k | if (!temp) |
1201 | 0 | goto error; |
1202 | 9.01k | Py_DECREF(temp); |
1203 | 9.01k | } |
1204 | 1.02k | else { |
1205 | | /* Special-case __class__ and __classdict__ */ |
1206 | 1.02k | if (PySet_Add(newbound, &_Py_ID(__class__)) < 0) |
1207 | 0 | goto error; |
1208 | 1.02k | if (PySet_Add(newbound, &_Py_ID(__classdict__)) < 0) |
1209 | 0 | goto error; |
1210 | 1.02k | if (PySet_Add(newbound, &_Py_ID(__conditional_annotations__)) < 0) |
1211 | 0 | goto error; |
1212 | 1.02k | } |
1213 | | |
1214 | | /* Recursively call analyze_child_block() on each child block. |
1215 | | |
1216 | | newbound, newglobal now contain the names visible in |
1217 | | nested blocks. The free variables in the children will |
1218 | | be added to newfree. |
1219 | | */ |
1220 | 19.7k | for (i = 0; i < PyList_GET_SIZE(ste->ste_children); ++i) { |
1221 | 9.72k | PyObject *child_free = NULL; |
1222 | 9.72k | PyObject *c = PyList_GET_ITEM(ste->ste_children, i); |
1223 | 9.72k | PySTEntryObject* entry; |
1224 | 9.72k | assert(c && PySTEntry_Check(c)); |
1225 | 9.72k | entry = (PySTEntryObject*)c; |
1226 | | |
1227 | 9.72k | PySTEntryObject *new_class_entry = NULL; |
1228 | 9.72k | if (entry->ste_can_see_class_scope) { |
1229 | 2.75k | if (ste->ste_type == ClassBlock) { |
1230 | 2.75k | new_class_entry = ste; |
1231 | 2.75k | } |
1232 | 0 | else if (class_entry) { |
1233 | 0 | new_class_entry = class_entry; |
1234 | 0 | } |
1235 | 2.75k | } |
1236 | | |
1237 | | // we inline all non-generator-expression comprehensions, |
1238 | | // except those in annotation scopes that are nested in classes |
1239 | 9.72k | int inline_comp = |
1240 | 9.72k | entry->ste_comprehension && |
1241 | 9.72k | !entry->ste_generator && |
1242 | 9.72k | !ste->ste_can_see_class_scope; |
1243 | | |
1244 | 9.72k | if (!analyze_child_block(entry, newbound, newfree, newglobal, |
1245 | 9.72k | type_params, new_class_entry, &child_free)) |
1246 | 0 | { |
1247 | 0 | goto error; |
1248 | 0 | } |
1249 | 9.72k | if (inline_comp) { |
1250 | 185 | if (!inline_comprehension(ste, entry, scopes, child_free, inlined_cells)) { |
1251 | 0 | Py_DECREF(child_free); |
1252 | 0 | goto error; |
1253 | 0 | } |
1254 | 185 | entry->ste_comp_inlined = 1; |
1255 | 185 | } |
1256 | 9.72k | temp = PyNumber_InPlaceOr(newfree, child_free); |
1257 | 9.72k | Py_DECREF(child_free); |
1258 | 9.72k | if (!temp) |
1259 | 0 | goto error; |
1260 | 9.72k | Py_DECREF(temp); |
1261 | 9.72k | } |
1262 | | |
1263 | | /* Splice children of inlined comprehensions into our children list */ |
1264 | 19.7k | for (i = PyList_GET_SIZE(ste->ste_children) - 1; i >= 0; --i) { |
1265 | 9.72k | PyObject* c = PyList_GET_ITEM(ste->ste_children, i); |
1266 | 9.72k | PySTEntryObject* entry; |
1267 | 9.72k | assert(c && PySTEntry_Check(c)); |
1268 | 9.72k | entry = (PySTEntryObject*)c; |
1269 | 9.72k | if (entry->ste_comp_inlined && |
1270 | 9.72k | PyList_SetSlice(ste->ste_children, i, i + 1, |
1271 | 185 | entry->ste_children) < 0) |
1272 | 0 | { |
1273 | 0 | goto error; |
1274 | 0 | } |
1275 | 9.72k | } |
1276 | | |
1277 | | /* Check if any local variables must be converted to cell variables */ |
1278 | 10.0k | if (_PyST_IsFunctionLike(ste) && !analyze_cells(scopes, newfree, inlined_cells)) |
1279 | 0 | goto error; |
1280 | 10.0k | else if (ste->ste_type == ClassBlock && !drop_class_free(ste, newfree)) |
1281 | 0 | goto error; |
1282 | | /* Records the results of the analysis in the symbol table entry */ |
1283 | 10.0k | if (!update_symbols(ste->ste_symbols, scopes, bound, newfree, inlined_cells, |
1284 | 10.0k | (ste->ste_type == ClassBlock) || ste->ste_can_see_class_scope)) |
1285 | 0 | goto error; |
1286 | | |
1287 | 10.0k | temp = PyNumber_InPlaceOr(free, newfree); |
1288 | 10.0k | if (!temp) |
1289 | 0 | goto error; |
1290 | 10.0k | Py_DECREF(temp); |
1291 | 10.0k | success = 1; |
1292 | 10.0k | error: |
1293 | 10.0k | Py_XDECREF(scopes); |
1294 | 10.0k | Py_XDECREF(local); |
1295 | 10.0k | Py_XDECREF(newbound); |
1296 | 10.0k | Py_XDECREF(newglobal); |
1297 | 10.0k | Py_XDECREF(newfree); |
1298 | 10.0k | Py_XDECREF(inlined_cells); |
1299 | 10.0k | if (!success) |
1300 | 0 | assert(PyErr_Occurred()); |
1301 | 10.0k | return success; |
1302 | 10.0k | } |
1303 | | |
1304 | | static int |
1305 | | analyze_child_block(PySTEntryObject *entry, PyObject *bound, PyObject *free, |
1306 | | PyObject *global, PyObject *type_params, |
1307 | | PySTEntryObject *class_entry, PyObject** child_free) |
1308 | 9.72k | { |
1309 | 9.72k | PyObject *temp_bound = NULL, *temp_global = NULL, *temp_free = NULL; |
1310 | 9.72k | PyObject *temp_type_params = NULL; |
1311 | | |
1312 | | /* Copy the bound/global/free sets. |
1313 | | |
1314 | | These sets are used by all blocks enclosed by the |
1315 | | current block. The analyze_block() call modifies these |
1316 | | sets. |
1317 | | |
1318 | | */ |
1319 | 9.72k | temp_bound = PySet_New(bound); |
1320 | 9.72k | if (!temp_bound) |
1321 | 0 | goto error; |
1322 | 9.72k | temp_free = PySet_New(free); |
1323 | 9.72k | if (!temp_free) |
1324 | 0 | goto error; |
1325 | 9.72k | temp_global = PySet_New(global); |
1326 | 9.72k | if (!temp_global) |
1327 | 0 | goto error; |
1328 | 9.72k | temp_type_params = PySet_New(type_params); |
1329 | 9.72k | if (!temp_type_params) |
1330 | 0 | goto error; |
1331 | | |
1332 | 9.72k | if (!analyze_block(entry, temp_bound, temp_free, temp_global, |
1333 | 9.72k | temp_type_params, class_entry)) |
1334 | 0 | goto error; |
1335 | 9.72k | *child_free = temp_free; |
1336 | 9.72k | Py_DECREF(temp_bound); |
1337 | 9.72k | Py_DECREF(temp_global); |
1338 | 9.72k | Py_DECREF(temp_type_params); |
1339 | 9.72k | return 1; |
1340 | 0 | error: |
1341 | 0 | Py_XDECREF(temp_bound); |
1342 | 0 | Py_XDECREF(temp_free); |
1343 | 0 | Py_XDECREF(temp_global); |
1344 | 0 | Py_XDECREF(temp_type_params); |
1345 | 0 | return 0; |
1346 | 9.72k | } |
1347 | | |
1348 | | static int |
1349 | | symtable_analyze(struct symtable *st) |
1350 | 307 | { |
1351 | 307 | PyObject *free, *global, *type_params; |
1352 | 307 | int r; |
1353 | | |
1354 | 307 | free = PySet_New(NULL); |
1355 | 307 | if (!free) |
1356 | 0 | return 0; |
1357 | 307 | global = PySet_New(NULL); |
1358 | 307 | if (!global) { |
1359 | 0 | Py_DECREF(free); |
1360 | 0 | return 0; |
1361 | 0 | } |
1362 | 307 | type_params = PySet_New(NULL); |
1363 | 307 | if (!type_params) { |
1364 | 0 | Py_DECREF(free); |
1365 | 0 | Py_DECREF(global); |
1366 | 0 | return 0; |
1367 | 0 | } |
1368 | 307 | r = analyze_block(st->st_top, NULL, free, global, type_params, NULL); |
1369 | 307 | Py_DECREF(free); |
1370 | 307 | Py_DECREF(global); |
1371 | 307 | Py_DECREF(type_params); |
1372 | 307 | return r; |
1373 | 307 | } |
1374 | | |
1375 | | /* symtable_enter_block() gets a reference via ste_new. |
1376 | | This reference is released when the block is exited, via the DECREF |
1377 | | in symtable_exit_block(). |
1378 | | */ |
1379 | | |
1380 | | static int |
1381 | | symtable_exit_block(struct symtable *st) |
1382 | 10.0k | { |
1383 | 10.0k | Py_ssize_t size; |
1384 | | |
1385 | 10.0k | st->st_cur = NULL; |
1386 | 10.0k | size = PyList_GET_SIZE(st->st_stack); |
1387 | 10.0k | if (size) { |
1388 | 10.0k | if (PyList_SetSlice(st->st_stack, size - 1, size, NULL) < 0) |
1389 | 0 | return 0; |
1390 | 10.0k | if (--size) |
1391 | 9.72k | st->st_cur = (PySTEntryObject *)PyList_GET_ITEM(st->st_stack, size - 1); |
1392 | 10.0k | } |
1393 | 10.0k | return 1; |
1394 | 10.0k | } |
1395 | | |
1396 | | static int |
1397 | | symtable_enter_existing_block(struct symtable *st, PySTEntryObject* ste, bool add_to_children) |
1398 | 10.0k | { |
1399 | 10.0k | if (PyList_Append(st->st_stack, (PyObject *)ste) < 0) { |
1400 | 0 | return 0; |
1401 | 0 | } |
1402 | 10.0k | PySTEntryObject *prev = st->st_cur; |
1403 | | /* bpo-37757: For now, disallow *all* assignment expressions in the |
1404 | | * outermost iterator expression of a comprehension, even those inside |
1405 | | * a nested comprehension or a lambda expression. |
1406 | | */ |
1407 | 10.0k | if (prev) { |
1408 | 9.72k | ste->ste_comp_iter_expr = prev->ste_comp_iter_expr; |
1409 | 9.72k | } |
1410 | | /* No need to inherit ste_mangled_names in classes, where all names |
1411 | | * are mangled. */ |
1412 | 10.0k | if (prev && prev->ste_mangled_names != NULL && ste->ste_type != ClassBlock) { |
1413 | 0 | ste->ste_mangled_names = Py_NewRef(prev->ste_mangled_names); |
1414 | 0 | } |
1415 | | /* The entry is owned by the stack. Borrow it for st_cur. */ |
1416 | 10.0k | st->st_cur = ste; |
1417 | | |
1418 | | /* If "from __future__ import annotations" is active, |
1419 | | * annotation blocks shouldn't have any affect on the symbol table since in |
1420 | | * the compilation stage, they will all be transformed to strings. */ |
1421 | 10.0k | if (st->st_future->ff_features & CO_FUTURE_ANNOTATIONS && ste->ste_type == AnnotationBlock) { |
1422 | 0 | return 1; |
1423 | 0 | } |
1424 | | |
1425 | 10.0k | if (ste->ste_type == ModuleBlock) |
1426 | 307 | st->st_global = st->st_cur->ste_symbols; |
1427 | | |
1428 | 10.0k | if (add_to_children && prev) { |
1429 | 9.72k | if (PyList_Append(prev->ste_children, (PyObject *)ste) < 0) { |
1430 | 0 | return 0; |
1431 | 0 | } |
1432 | 9.72k | } |
1433 | 10.0k | return 1; |
1434 | 10.0k | } |
1435 | | |
1436 | | static int |
1437 | | symtable_enter_block(struct symtable *st, identifier name, _Py_block_ty block, |
1438 | | void *ast, _Py_SourceLocation loc) |
1439 | 5.90k | { |
1440 | 5.90k | PySTEntryObject *ste = ste_new(st, name, block, ast, loc); |
1441 | 5.90k | if (ste == NULL) |
1442 | 0 | return 0; |
1443 | 5.90k | int result = symtable_enter_existing_block(st, ste, /* add_to_children */true); |
1444 | 5.90k | Py_DECREF(ste); |
1445 | 5.90k | if (block == AnnotationBlock || block == TypeVariableBlock || block == TypeAliasBlock) { |
1446 | 4.13k | _Py_DECLARE_STR(format, ".format"); |
1447 | | // We need to insert code that reads this "parameter" to the function. |
1448 | 4.13k | if (!symtable_add_def(st, &_Py_STR(format), DEF_PARAM, loc)) { |
1449 | 0 | return 0; |
1450 | 0 | } |
1451 | 4.13k | if (!symtable_add_def(st, &_Py_STR(format), USE, loc)) { |
1452 | 0 | return 0; |
1453 | 0 | } |
1454 | 4.13k | } |
1455 | 5.90k | return result; |
1456 | 5.90k | } |
1457 | | |
1458 | | static long |
1459 | | symtable_lookup_entry(struct symtable *st, PySTEntryObject *ste, PyObject *name) |
1460 | 84 | { |
1461 | 84 | PyObject *mangled = _Py_MaybeMangle(st->st_private, ste, name); |
1462 | 84 | if (!mangled) |
1463 | 0 | return -1; |
1464 | 84 | long ret = _PyST_GetSymbol(ste, mangled); |
1465 | 84 | Py_DECREF(mangled); |
1466 | 84 | if (ret < 0) { |
1467 | 0 | return -1; |
1468 | 0 | } |
1469 | 84 | return ret; |
1470 | 84 | } |
1471 | | |
1472 | | static long |
1473 | | symtable_lookup(struct symtable *st, PyObject *name) |
1474 | 84 | { |
1475 | 84 | return symtable_lookup_entry(st, st->st_cur, name); |
1476 | 84 | } |
1477 | | |
1478 | | static int |
1479 | | symtable_add_def_helper(struct symtable *st, PyObject *name, int flag, struct _symtable_entry *ste, |
1480 | | _Py_SourceLocation loc) |
1481 | 96.7k | { |
1482 | 96.7k | PyObject *o; |
1483 | 96.7k | PyObject *dict; |
1484 | 96.7k | long val; |
1485 | 96.7k | PyObject *mangled = _Py_MaybeMangle(st->st_private, st->st_cur, name); |
1486 | | |
1487 | 96.7k | if (!mangled) |
1488 | 0 | return 0; |
1489 | 96.7k | dict = ste->ste_symbols; |
1490 | 96.7k | if ((o = PyDict_GetItemWithError(dict, mangled))) { |
1491 | 55.4k | val = PyLong_AsLong(o); |
1492 | 55.4k | if (val == -1 && PyErr_Occurred()) { |
1493 | 0 | goto error; |
1494 | 0 | } |
1495 | 55.4k | if ((flag & DEF_PARAM) && (val & DEF_PARAM)) { |
1496 | | /* Is it better to use 'mangled' or 'name' here? */ |
1497 | 0 | PyErr_Format(PyExc_SyntaxError, DUPLICATE_PARAMETER, name); |
1498 | 0 | SET_ERROR_LOCATION(st->st_filename, loc); |
1499 | 0 | goto error; |
1500 | 0 | } |
1501 | 55.4k | if ((flag & DEF_TYPE_PARAM) && (val & DEF_TYPE_PARAM)) { |
1502 | 0 | PyErr_Format(PyExc_SyntaxError, DUPLICATE_TYPE_PARAM, name); |
1503 | 0 | SET_ERROR_LOCATION(st->st_filename, loc); |
1504 | 0 | goto error; |
1505 | 0 | } |
1506 | 55.4k | val |= flag; |
1507 | 55.4k | } |
1508 | 41.3k | else if (PyErr_Occurred()) { |
1509 | 0 | goto error; |
1510 | 0 | } |
1511 | 41.3k | else { |
1512 | 41.3k | val = flag; |
1513 | 41.3k | } |
1514 | 96.7k | if (ste->ste_comp_iter_target) { |
1515 | | /* This name is an iteration variable in a comprehension, |
1516 | | * so check for a binding conflict with any named expressions. |
1517 | | * Otherwise, mark it as an iteration variable so subsequent |
1518 | | * named expressions can check for conflicts. |
1519 | | */ |
1520 | 400 | if (val & (DEF_GLOBAL | DEF_NONLOCAL)) { |
1521 | 0 | PyErr_Format(PyExc_SyntaxError, |
1522 | 0 | NAMED_EXPR_COMP_INNER_LOOP_CONFLICT, name); |
1523 | 0 | SET_ERROR_LOCATION(st->st_filename, loc); |
1524 | 0 | goto error; |
1525 | 0 | } |
1526 | 400 | val |= DEF_COMP_ITER; |
1527 | 400 | } |
1528 | 96.7k | o = PyLong_FromLong(val); |
1529 | 96.7k | if (o == NULL) |
1530 | 0 | goto error; |
1531 | 96.7k | if (PyDict_SetItem(dict, mangled, o) < 0) { |
1532 | 0 | Py_DECREF(o); |
1533 | 0 | goto error; |
1534 | 0 | } |
1535 | 96.7k | Py_DECREF(o); |
1536 | | |
1537 | 96.7k | if (flag & DEF_PARAM) { |
1538 | 12.9k | if (PyList_Append(ste->ste_varnames, mangled) < 0) |
1539 | 0 | goto error; |
1540 | 83.7k | } else if (flag & DEF_GLOBAL) { |
1541 | | /* XXX need to update DEF_GLOBAL for other flags too; |
1542 | | perhaps only DEF_FREE_GLOBAL */ |
1543 | 37 | val = 0; |
1544 | 37 | if ((o = PyDict_GetItemWithError(st->st_global, mangled))) { |
1545 | 36 | val = PyLong_AsLong(o); |
1546 | 36 | if (val == -1 && PyErr_Occurred()) { |
1547 | 0 | goto error; |
1548 | 0 | } |
1549 | 36 | } |
1550 | 1 | else if (PyErr_Occurred()) { |
1551 | 0 | goto error; |
1552 | 0 | } |
1553 | 37 | val |= flag; |
1554 | 37 | o = PyLong_FromLong(val); |
1555 | 37 | if (o == NULL) |
1556 | 0 | goto error; |
1557 | 37 | if (PyDict_SetItem(st->st_global, mangled, o) < 0) { |
1558 | 0 | Py_DECREF(o); |
1559 | 0 | goto error; |
1560 | 0 | } |
1561 | 37 | Py_DECREF(o); |
1562 | 37 | } |
1563 | 96.7k | Py_DECREF(mangled); |
1564 | 96.7k | return 1; |
1565 | | |
1566 | 0 | error: |
1567 | 0 | Py_DECREF(mangled); |
1568 | 0 | return 0; |
1569 | 96.7k | } |
1570 | | |
1571 | | static int |
1572 | | check_name(struct symtable *st, PyObject *name, _Py_SourceLocation loc, |
1573 | | expr_context_ty ctx) |
1574 | 51.5k | { |
1575 | 51.5k | if (ctx == Store && _PyUnicode_EqualToASCIIString(name, "__debug__")) { |
1576 | 0 | PyErr_SetString(PyExc_SyntaxError, "cannot assign to __debug__"); |
1577 | 0 | SET_ERROR_LOCATION(st->st_filename, loc); |
1578 | 0 | return 0; |
1579 | 0 | } |
1580 | 51.5k | if (ctx == Del && _PyUnicode_EqualToASCIIString(name, "__debug__")) { |
1581 | 0 | PyErr_SetString(PyExc_SyntaxError, "cannot delete __debug__"); |
1582 | 0 | SET_ERROR_LOCATION(st->st_filename, loc); |
1583 | 0 | return 0; |
1584 | 0 | } |
1585 | 51.5k | return 1; |
1586 | 51.5k | } |
1587 | | |
1588 | | static int |
1589 | | check_keywords(struct symtable *st, asdl_keyword_seq *keywords) |
1590 | 17.8k | { |
1591 | 19.5k | for (Py_ssize_t i = 0; i < asdl_seq_LEN(keywords); i++) { |
1592 | 1.71k | keyword_ty key = ((keyword_ty)asdl_seq_GET(keywords, i)); |
1593 | 1.71k | if (key->arg && !check_name(st, key->arg, LOCATION(key), Store)) { |
1594 | 0 | return 0; |
1595 | 0 | } |
1596 | 1.71k | } |
1597 | 17.8k | return 1; |
1598 | 17.8k | } |
1599 | | |
1600 | | static int |
1601 | | check_kwd_patterns(struct symtable *st, pattern_ty p) |
1602 | 0 | { |
1603 | 0 | assert(p->kind == MatchClass_kind); |
1604 | 0 | asdl_identifier_seq *kwd_attrs = p->v.MatchClass.kwd_attrs; |
1605 | 0 | asdl_pattern_seq *kwd_patterns = p->v.MatchClass.kwd_patterns; |
1606 | 0 | for (Py_ssize_t i = 0; i < asdl_seq_LEN(kwd_attrs); i++) { |
1607 | 0 | _Py_SourceLocation loc = LOCATION(asdl_seq_GET(kwd_patterns, i)); |
1608 | 0 | if (!check_name(st, asdl_seq_GET(kwd_attrs, i), loc, Store)) { |
1609 | 0 | return 0; |
1610 | 0 | } |
1611 | 0 | } |
1612 | 0 | return 1; |
1613 | 0 | } |
1614 | | |
1615 | | static int |
1616 | | symtable_add_def_ctx(struct symtable *st, PyObject *name, int flag, |
1617 | | _Py_SourceLocation loc, expr_context_ty ctx) |
1618 | 96.7k | { |
1619 | 96.7k | int write_mask = DEF_PARAM | DEF_LOCAL | DEF_IMPORT; |
1620 | 96.7k | if ((flag & write_mask) && !check_name(st, name, loc, ctx)) { |
1621 | 0 | return 0; |
1622 | 0 | } |
1623 | 96.7k | if ((flag & DEF_TYPE_PARAM) && st->st_cur->ste_mangled_names != NULL) { |
1624 | 0 | if(PySet_Add(st->st_cur->ste_mangled_names, name) < 0) { |
1625 | 0 | return 0; |
1626 | 0 | } |
1627 | 0 | } |
1628 | 96.7k | return symtable_add_def_helper(st, name, flag, st->st_cur, loc); |
1629 | 96.7k | } |
1630 | | |
1631 | | static int |
1632 | | symtable_add_def(struct symtable *st, PyObject *name, int flag, |
1633 | | _Py_SourceLocation loc) |
1634 | 26.4k | { |
1635 | 26.4k | return symtable_add_def_ctx(st, name, flag, loc, |
1636 | 26.4k | flag == USE ? Load : Store); |
1637 | 26.4k | } |
1638 | | |
1639 | | static int |
1640 | | symtable_enter_type_param_block(struct symtable *st, identifier name, |
1641 | | void *ast, int has_defaults, int has_kwdefaults, |
1642 | | enum _stmt_kind kind, _Py_SourceLocation loc) |
1643 | 0 | { |
1644 | 0 | _Py_block_ty current_type = st->st_cur->ste_type; |
1645 | 0 | if(!symtable_enter_block(st, name, TypeParametersBlock, ast, loc)) { |
1646 | 0 | return 0; |
1647 | 0 | } |
1648 | 0 | if (current_type == ClassBlock) { |
1649 | 0 | st->st_cur->ste_can_see_class_scope = 1; |
1650 | 0 | if (!symtable_add_def(st, &_Py_ID(__classdict__), USE, loc)) { |
1651 | 0 | return 0; |
1652 | 0 | } |
1653 | 0 | } |
1654 | 0 | if (kind == ClassDef_kind) { |
1655 | 0 | _Py_DECLARE_STR(type_params, ".type_params"); |
1656 | | // It gets "set" when we create the type params tuple and |
1657 | | // "used" when we build up the bases. |
1658 | 0 | if (!symtable_add_def(st, &_Py_STR(type_params), DEF_LOCAL, loc)) { |
1659 | 0 | return 0; |
1660 | 0 | } |
1661 | 0 | if (!symtable_add_def(st, &_Py_STR(type_params), USE, loc)) { |
1662 | 0 | return 0; |
1663 | 0 | } |
1664 | | // This is used for setting the generic base |
1665 | 0 | _Py_DECLARE_STR(generic_base, ".generic_base"); |
1666 | 0 | if (!symtable_add_def(st, &_Py_STR(generic_base), DEF_LOCAL, loc)) { |
1667 | 0 | return 0; |
1668 | 0 | } |
1669 | 0 | if (!symtable_add_def(st, &_Py_STR(generic_base), USE, loc)) { |
1670 | 0 | return 0; |
1671 | 0 | } |
1672 | 0 | } |
1673 | 0 | if (has_defaults) { |
1674 | 0 | _Py_DECLARE_STR(defaults, ".defaults"); |
1675 | 0 | if (!symtable_add_def(st, &_Py_STR(defaults), DEF_PARAM, loc)) { |
1676 | 0 | return 0; |
1677 | 0 | } |
1678 | 0 | } |
1679 | 0 | if (has_kwdefaults) { |
1680 | 0 | _Py_DECLARE_STR(kwdefaults, ".kwdefaults"); |
1681 | 0 | if (!symtable_add_def(st, &_Py_STR(kwdefaults), DEF_PARAM, loc)) { |
1682 | 0 | return 0; |
1683 | 0 | } |
1684 | 0 | } |
1685 | 0 | return 1; |
1686 | 0 | } |
1687 | | |
1688 | | /* VISIT, VISIT_SEQ and VIST_SEQ_TAIL take an ASDL type as their second argument. |
1689 | | They use the ASDL name to synthesize the name of the C type and the visit |
1690 | | function. |
1691 | | |
1692 | | VISIT_SEQ_TAIL permits the start of an ASDL sequence to be skipped, which is |
1693 | | useful if the first node in the sequence requires special treatment. |
1694 | | |
1695 | | ENTER_RECURSIVE macro increments the current recursion depth counter. |
1696 | | It should be used at the beginning of the recursive function. |
1697 | | |
1698 | | LEAVE_RECURSIVE macro decrements the current recursion depth counter. |
1699 | | It should be used at the end of the recursive function. |
1700 | | */ |
1701 | | |
1702 | | #define VISIT(ST, TYPE, V) \ |
1703 | 98.2k | do { \ |
1704 | 98.2k | if (!symtable_visit_ ## TYPE((ST), (V))) { \ |
1705 | 0 | return 0; \ |
1706 | 0 | } \ |
1707 | 98.2k | } while(0) |
1708 | | |
1709 | | #define VISIT_SEQ(ST, TYPE, SEQ) \ |
1710 | 65.9k | do { \ |
1711 | 65.9k | Py_ssize_t i; \ |
1712 | 65.9k | asdl_ ## TYPE ## _seq *seq = (SEQ); /* avoid variable capture */ \ |
1713 | 168k | for (i = 0; i < asdl_seq_LEN(seq); i++) { \ |
1714 | 102k | TYPE ## _ty elt = (TYPE ## _ty)asdl_seq_GET(seq, i); \ |
1715 | 102k | if (!symtable_visit_ ## TYPE((ST), elt)) \ |
1716 | 102k | return 0; \ |
1717 | 102k | } \ |
1718 | 65.9k | } while(0) |
1719 | | |
1720 | | #define VISIT_SEQ_TAIL(ST, TYPE, SEQ, START) \ |
1721 | 322 | do { \ |
1722 | 322 | Py_ssize_t i; \ |
1723 | 322 | asdl_ ## TYPE ## _seq *seq = (SEQ); /* avoid variable capture */ \ |
1724 | 336 | for (i = (START); i < asdl_seq_LEN(seq); i++) { \ |
1725 | 14 | TYPE ## _ty elt = (TYPE ## _ty)asdl_seq_GET(seq, i); \ |
1726 | 14 | if (!symtable_visit_ ## TYPE((ST), elt)) \ |
1727 | 14 | return 0; \ |
1728 | 14 | } \ |
1729 | 322 | } while(0) |
1730 | | |
1731 | | #define VISIT_SEQ_WITH_NULL(ST, TYPE, SEQ) \ |
1732 | 21.3k | do { \ |
1733 | 21.3k | int i = 0; \ |
1734 | 21.3k | asdl_ ## TYPE ## _seq *seq = (SEQ); /* avoid variable capture */ \ |
1735 | 34.3k | for (i = 0; i < asdl_seq_LEN(seq); i++) { \ |
1736 | 13.0k | TYPE ## _ty elt = (TYPE ## _ty)asdl_seq_GET(seq, i); \ |
1737 | 13.0k | if (!elt) continue; /* can be NULL */ \ |
1738 | 13.0k | if (!symtable_visit_ ## TYPE((ST), elt)) \ |
1739 | 13.0k | return 0; \ |
1740 | 13.0k | } \ |
1741 | 21.3k | } while(0) |
1742 | | |
1743 | | #define ENTER_CONDITIONAL_BLOCK(ST) \ |
1744 | 8.38k | int in_conditional_block = (ST)->st_cur->ste_in_conditional_block; \ |
1745 | 8.38k | (ST)->st_cur->ste_in_conditional_block = 1; |
1746 | | |
1747 | | #define LEAVE_CONDITIONAL_BLOCK(ST) \ |
1748 | 8.38k | (ST)->st_cur->ste_in_conditional_block = in_conditional_block; |
1749 | | |
1750 | 209k | #define ENTER_RECURSIVE() \ |
1751 | 209k | if (Py_EnterRecursiveCall(" during compilation")) { \ |
1752 | 0 | return 0; \ |
1753 | 0 | } |
1754 | | |
1755 | 209k | #define LEAVE_RECURSIVE() Py_LeaveRecursiveCall(); |
1756 | | |
1757 | | |
1758 | | static int |
1759 | | symtable_record_directive(struct symtable *st, identifier name, _Py_SourceLocation loc) |
1760 | 84 | { |
1761 | 84 | PyObject *data, *mangled; |
1762 | 84 | int res; |
1763 | 84 | if (!st->st_cur->ste_directives) { |
1764 | 62 | st->st_cur->ste_directives = PyList_New(0); |
1765 | 62 | if (!st->st_cur->ste_directives) |
1766 | 0 | return 0; |
1767 | 62 | } |
1768 | 84 | mangled = _Py_MaybeMangle(st->st_private, st->st_cur, name); |
1769 | 84 | if (!mangled) |
1770 | 0 | return 0; |
1771 | 84 | data = Py_BuildValue("(Niiii)", mangled, loc.lineno, loc.col_offset, |
1772 | 84 | loc.end_lineno, loc.end_col_offset); |
1773 | 84 | if (!data) |
1774 | 0 | return 0; |
1775 | 84 | res = PyList_Append(st->st_cur->ste_directives, data); |
1776 | 84 | Py_DECREF(data); |
1777 | 84 | return res == 0; |
1778 | 84 | } |
1779 | | |
1780 | | static int |
1781 | | has_kwonlydefaults(asdl_arg_seq *kwonlyargs, asdl_expr_seq *kw_defaults) |
1782 | 0 | { |
1783 | 0 | for (int i = 0; i < asdl_seq_LEN(kwonlyargs); i++) { |
1784 | 0 | expr_ty default_ = asdl_seq_GET(kw_defaults, i); |
1785 | 0 | if (default_) { |
1786 | 0 | return 1; |
1787 | 0 | } |
1788 | 0 | } |
1789 | 0 | return 0; |
1790 | 0 | } |
1791 | | |
1792 | | static int |
1793 | | check_import_from(struct symtable *st, stmt_ty s) |
1794 | 296 | { |
1795 | 296 | assert(s->kind == ImportFrom_kind); |
1796 | 296 | _Py_SourceLocation fut = st->st_future->ff_location; |
1797 | 296 | if (s->v.ImportFrom.module && s->v.ImportFrom.level == 0 && |
1798 | 296 | _PyUnicode_EqualToASCIIString(s->v.ImportFrom.module, "__future__") && |
1799 | 296 | ((s->lineno > fut.lineno) || |
1800 | 0 | ((s->lineno == fut.end_lineno) && (s->col_offset > fut.end_col_offset)))) |
1801 | 0 | { |
1802 | 0 | PyErr_SetString(PyExc_SyntaxError, |
1803 | 0 | "from __future__ imports must occur " |
1804 | 0 | "at the beginning of the file"); |
1805 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(s)); |
1806 | 0 | return 0; |
1807 | 0 | } |
1808 | 296 | return 1; |
1809 | 296 | } |
1810 | | |
1811 | | static bool |
1812 | | allows_top_level_await(struct symtable *st) |
1813 | 12 | { |
1814 | 12 | return (st->st_future->ff_features & PyCF_ALLOW_TOP_LEVEL_AWAIT) && |
1815 | 12 | st->st_cur->ste_type == ModuleBlock; |
1816 | 12 | } |
1817 | | |
1818 | | |
1819 | | static void |
1820 | | maybe_set_ste_coroutine_for_module(struct symtable *st, stmt_ty s) |
1821 | 1 | { |
1822 | 1 | if (allows_top_level_await(st)) { |
1823 | 0 | st->st_cur->ste_coroutine = 1; |
1824 | 0 | } |
1825 | 1 | } |
1826 | | |
1827 | | static int |
1828 | | symtable_visit_stmt(struct symtable *st, stmt_ty s) |
1829 | 38.9k | { |
1830 | 38.9k | ENTER_RECURSIVE(); |
1831 | 38.9k | switch (s->kind) { |
1832 | 4.11k | case FunctionDef_kind: { |
1833 | 4.11k | if (!symtable_add_def(st, s->v.FunctionDef.name, DEF_LOCAL, LOCATION(s))) |
1834 | 0 | return 0; |
1835 | 4.11k | if (s->v.FunctionDef.args->defaults) |
1836 | 4.11k | VISIT_SEQ(st, expr, s->v.FunctionDef.args->defaults); |
1837 | 4.11k | if (s->v.FunctionDef.args->kw_defaults) |
1838 | 4.11k | VISIT_SEQ_WITH_NULL(st, expr, s->v.FunctionDef.args->kw_defaults); |
1839 | 4.11k | if (s->v.FunctionDef.decorator_list) |
1840 | 577 | VISIT_SEQ(st, expr, s->v.FunctionDef.decorator_list); |
1841 | 4.11k | if (asdl_seq_LEN(s->v.FunctionDef.type_params) > 0) { |
1842 | 0 | if (!symtable_enter_type_param_block( |
1843 | 0 | st, s->v.FunctionDef.name, |
1844 | 0 | (void *)s->v.FunctionDef.type_params, |
1845 | 0 | s->v.FunctionDef.args->defaults != NULL, |
1846 | 0 | has_kwonlydefaults(s->v.FunctionDef.args->kwonlyargs, |
1847 | 0 | s->v.FunctionDef.args->kw_defaults), |
1848 | 0 | s->kind, |
1849 | 0 | LOCATION(s))) { |
1850 | 0 | return 0; |
1851 | 0 | } |
1852 | 0 | VISIT_SEQ(st, type_param, s->v.FunctionDef.type_params); |
1853 | 0 | } |
1854 | 4.11k | PySTEntryObject *new_ste = ste_new(st, s->v.FunctionDef.name, FunctionBlock, (void *)s, |
1855 | 4.11k | LOCATION(s)); |
1856 | 4.11k | if (!new_ste) { |
1857 | 0 | return 0; |
1858 | 0 | } |
1859 | | |
1860 | 4.11k | if (_PyAST_GetDocString(s->v.FunctionDef.body)) { |
1861 | 1.44k | new_ste->ste_has_docstring = 1; |
1862 | 1.44k | } |
1863 | | |
1864 | 4.11k | if (!symtable_visit_annotations(st, s, s->v.FunctionDef.args, |
1865 | 4.11k | s->v.FunctionDef.returns, new_ste)) { |
1866 | 0 | Py_DECREF(new_ste); |
1867 | 0 | return 0; |
1868 | 0 | } |
1869 | 4.11k | if (!symtable_enter_existing_block(st, new_ste, /* add_to_children */true)) { |
1870 | 0 | Py_DECREF(new_ste); |
1871 | 0 | return 0; |
1872 | 0 | } |
1873 | 4.11k | Py_DECREF(new_ste); |
1874 | 4.11k | VISIT(st, arguments, s->v.FunctionDef.args); |
1875 | 4.11k | VISIT_SEQ(st, stmt, s->v.FunctionDef.body); |
1876 | 4.11k | if (!symtable_exit_block(st)) |
1877 | 0 | return 0; |
1878 | 4.11k | if (asdl_seq_LEN(s->v.FunctionDef.type_params) > 0) { |
1879 | 0 | if (!symtable_exit_block(st)) |
1880 | 0 | return 0; |
1881 | 0 | } |
1882 | 4.11k | break; |
1883 | 4.11k | } |
1884 | 4.11k | case ClassDef_kind: { |
1885 | 1.02k | PyObject *tmp; |
1886 | 1.02k | if (!symtable_add_def(st, s->v.ClassDef.name, DEF_LOCAL, LOCATION(s))) |
1887 | 0 | return 0; |
1888 | 1.02k | if (s->v.ClassDef.decorator_list) |
1889 | 23 | VISIT_SEQ(st, expr, s->v.ClassDef.decorator_list); |
1890 | 1.02k | tmp = st->st_private; |
1891 | 1.02k | if (asdl_seq_LEN(s->v.ClassDef.type_params) > 0) { |
1892 | 0 | if (!symtable_enter_type_param_block(st, s->v.ClassDef.name, |
1893 | 0 | (void *)s->v.ClassDef.type_params, |
1894 | 0 | false, false, s->kind, |
1895 | 0 | LOCATION(s))) { |
1896 | 0 | return 0; |
1897 | 0 | } |
1898 | 0 | st->st_private = s->v.ClassDef.name; |
1899 | 0 | st->st_cur->ste_mangled_names = PySet_New(NULL); |
1900 | 0 | if (!st->st_cur->ste_mangled_names) { |
1901 | 0 | return 0; |
1902 | 0 | } |
1903 | 0 | VISIT_SEQ(st, type_param, s->v.ClassDef.type_params); |
1904 | 0 | } |
1905 | 1.02k | VISIT_SEQ(st, expr, s->v.ClassDef.bases); |
1906 | 1.02k | if (!check_keywords(st, s->v.ClassDef.keywords)) { |
1907 | 0 | return 0; |
1908 | 0 | } |
1909 | 1.02k | VISIT_SEQ(st, keyword, s->v.ClassDef.keywords); |
1910 | 1.02k | if (!symtable_enter_block(st, s->v.ClassDef.name, ClassBlock, |
1911 | 1.02k | (void *)s, LOCATION(s))) { |
1912 | 0 | return 0; |
1913 | 0 | } |
1914 | 1.02k | st->st_private = s->v.ClassDef.name; |
1915 | 1.02k | if (asdl_seq_LEN(s->v.ClassDef.type_params) > 0) { |
1916 | 0 | if (!symtable_add_def(st, &_Py_ID(__type_params__), |
1917 | 0 | DEF_LOCAL, LOCATION(s))) { |
1918 | 0 | return 0; |
1919 | 0 | } |
1920 | 0 | _Py_DECLARE_STR(type_params, ".type_params"); |
1921 | 0 | if (!symtable_add_def(st, &_Py_STR(type_params), |
1922 | 0 | USE, LOCATION(s))) { |
1923 | 0 | return 0; |
1924 | 0 | } |
1925 | 0 | } |
1926 | | |
1927 | 1.02k | if (_PyAST_GetDocString(s->v.ClassDef.body)) { |
1928 | 260 | st->st_cur->ste_has_docstring = 1; |
1929 | 260 | } |
1930 | | |
1931 | 1.02k | VISIT_SEQ(st, stmt, s->v.ClassDef.body); |
1932 | 1.02k | if (!symtable_exit_block(st)) |
1933 | 0 | return 0; |
1934 | 1.02k | if (asdl_seq_LEN(s->v.ClassDef.type_params) > 0) { |
1935 | 0 | if (!symtable_exit_block(st)) |
1936 | 0 | return 0; |
1937 | 0 | } |
1938 | 1.02k | st->st_private = tmp; |
1939 | 1.02k | break; |
1940 | 1.02k | } |
1941 | 0 | case TypeAlias_kind: { |
1942 | 0 | VISIT(st, expr, s->v.TypeAlias.name); |
1943 | 0 | assert(s->v.TypeAlias.name->kind == Name_kind); |
1944 | 0 | PyObject *name = s->v.TypeAlias.name->v.Name.id; |
1945 | 0 | int is_in_class = st->st_cur->ste_type == ClassBlock; |
1946 | 0 | int is_generic = asdl_seq_LEN(s->v.TypeAlias.type_params) > 0; |
1947 | 0 | if (is_generic) { |
1948 | 0 | if (!symtable_enter_type_param_block( |
1949 | 0 | st, name, |
1950 | 0 | (void *)s->v.TypeAlias.type_params, |
1951 | 0 | false, false, s->kind, |
1952 | 0 | LOCATION(s))) { |
1953 | 0 | return 0; |
1954 | 0 | } |
1955 | 0 | VISIT_SEQ(st, type_param, s->v.TypeAlias.type_params); |
1956 | 0 | } |
1957 | 0 | if (!symtable_enter_block(st, name, TypeAliasBlock, |
1958 | 0 | (void *)s, LOCATION(s))) { |
1959 | 0 | return 0; |
1960 | 0 | } |
1961 | 0 | st->st_cur->ste_can_see_class_scope = is_in_class; |
1962 | 0 | if (is_in_class && !symtable_add_def(st, &_Py_ID(__classdict__), USE, LOCATION(s->v.TypeAlias.value))) { |
1963 | 0 | return 0; |
1964 | 0 | } |
1965 | 0 | VISIT(st, expr, s->v.TypeAlias.value); |
1966 | 0 | if (!symtable_exit_block(st)) |
1967 | 0 | return 0; |
1968 | 0 | if (is_generic) { |
1969 | 0 | if (!symtable_exit_block(st)) |
1970 | 0 | return 0; |
1971 | 0 | } |
1972 | 0 | break; |
1973 | 0 | } |
1974 | 4.53k | case Return_kind: |
1975 | 4.53k | if (s->v.Return.value) { |
1976 | 4.39k | VISIT(st, expr, s->v.Return.value); |
1977 | 4.39k | st->st_cur->ste_returns_value = 1; |
1978 | 4.39k | } |
1979 | 4.53k | break; |
1980 | 4.53k | case Delete_kind: |
1981 | 101 | VISIT_SEQ(st, expr, s->v.Delete.targets); |
1982 | 101 | break; |
1983 | 11.4k | case Assign_kind: |
1984 | 11.4k | VISIT_SEQ(st, expr, s->v.Assign.targets); |
1985 | 11.4k | VISIT(st, expr, s->v.Assign.value); |
1986 | 11.4k | break; |
1987 | 11.4k | case AnnAssign_kind: |
1988 | 0 | st->st_cur->ste_annotations_used = 1; |
1989 | 0 | if (s->v.AnnAssign.target->kind == Name_kind) { |
1990 | 0 | expr_ty e_name = s->v.AnnAssign.target; |
1991 | 0 | long cur = symtable_lookup(st, e_name->v.Name.id); |
1992 | 0 | if (cur < 0) { |
1993 | 0 | return 0; |
1994 | 0 | } |
1995 | 0 | if ((cur & (DEF_GLOBAL | DEF_NONLOCAL)) |
1996 | 0 | && (st->st_cur->ste_symbols != st->st_global) |
1997 | 0 | && s->v.AnnAssign.simple) { |
1998 | 0 | PyErr_Format(PyExc_SyntaxError, |
1999 | 0 | cur & DEF_GLOBAL ? GLOBAL_ANNOT : NONLOCAL_ANNOT, |
2000 | 0 | e_name->v.Name.id); |
2001 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(s)); |
2002 | 0 | return 0; |
2003 | 0 | } |
2004 | 0 | if (s->v.AnnAssign.simple && |
2005 | 0 | !symtable_add_def(st, e_name->v.Name.id, |
2006 | 0 | DEF_ANNOT | DEF_LOCAL, LOCATION(e_name))) { |
2007 | 0 | return 0; |
2008 | 0 | } |
2009 | 0 | else { |
2010 | 0 | if (s->v.AnnAssign.value |
2011 | 0 | && !symtable_add_def(st, e_name->v.Name.id, DEF_LOCAL, LOCATION(e_name))) { |
2012 | 0 | return 0; |
2013 | 0 | } |
2014 | 0 | } |
2015 | 0 | } |
2016 | 0 | else { |
2017 | 0 | VISIT(st, expr, s->v.AnnAssign.target); |
2018 | 0 | } |
2019 | 0 | if (!symtable_visit_annotation(st, s->v.AnnAssign.annotation, |
2020 | 0 | (void *)((uintptr_t)st->st_cur->ste_id + 1))) { |
2021 | 0 | return 0; |
2022 | 0 | } |
2023 | | |
2024 | 0 | if (s->v.AnnAssign.value) { |
2025 | 0 | VISIT(st, expr, s->v.AnnAssign.value); |
2026 | 0 | } |
2027 | 0 | break; |
2028 | 577 | case AugAssign_kind: { |
2029 | 577 | VISIT(st, expr, s->v.AugAssign.target); |
2030 | 577 | VISIT(st, expr, s->v.AugAssign.value); |
2031 | 577 | break; |
2032 | 577 | } |
2033 | 848 | case For_kind: { |
2034 | 848 | VISIT(st, expr, s->v.For.target); |
2035 | 848 | VISIT(st, expr, s->v.For.iter); |
2036 | 848 | ENTER_CONDITIONAL_BLOCK(st); |
2037 | 848 | VISIT_SEQ(st, stmt, s->v.For.body); |
2038 | 848 | if (s->v.For.orelse) |
2039 | 42 | VISIT_SEQ(st, stmt, s->v.For.orelse); |
2040 | 848 | LEAVE_CONDITIONAL_BLOCK(st); |
2041 | 848 | break; |
2042 | 848 | } |
2043 | 259 | case While_kind: { |
2044 | 259 | VISIT(st, expr, s->v.While.test); |
2045 | 259 | ENTER_CONDITIONAL_BLOCK(st); |
2046 | 259 | VISIT_SEQ(st, stmt, s->v.While.body); |
2047 | 259 | if (s->v.While.orelse) |
2048 | 3 | VISIT_SEQ(st, stmt, s->v.While.orelse); |
2049 | 259 | LEAVE_CONDITIONAL_BLOCK(st); |
2050 | 259 | break; |
2051 | 259 | } |
2052 | 6.45k | case If_kind: { |
2053 | | /* XXX if 0: and lookup_yield() hacks */ |
2054 | 6.45k | VISIT(st, expr, s->v.If.test); |
2055 | 6.45k | ENTER_CONDITIONAL_BLOCK(st); |
2056 | 6.45k | VISIT_SEQ(st, stmt, s->v.If.body); |
2057 | 6.45k | if (s->v.If.orelse) |
2058 | 1.96k | VISIT_SEQ(st, stmt, s->v.If.orelse); |
2059 | 6.45k | LEAVE_CONDITIONAL_BLOCK(st); |
2060 | 6.45k | break; |
2061 | 6.45k | } |
2062 | 0 | case Match_kind: { |
2063 | 0 | VISIT(st, expr, s->v.Match.subject); |
2064 | 0 | ENTER_CONDITIONAL_BLOCK(st); |
2065 | 0 | VISIT_SEQ(st, match_case, s->v.Match.cases); |
2066 | 0 | LEAVE_CONDITIONAL_BLOCK(st); |
2067 | 0 | break; |
2068 | 0 | } |
2069 | 1.46k | case Raise_kind: |
2070 | 1.46k | if (s->v.Raise.exc) { |
2071 | 1.40k | VISIT(st, expr, s->v.Raise.exc); |
2072 | 1.40k | if (s->v.Raise.cause) { |
2073 | 108 | VISIT(st, expr, s->v.Raise.cause); |
2074 | 108 | } |
2075 | 1.40k | } |
2076 | 1.46k | break; |
2077 | 1.46k | case Try_kind: { |
2078 | 732 | ENTER_CONDITIONAL_BLOCK(st); |
2079 | 732 | VISIT_SEQ(st, stmt, s->v.Try.body); |
2080 | 732 | VISIT_SEQ(st, excepthandler, s->v.Try.handlers); |
2081 | 732 | VISIT_SEQ(st, stmt, s->v.Try.orelse); |
2082 | 732 | VISIT_SEQ(st, stmt, s->v.Try.finalbody); |
2083 | 732 | LEAVE_CONDITIONAL_BLOCK(st); |
2084 | 732 | break; |
2085 | 732 | } |
2086 | 0 | case TryStar_kind: { |
2087 | 0 | ENTER_CONDITIONAL_BLOCK(st); |
2088 | 0 | VISIT_SEQ(st, stmt, s->v.TryStar.body); |
2089 | 0 | VISIT_SEQ(st, excepthandler, s->v.TryStar.handlers); |
2090 | 0 | VISIT_SEQ(st, stmt, s->v.TryStar.orelse); |
2091 | 0 | VISIT_SEQ(st, stmt, s->v.TryStar.finalbody); |
2092 | 0 | LEAVE_CONDITIONAL_BLOCK(st); |
2093 | 0 | break; |
2094 | 0 | } |
2095 | 108 | case Assert_kind: |
2096 | 108 | VISIT(st, expr, s->v.Assert.test); |
2097 | 108 | if (s->v.Assert.msg) |
2098 | 26 | VISIT(st, expr, s->v.Assert.msg); |
2099 | 108 | break; |
2100 | 489 | case Import_kind: |
2101 | 489 | VISIT_SEQ(st, alias, s->v.Import.names); |
2102 | 489 | break; |
2103 | 489 | case ImportFrom_kind: |
2104 | 296 | VISIT_SEQ(st, alias, s->v.ImportFrom.names); |
2105 | 296 | if (!check_import_from(st, s)) { |
2106 | 0 | return 0; |
2107 | 0 | } |
2108 | 296 | break; |
2109 | 296 | case Global_kind: { |
2110 | 33 | Py_ssize_t i; |
2111 | 33 | asdl_identifier_seq *seq = s->v.Global.names; |
2112 | 70 | for (i = 0; i < asdl_seq_LEN(seq); i++) { |
2113 | 37 | identifier name = (identifier)asdl_seq_GET(seq, i); |
2114 | 37 | long cur = symtable_lookup(st, name); |
2115 | 37 | if (cur < 0) |
2116 | 0 | return 0; |
2117 | 37 | if (cur & (DEF_PARAM | DEF_LOCAL | USE | DEF_ANNOT)) { |
2118 | 0 | const char* msg; |
2119 | 0 | if (cur & DEF_PARAM) { |
2120 | 0 | msg = GLOBAL_PARAM; |
2121 | 0 | } else if (cur & USE) { |
2122 | 0 | msg = GLOBAL_AFTER_USE; |
2123 | 0 | } else if (cur & DEF_ANNOT) { |
2124 | 0 | msg = GLOBAL_ANNOT; |
2125 | 0 | } else { /* DEF_LOCAL */ |
2126 | 0 | msg = GLOBAL_AFTER_ASSIGN; |
2127 | 0 | } |
2128 | 0 | PyErr_Format(PyExc_SyntaxError, |
2129 | 0 | msg, name); |
2130 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(s)); |
2131 | 0 | return 0; |
2132 | 0 | } |
2133 | 37 | if (!symtable_add_def(st, name, DEF_GLOBAL, LOCATION(s))) { |
2134 | 0 | return 0; |
2135 | 0 | } |
2136 | 37 | if (!symtable_record_directive(st, name, LOCATION(s))) { |
2137 | 0 | return 0; |
2138 | 0 | } |
2139 | 37 | } |
2140 | 33 | break; |
2141 | 33 | } |
2142 | 33 | case Nonlocal_kind: { |
2143 | 29 | Py_ssize_t i; |
2144 | 29 | asdl_identifier_seq *seq = s->v.Nonlocal.names; |
2145 | 76 | for (i = 0; i < asdl_seq_LEN(seq); i++) { |
2146 | 47 | identifier name = (identifier)asdl_seq_GET(seq, i); |
2147 | 47 | long cur = symtable_lookup(st, name); |
2148 | 47 | if (cur < 0) |
2149 | 0 | return 0; |
2150 | 47 | if (cur & (DEF_PARAM | DEF_LOCAL | USE | DEF_ANNOT)) { |
2151 | 0 | const char* msg; |
2152 | 0 | if (cur & DEF_PARAM) { |
2153 | 0 | msg = NONLOCAL_PARAM; |
2154 | 0 | } else if (cur & USE) { |
2155 | 0 | msg = NONLOCAL_AFTER_USE; |
2156 | 0 | } else if (cur & DEF_ANNOT) { |
2157 | 0 | msg = NONLOCAL_ANNOT; |
2158 | 0 | } else { /* DEF_LOCAL */ |
2159 | 0 | msg = NONLOCAL_AFTER_ASSIGN; |
2160 | 0 | } |
2161 | 0 | PyErr_Format(PyExc_SyntaxError, msg, name); |
2162 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(s)); |
2163 | 0 | return 0; |
2164 | 0 | } |
2165 | 47 | if (!symtable_add_def(st, name, DEF_NONLOCAL, LOCATION(s))) |
2166 | 0 | return 0; |
2167 | 47 | if (!symtable_record_directive(st, name, LOCATION(s))) { |
2168 | 0 | return 0; |
2169 | 0 | } |
2170 | 47 | } |
2171 | 29 | break; |
2172 | 29 | } |
2173 | 5.52k | case Expr_kind: |
2174 | 5.52k | VISIT(st, expr, s->v.Expr.value); |
2175 | 5.52k | break; |
2176 | 5.52k | case Pass_kind: |
2177 | 627 | case Break_kind: |
2178 | 834 | case Continue_kind: |
2179 | | /* nothing to do here */ |
2180 | 834 | break; |
2181 | 93 | case With_kind: { |
2182 | 93 | ENTER_CONDITIONAL_BLOCK(st); |
2183 | 93 | VISIT_SEQ(st, withitem, s->v.With.items); |
2184 | 93 | VISIT_SEQ(st, stmt, s->v.With.body); |
2185 | 93 | LEAVE_CONDITIONAL_BLOCK(st); |
2186 | 93 | break; |
2187 | 93 | } |
2188 | 16 | case AsyncFunctionDef_kind: { |
2189 | 16 | if (!symtable_add_def(st, s->v.AsyncFunctionDef.name, DEF_LOCAL, LOCATION(s))) |
2190 | 0 | return 0; |
2191 | 16 | if (s->v.AsyncFunctionDef.args->defaults) |
2192 | 16 | VISIT_SEQ(st, expr, s->v.AsyncFunctionDef.args->defaults); |
2193 | 16 | if (s->v.AsyncFunctionDef.args->kw_defaults) |
2194 | 16 | VISIT_SEQ_WITH_NULL(st, expr, |
2195 | 16 | s->v.AsyncFunctionDef.args->kw_defaults); |
2196 | 16 | if (s->v.AsyncFunctionDef.decorator_list) |
2197 | 2 | VISIT_SEQ(st, expr, s->v.AsyncFunctionDef.decorator_list); |
2198 | 16 | if (asdl_seq_LEN(s->v.AsyncFunctionDef.type_params) > 0) { |
2199 | 0 | if (!symtable_enter_type_param_block( |
2200 | 0 | st, s->v.AsyncFunctionDef.name, |
2201 | 0 | (void *)s->v.AsyncFunctionDef.type_params, |
2202 | 0 | s->v.AsyncFunctionDef.args->defaults != NULL, |
2203 | 0 | has_kwonlydefaults(s->v.AsyncFunctionDef.args->kwonlyargs, |
2204 | 0 | s->v.AsyncFunctionDef.args->kw_defaults), |
2205 | 0 | s->kind, |
2206 | 0 | LOCATION(s))) { |
2207 | 0 | return 0; |
2208 | 0 | } |
2209 | 0 | VISIT_SEQ(st, type_param, s->v.AsyncFunctionDef.type_params); |
2210 | 0 | } |
2211 | 16 | PySTEntryObject *new_ste = ste_new(st, s->v.FunctionDef.name, FunctionBlock, (void *)s, |
2212 | 16 | LOCATION(s)); |
2213 | 16 | if (!new_ste) { |
2214 | 0 | return 0; |
2215 | 0 | } |
2216 | | |
2217 | 16 | if (_PyAST_GetDocString(s->v.AsyncFunctionDef.body)) { |
2218 | 4 | new_ste->ste_has_docstring = 1; |
2219 | 4 | } |
2220 | | |
2221 | 16 | if (!symtable_visit_annotations(st, s, s->v.AsyncFunctionDef.args, |
2222 | 16 | s->v.AsyncFunctionDef.returns, new_ste)) { |
2223 | 0 | Py_DECREF(new_ste); |
2224 | 0 | return 0; |
2225 | 0 | } |
2226 | 16 | if (!symtable_enter_existing_block(st, new_ste, /* add_to_children */true)) { |
2227 | 0 | Py_DECREF(new_ste); |
2228 | 0 | return 0; |
2229 | 0 | } |
2230 | 16 | Py_DECREF(new_ste); |
2231 | | |
2232 | 16 | st->st_cur->ste_coroutine = 1; |
2233 | 16 | VISIT(st, arguments, s->v.AsyncFunctionDef.args); |
2234 | 16 | VISIT_SEQ(st, stmt, s->v.AsyncFunctionDef.body); |
2235 | 16 | if (!symtable_exit_block(st)) |
2236 | 0 | return 0; |
2237 | 16 | if (asdl_seq_LEN(s->v.AsyncFunctionDef.type_params) > 0) { |
2238 | 0 | if (!symtable_exit_block(st)) |
2239 | 0 | return 0; |
2240 | 0 | } |
2241 | 16 | break; |
2242 | 16 | } |
2243 | 16 | case AsyncWith_kind: { |
2244 | 1 | maybe_set_ste_coroutine_for_module(st, s); |
2245 | 1 | if (!symtable_raise_if_not_coroutine(st, ASYNC_WITH_OUTSIDE_ASYNC_FUNC, LOCATION(s))) { |
2246 | 0 | return 0; |
2247 | 0 | } |
2248 | 1 | ENTER_CONDITIONAL_BLOCK(st); |
2249 | 1 | VISIT_SEQ(st, withitem, s->v.AsyncWith.items); |
2250 | 1 | VISIT_SEQ(st, stmt, s->v.AsyncWith.body); |
2251 | 1 | LEAVE_CONDITIONAL_BLOCK(st); |
2252 | 1 | break; |
2253 | 1 | } |
2254 | 0 | case AsyncFor_kind: { |
2255 | 0 | maybe_set_ste_coroutine_for_module(st, s); |
2256 | 0 | if (!symtable_raise_if_not_coroutine(st, ASYNC_FOR_OUTSIDE_ASYNC_FUNC, LOCATION(s))) { |
2257 | 0 | return 0; |
2258 | 0 | } |
2259 | 0 | VISIT(st, expr, s->v.AsyncFor.target); |
2260 | 0 | VISIT(st, expr, s->v.AsyncFor.iter); |
2261 | 0 | ENTER_CONDITIONAL_BLOCK(st); |
2262 | 0 | VISIT_SEQ(st, stmt, s->v.AsyncFor.body); |
2263 | 0 | if (s->v.AsyncFor.orelse) |
2264 | 0 | VISIT_SEQ(st, stmt, s->v.AsyncFor.orelse); |
2265 | 0 | LEAVE_CONDITIONAL_BLOCK(st); |
2266 | 0 | break; |
2267 | 0 | } |
2268 | 38.9k | } |
2269 | 38.9k | LEAVE_RECURSIVE(); |
2270 | 38.9k | return 1; |
2271 | 38.9k | } |
2272 | | |
2273 | | static int |
2274 | | symtable_extend_namedexpr_scope(struct symtable *st, expr_ty e) |
2275 | 0 | { |
2276 | 0 | assert(st->st_stack); |
2277 | 0 | assert(e->kind == Name_kind); |
2278 | |
|
2279 | 0 | PyObject *target_name = e->v.Name.id; |
2280 | 0 | Py_ssize_t i, size; |
2281 | 0 | struct _symtable_entry *ste; |
2282 | 0 | size = PyList_GET_SIZE(st->st_stack); |
2283 | 0 | assert(size); |
2284 | | |
2285 | | /* Iterate over the stack in reverse and add to the nearest adequate scope */ |
2286 | 0 | for (i = size - 1; i >= 0; i--) { |
2287 | 0 | ste = (struct _symtable_entry *) PyList_GET_ITEM(st->st_stack, i); |
2288 | | |
2289 | | /* If we find a comprehension scope, check for a target |
2290 | | * binding conflict with iteration variables, otherwise skip it |
2291 | | */ |
2292 | 0 | if (ste->ste_comprehension) { |
2293 | 0 | long target_in_scope = symtable_lookup_entry(st, ste, target_name); |
2294 | 0 | if (target_in_scope < 0) { |
2295 | 0 | return 0; |
2296 | 0 | } |
2297 | 0 | if ((target_in_scope & DEF_COMP_ITER) && |
2298 | 0 | (target_in_scope & DEF_LOCAL)) { |
2299 | 0 | PyErr_Format(PyExc_SyntaxError, NAMED_EXPR_COMP_CONFLICT, target_name); |
2300 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(e)); |
2301 | 0 | return 0; |
2302 | 0 | } |
2303 | 0 | continue; |
2304 | 0 | } |
2305 | | |
2306 | | /* If we find a FunctionBlock entry, add as GLOBAL/LOCAL or NONLOCAL/LOCAL */ |
2307 | 0 | if (ste->ste_type == FunctionBlock) { |
2308 | 0 | long target_in_scope = symtable_lookup_entry(st, ste, target_name); |
2309 | 0 | if (target_in_scope < 0) { |
2310 | 0 | return 0; |
2311 | 0 | } |
2312 | 0 | if (target_in_scope & DEF_GLOBAL) { |
2313 | 0 | if (!symtable_add_def(st, target_name, DEF_GLOBAL, LOCATION(e))) |
2314 | 0 | return 0; |
2315 | 0 | } else { |
2316 | 0 | if (!symtable_add_def(st, target_name, DEF_NONLOCAL, LOCATION(e))) { |
2317 | 0 | return 0; |
2318 | 0 | } |
2319 | 0 | } |
2320 | 0 | if (!symtable_record_directive(st, target_name, LOCATION(e))) { |
2321 | 0 | return 0; |
2322 | 0 | } |
2323 | | |
2324 | 0 | return symtable_add_def_helper(st, target_name, DEF_LOCAL, ste, LOCATION(e)); |
2325 | 0 | } |
2326 | | /* If we find a ModuleBlock entry, add as GLOBAL */ |
2327 | 0 | if (ste->ste_type == ModuleBlock) { |
2328 | 0 | if (!symtable_add_def(st, target_name, DEF_GLOBAL, LOCATION(e))) { |
2329 | 0 | return 0; |
2330 | 0 | } |
2331 | 0 | if (!symtable_record_directive(st, target_name, LOCATION(e))) { |
2332 | 0 | return 0; |
2333 | 0 | } |
2334 | | |
2335 | 0 | return symtable_add_def_helper(st, target_name, DEF_GLOBAL, ste, LOCATION(e)); |
2336 | 0 | } |
2337 | | /* Disallow usage in ClassBlock and type scopes */ |
2338 | 0 | if (ste->ste_type == ClassBlock || |
2339 | 0 | ste->ste_type == TypeParametersBlock || |
2340 | 0 | ste->ste_type == TypeAliasBlock || |
2341 | 0 | ste->ste_type == TypeVariableBlock) { |
2342 | 0 | switch (ste->ste_type) { |
2343 | 0 | case ClassBlock: |
2344 | 0 | PyErr_Format(PyExc_SyntaxError, NAMED_EXPR_COMP_IN_CLASS); |
2345 | 0 | break; |
2346 | 0 | case TypeParametersBlock: |
2347 | 0 | PyErr_Format(PyExc_SyntaxError, NAMED_EXPR_COMP_IN_TYPEPARAM); |
2348 | 0 | break; |
2349 | 0 | case TypeAliasBlock: |
2350 | 0 | PyErr_Format(PyExc_SyntaxError, NAMED_EXPR_COMP_IN_TYPEALIAS); |
2351 | 0 | break; |
2352 | 0 | case TypeVariableBlock: |
2353 | 0 | PyErr_Format(PyExc_SyntaxError, NAMED_EXPR_COMP_IN_TYPEVAR_BOUND); |
2354 | 0 | break; |
2355 | 0 | default: |
2356 | 0 | Py_UNREACHABLE(); |
2357 | 0 | } |
2358 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(e)); |
2359 | 0 | return 0; |
2360 | 0 | } |
2361 | 0 | } |
2362 | | |
2363 | | /* We should always find either a function-like block, ModuleBlock or ClassBlock |
2364 | | and should never fall to this case |
2365 | | */ |
2366 | 0 | Py_UNREACHABLE(); |
2367 | 0 | return 0; |
2368 | 0 | } |
2369 | | |
2370 | | static int |
2371 | | symtable_handle_namedexpr(struct symtable *st, expr_ty e) |
2372 | 24 | { |
2373 | 24 | if (st->st_cur->ste_comp_iter_expr > 0) { |
2374 | | /* Assignment isn't allowed in a comprehension iterable expression */ |
2375 | 0 | PyErr_Format(PyExc_SyntaxError, NAMED_EXPR_COMP_ITER_EXPR); |
2376 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(e)); |
2377 | 0 | return 0; |
2378 | 0 | } |
2379 | 24 | if (st->st_cur->ste_comprehension) { |
2380 | | /* Inside a comprehension body, so find the right target scope */ |
2381 | 0 | if (!symtable_extend_namedexpr_scope(st, e->v.NamedExpr.target)) |
2382 | 0 | return 0; |
2383 | 0 | } |
2384 | 24 | VISIT(st, expr, e->v.NamedExpr.value); |
2385 | 24 | VISIT(st, expr, e->v.NamedExpr.target); |
2386 | 24 | return 1; |
2387 | 24 | } |
2388 | | |
2389 | | static int |
2390 | | symtable_visit_expr(struct symtable *st, expr_ty e) |
2391 | 170k | { |
2392 | 170k | ENTER_RECURSIVE(); |
2393 | 170k | switch (e->kind) { |
2394 | 24 | case NamedExpr_kind: |
2395 | 24 | if (!symtable_raise_if_annotation_block(st, "named expression", e)) { |
2396 | 0 | return 0; |
2397 | 0 | } |
2398 | 24 | if(!symtable_handle_namedexpr(st, e)) |
2399 | 0 | return 0; |
2400 | 24 | break; |
2401 | 1.34k | case BoolOp_kind: |
2402 | 1.34k | VISIT_SEQ(st, expr, e->v.BoolOp.values); |
2403 | 1.34k | break; |
2404 | 3.18k | case BinOp_kind: |
2405 | 3.18k | VISIT(st, expr, e->v.BinOp.left); |
2406 | 3.18k | VISIT(st, expr, e->v.BinOp.right); |
2407 | 3.18k | break; |
2408 | 3.18k | case UnaryOp_kind: |
2409 | 1.69k | VISIT(st, expr, e->v.UnaryOp.operand); |
2410 | 1.69k | break; |
2411 | 1.69k | case Lambda_kind: { |
2412 | 121 | if (e->v.Lambda.args->defaults) |
2413 | 121 | VISIT_SEQ(st, expr, e->v.Lambda.args->defaults); |
2414 | 121 | if (e->v.Lambda.args->kw_defaults) |
2415 | 121 | VISIT_SEQ_WITH_NULL(st, expr, e->v.Lambda.args->kw_defaults); |
2416 | 121 | if (!symtable_enter_block(st, &_Py_ID(lambda), |
2417 | 121 | FunctionBlock, (void *)e, LOCATION(e))) { |
2418 | 0 | return 0; |
2419 | 0 | } |
2420 | 121 | VISIT(st, arguments, e->v.Lambda.args); |
2421 | 121 | VISIT(st, expr, e->v.Lambda.body); |
2422 | 121 | if (!symtable_exit_block(st)) |
2423 | 0 | return 0; |
2424 | 121 | break; |
2425 | 121 | } |
2426 | 146 | case IfExp_kind: |
2427 | 146 | VISIT(st, expr, e->v.IfExp.test); |
2428 | 146 | VISIT(st, expr, e->v.IfExp.body); |
2429 | 146 | VISIT(st, expr, e->v.IfExp.orelse); |
2430 | 146 | break; |
2431 | 279 | case Dict_kind: |
2432 | 279 | VISIT_SEQ_WITH_NULL(st, expr, e->v.Dict.keys); |
2433 | 279 | VISIT_SEQ(st, expr, e->v.Dict.values); |
2434 | 279 | break; |
2435 | 279 | case Set_kind: |
2436 | 59 | VISIT_SEQ(st, expr, e->v.Set.elts); |
2437 | 59 | break; |
2438 | 137 | case GeneratorExp_kind: |
2439 | 137 | if (!symtable_visit_genexp(st, e)) |
2440 | 0 | return 0; |
2441 | 137 | break; |
2442 | 164 | case ListComp_kind: |
2443 | 164 | if (!symtable_visit_listcomp(st, e)) |
2444 | 0 | return 0; |
2445 | 164 | break; |
2446 | 164 | case SetComp_kind: |
2447 | 3 | if (!symtable_visit_setcomp(st, e)) |
2448 | 0 | return 0; |
2449 | 3 | break; |
2450 | 18 | case DictComp_kind: |
2451 | 18 | if (!symtable_visit_dictcomp(st, e)) |
2452 | 0 | return 0; |
2453 | 18 | break; |
2454 | 183 | case Yield_kind: |
2455 | 183 | if (!symtable_raise_if_annotation_block(st, "yield expression", e)) { |
2456 | 0 | return 0; |
2457 | 0 | } |
2458 | 183 | if (e->v.Yield.value) |
2459 | 180 | VISIT(st, expr, e->v.Yield.value); |
2460 | 183 | st->st_cur->ste_generator = 1; |
2461 | 183 | if (st->st_cur->ste_comprehension) { |
2462 | 0 | return symtable_raise_if_comprehension_block(st, e); |
2463 | 0 | } |
2464 | 183 | break; |
2465 | 183 | case YieldFrom_kind: |
2466 | 30 | if (!symtable_raise_if_annotation_block(st, "yield expression", e)) { |
2467 | 0 | return 0; |
2468 | 0 | } |
2469 | 30 | VISIT(st, expr, e->v.YieldFrom.value); |
2470 | 30 | st->st_cur->ste_generator = 1; |
2471 | 30 | if (st->st_cur->ste_comprehension) { |
2472 | 0 | return symtable_raise_if_comprehension_block(st, e); |
2473 | 0 | } |
2474 | 30 | break; |
2475 | 30 | case Await_kind: |
2476 | 11 | if (!symtable_raise_if_annotation_block(st, "await expression", e)) { |
2477 | 0 | return 0; |
2478 | 0 | } |
2479 | 11 | if (!allows_top_level_await(st)) { |
2480 | 11 | if (!_PyST_IsFunctionLike(st->st_cur)) { |
2481 | 0 | PyErr_SetString(PyExc_SyntaxError, |
2482 | 0 | "'await' outside function"); |
2483 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(e)); |
2484 | 0 | return 0; |
2485 | 0 | } |
2486 | 11 | if (!IS_ASYNC_DEF(st) && st->st_cur->ste_comprehension == NoComprehension) { |
2487 | 0 | PyErr_SetString(PyExc_SyntaxError, |
2488 | 0 | "'await' outside async function"); |
2489 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(e)); |
2490 | 0 | return 0; |
2491 | 0 | } |
2492 | 11 | } |
2493 | 11 | VISIT(st, expr, e->v.Await.value); |
2494 | 11 | st->st_cur->ste_coroutine = 1; |
2495 | 11 | break; |
2496 | 5.08k | case Compare_kind: |
2497 | 5.08k | VISIT(st, expr, e->v.Compare.left); |
2498 | 5.08k | VISIT_SEQ(st, expr, e->v.Compare.comparators); |
2499 | 5.08k | break; |
2500 | 16.7k | case Call_kind: |
2501 | 16.7k | VISIT(st, expr, e->v.Call.func); |
2502 | 16.7k | VISIT_SEQ(st, expr, e->v.Call.args); |
2503 | 16.7k | if (!check_keywords(st, e->v.Call.keywords)) { |
2504 | 0 | return 0; |
2505 | 0 | } |
2506 | 16.7k | VISIT_SEQ_WITH_NULL(st, keyword, e->v.Call.keywords); |
2507 | 16.7k | break; |
2508 | 16.7k | case FormattedValue_kind: |
2509 | 1.13k | VISIT(st, expr, e->v.FormattedValue.value); |
2510 | 1.13k | if (e->v.FormattedValue.format_spec) |
2511 | 11 | VISIT(st, expr, e->v.FormattedValue.format_spec); |
2512 | 1.13k | break; |
2513 | 1.13k | case Interpolation_kind: |
2514 | 0 | VISIT(st, expr, e->v.Interpolation.value); |
2515 | 0 | if (e->v.Interpolation.format_spec) |
2516 | 0 | VISIT(st, expr, e->v.Interpolation.format_spec); |
2517 | 0 | break; |
2518 | 651 | case JoinedStr_kind: |
2519 | 651 | VISIT_SEQ(st, expr, e->v.JoinedStr.values); |
2520 | 651 | break; |
2521 | 651 | case TemplateStr_kind: |
2522 | 0 | VISIT_SEQ(st, expr, e->v.TemplateStr.values); |
2523 | 0 | break; |
2524 | 43.4k | case Constant_kind: |
2525 | | /* Nothing to do here. */ |
2526 | 43.4k | break; |
2527 | | /* The following exprs can be assignment targets. */ |
2528 | 18.0k | case Attribute_kind: |
2529 | 18.0k | if (!check_name(st, e->v.Attribute.attr, LOCATION(e), e->v.Attribute.ctx)) { |
2530 | 0 | return 0; |
2531 | 0 | } |
2532 | 18.0k | VISIT(st, expr, e->v.Attribute.value); |
2533 | 18.0k | break; |
2534 | 18.0k | case Subscript_kind: |
2535 | 3.39k | VISIT(st, expr, e->v.Subscript.value); |
2536 | 3.39k | VISIT(st, expr, e->v.Subscript.slice); |
2537 | 3.39k | break; |
2538 | 3.39k | case Starred_kind: |
2539 | 202 | VISIT(st, expr, e->v.Starred.value); |
2540 | 202 | break; |
2541 | 759 | case Slice_kind: |
2542 | 759 | if (e->v.Slice.lower) |
2543 | 501 | VISIT(st, expr, e->v.Slice.lower); |
2544 | 759 | if (e->v.Slice.upper) |
2545 | 415 | VISIT(st, expr, e->v.Slice.upper); |
2546 | 759 | if (e->v.Slice.step) |
2547 | 23 | VISIT(st, expr, e->v.Slice.step); |
2548 | 759 | break; |
2549 | 70.2k | case Name_kind: |
2550 | 70.2k | if (!st->st_cur->ste_in_unevaluated_annotation) { |
2551 | 70.2k | if (!symtable_add_def_ctx(st, e->v.Name.id, |
2552 | 70.2k | e->v.Name.ctx == Load ? USE : DEF_LOCAL, |
2553 | 70.2k | LOCATION(e), e->v.Name.ctx)) { |
2554 | 0 | return 0; |
2555 | 0 | } |
2556 | | /* Special-case super: it counts as a use of __class__ */ |
2557 | 70.2k | if (e->v.Name.ctx == Load && |
2558 | 70.2k | _PyST_IsFunctionLike(st->st_cur) && |
2559 | 70.2k | _PyUnicode_EqualToASCIIString(e->v.Name.id, "super")) { |
2560 | 178 | if (!symtable_add_def(st, &_Py_ID(__class__), USE, LOCATION(e))) |
2561 | 0 | return 0; |
2562 | 178 | } |
2563 | 70.2k | } |
2564 | 70.2k | break; |
2565 | | /* child nodes of List and Tuple will have expr_context set */ |
2566 | 70.2k | case List_kind: |
2567 | 766 | VISIT_SEQ(st, expr, e->v.List.elts); |
2568 | 766 | break; |
2569 | 2.89k | case Tuple_kind: |
2570 | 2.89k | VISIT_SEQ(st, expr, e->v.Tuple.elts); |
2571 | 2.89k | break; |
2572 | 170k | } |
2573 | 170k | LEAVE_RECURSIVE(); |
2574 | 170k | return 1; |
2575 | 170k | } |
2576 | | |
2577 | | static int |
2578 | | symtable_visit_type_param_bound_or_default( |
2579 | | struct symtable *st, expr_ty e, identifier name, |
2580 | | type_param_ty tp, const char *ste_scope_info) |
2581 | 0 | { |
2582 | 0 | if (_PyUnicode_Equal(name, &_Py_ID(__classdict__))) { |
2583 | |
|
2584 | 0 | PyObject *error_msg = PyUnicode_FromFormat("reserved name '%U' cannot be " |
2585 | 0 | "used for type parameter", name); |
2586 | 0 | PyErr_SetObject(PyExc_SyntaxError, error_msg); |
2587 | 0 | Py_DECREF(error_msg); |
2588 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(tp)); |
2589 | 0 | return 0; |
2590 | 0 | } |
2591 | | |
2592 | 0 | if (e) { |
2593 | 0 | int is_in_class = st->st_cur->ste_can_see_class_scope; |
2594 | 0 | if (!symtable_enter_block(st, name, TypeVariableBlock, (void *)tp, LOCATION(e))) { |
2595 | 0 | return 0; |
2596 | 0 | } |
2597 | | |
2598 | 0 | st->st_cur->ste_can_see_class_scope = is_in_class; |
2599 | 0 | if (is_in_class && !symtable_add_def(st, &_Py_ID(__classdict__), USE, LOCATION(e))) { |
2600 | 0 | return 0; |
2601 | 0 | } |
2602 | | |
2603 | 0 | assert(ste_scope_info != NULL); |
2604 | 0 | st->st_cur->ste_scope_info = ste_scope_info; |
2605 | 0 | VISIT(st, expr, e); |
2606 | | |
2607 | 0 | if (!symtable_exit_block(st)) { |
2608 | 0 | return 0; |
2609 | 0 | } |
2610 | 0 | } |
2611 | 0 | return 1; |
2612 | 0 | } |
2613 | | |
2614 | | static int |
2615 | | symtable_visit_type_param(struct symtable *st, type_param_ty tp) |
2616 | 0 | { |
2617 | 0 | ENTER_RECURSIVE(); |
2618 | 0 | switch(tp->kind) { |
2619 | 0 | case TypeVar_kind: |
2620 | 0 | if (!symtable_add_def(st, tp->v.TypeVar.name, DEF_TYPE_PARAM | DEF_LOCAL, LOCATION(tp))) |
2621 | 0 | return 0; |
2622 | | |
2623 | 0 | const char *ste_scope_info = NULL; |
2624 | 0 | const expr_ty bound = tp->v.TypeVar.bound; |
2625 | 0 | if (bound != NULL) { |
2626 | 0 | ste_scope_info = bound->kind == Tuple_kind ? "a TypeVar constraint" : "a TypeVar bound"; |
2627 | 0 | } |
2628 | | |
2629 | | // We must use a different key for the bound and default. The obvious choice would be to |
2630 | | // use the .bound and .default_value pointers, but that fails when the expression immediately |
2631 | | // inside the bound or default is a comprehension: we would reuse the same key for |
2632 | | // the comprehension scope. Therefore, use the address + 1 as the second key. |
2633 | | // The only requirement for the key is that it is unique and it matches the logic in |
2634 | | // compile.c where the scope is retrieved. |
2635 | 0 | if (!symtable_visit_type_param_bound_or_default(st, tp->v.TypeVar.bound, tp->v.TypeVar.name, |
2636 | 0 | tp, ste_scope_info)) { |
2637 | 0 | return 0; |
2638 | 0 | } |
2639 | | |
2640 | 0 | if (!symtable_visit_type_param_bound_or_default(st, tp->v.TypeVar.default_value, tp->v.TypeVar.name, |
2641 | 0 | (type_param_ty)((uintptr_t)tp + 1), "a TypeVar default")) { |
2642 | 0 | return 0; |
2643 | 0 | } |
2644 | 0 | break; |
2645 | 0 | case TypeVarTuple_kind: |
2646 | 0 | if (!symtable_add_def(st, tp->v.TypeVarTuple.name, DEF_TYPE_PARAM | DEF_LOCAL, LOCATION(tp))) { |
2647 | 0 | return 0; |
2648 | 0 | } |
2649 | | |
2650 | 0 | if (!symtable_visit_type_param_bound_or_default(st, tp->v.TypeVarTuple.default_value, tp->v.TypeVarTuple.name, |
2651 | 0 | tp, "a TypeVarTuple default")) { |
2652 | 0 | return 0; |
2653 | 0 | } |
2654 | 0 | break; |
2655 | 0 | case ParamSpec_kind: |
2656 | 0 | if (!symtable_add_def(st, tp->v.ParamSpec.name, DEF_TYPE_PARAM | DEF_LOCAL, LOCATION(tp))) { |
2657 | 0 | return 0; |
2658 | 0 | } |
2659 | | |
2660 | 0 | if (!symtable_visit_type_param_bound_or_default(st, tp->v.ParamSpec.default_value, tp->v.ParamSpec.name, |
2661 | 0 | tp, "a ParamSpec default")) { |
2662 | 0 | return 0; |
2663 | 0 | } |
2664 | 0 | break; |
2665 | 0 | } |
2666 | 0 | LEAVE_RECURSIVE(); |
2667 | 0 | return 1; |
2668 | 0 | } |
2669 | | |
2670 | | static int |
2671 | | symtable_visit_pattern(struct symtable *st, pattern_ty p) |
2672 | 0 | { |
2673 | 0 | ENTER_RECURSIVE(); |
2674 | 0 | switch (p->kind) { |
2675 | 0 | case MatchValue_kind: |
2676 | 0 | VISIT(st, expr, p->v.MatchValue.value); |
2677 | 0 | break; |
2678 | 0 | case MatchSingleton_kind: |
2679 | | /* Nothing to do here. */ |
2680 | 0 | break; |
2681 | 0 | case MatchSequence_kind: |
2682 | 0 | VISIT_SEQ(st, pattern, p->v.MatchSequence.patterns); |
2683 | 0 | break; |
2684 | 0 | case MatchStar_kind: |
2685 | 0 | if (p->v.MatchStar.name) { |
2686 | 0 | if (!symtable_add_def(st, p->v.MatchStar.name, DEF_LOCAL, LOCATION(p))) { |
2687 | 0 | return 0; |
2688 | 0 | } |
2689 | 0 | } |
2690 | 0 | break; |
2691 | 0 | case MatchMapping_kind: |
2692 | 0 | VISIT_SEQ(st, expr, p->v.MatchMapping.keys); |
2693 | 0 | VISIT_SEQ(st, pattern, p->v.MatchMapping.patterns); |
2694 | 0 | if (p->v.MatchMapping.rest) { |
2695 | 0 | if (!symtable_add_def(st, p->v.MatchMapping.rest, DEF_LOCAL, LOCATION(p))) { |
2696 | 0 | return 0; |
2697 | 0 | } |
2698 | 0 | } |
2699 | 0 | break; |
2700 | 0 | case MatchClass_kind: |
2701 | 0 | VISIT(st, expr, p->v.MatchClass.cls); |
2702 | 0 | VISIT_SEQ(st, pattern, p->v.MatchClass.patterns); |
2703 | 0 | if (!check_kwd_patterns(st, p)) { |
2704 | 0 | return 0; |
2705 | 0 | } |
2706 | 0 | VISIT_SEQ(st, pattern, p->v.MatchClass.kwd_patterns); |
2707 | 0 | break; |
2708 | 0 | case MatchAs_kind: |
2709 | 0 | if (p->v.MatchAs.pattern) { |
2710 | 0 | VISIT(st, pattern, p->v.MatchAs.pattern); |
2711 | 0 | } |
2712 | 0 | if (p->v.MatchAs.name) { |
2713 | 0 | if (!symtable_add_def(st, p->v.MatchAs.name, DEF_LOCAL, LOCATION(p))) { |
2714 | 0 | return 0; |
2715 | 0 | } |
2716 | 0 | } |
2717 | 0 | break; |
2718 | 0 | case MatchOr_kind: |
2719 | 0 | VISIT_SEQ(st, pattern, p->v.MatchOr.patterns); |
2720 | 0 | break; |
2721 | 0 | } |
2722 | 0 | LEAVE_RECURSIVE(); |
2723 | 0 | return 1; |
2724 | 0 | } |
2725 | | |
2726 | | static int |
2727 | | symtable_implicit_arg(struct symtable *st, int pos) |
2728 | 322 | { |
2729 | 322 | PyObject *id = PyUnicode_FromFormat(".%d", pos); |
2730 | 322 | if (id == NULL) |
2731 | 0 | return 0; |
2732 | 322 | if (!symtable_add_def(st, id, DEF_PARAM, st->st_cur->ste_loc)) { |
2733 | 0 | Py_DECREF(id); |
2734 | 0 | return 0; |
2735 | 0 | } |
2736 | 322 | Py_DECREF(id); |
2737 | 322 | return 1; |
2738 | 322 | } |
2739 | | |
2740 | | static int |
2741 | | symtable_visit_params(struct symtable *st, asdl_arg_seq *args) |
2742 | 12.7k | { |
2743 | 12.7k | Py_ssize_t i; |
2744 | | |
2745 | 21.0k | for (i = 0; i < asdl_seq_LEN(args); i++) { |
2746 | 8.24k | arg_ty arg = (arg_ty)asdl_seq_GET(args, i); |
2747 | 8.24k | if (!symtable_add_def(st, arg->arg, DEF_PARAM, LOCATION(arg))) |
2748 | 0 | return 0; |
2749 | 8.24k | } |
2750 | | |
2751 | 12.7k | return 1; |
2752 | 12.7k | } |
2753 | | |
2754 | | static int |
2755 | | symtable_visit_annotation(struct symtable *st, expr_ty annotation, void *key) |
2756 | 0 | { |
2757 | | // Annotations in local scopes are not executed and should not affect the symtable |
2758 | 0 | bool is_unevaluated = st->st_cur->ste_type == FunctionBlock; |
2759 | | |
2760 | | // Module-level annotations are always considered conditional because the module |
2761 | | // may be partially executed. |
2762 | 0 | if ((((st->st_cur->ste_type == ClassBlock && st->st_cur->ste_in_conditional_block) |
2763 | 0 | || st->st_cur->ste_type == ModuleBlock)) |
2764 | 0 | && !st->st_cur->ste_has_conditional_annotations) |
2765 | 0 | { |
2766 | 0 | st->st_cur->ste_has_conditional_annotations = 1; |
2767 | 0 | if (!symtable_add_def(st, &_Py_ID(__conditional_annotations__), USE, LOCATION(annotation))) { |
2768 | 0 | return 0; |
2769 | 0 | } |
2770 | 0 | } |
2771 | 0 | struct _symtable_entry *parent_ste = st->st_cur; |
2772 | 0 | if (parent_ste->ste_annotation_block == NULL) { |
2773 | 0 | _Py_block_ty current_type = parent_ste->ste_type; |
2774 | 0 | if (!symtable_enter_block(st, &_Py_ID(__annotate__), AnnotationBlock, |
2775 | 0 | key, LOCATION(annotation))) { |
2776 | 0 | return 0; |
2777 | 0 | } |
2778 | 0 | parent_ste->ste_annotation_block = |
2779 | 0 | (struct _symtable_entry *)Py_NewRef(st->st_cur); |
2780 | 0 | int future_annotations = st->st_future->ff_features & CO_FUTURE_ANNOTATIONS; |
2781 | 0 | if (current_type == ClassBlock && !future_annotations) { |
2782 | 0 | st->st_cur->ste_can_see_class_scope = 1; |
2783 | 0 | if (!symtable_add_def(st, &_Py_ID(__classdict__), USE, LOCATION(annotation))) { |
2784 | 0 | return 0; |
2785 | 0 | } |
2786 | 0 | } |
2787 | 0 | } |
2788 | 0 | else { |
2789 | 0 | if (!symtable_enter_existing_block(st, parent_ste->ste_annotation_block, |
2790 | 0 | /* add_to_children */false)) { |
2791 | 0 | return 0; |
2792 | 0 | } |
2793 | 0 | } |
2794 | 0 | if (is_unevaluated) { |
2795 | 0 | st->st_cur->ste_in_unevaluated_annotation = 1; |
2796 | 0 | } |
2797 | 0 | int rc = symtable_visit_expr(st, annotation); |
2798 | 0 | if (is_unevaluated) { |
2799 | 0 | st->st_cur->ste_in_unevaluated_annotation = 0; |
2800 | 0 | } |
2801 | 0 | if (!symtable_exit_block(st)) { |
2802 | 0 | return 0; |
2803 | 0 | } |
2804 | 0 | return rc; |
2805 | 0 | } |
2806 | | |
2807 | | static int |
2808 | | symtable_visit_argannotations(struct symtable *st, asdl_arg_seq *args) |
2809 | 12.3k | { |
2810 | 12.3k | Py_ssize_t i; |
2811 | | |
2812 | 20.3k | for (i = 0; i < asdl_seq_LEN(args); i++) { |
2813 | 7.97k | arg_ty arg = (arg_ty)asdl_seq_GET(args, i); |
2814 | 7.97k | if (arg->annotation) { |
2815 | 8 | st->st_cur->ste_annotations_used = 1; |
2816 | 8 | VISIT(st, expr, arg->annotation); |
2817 | 8 | } |
2818 | 7.97k | } |
2819 | | |
2820 | 12.3k | return 1; |
2821 | 12.3k | } |
2822 | | |
2823 | | static int |
2824 | | symtable_visit_annotations(struct symtable *st, stmt_ty o, arguments_ty a, expr_ty returns, |
2825 | | struct _symtable_entry *function_ste) |
2826 | 4.13k | { |
2827 | 4.13k | int is_in_class = st->st_cur->ste_can_see_class_scope; |
2828 | 4.13k | _Py_block_ty current_type = st->st_cur->ste_type; |
2829 | 4.13k | if (!symtable_enter_block(st, &_Py_ID(__annotate__), AnnotationBlock, |
2830 | 4.13k | (void *)a, LOCATION(o))) { |
2831 | 0 | return 0; |
2832 | 0 | } |
2833 | 4.13k | if (is_in_class || current_type == ClassBlock) { |
2834 | 2.75k | st->st_cur->ste_can_see_class_scope = 1; |
2835 | 2.75k | if (!symtable_add_def(st, &_Py_ID(__classdict__), USE, LOCATION(o))) { |
2836 | 0 | return 0; |
2837 | 0 | } |
2838 | 2.75k | } |
2839 | 4.13k | if (a->posonlyargs && !symtable_visit_argannotations(st, a->posonlyargs)) |
2840 | 0 | return 0; |
2841 | 4.13k | if (a->args && !symtable_visit_argannotations(st, a->args)) |
2842 | 0 | return 0; |
2843 | 4.13k | if (a->vararg && a->vararg->annotation) { |
2844 | 0 | st->st_cur->ste_annotations_used = 1; |
2845 | 0 | VISIT(st, expr, a->vararg->annotation); |
2846 | 0 | } |
2847 | 4.13k | if (a->kwarg && a->kwarg->annotation) { |
2848 | 0 | st->st_cur->ste_annotations_used = 1; |
2849 | 0 | VISIT(st, expr, a->kwarg->annotation); |
2850 | 0 | } |
2851 | 4.13k | if (a->kwonlyargs && !symtable_visit_argannotations(st, a->kwonlyargs)) |
2852 | 0 | return 0; |
2853 | 4.13k | if (returns) { |
2854 | 5 | st->st_cur->ste_annotations_used = 1; |
2855 | 5 | VISIT(st, expr, returns); |
2856 | 5 | } |
2857 | 4.13k | if (!symtable_exit_block(st)) { |
2858 | 0 | return 0; |
2859 | 0 | } |
2860 | 4.13k | return 1; |
2861 | 4.13k | } |
2862 | | |
2863 | | static int |
2864 | | symtable_visit_arguments(struct symtable *st, arguments_ty a) |
2865 | 4.25k | { |
2866 | | /* skip default arguments inside function block |
2867 | | XXX should ast be different? |
2868 | | */ |
2869 | 4.25k | if (a->posonlyargs && !symtable_visit_params(st, a->posonlyargs)) |
2870 | 0 | return 0; |
2871 | 4.25k | if (a->args && !symtable_visit_params(st, a->args)) |
2872 | 0 | return 0; |
2873 | 4.25k | if (a->kwonlyargs && !symtable_visit_params(st, a->kwonlyargs)) |
2874 | 0 | return 0; |
2875 | 4.25k | if (a->vararg) { |
2876 | 168 | if (!symtable_add_def(st, a->vararg->arg, DEF_PARAM, LOCATION(a->vararg))) |
2877 | 0 | return 0; |
2878 | 168 | st->st_cur->ste_varargs = 1; |
2879 | 168 | } |
2880 | 4.25k | if (a->kwarg) { |
2881 | 131 | if (!symtable_add_def(st, a->kwarg->arg, DEF_PARAM, LOCATION(a->kwarg))) |
2882 | 0 | return 0; |
2883 | 131 | st->st_cur->ste_varkeywords = 1; |
2884 | 131 | } |
2885 | 4.25k | return 1; |
2886 | 4.25k | } |
2887 | | |
2888 | | |
2889 | | static int |
2890 | | symtable_visit_excepthandler(struct symtable *st, excepthandler_ty eh) |
2891 | 718 | { |
2892 | 718 | if (eh->v.ExceptHandler.type) |
2893 | 697 | VISIT(st, expr, eh->v.ExceptHandler.type); |
2894 | 718 | if (eh->v.ExceptHandler.name) |
2895 | 115 | if (!symtable_add_def(st, eh->v.ExceptHandler.name, DEF_LOCAL, LOCATION(eh))) |
2896 | 0 | return 0; |
2897 | 718 | VISIT_SEQ(st, stmt, eh->v.ExceptHandler.body); |
2898 | 718 | return 1; |
2899 | 718 | } |
2900 | | |
2901 | | static int |
2902 | | symtable_visit_withitem(struct symtable *st, withitem_ty item) |
2903 | 98 | { |
2904 | 98 | VISIT(st, expr, item->context_expr); |
2905 | 98 | if (item->optional_vars) { |
2906 | 28 | VISIT(st, expr, item->optional_vars); |
2907 | 28 | } |
2908 | 98 | return 1; |
2909 | 98 | } |
2910 | | |
2911 | | static int |
2912 | | symtable_visit_match_case(struct symtable *st, match_case_ty m) |
2913 | 0 | { |
2914 | 0 | VISIT(st, pattern, m->pattern); |
2915 | 0 | if (m->guard) { |
2916 | 0 | VISIT(st, expr, m->guard); |
2917 | 0 | } |
2918 | 0 | VISIT_SEQ(st, stmt, m->body); |
2919 | 0 | return 1; |
2920 | 0 | } |
2921 | | |
2922 | | static int |
2923 | | symtable_visit_alias(struct symtable *st, alias_ty a) |
2924 | 1.05k | { |
2925 | | /* Compute store_name, the name actually bound by the import |
2926 | | operation. It is different than a->name when a->name is a |
2927 | | dotted package name (e.g. spam.eggs) |
2928 | | */ |
2929 | 1.05k | PyObject *store_name; |
2930 | 1.05k | PyObject *name = (a->asname == NULL) ? a->name : a->asname; |
2931 | 1.05k | Py_ssize_t dot = PyUnicode_FindChar(name, '.', 0, |
2932 | 1.05k | PyUnicode_GET_LENGTH(name), 1); |
2933 | 1.05k | if (dot != -1) { |
2934 | 25 | store_name = PyUnicode_Substring(name, 0, dot); |
2935 | 25 | if (!store_name) |
2936 | 0 | return 0; |
2937 | 25 | } |
2938 | 1.03k | else { |
2939 | 1.03k | store_name = Py_NewRef(name); |
2940 | 1.03k | } |
2941 | 1.05k | if (!_PyUnicode_EqualToASCIIString(name, "*")) { |
2942 | 1.04k | int r = symtable_add_def(st, store_name, DEF_IMPORT, LOCATION(a)); |
2943 | 1.04k | Py_DECREF(store_name); |
2944 | 1.04k | return r; |
2945 | 1.04k | } |
2946 | 17 | else { |
2947 | 17 | if (st->st_cur->ste_type != ModuleBlock) { |
2948 | 0 | PyErr_SetString(PyExc_SyntaxError, IMPORT_STAR_WARNING); |
2949 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(a)); |
2950 | 0 | Py_DECREF(store_name); |
2951 | 0 | return 0; |
2952 | 0 | } |
2953 | 17 | Py_DECREF(store_name); |
2954 | 17 | return 1; |
2955 | 17 | } |
2956 | 1.05k | } |
2957 | | |
2958 | | |
2959 | | static int |
2960 | | symtable_visit_comprehension(struct symtable *st, comprehension_ty lc) |
2961 | 14 | { |
2962 | 14 | st->st_cur->ste_comp_iter_target = 1; |
2963 | 14 | VISIT(st, expr, lc->target); |
2964 | 14 | st->st_cur->ste_comp_iter_target = 0; |
2965 | 14 | st->st_cur->ste_comp_iter_expr++; |
2966 | 14 | VISIT(st, expr, lc->iter); |
2967 | 14 | st->st_cur->ste_comp_iter_expr--; |
2968 | 14 | VISIT_SEQ(st, expr, lc->ifs); |
2969 | 14 | if (lc->is_async) { |
2970 | 0 | st->st_cur->ste_coroutine = 1; |
2971 | 0 | } |
2972 | 14 | return 1; |
2973 | 14 | } |
2974 | | |
2975 | | |
2976 | | static int |
2977 | | symtable_visit_keyword(struct symtable *st, keyword_ty k) |
2978 | 1.71k | { |
2979 | 1.71k | VISIT(st, expr, k->value); |
2980 | 1.71k | return 1; |
2981 | 1.71k | } |
2982 | | |
2983 | | |
2984 | | static int |
2985 | | symtable_handle_comprehension(struct symtable *st, expr_ty e, |
2986 | | identifier scope_name, asdl_comprehension_seq *generators, |
2987 | | expr_ty elt, expr_ty value) |
2988 | 322 | { |
2989 | 322 | int is_generator = (e->kind == GeneratorExp_kind); |
2990 | 322 | comprehension_ty outermost = ((comprehension_ty) |
2991 | 322 | asdl_seq_GET(generators, 0)); |
2992 | | /* Outermost iterator is evaluated in current scope */ |
2993 | 322 | st->st_cur->ste_comp_iter_expr++; |
2994 | 322 | VISIT(st, expr, outermost->iter); |
2995 | 322 | st->st_cur->ste_comp_iter_expr--; |
2996 | | /* Create comprehension scope for the rest */ |
2997 | 322 | if (!scope_name || |
2998 | 322 | !symtable_enter_block(st, scope_name, FunctionBlock, (void *)e, LOCATION(e))) { |
2999 | 0 | return 0; |
3000 | 0 | } |
3001 | 322 | switch(e->kind) { |
3002 | 164 | case ListComp_kind: |
3003 | 164 | st->st_cur->ste_comprehension = ListComprehension; |
3004 | 164 | break; |
3005 | 3 | case SetComp_kind: |
3006 | 3 | st->st_cur->ste_comprehension = SetComprehension; |
3007 | 3 | break; |
3008 | 18 | case DictComp_kind: |
3009 | 18 | st->st_cur->ste_comprehension = DictComprehension; |
3010 | 18 | break; |
3011 | 137 | default: |
3012 | 137 | st->st_cur->ste_comprehension = GeneratorExpression; |
3013 | 137 | break; |
3014 | 322 | } |
3015 | 322 | if (outermost->is_async) { |
3016 | 0 | st->st_cur->ste_coroutine = 1; |
3017 | 0 | } |
3018 | | |
3019 | | /* Outermost iter is received as an argument */ |
3020 | 322 | if (!symtable_implicit_arg(st, 0)) { |
3021 | 0 | symtable_exit_block(st); |
3022 | 0 | return 0; |
3023 | 0 | } |
3024 | | /* Visit iteration variable target, and mark them as such */ |
3025 | 322 | st->st_cur->ste_comp_iter_target = 1; |
3026 | 322 | VISIT(st, expr, outermost->target); |
3027 | 322 | st->st_cur->ste_comp_iter_target = 0; |
3028 | | /* Visit the rest of the comprehension body */ |
3029 | 322 | VISIT_SEQ(st, expr, outermost->ifs); |
3030 | 322 | VISIT_SEQ_TAIL(st, comprehension, generators, 1); |
3031 | 322 | if (value) |
3032 | 18 | VISIT(st, expr, value); |
3033 | 322 | VISIT(st, expr, elt); |
3034 | 322 | st->st_cur->ste_generator = is_generator; |
3035 | 322 | int is_async = st->st_cur->ste_coroutine && !is_generator; |
3036 | 322 | if (!symtable_exit_block(st)) { |
3037 | 0 | return 0; |
3038 | 0 | } |
3039 | 322 | if (is_async && |
3040 | 322 | !IS_ASYNC_DEF(st) && |
3041 | 322 | st->st_cur->ste_comprehension == NoComprehension && |
3042 | 322 | !allows_top_level_await(st)) |
3043 | 0 | { |
3044 | 0 | PyErr_SetString(PyExc_SyntaxError, "asynchronous comprehension outside of " |
3045 | 0 | "an asynchronous function"); |
3046 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(e)); |
3047 | 0 | return 0; |
3048 | 0 | } |
3049 | 322 | if (is_async) { |
3050 | 0 | st->st_cur->ste_coroutine = 1; |
3051 | 0 | } |
3052 | 322 | return 1; |
3053 | 322 | } |
3054 | | |
3055 | | static int |
3056 | | symtable_visit_genexp(struct symtable *st, expr_ty e) |
3057 | 137 | { |
3058 | 137 | return symtable_handle_comprehension(st, e, &_Py_ID(genexpr), |
3059 | 137 | e->v.GeneratorExp.generators, |
3060 | 137 | e->v.GeneratorExp.elt, NULL); |
3061 | 137 | } |
3062 | | |
3063 | | static int |
3064 | | symtable_visit_listcomp(struct symtable *st, expr_ty e) |
3065 | 164 | { |
3066 | 164 | return symtable_handle_comprehension(st, e, &_Py_ID(listcomp), |
3067 | 164 | e->v.ListComp.generators, |
3068 | 164 | e->v.ListComp.elt, NULL); |
3069 | 164 | } |
3070 | | |
3071 | | static int |
3072 | | symtable_visit_setcomp(struct symtable *st, expr_ty e) |
3073 | 3 | { |
3074 | 3 | return symtable_handle_comprehension(st, e, &_Py_ID(setcomp), |
3075 | 3 | e->v.SetComp.generators, |
3076 | 3 | e->v.SetComp.elt, NULL); |
3077 | 3 | } |
3078 | | |
3079 | | static int |
3080 | | symtable_visit_dictcomp(struct symtable *st, expr_ty e) |
3081 | 18 | { |
3082 | 18 | return symtable_handle_comprehension(st, e, &_Py_ID(dictcomp), |
3083 | 18 | e->v.DictComp.generators, |
3084 | 18 | e->v.DictComp.key, |
3085 | 18 | e->v.DictComp.value); |
3086 | 18 | } |
3087 | | |
3088 | | static int |
3089 | | symtable_raise_if_annotation_block(struct symtable *st, const char *name, expr_ty e) |
3090 | 248 | { |
3091 | 248 | _Py_block_ty type = st->st_cur->ste_type; |
3092 | 248 | if (type == AnnotationBlock) |
3093 | 0 | PyErr_Format(PyExc_SyntaxError, ANNOTATION_NOT_ALLOWED, name); |
3094 | 248 | else if (type == TypeVariableBlock) { |
3095 | 0 | const char *info = st->st_cur->ste_scope_info; |
3096 | 0 | assert(info != NULL); // e.g., info == "a ParamSpec default" |
3097 | 0 | PyErr_Format(PyExc_SyntaxError, EXPR_NOT_ALLOWED_IN_TYPE_VARIABLE, name, info); |
3098 | 0 | } |
3099 | 248 | else if (type == TypeAliasBlock) { |
3100 | | // for now, we do not have any extra information |
3101 | 0 | assert(st->st_cur->ste_scope_info == NULL); |
3102 | 0 | PyErr_Format(PyExc_SyntaxError, EXPR_NOT_ALLOWED_IN_TYPE_ALIAS, name); |
3103 | 0 | } |
3104 | 248 | else if (type == TypeParametersBlock) { |
3105 | | // for now, we do not have any extra information |
3106 | 0 | assert(st->st_cur->ste_scope_info == NULL); |
3107 | 0 | PyErr_Format(PyExc_SyntaxError, EXPR_NOT_ALLOWED_IN_TYPE_PARAMETERS, name); |
3108 | 0 | } |
3109 | 248 | else |
3110 | 248 | return 1; |
3111 | | |
3112 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(e)); |
3113 | 0 | return 0; |
3114 | 248 | } |
3115 | | |
3116 | | static int |
3117 | 0 | symtable_raise_if_comprehension_block(struct symtable *st, expr_ty e) { |
3118 | 0 | _Py_comprehension_ty type = st->st_cur->ste_comprehension; |
3119 | 0 | PyErr_SetString(PyExc_SyntaxError, |
3120 | 0 | (type == ListComprehension) ? "'yield' inside list comprehension" : |
3121 | 0 | (type == SetComprehension) ? "'yield' inside set comprehension" : |
3122 | 0 | (type == DictComprehension) ? "'yield' inside dict comprehension" : |
3123 | 0 | "'yield' inside generator expression"); |
3124 | 0 | SET_ERROR_LOCATION(st->st_filename, LOCATION(e)); |
3125 | 0 | return 0; |
3126 | 0 | } |
3127 | | |
3128 | | static int |
3129 | 1 | symtable_raise_if_not_coroutine(struct symtable *st, const char *msg, _Py_SourceLocation loc) { |
3130 | 1 | if (!st->st_cur->ste_coroutine) { |
3131 | 0 | PyErr_SetString(PyExc_SyntaxError, msg); |
3132 | 0 | SET_ERROR_LOCATION(st->st_filename, loc); |
3133 | 0 | return 0; |
3134 | 0 | } |
3135 | 1 | return 1; |
3136 | 1 | } |
3137 | | |
3138 | | struct symtable * |
3139 | | _Py_SymtableStringObjectFlags(const char *str, PyObject *filename, |
3140 | | int start, PyCompilerFlags *flags) |
3141 | 0 | { |
3142 | 0 | struct symtable *st; |
3143 | 0 | mod_ty mod; |
3144 | 0 | PyArena *arena; |
3145 | |
|
3146 | 0 | arena = _PyArena_New(); |
3147 | 0 | if (arena == NULL) |
3148 | 0 | return NULL; |
3149 | | |
3150 | 0 | mod = _PyParser_ASTFromString(str, filename, start, flags, arena); |
3151 | 0 | if (mod == NULL) { |
3152 | 0 | _PyArena_Free(arena); |
3153 | 0 | return NULL; |
3154 | 0 | } |
3155 | 0 | _PyFutureFeatures future; |
3156 | 0 | if (!_PyFuture_FromAST(mod, filename, &future)) { |
3157 | 0 | _PyArena_Free(arena); |
3158 | 0 | return NULL; |
3159 | 0 | } |
3160 | 0 | future.ff_features |= flags->cf_flags; |
3161 | 0 | st = _PySymtable_Build(mod, filename, &future); |
3162 | 0 | _PyArena_Free(arena); |
3163 | 0 | return st; |
3164 | 0 | } |
3165 | | |
3166 | | PyObject * |
3167 | | _Py_MaybeMangle(PyObject *privateobj, PySTEntryObject *ste, PyObject *name) |
3168 | 202k | { |
3169 | | /* Special case for type parameter blocks around generic classes: |
3170 | | * we want to mangle type parameter names (so a type param with a private |
3171 | | * name can be used inside the class body), but we don't want to mangle |
3172 | | * any other names that appear within the type parameter scope. |
3173 | | */ |
3174 | 202k | if (ste->ste_mangled_names != NULL) { |
3175 | 0 | int result = PySet_Contains(ste->ste_mangled_names, name); |
3176 | 0 | if (result < 0) { |
3177 | 0 | return NULL; |
3178 | 0 | } |
3179 | 0 | if (result == 0) { |
3180 | 0 | return Py_NewRef(name); |
3181 | 0 | } |
3182 | 0 | } |
3183 | 202k | return _Py_Mangle(privateobj, name); |
3184 | 202k | } |
3185 | | |
3186 | | PyObject * |
3187 | | _Py_Mangle(PyObject *privateobj, PyObject *ident) |
3188 | 205k | { |
3189 | | /* Name mangling: __private becomes _classname__private. |
3190 | | This is independent from how the name is used. */ |
3191 | 205k | if (privateobj == NULL || !PyUnicode_Check(privateobj) || |
3192 | 205k | PyUnicode_READ_CHAR(ident, 0) != '_' || |
3193 | 205k | PyUnicode_READ_CHAR(ident, 1) != '_') { |
3194 | 192k | return Py_NewRef(ident); |
3195 | 192k | } |
3196 | 12.9k | size_t nlen = PyUnicode_GET_LENGTH(ident); |
3197 | 12.9k | size_t plen = PyUnicode_GET_LENGTH(privateobj); |
3198 | | /* Don't mangle __id__ or names with dots. |
3199 | | |
3200 | | The only time a name with a dot can occur is when |
3201 | | we are compiling an import statement that has a |
3202 | | package name. |
3203 | | |
3204 | | TODO(jhylton): Decide whether we want to support |
3205 | | mangling of the module name, e.g. __M.X. |
3206 | | */ |
3207 | 12.9k | if ((PyUnicode_READ_CHAR(ident, nlen-1) == '_' && |
3208 | 12.9k | PyUnicode_READ_CHAR(ident, nlen-2) == '_') || |
3209 | 12.9k | PyUnicode_FindChar(ident, '.', 0, nlen, 1) != -1) { |
3210 | 12.7k | return Py_NewRef(ident); /* Don't mangle __whatever__ */ |
3211 | 12.7k | } |
3212 | | /* Strip leading underscores from class name */ |
3213 | 125 | size_t ipriv = 0; |
3214 | 152 | while (PyUnicode_READ_CHAR(privateobj, ipriv) == '_') { |
3215 | 27 | ipriv++; |
3216 | 27 | } |
3217 | 125 | if (ipriv == plen) { |
3218 | 0 | return Py_NewRef(ident); /* Don't mangle if class is just underscores */ |
3219 | 0 | } |
3220 | | |
3221 | 125 | if (nlen + (plen - ipriv) >= PY_SSIZE_T_MAX - 1) { |
3222 | 0 | PyErr_SetString(PyExc_OverflowError, |
3223 | 0 | "private identifier too large to be mangled"); |
3224 | 0 | return NULL; |
3225 | 0 | } |
3226 | | |
3227 | 125 | PyUnicodeWriter *writer = PyUnicodeWriter_Create(1 + nlen + (plen - ipriv)); |
3228 | 125 | if (!writer) { |
3229 | 0 | return NULL; |
3230 | 0 | } |
3231 | | // ident = "_" + priv[ipriv:] + ident |
3232 | 125 | if (PyUnicodeWriter_WriteChar(writer, '_') < 0) { |
3233 | 0 | goto error; |
3234 | 0 | } |
3235 | 125 | if (PyUnicodeWriter_WriteSubstring(writer, privateobj, ipriv, plen) < 0) { |
3236 | 0 | goto error; |
3237 | 0 | } |
3238 | 125 | if (PyUnicodeWriter_WriteStr(writer, ident) < 0) { |
3239 | 0 | goto error; |
3240 | 0 | } |
3241 | 125 | return PyUnicodeWriter_Finish(writer); |
3242 | | |
3243 | 0 | error: |
3244 | 0 | PyUnicodeWriter_Discard(writer); |
3245 | 0 | return NULL; |
3246 | 125 | } |