diff --git a/Lib/test/test_coroutines.py b/Lib/test/test_coroutines.py index 94994e548bd..14682ca6047 100644 --- a/Lib/test/test_coroutines.py +++ b/Lib/test/test_coroutines.py @@ -211,6 +211,10 @@ class AsyncBadSyntaxTest(unittest.TestCase): pass """, + """async def foo(a:await b): + pass + """, + """def baz(): async def foo(a=await b): pass diff --git a/Lib/test/test_grammar.py b/Lib/test/test_grammar.py index ca6b5d0c385..9b41df1ad86 100644 --- a/Lib/test/test_grammar.py +++ b/Lib/test/test_grammar.py @@ -534,7 +534,8 @@ class GrammarTests(unittest.TestCase): # Not allowed at class scope check_syntax_error(self, "class foo:yield 1") check_syntax_error(self, "class foo:yield from ()") - + # Check annotation refleak on SyntaxError + check_syntax_error(self, "def g(a:(yield)): pass") def test_raise(self): # 'raise' test [',' test] diff --git a/Misc/NEWS b/Misc/NEWS index 2b57318a588..5b13cef44f4 100644 --- a/Misc/NEWS +++ b/Misc/NEWS @@ -48,6 +48,9 @@ Core and Builtins - Issue #24619: New approach for tokenizing async/await. As a consequence, is is now possible to have one-line 'async def foo(): await ..' functions. +- Issue #24687: Plug refleak on SyntaxError in function parameters + annotations. + Library ------- diff --git a/Python/compile.c b/Python/compile.c index cb36d5794ab..803c964a385 100644 --- a/Python/compile.c +++ b/Python/compile.c @@ -1559,32 +1559,31 @@ compiler_visit_argannotation(struct compiler *c, identifier id, VISIT(c, expr, annotation); mangled = _Py_Mangle(c->u->u_private, id); if (!mangled) - return -1; + return 0; if (PyList_Append(names, mangled) < 0) { Py_DECREF(mangled); - return -1; + return 0; } Py_DECREF(mangled); } - return 0; + return 1; } static int compiler_visit_argannotations(struct compiler *c, asdl_seq* args, PyObject *names) { - int i, error; + int i; for (i = 0; i < asdl_seq_LEN(args); i++) { arg_ty arg = (arg_ty)asdl_seq_GET(args, i); - error = compiler_visit_argannotation( + if (!compiler_visit_argannotation( c, arg->arg, arg->annotation, - names); - if (error) - return error; + names)) + return 0; } - return 0; + return 1; } static int @@ -1604,16 +1603,16 @@ compiler_visit_annotations(struct compiler *c, arguments_ty args, if (!names) return -1; - if (compiler_visit_argannotations(c, args->args, names)) + if (!compiler_visit_argannotations(c, args->args, names)) goto error; if (args->vararg && args->vararg->annotation && - compiler_visit_argannotation(c, args->vararg->arg, + !compiler_visit_argannotation(c, args->vararg->arg, args->vararg->annotation, names)) goto error; - if (compiler_visit_argannotations(c, args->kwonlyargs, names)) + if (!compiler_visit_argannotations(c, args->kwonlyargs, names)) goto error; if (args->kwarg && args->kwarg->annotation && - compiler_visit_argannotation(c, args->kwarg->arg, + !compiler_visit_argannotation(c, args->kwarg->arg, args->kwarg->annotation, names)) goto error; @@ -1622,7 +1621,7 @@ compiler_visit_annotations(struct compiler *c, arguments_ty args, if (!return_str) goto error; } - if (compiler_visit_argannotation(c, return_str, returns, names)) { + if (!compiler_visit_argannotation(c, return_str, returns, names)) { goto error; }