From 34f439774eb3548367b3dab856ba8267623d41d9 Mon Sep 17 00:00:00 2001 From: Pablo Galindo Date: Tue, 11 Jan 2022 11:50:43 +0000 Subject: [PATCH 1/2] bpo-46339: Fix crash in the parser when computing error text for multi-line f-strings --- Lib/test/test_exceptions.py | 6 ++++++ .../2022-01-11-11-50-19.bpo-46339.OVumDZ.rst | 3 +++ Parser/pegen_errors.c | 10 ++++++++-- 3 files changed, 17 insertions(+), 2 deletions(-) create mode 100644 Misc/NEWS.d/next/Core and Builtins/2022-01-11-11-50-19.bpo-46339.OVumDZ.rst diff --git a/Lib/test/test_exceptions.py b/Lib/test/test_exceptions.py index e4d685f4154ed8..531b9c92deae5a 100644 --- a/Lib/test/test_exceptions.py +++ b/Lib/test/test_exceptions.py @@ -280,6 +280,12 @@ def baz(): } \"\"\" }'''""", 5, 17) + check('''f""" + + + { + 6 + 0="""''', 5, 13) # Errors thrown by symtable.c check('x = [(yield i) for i in range(3)]', 1, 7) diff --git a/Misc/NEWS.d/next/Core and Builtins/2022-01-11-11-50-19.bpo-46339.OVumDZ.rst b/Misc/NEWS.d/next/Core and Builtins/2022-01-11-11-50-19.bpo-46339.OVumDZ.rst new file mode 100644 index 00000000000000..cd04f060826b28 --- /dev/null +++ b/Misc/NEWS.d/next/Core and Builtins/2022-01-11-11-50-19.bpo-46339.OVumDZ.rst @@ -0,0 +1,3 @@ +Fix a crash in the parser when retrieving the error text for multi-line +f-strings expressions that do not start in the first line of the string. +Patch by Pablo Galindo diff --git a/Parser/pegen_errors.c b/Parser/pegen_errors.c index f07d9d8a34df70..7b823f94d6d9d9 100644 --- a/Parser/pegen_errors.c +++ b/Parser/pegen_errors.c @@ -250,8 +250,14 @@ get_error_line_from_tokenizer_buffers(Parser *p, Py_ssize_t lineno) char *cur_line = p->tok->fp_interactive ? p->tok->interactive_src_start : p->tok->str; assert(cur_line != NULL); - for (int i = 0; i < lineno - 1; i++) { - cur_line = strchr(cur_line, '\n') + 1; + Py_ssize_t relative_lineno = p->starting_lineno ? lineno - p->starting_lineno + 1 : lineno; + + for (int i = 0; i < relative_lineno - 1; i++) { + char *new_line = strchr(cur_line, '\n') + 1; + if (new_line == NULL || new_line >= p->tok->inp) { + break; + } + cur_line = new_line; } char *next_newline; From 998938aede388a48c19722439feceaacce1b7c5d Mon Sep 17 00:00:00 2001 From: Pablo Galindo Salgado Date: Tue, 11 Jan 2022 16:03:25 +0000 Subject: [PATCH 2/2] Update Parser/pegen_errors.c --- Parser/pegen_errors.c | 1 + 1 file changed, 1 insertion(+) diff --git a/Parser/pegen_errors.c b/Parser/pegen_errors.c index 7b823f94d6d9d9..bffae8532ca2b7 100644 --- a/Parser/pegen_errors.c +++ b/Parser/pegen_errors.c @@ -254,6 +254,7 @@ get_error_line_from_tokenizer_buffers(Parser *p, Py_ssize_t lineno) for (int i = 0; i < relative_lineno - 1; i++) { char *new_line = strchr(cur_line, '\n') + 1; + assert(new_line != NULL && new_line < p->tok->inp); if (new_line == NULL || new_line >= p->tok->inp) { break; }