Branch: refs/heads/master Author: Colomban Wendling ban@herbesfolles.org Committer: Colomban Wendling ban@herbesfolles.org Date: Tue, 02 Dec 2014 14:02:39 UTC Commit: 02bc3b36387671061ed61dba4cdd31f843c44ed3 https://github.com/geany/geany/commit/02bc3b36387671061ed61dba4cdd31f843c44e...
Log Message: ----------- javascript: Improve string literals handling
1. Don't include the newline itself in a line continuation construct. This fixes generation of e.g. properties with embedded line continuations. 2. Don't continue parsing strings past an unescaped newline (as naked newlines are invalid inside strings). This avoids parsing the whole remaining file as a string in case of broken input. It is both useful to better support partly written files and to avoid loading a whole malformed file in memory while reading it as a string.
See section 7.8.4 "String Literals" of ECMA-262: http://www.ecma-international.org/publications/files/ECMA-ST/Ecma-262.pdf
Modified Paths: -------------- tagmanager/ctags/js.c tests/ctags/Makefile.am tests/ctags/js-broken-strings.js tests/ctags/js-broken-strings.js.tags tests/ctags/js-string-continuation.js tests/ctags/js-string-continuation.js.tags
Modified: tagmanager/ctags/js.c 25 lines changed, 23 insertions(+), 2 deletions(-) =================================================================== @@ -360,11 +360,32 @@ static void parseString (vString *const string, const int delimiter) end = TRUE; else if (c == '\') { - c = fileGetc(); /* This maybe a ' or ". */ - vStringPut(string, c); + /* Eat the escape sequence (", ', etc). We properly handle + * <LineContinuation> by eating a whole <CR><LF> not to see <LF> + * as an unescaped character, which is invalid and handled below. + * Also, handle the fact that <LineContinuation> produces an empty + * sequence. + * See ECMA-262 7.8.4 */ + c = fileGetc(); + if (c != '\r' && c != '\n') + vStringPut(string, c); + else if (c == '\r') + { + c = fileGetc(); + if (c != '\n') + fileUngetc (c); + } } else if (c == delimiter) end = TRUE; + else if (c == '\r' || c == '\n') + { + /* those are invalid when not escaped */ + end = TRUE; + /* we don't want to eat the newline itself to let the automatic + * semicolon insertion code kick in */ + fileUngetc (c); + } else vStringPut (string, c); }
Modified: tests/ctags/Makefile.am 2 lines changed, 2 insertions(+), 0 deletions(-) =================================================================== @@ -159,12 +159,14 @@ test_sources = \ intro.tex \ invalid_name.f90 \ java_enum.java \ + js-broken-strings.js \ js-class-related-unterminated.js \ js-const.js \ js-implicit-semicolons.js \ js-let.js \ js-scope.js \ js-signature.js \ + js-string-continuation.js \ js-sub-block-scope.js \ js-unknown-construct-nesting.js \ jsFunc_tutorial.js \
Modified: tests/ctags/js-broken-strings.js 10 lines changed, 10 insertions(+), 0 deletions(-) =================================================================== @@ -0,0 +1,10 @@ +// this file willfully uses CR-LF line endings to check their handling + +var s1 = "I'm invalid because not terminated + +var s2 = "I'm valid, I have a line continuation:\ +; function bug1(){}"; + +var s3 = "I'm invalid because I'm not terminated either \ +var bug2 = 'this is inside the s3 string' +var s4 = 'this is a separate, valid string'
Modified: tests/ctags/js-broken-strings.js.tags 5 lines changed, 5 insertions(+), 0 deletions(-) =================================================================== @@ -0,0 +1,5 @@ +# format=tagmanager +s1�16384�0 +s2�16384�0 +s3�16384�0 +s4�16384�0
Modified: tests/ctags/js-string-continuation.js 19 lines changed, 19 insertions(+), 0 deletions(-) =================================================================== @@ -0,0 +1,19 @@ + +var o = { + "first": function(){}, + "sec\ +ond": function(){}, + "\ +t\ +h\ +i\ +r\ +d\ +": function(){}, + "fourth": function(){}, +}; + +o.first(); +o.second(); +o.third(); +o.fourth();
Modified: tests/ctags/js-string-continuation.js.tags 6 lines changed, 6 insertions(+), 0 deletions(-) =================================================================== @@ -0,0 +1,6 @@ +# format=tagmanager +first�128�()�o�0 +fourth�128�()�o�0 +o�16384�0 +second�128�()�o�0 +third�128�()�o�0
-------------- This E-Mail was brought to you by github_commit_mail.py (Source: https://github.com/geany/infrastructure).