diff options
author | Florian Frank <flori@ping.de> | 2016-07-01 16:00:10 +0200 |
---|---|---|
committer | Florian Frank <flori@ping.de> | 2016-07-01 16:00:10 +0200 |
commit | 4219871ff5ac9752fce7b8b23296e9aeae8e42ff (patch) | |
tree | aa1e779c17e34576429ef22a804a101c29c2b700 | |
parent | d5115edb0ea309620e09c9970a5add4bbb2abac4 (diff) | |
download | json-4219871ff5ac9752fce7b8b23296e9aeae8e42ff.tar.gz |
Stores current nesting on stack
-rw-r--r-- | ext/json/ext/parser/parser.c | 127 | ||||
-rw-r--r-- | ext/json/ext/parser/parser.h | 7 | ||||
-rw-r--r-- | ext/json/ext/parser/parser.rl | 29 |
3 files changed, 76 insertions, 87 deletions
diff --git a/ext/json/ext/parser/parser.c b/ext/json/ext/parser/parser.c index a65d17d..975a267 100644 --- a/ext/json/ext/parser/parser.c +++ b/ext/json/ext/parser/parser.c @@ -113,14 +113,14 @@ enum {JSON_object_en_main = 1}; #line 165 "parser.rl" -static char *JSON_parse_object(JSON_Parser *json, char *p, char *pe, VALUE *result) +static char *JSON_parse_object(JSON_Parser *json, char *p, char *pe, VALUE *result, int current_nesting) { int cs = EVIL; VALUE last_name = Qnil; VALUE object_class = json->object_class; - if (json->max_nesting && json->current_nesting > json->max_nesting) { - rb_raise(eNestingError, "nesting of %d is too deep", json->current_nesting); + if (json->max_nesting && current_nesting > json->max_nesting) { + rb_raise(eNestingError, "nesting of %d is too deep", current_nesting); } *result = NIL_P(object_class) ? rb_hash_new() : rb_class_new_instance(0, 0, object_class); @@ -244,7 +244,7 @@ tr11: #line 132 "parser.rl" { VALUE v = Qnil; - char *np = JSON_parse_value(json, p, pe, &v); + char *np = JSON_parse_value(json, p, pe, &v, current_nesting); if (np == NULL) { p--; {p++; cs = 9; goto _out;} } else { @@ -488,10 +488,10 @@ enum {JSON_value_error = 0}; enum {JSON_value_en_main = 1}; -#line 285 "parser.rl" +#line 281 "parser.rl" -static char *JSON_parse_value(JSON_Parser *json, char *p, char *pe, VALUE *result) +static char *JSON_parse_value(JSON_Parser *json, char *p, char *pe, VALUE *result, int current_nesting) { int cs = EVIL; @@ -501,7 +501,7 @@ static char *JSON_parse_value(JSON_Parser *json, char *p, char *pe, VALUE *resul cs = JSON_value_start; } -#line 292 "parser.rl" +#line 288 "parser.rl" #line 507 "parser.c" { @@ -567,19 +567,15 @@ tr7: #line 256 "parser.rl" { char *np; - json->current_nesting++; - np = JSON_parse_array(json, p, pe, result); - json->current_nesting--; + np = JSON_parse_array(json, p, pe, result, current_nesting + 1); if (np == NULL) { p--; {p++; cs = 29; goto _out;} } else {p = (( np))-1;} } goto st29; tr11: -#line 264 "parser.rl" +#line 262 "parser.rl" { char *np; - json->current_nesting++; - np = JSON_parse_object(json, p, pe, result); - json->current_nesting--; + np = JSON_parse_object(json, p, pe, result, current_nesting + 1); if (np == NULL) { p--; {p++; cs = 29; goto _out;} } else {p = (( np))-1;} } goto st29; @@ -625,9 +621,9 @@ st29: if ( ++p == pe ) goto _test_eof29; case 29: -#line 272 "parser.rl" +#line 268 "parser.rl" { p--; {p++; cs = 29; goto _out;} } -#line 631 "parser.c" +#line 627 "parser.c" switch( (*p) ) { case 13: goto st29; case 32: goto st29; @@ -868,7 +864,7 @@ case 28: _out: {} } -#line 293 "parser.rl" +#line 289 "parser.rl" if (cs >= JSON_value_first_final) { return p; @@ -878,7 +874,7 @@ case 28: } -#line 882 "parser.c" +#line 878 "parser.c" enum {JSON_integer_start = 1}; enum {JSON_integer_first_final = 3}; enum {JSON_integer_error = 0}; @@ -886,7 +882,7 @@ enum {JSON_integer_error = 0}; enum {JSON_integer_en_main = 1}; -#line 309 "parser.rl" +#line 305 "parser.rl" static char *JSON_parse_integer(JSON_Parser *json, char *p, char *pe, VALUE *result) @@ -894,15 +890,15 @@ static char *JSON_parse_integer(JSON_Parser *json, char *p, char *pe, VALUE *res int cs = EVIL; -#line 898 "parser.c" +#line 894 "parser.c" { cs = JSON_integer_start; } -#line 316 "parser.rl" +#line 312 "parser.rl" json->memo = p; -#line 906 "parser.c" +#line 902 "parser.c" { if ( p == pe ) goto _test_eof; @@ -936,14 +932,14 @@ case 3: goto st0; goto tr4; tr4: -#line 306 "parser.rl" +#line 302 "parser.rl" { p--; {p++; cs = 4; goto _out;} } goto st4; st4: if ( ++p == pe ) goto _test_eof4; case 4: -#line 947 "parser.c" +#line 943 "parser.c" goto st0; st5: if ( ++p == pe ) @@ -962,7 +958,7 @@ case 5: _out: {} } -#line 318 "parser.rl" +#line 314 "parser.rl" if (cs >= JSON_integer_first_final) { long len = p - json->memo; @@ -977,7 +973,7 @@ case 5: } -#line 981 "parser.c" +#line 977 "parser.c" enum {JSON_float_start = 1}; enum {JSON_float_first_final = 8}; enum {JSON_float_error = 0}; @@ -985,7 +981,7 @@ enum {JSON_float_error = 0}; enum {JSON_float_en_main = 1}; -#line 343 "parser.rl" +#line 339 "parser.rl" static char *JSON_parse_float(JSON_Parser *json, char *p, char *pe, VALUE *result) @@ -993,15 +989,15 @@ static char *JSON_parse_float(JSON_Parser *json, char *p, char *pe, VALUE *resul int cs = EVIL; -#line 997 "parser.c" +#line 993 "parser.c" { cs = JSON_float_start; } -#line 350 "parser.rl" +#line 346 "parser.rl" json->memo = p; -#line 1005 "parser.c" +#line 1001 "parser.c" { if ( p == pe ) goto _test_eof; @@ -1059,14 +1055,14 @@ case 8: goto st0; goto tr9; tr9: -#line 337 "parser.rl" +#line 333 "parser.rl" { p--; {p++; cs = 9; goto _out;} } goto st9; st9: if ( ++p == pe ) goto _test_eof9; case 9: -#line 1070 "parser.c" +#line 1066 "parser.c" goto st0; st5: if ( ++p == pe ) @@ -1127,7 +1123,7 @@ case 7: _out: {} } -#line 352 "parser.rl" +#line 348 "parser.rl" if (cs >= JSON_float_first_final) { long len = p - json->memo; @@ -1143,7 +1139,7 @@ case 7: -#line 1147 "parser.c" +#line 1143 "parser.c" enum {JSON_array_start = 1}; enum {JSON_array_first_final = 17}; enum {JSON_array_error = 0}; @@ -1151,28 +1147,28 @@ enum {JSON_array_error = 0}; enum {JSON_array_en_main = 1}; -#line 395 "parser.rl" +#line 391 "parser.rl" -static char *JSON_parse_array(JSON_Parser *json, char *p, char *pe, VALUE *result) +static char *JSON_parse_array(JSON_Parser *json, char *p, char *pe, VALUE *result, int current_nesting) { int cs = EVIL; VALUE array_class = json->array_class; - if (json->max_nesting && json->current_nesting > json->max_nesting) { - rb_raise(eNestingError, "nesting of %d is too deep", json->current_nesting); + if (json->max_nesting && current_nesting > json->max_nesting) { + rb_raise(eNestingError, "nesting of %d is too deep", current_nesting); } *result = NIL_P(array_class) ? rb_ary_new() : rb_class_new_instance(0, 0, array_class); -#line 1169 "parser.c" +#line 1165 "parser.c" { cs = JSON_array_start; } -#line 408 "parser.rl" +#line 404 "parser.rl" -#line 1176 "parser.c" +#line 1172 "parser.c" { if ( p == pe ) goto _test_eof; @@ -1211,10 +1207,10 @@ case 2: goto st2; goto st0; tr2: -#line 372 "parser.rl" +#line 368 "parser.rl" { VALUE v = Qnil; - char *np = JSON_parse_value(json, p, pe, &v); + char *np = JSON_parse_value(json, p, pe, &v, current_nesting); if (np == NULL) { p--; {p++; cs = 3; goto _out;} } else { @@ -1231,7 +1227,7 @@ st3: if ( ++p == pe ) goto _test_eof3; case 3: -#line 1235 "parser.c" +#line 1231 "parser.c" switch( (*p) ) { case 13: goto st3; case 32: goto st3; @@ -1331,14 +1327,14 @@ case 12: goto st3; goto st12; tr4: -#line 387 "parser.rl" +#line 383 "parser.rl" { p--; {p++; cs = 17; goto _out;} } goto st17; st17: if ( ++p == pe ) goto _test_eof17; case 17: -#line 1342 "parser.c" +#line 1338 "parser.c" goto st0; st13: if ( ++p == pe ) @@ -1394,7 +1390,7 @@ case 16: _out: {} } -#line 409 "parser.rl" +#line 405 "parser.rl" if(cs >= JSON_array_first_final) { return p + 1; @@ -1475,7 +1471,7 @@ static VALUE json_string_unescape(VALUE result, char *string, char *stringEnd) } -#line 1479 "parser.c" +#line 1475 "parser.c" enum {JSON_string_start = 1}; enum {JSON_string_first_final = 8}; enum {JSON_string_error = 0}; @@ -1483,7 +1479,7 @@ enum {JSON_string_error = 0}; enum {JSON_string_en_main = 1}; -#line 508 "parser.rl" +#line 504 "parser.rl" static int @@ -1505,15 +1501,15 @@ static char *JSON_parse_string(JSON_Parser *json, char *p, char *pe, VALUE *resu *result = rb_str_buf_new(0); -#line 1509 "parser.c" +#line 1505 "parser.c" { cs = JSON_string_start; } -#line 529 "parser.rl" +#line 525 "parser.rl" json->memo = p; -#line 1517 "parser.c" +#line 1513 "parser.c" { if ( p == pe ) goto _test_eof; @@ -1538,7 +1534,7 @@ case 2: goto st0; goto st2; tr2: -#line 494 "parser.rl" +#line 490 "parser.rl" { *result = json_string_unescape(*result, json->memo + 1, p); if (NIL_P(*result)) { @@ -1549,14 +1545,14 @@ tr2: {p = (( p + 1))-1;} } } -#line 505 "parser.rl" +#line 501 "parser.rl" { p--; {p++; cs = 8; goto _out;} } goto st8; st8: if ( ++p == pe ) goto _test_eof8; case 8: -#line 1560 "parser.c" +#line 1556 "parser.c" goto st0; st3: if ( ++p == pe ) @@ -1632,7 +1628,7 @@ case 7: _out: {} } -#line 531 "parser.rl" +#line 527 "parser.rl" if (json->create_additions && RTEST(match_string = json->match_string)) { VALUE klass; @@ -1801,7 +1797,6 @@ static VALUE cParser_initialize(int argc, VALUE *argv, VALUE self) json->array_class = Qnil; } source = convert_encoding(StringValue(source)); - json->current_nesting = 0; StringValue(source); json->len = RSTRING_LEN(source); json->source = RSTRING_PTR(source);; @@ -1810,7 +1805,7 @@ static VALUE cParser_initialize(int argc, VALUE *argv, VALUE self) } -#line 1814 "parser.c" +#line 1809 "parser.c" enum {JSON_start = 1}; enum {JSON_first_final = 10}; enum {JSON_error = 0}; @@ -1818,7 +1813,7 @@ enum {JSON_error = 0}; enum {JSON_en_main = 1}; -#line 722 "parser.rl" +#line 717 "parser.rl" /* @@ -1835,16 +1830,16 @@ static VALUE cParser_parse(VALUE self) GET_PARSER; -#line 1839 "parser.c" +#line 1834 "parser.c" { cs = JSON_start; } -#line 738 "parser.rl" +#line 733 "parser.rl" p = json->source; pe = p + json->len; -#line 1848 "parser.c" +#line 1843 "parser.c" { if ( p == pe ) goto _test_eof; @@ -1878,9 +1873,9 @@ st0: cs = 0; goto _out; tr2: -#line 714 "parser.rl" +#line 709 "parser.rl" { - char *np = JSON_parse_value(json, p, pe, &result); + char *np = JSON_parse_value(json, p, pe, &result, 0); if (np == NULL) { p--; {p++; cs = 10; goto _out;} } else {p = (( np))-1;} } goto st10; @@ -1888,7 +1883,7 @@ st10: if ( ++p == pe ) goto _test_eof10; case 10: -#line 1892 "parser.c" +#line 1887 "parser.c" switch( (*p) ) { case 13: goto st10; case 32: goto st10; @@ -1977,7 +1972,7 @@ case 9: _out: {} } -#line 741 "parser.rl" +#line 736 "parser.rl" if (cs >= JSON_first_final && p == pe) { return result; diff --git a/ext/json/ext/parser/parser.h b/ext/json/ext/parser/parser.h index ec26e85..1d46831 100644 --- a/ext/json/ext/parser/parser.h +++ b/ext/json/ext/parser/parser.h @@ -34,7 +34,6 @@ typedef struct JSON_ParserStruct { char *memo; VALUE create_id; int max_nesting; - int current_nesting; int allow_nan; int parsing_name; int symbolize_names; @@ -57,11 +56,11 @@ typedef struct JSON_ParserStruct { static UTF32 unescape_unicode(const unsigned char *p); static int convert_UTF32_to_UTF8(char *buf, UTF32 ch); -static char *JSON_parse_object(JSON_Parser *json, char *p, char *pe, VALUE *result); -static char *JSON_parse_value(JSON_Parser *json, char *p, char *pe, VALUE *result); +static char *JSON_parse_object(JSON_Parser *json, char *p, char *pe, VALUE *result, int current_nesting); +static char *JSON_parse_value(JSON_Parser *json, char *p, char *pe, VALUE *result, int current_nesting); static char *JSON_parse_integer(JSON_Parser *json, char *p, char *pe, VALUE *result); static char *JSON_parse_float(JSON_Parser *json, char *p, char *pe, VALUE *result); -static char *JSON_parse_array(JSON_Parser *json, char *p, char *pe, VALUE *result); +static char *JSON_parse_array(JSON_Parser *json, char *p, char *pe, VALUE *result, int current_nesting); static VALUE json_string_unescape(VALUE result, char *string, char *stringEnd); static char *JSON_parse_string(JSON_Parser *json, char *p, char *pe, VALUE *result); static VALUE convert_encoding(VALUE source); diff --git a/ext/json/ext/parser/parser.rl b/ext/json/ext/parser/parser.rl index eac3e6c..c67634b 100644 --- a/ext/json/ext/parser/parser.rl +++ b/ext/json/ext/parser/parser.rl @@ -131,7 +131,7 @@ static ID i_json_creatable_p, i_json_create, i_create_id, i_create_additions, action parse_value { VALUE v = Qnil; - char *np = JSON_parse_value(json, fpc, pe, &v); + char *np = JSON_parse_value(json, fpc, pe, &v, current_nesting); if (np == NULL) { fhold; fbreak; } else { @@ -164,14 +164,14 @@ static ID i_json_creatable_p, i_json_create, i_create_id, i_create_additions, ) @exit; }%% -static char *JSON_parse_object(JSON_Parser *json, char *p, char *pe, VALUE *result) +static char *JSON_parse_object(JSON_Parser *json, char *p, char *pe, VALUE *result, int current_nesting) { int cs = EVIL; VALUE last_name = Qnil; VALUE object_class = json->object_class; - if (json->max_nesting && json->current_nesting > json->max_nesting) { - rb_raise(eNestingError, "nesting of %d is too deep", json->current_nesting); + if (json->max_nesting && current_nesting > json->max_nesting) { + rb_raise(eNestingError, "nesting of %d is too deep", current_nesting); } *result = NIL_P(object_class) ? rb_hash_new() : rb_class_new_instance(0, 0, object_class); @@ -255,17 +255,13 @@ static char *JSON_parse_object(JSON_Parser *json, char *p, char *pe, VALUE *resu action parse_array { char *np; - json->current_nesting++; - np = JSON_parse_array(json, fpc, pe, result); - json->current_nesting--; + np = JSON_parse_array(json, fpc, pe, result, current_nesting + 1); if (np == NULL) { fhold; fbreak; } else fexec np; } action parse_object { char *np; - json->current_nesting++; - np = JSON_parse_object(json, fpc, pe, result); - json->current_nesting--; + np = JSON_parse_object(json, fpc, pe, result, current_nesting + 1); if (np == NULL) { fhold; fbreak; } else fexec np; } @@ -284,7 +280,7 @@ main := ignore* ( ) ignore* %*exit; }%% -static char *JSON_parse_value(JSON_Parser *json, char *p, char *pe, VALUE *result) +static char *JSON_parse_value(JSON_Parser *json, char *p, char *pe, VALUE *result, int current_nesting) { int cs = EVIL; @@ -371,7 +367,7 @@ static char *JSON_parse_float(JSON_Parser *json, char *p, char *pe, VALUE *resul action parse_value { VALUE v = Qnil; - char *np = JSON_parse_value(json, fpc, pe, &v); + char *np = JSON_parse_value(json, fpc, pe, &v, current_nesting); if (np == NULL) { fhold; fbreak; } else { @@ -394,13 +390,13 @@ static char *JSON_parse_float(JSON_Parser *json, char *p, char *pe, VALUE *resul end_array @exit; }%% -static char *JSON_parse_array(JSON_Parser *json, char *p, char *pe, VALUE *result) +static char *JSON_parse_array(JSON_Parser *json, char *p, char *pe, VALUE *result, int current_nesting) { int cs = EVIL; VALUE array_class = json->array_class; - if (json->max_nesting && json->current_nesting > json->max_nesting) { - rb_raise(eNestingError, "nesting of %d is too deep", json->current_nesting); + if (json->max_nesting && current_nesting > json->max_nesting) { + rb_raise(eNestingError, "nesting of %d is too deep", current_nesting); } *result = NIL_P(array_class) ? rb_ary_new() : rb_class_new_instance(0, 0, array_class); @@ -696,7 +692,6 @@ static VALUE cParser_initialize(int argc, VALUE *argv, VALUE self) json->array_class = Qnil; } source = convert_encoding(StringValue(source)); - json->current_nesting = 0; StringValue(source); json->len = RSTRING_LEN(source); json->source = RSTRING_PTR(source);; @@ -712,7 +707,7 @@ static VALUE cParser_initialize(int argc, VALUE *argv, VALUE self) include JSON_common; action parse_value { - char *np = JSON_parse_value(json, fpc, pe, &result); + char *np = JSON_parse_value(json, fpc, pe, &result, 0); if (np == NULL) { fhold; fbreak; } else fexec np; } |