From 67dd52d59cde0d2f1ebb3e299b605ed239b59f5b Mon Sep 17 00:00:00 2001 From: Nobuyoshi Nakada Date: Sun, 19 Mar 2023 01:35:21 +0900 Subject: [PATCH] [Bug #19539] Match heredoc identifier from end of line Not to ignore leading spaces in indented heredoc identifier. --- parse.y | 20 ++++++++++---------- test/ruby/test_parse.rb | 10 ++++++++++ 2 files changed, 20 insertions(+), 10 deletions(-) diff --git a/parse.y b/parse.y index b05f1ba76a..4ef5b88407 100644 --- a/parse.y +++ b/parse.y @@ -8200,19 +8200,19 @@ parser_dedent_string(VALUE self, VALUE input, VALUE width) static int whole_match_p(struct parser_params *p, const char *eos, long len, int indent) { - const char *ptr = p->lex.pbeg; - long n; + const char *beg = p->lex.pbeg; + const char *ptr = p->lex.pend; + if (ptr - beg < len) return FALSE; + if (ptr > beg && ptr[-1] == '\n') { + if (--ptr > beg && ptr[-1] == '\r') --ptr; + if (ptr - beg < len) return FALSE; + } + if (strncmp(eos, ptr -= len, len)) return FALSE; if (indent) { - while (*ptr && ISSPACE(*ptr)) ptr++; + while (beg < ptr && ISSPACE(*beg)) beg++; } - n = p->lex.pend - (ptr + len); - if (n < 0) return FALSE; - if (n > 0 && ptr[len] != '\n') { - if (ptr[len] != '\r') return FALSE; - if (n <= 1 || ptr[len+1] != '\n') return FALSE; - } - return strncmp(eos, ptr, len) == 0; + return beg == ptr; } static int diff --git a/test/ruby/test_parse.rb b/test/ruby/test_parse.rb index 2f2c062ceb..49b25fcaf0 100644 --- a/test/ruby/test_parse.rb +++ b/test/ruby/test_parse.rb @@ -681,6 +681,16 @@ FOO eval "x = <<""FOO\r\n1\r\nFOO" end assert_equal("1\n", x) + + assert_nothing_raised do + x = eval "<<' FOO'\n""[Bug #19539]\n"" FOO\n" + end + assert_equal("[Bug #19539]\n", x) + + assert_nothing_raised do + x = eval "<<-' FOO'\n""[Bug #19539]\n"" FOO\n" + end + assert_equal("[Bug #19539]\n", x) end def test_magic_comment