diff options
author | Dieter Verfaillie <dieterv@optionexplicit.be> | 2013-08-29 07:45:04 +0200 |
---|---|---|
committer | Dieter Verfaillie <dieterv@optionexplicit.be> | 2013-10-08 20:57:25 +0200 |
commit | aa4a40288533b3d06d69ebe8fe1a12bfec2a8cda (patch) | |
tree | 1c33f5f4d8672130ed2a70438b6b86657c81296e | |
parent | ce352de62e1ccc9ecaa2649d85569acc272ee0ed (diff) | |
download | gobject-introspection-aa4a40288533b3d06d69ebe8fe1a12bfec2a8cda.tar.gz |
giscanner: fix c0e748e1cdf8cf0803266f94c3c5ad154df504a8
When encountering /**/ in the source, parse_gtk_doc_comment()
would be executed (due to the /** part starting a GTK-Doc
comment block) and would happily consume the / and everything
up until the next comment block was closed or EOF, thus
consuming a whole block of C code...
Encoutered in the wild here:
https://git.gnome.org/browse/clutter-gst/tree/clutter-gst/clutter-gst-player.c?id=03f0d8f48bd7f60e582e6185cb73a07038e8d55d#n1926
-rw-r--r-- | giscanner/annotationparser.py | 3 | ||||
-rw-r--r-- | giscanner/scannerlexer.l | 98 | ||||
-rw-r--r-- | tests/scanner/annotationparser/test_patterns.py | 2 |
3 files changed, 52 insertions, 51 deletions
diff --git a/giscanner/annotationparser.py b/giscanner/annotationparser.py index 244df114..a00bac1d 100644 --- a/giscanner/annotationparser.py +++ b/giscanner/annotationparser.py @@ -294,8 +294,9 @@ COMMENT_BLOCK_START_RE = re.compile( ^ # start (?P<code>.*?) # whitespace, code, ... \s* # 0 or more whitespace characters - (?P<token>/\*{2}(?!\*)) # 1 forward slash character followed + (?P<token>/\*{2}(?![\*/])) # 1 forward slash character followed # by exactly 2 asterisk characters + # and not followed by a slash character \s* # 0 or more whitespace characters (?P<comment>.*?) # GTK-Doc comment text \s* # 0 or more whitespace characters diff --git a/giscanner/scannerlexer.l b/giscanner/scannerlexer.l index 554e2da7..bf51d0d5 100644 --- a/giscanner/scannerlexer.l +++ b/giscanner/scannerlexer.l @@ -46,7 +46,6 @@ char linebuf[2000]; extern int yylex (GISourceScanner *scanner); #define YY_DECL int yylex (GISourceScanner *scanner) static int yywrap (void); -static void parse_gtk_doc_comment (GISourceScanner *scanner); static void parse_comment (GISourceScanner *scanner); static void parse_trigraph (GISourceScanner *scanner); static void process_linemarks (GISourceScanner *scanner); @@ -75,7 +74,6 @@ stringtext ([^\\\"])|(\\.) [\t\f\v\r ]+ { /* Ignore whitespace. */ } -"/**" { parse_gtk_doc_comment(scanner); } "/*" { parse_comment(scanner); } "/*"[\t ]?<[\t ,=A-Za-z0-9_]+>[\t ]?"*/" { parse_trigraph(scanner); } "//".* { /* Ignore C++ style comments. */ } @@ -224,72 +222,72 @@ yywrap (void) } static void -parse_gtk_doc_comment (GISourceScanner *scanner) +parse_comment (GISourceScanner *scanner) { - GString *string = NULL; int c1, c2; + GString *string = NULL; GISourceComment *comment; int comment_lineno; int skip = FALSE; - if (!g_list_find_custom (scanner->filenames, - scanner->current_filename, - (GCompareFunc)g_strcmp0)) { - skip = TRUE; - } else { - string = g_string_new (yytext); - } - c1 = input(); c2 = input(); - comment_lineno = lineno; - - while (c2 != EOF && !(c1 == '*' && c2 == '/')) - { - if (!skip) - g_string_append_c (string, c1); - - if (c1 == '\n') - lineno++; - - c1 = c2; - c2 = input(); + if (c2 != EOF && (c1 == '*' && c2 != '*' && c2 != '/')) { + /* + * Store GTK-Doc comment blocks, + * starts with one '/' followed by exactly two '*' and not followed by a '/' + */ + if (!g_list_find_custom (scanner->filenames, + scanner->current_filename, + (GCompareFunc)g_strcmp0)) { + skip = TRUE; + } else { + string = g_string_new (yytext); } - if (skip) { - return; - } - - g_string_append (string, "*/"); + comment_lineno = lineno; - comment = g_slice_new (GISourceComment); - comment->comment = g_string_free (string, FALSE); - comment->line = comment_lineno; - comment->filename = g_strdup(scanner->current_filename); + while (c2 != EOF && !(c1 == '*' && c2 == '/')) + { + if (!skip) + g_string_append_c (string, c1); - scanner->comments = g_slist_prepend (scanner->comments, - comment); -} + if (c1 == '\n') + lineno++; -static void -parse_comment (GISourceScanner *scanner) -{ - int c1, c2; + c1 = c2; + c2 = input(); + } - c1 = input(); - c2 = input(); + if (skip) { + return; + } - while (c2 != EOF && !(c1 == '*' && c2 == '/')) - { - if (c1 == '\n') - lineno++; + g_string_append (string, "*/"); - c1 = c2; - c2 = input(); - } + comment = g_slice_new (GISourceComment); + comment->comment = g_string_free (string, FALSE); + comment->line = comment_lineno; + comment->filename = g_strdup(scanner->current_filename); - return; + scanner->comments = g_slist_prepend (scanner->comments, + comment); + } else { + /* + * Ignore all other comment blocks + */ + while (c2 != EOF && !(c1 == '*' && c2 == '/')) + { + if (c1 == '\n') + lineno++; + + c1 = c2; + c2 = input(); + } + + return; + } } static int diff --git a/tests/scanner/annotationparser/test_patterns.py b/tests/scanner/annotationparser/test_patterns.py index ed687a43..d5da82b6 100644 --- a/tests/scanner/annotationparser/test_patterns.py +++ b/tests/scanner/annotationparser/test_patterns.py @@ -84,6 +84,8 @@ comment_start_tests = [ None), (COMMENT_BLOCK_START_RE, ' /*****xyz', None), + (COMMENT_BLOCK_START_RE, ' /**/', + None), ] |