json 1.5.3 → 1.5.4

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of json might be problematic. Click here for more details.

data/CHANGES CHANGED
@@ -1,3 +1,11 @@
1
+ 2011-08-31 (1.5.4)
2
+ * Fix memory leak when used from multiple JRuby. (Patch by
3
+ jfirebaugh@github).
4
+ * Apply patch by Eric Wong <nocode@yhbt.net> that fixes garbage collection problem
5
+ reported in https://github.com/flori/json/issues/46.
6
+ * Add :quirks_mode option to parser and generator.
7
+ * Add support for Rational and Complex number additions via json/add/complex
8
+ and json/add/rational requires.
1
9
  2011-06-20 (1.5.3)
2
10
  * Alias State#configure method as State#merge to increase duck type synonymy with Hash.
3
11
  * Add as_json methods in json/add/core, so rails can create its json objects
data/Gemfile CHANGED
@@ -2,8 +2,6 @@
2
2
 
3
3
  source :rubygems
4
4
 
5
- group :test do
6
- gem 'permutation', '~>0.1'
7
- gem 'test-unit', '~>2.3'
8
- gem 'rake', '~>0.9'
9
- end
5
+ gemspec :name => 'json'
6
+ gemspec :name => 'json_pure'
7
+ gemspec :name => 'json-java'
data/Rakefile CHANGED
@@ -4,7 +4,12 @@ rescue LoadError
4
4
  end
5
5
 
6
6
  require 'rbconfig'
7
- include Config
7
+ begin
8
+ include RbConfig
9
+ rescue NameError
10
+ include Config
11
+ end
12
+
8
13
 
9
14
  require 'rake/clean'
10
15
  CLOBBER.include Dir['benchmarks/data/*.{dat,log}'], 'doc', 'Gemfile.lock'
@@ -63,6 +68,7 @@ task :install_ext_really do
63
68
  mkdir_p File.dirname(d)
64
69
  install(file, d)
65
70
  end
71
+ warn " *** Installed EXT ruby library."
66
72
  end
67
73
  end
68
74
 
@@ -89,6 +95,8 @@ if defined?(Gem) and defined?(Gem::PackageTask)
89
95
  s.add_development_dependency 'permutation'
90
96
  s.add_development_dependency 'bullshit'
91
97
  s.add_development_dependency 'sdoc'
98
+ s.add_development_dependency 'rake', '~>0.9.2'
99
+ s.add_dependency 'spruz', '~>0.2.8'
92
100
 
93
101
  s.bindir = "bin"
94
102
  s.executables = [ "edit_json.rb", "prettify_json.rb" ]
@@ -191,7 +199,22 @@ end
191
199
  desc "Testing library (pure ruby and extension)"
192
200
  task :test => [ :test_pure, :test_ext ]
193
201
 
202
+ namespace :gems do
203
+ task :install do
204
+ sh 'bundle'
205
+ end
206
+ end
207
+
194
208
  if defined?(RUBY_ENGINE) and RUBY_ENGINE == 'jruby'
209
+ if ENV.key?('JAVA_HOME')
210
+ warn " *** JAVA_HOME was set to #{ENV['JAVA_HOME'].inspect}"
211
+ else File.directory?(local_java = '/usr/local/java/jdk')
212
+ ENV['JAVA_HOME'] = local_java
213
+ warn " *** JAVA_HOME is set to #{ENV['JAVA_HOME'].inspect}"
214
+ ENV['PATH'] = ENV['PATH'].split(/:/).unshift(java_path = "#{ENV['JAVA_HOME']}/bin") * ':'
215
+ warn " *** java binaries are assumed to be in #{java_path.inspect}"
216
+ end
217
+
195
218
  file JAVA_PARSER_SRC => JAVA_RAGEL_PATH do
196
219
  cd JAVA_DIR do
197
220
  if RAGEL_CODEGEN == 'ragel'
@@ -210,7 +233,7 @@ if defined?(RUBY_ENGINE) and RUBY_ENGINE == 'jruby'
210
233
  rm_rf JAVA_PARSER_SRC
211
234
  end
212
235
 
213
- JRUBY_JAR = File.join(Config::CONFIG["libdir"], "jruby.jar")
236
+ JRUBY_JAR = File.join(CONFIG["libdir"], "jruby.jar")
214
237
  if File.exist?(JRUBY_JAR)
215
238
  JAVA_SOURCES.each do |src|
216
239
  classpath = (Dir['java/lib/*.jar'] << 'java/src' << JRUBY_JAR) * ':'
@@ -280,7 +303,9 @@ if defined?(RUBY_ENGINE) and RUBY_ENGINE == 'jruby'
280
303
  task :create_jar => [ :create_parser_jar, :create_generator_jar ]
281
304
 
282
305
  desc "Build all gems and archives for a new release of the jruby extension."
283
- task :release => [ :clean, :version, :jruby_gem ]
306
+ task :build => [ :clean, :version, :jruby_gem ]
307
+
308
+ task :release => :build
284
309
  else
285
310
  desc "Compiling extension"
286
311
  task :compile => [ EXT_PARSER_DL, EXT_GENERATOR_DL ]
@@ -345,6 +370,8 @@ else
345
370
  else
346
371
  sh "ragel -x parser.rl | #{RAGEL_CODEGEN} -G2"
347
372
  end
373
+ src = File.read("parser.c").gsub(/[ \t]+$/, '')
374
+ File.open("parser.c", "w") {|f| f.print src}
348
375
  end
349
376
  end
350
377
 
@@ -380,8 +407,10 @@ else
380
407
  task :ragel_dot => [ :ragel_dot_png, :ragel_dot_ps ]
381
408
 
382
409
  desc "Build all gems and archives for a new release of json and json_pure."
383
- task :release => [ :clean, :gemspec, :package ]
410
+ task :build => [ :clean, :gemspec, :package ]
411
+
412
+ task :release => :build
384
413
  end
385
414
 
386
415
  desc "Compile in the the source directory"
387
- task :default => [ :clean, :gemspec, :compile ]
416
+ task :default => [ :clean, :gemspec, :test ]
data/VERSION CHANGED
@@ -1 +1 @@
1
- 1.5.3
1
+ 1.5.4
@@ -3,37 +3,8 @@
3
3
  require 'json'
4
4
  require 'fileutils'
5
5
  include FileUtils
6
-
7
- # Parses the argument array _args_, according to the pattern _s_, to
8
- # retrieve the single character command line options from it. If _s_ is
9
- # 'xy:' an option '-x' without an option argument is searched, and an
10
- # option '-y foo' with an option argument ('foo').
11
- #
12
- # An option hash is returned with all found options set to true or the
13
- # found option argument.
14
- def go(s, args = ARGV)
15
- b, v = s.scan(/(.)(:?)/).inject([{},{}]) { |t,(o,a)|
16
- t[a.empty? ? 0 : 1][o] = a.empty? ? false : nil
17
- t
18
- }
19
- while a = args.shift
20
- a !~ /\A-(.+)/ and args.unshift a and break
21
- p = $1
22
- until p == ''
23
- o = p.slice!(0, 1)
24
- if v.key?(o)
25
- v[o] = if p == '' then args.shift or break 1 else p end
26
- break
27
- elsif b.key?(o)
28
- b[o] = true
29
- else
30
- args.unshift a
31
- break 1
32
- end
33
- end and break
34
- end
35
- b.merge(v)
36
- end
6
+ require 'spruz/go'
7
+ include Spruz::GO
37
8
 
38
9
  opts = go 'slhi:', args = ARGV.dup
39
10
  if opts['h'] || opts['l'] && opts['s']
@@ -52,19 +23,21 @@ EOT
52
23
  exit 0
53
24
  end
54
25
 
55
- filename = nil
56
- json = JSON[
57
- if args.empty?
58
- STDIN.read
26
+ json_opts = { :max_nesting => false, :create_additions => false }
27
+
28
+ document =
29
+ if filename = args.first or filename == '-'
30
+ File.read(filename)
59
31
  else
60
- File.read filename = args.first
32
+ STDIN.read
61
33
  end
62
- ]
34
+
35
+ json = JSON.parse document, json_opts
63
36
 
64
37
  output = if opts['s']
65
- JSON.fast_generate json
38
+ JSON.fast_generate json, json_opts
66
39
  else # default is -l
67
- JSON.pretty_generate json
40
+ JSON.pretty_generate json, json_opts
68
41
  end
69
42
 
70
43
  if opts['i'] && filename
@@ -13,14 +13,14 @@ static VALUE mJSON, mExt, mGenerator, cState, mGeneratorMethods, mObject,
13
13
 
14
14
  static ID i_to_s, i_to_json, i_new, i_indent, i_space, i_space_before,
15
15
  i_object_nl, i_array_nl, i_max_nesting, i_allow_nan, i_ascii_only,
16
- i_pack, i_unpack, i_create_id, i_extend, i_key_p, i_aref, i_send,
17
- i_respond_to_p, i_match, i_keys, i_depth, i_dup;
16
+ i_quirks_mode, i_pack, i_unpack, i_create_id, i_extend, i_key_p,
17
+ i_aref, i_send, i_respond_to_p, i_match, i_keys, i_depth, i_dup;
18
18
 
19
19
  /*
20
20
  * Copyright 2001-2004 Unicode, Inc.
21
- *
21
+ *
22
22
  * Disclaimer
23
- *
23
+ *
24
24
  * This source code is provided as is by Unicode, Inc. No claims are
25
25
  * made as to fitness for any particular purpose. No warranties of any
26
26
  * kind are expressed or implied. The recipient agrees to determine
@@ -28,9 +28,9 @@ static ID i_to_s, i_to_json, i_new, i_indent, i_space, i_space_before,
28
28
  * purchased on magnetic or optical media from Unicode, Inc., the
29
29
  * sole remedy for any claim will be exchange of defective media
30
30
  * within 90 days of receipt.
31
- *
31
+ *
32
32
  * Limitations on Rights to Redistribute This Code
33
- *
33
+ *
34
34
  * Unicode, Inc. hereby grants the right to freely use the information
35
35
  * supplied in this file in the creation of products supporting the
36
36
  * Unicode Standard, and to make copies of this file in any form
@@ -61,7 +61,7 @@ static const char trailingBytesForUTF8[256] = {
61
61
  * This table contains as many values as there might be trailing bytes
62
62
  * in a UTF-8 sequence.
63
63
  */
64
- static const UTF32 offsetsFromUTF8[6] = { 0x00000000UL, 0x00003080UL, 0x000E2080UL,
64
+ static const UTF32 offsetsFromUTF8[6] = { 0x00000000UL, 0x00003080UL, 0x000E2080UL,
65
65
  0x03C82080UL, 0xFA082080UL, 0x82082080UL };
66
66
 
67
67
  /*
@@ -318,11 +318,6 @@ static void fbuffer_free(FBuffer *fb)
318
318
  ruby_xfree(fb);
319
319
  }
320
320
 
321
- static void fbuffer_free_only_buffer(FBuffer *fb)
322
- {
323
- ruby_xfree(fb);
324
- }
325
-
326
321
  static void fbuffer_clear(FBuffer *fb)
327
322
  {
328
323
  fb->len = 0;
@@ -354,6 +349,16 @@ static void fbuffer_append(FBuffer *fb, const char *newstr, unsigned long len)
354
349
  }
355
350
  }
356
351
 
352
+ static void fbuffer_append_str(FBuffer *fb, VALUE str)
353
+ {
354
+ const char *newstr = StringValuePtr(str);
355
+ unsigned long len = RSTRING_LEN(str);
356
+
357
+ RB_GC_GUARD(str);
358
+
359
+ fbuffer_append(fb, newstr, len);
360
+ }
361
+
357
362
  static void fbuffer_append_char(FBuffer *fb, char newchr)
358
363
  {
359
364
  fbuffer_inc_capa(fb, 1);
@@ -404,7 +409,7 @@ static FBuffer *fbuffer_dup(FBuffer *fb)
404
409
  return result;
405
410
  }
406
411
 
407
- /*
412
+ /*
408
413
  * Document-module: JSON::Ext::Generator
409
414
  *
410
415
  * This is the JSON generator implemented as a C extension. It can be
@@ -693,6 +698,8 @@ static VALUE cState_configure(VALUE self, VALUE opts)
693
698
  state->allow_nan = RTEST(tmp);
694
699
  tmp = rb_hash_aref(opts, ID2SYM(i_ascii_only));
695
700
  state->ascii_only = RTEST(tmp);
701
+ tmp = rb_hash_aref(opts, ID2SYM(i_quirks_mode));
702
+ state->quirks_mode = RTEST(tmp);
696
703
  return self;
697
704
  }
698
705
 
@@ -713,6 +720,7 @@ static VALUE cState_to_h(VALUE self)
713
720
  rb_hash_aset(result, ID2SYM(i_array_nl), rb_str_new(state->array_nl, state->array_nl_len));
714
721
  rb_hash_aset(result, ID2SYM(i_allow_nan), state->allow_nan ? Qtrue : Qfalse);
715
722
  rb_hash_aset(result, ID2SYM(i_ascii_only), state->ascii_only ? Qtrue : Qfalse);
723
+ rb_hash_aset(result, ID2SYM(i_quirks_mode), state->quirks_mode ? Qtrue : Qfalse);
716
724
  rb_hash_aset(result, ID2SYM(i_max_nesting), LONG2FIX(state->max_nesting));
717
725
  rb_hash_aset(result, ID2SYM(i_depth), LONG2FIX(state->depth));
718
726
  return result;
@@ -857,7 +865,7 @@ static void generate_json_fixnum(FBuffer *buffer, VALUE Vstate, JSON_Generator_S
857
865
  static void generate_json_bignum(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj)
858
866
  {
859
867
  VALUE tmp = rb_funcall(obj, i_to_s, 0);
860
- fbuffer_append(buffer, RSTRING_PAIR(tmp));
868
+ fbuffer_append_str(buffer, tmp);
861
869
  }
862
870
 
863
871
  static void generate_json_float(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj)
@@ -874,7 +882,7 @@ static void generate_json_float(FBuffer *buffer, VALUE Vstate, JSON_Generator_St
874
882
  rb_raise(eGeneratorError, "%u: %s not allowed in JSON", __LINE__, StringValueCStr(tmp));
875
883
  }
876
884
  }
877
- fbuffer_append(buffer, RSTRING_PAIR(tmp));
885
+ fbuffer_append_str(buffer, tmp);
878
886
  }
879
887
 
880
888
  static void generate_json(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj)
@@ -902,7 +910,7 @@ static void generate_json(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *s
902
910
  } else if (rb_respond_to(obj, i_to_json)) {
903
911
  tmp = rb_funcall(obj, i_to_json, 1, Vstate);
904
912
  Check_Type(tmp, T_STRING);
905
- fbuffer_append(buffer, RSTRING_PAIR(tmp));
913
+ fbuffer_append_str(buffer, tmp);
906
914
  } else {
907
915
  tmp = rb_funcall(obj, i_to_s, 0);
908
916
  Check_Type(tmp, T_STRING);
@@ -966,11 +974,14 @@ static VALUE cState_generate(VALUE self, VALUE obj)
966
974
  {
967
975
  VALUE result = cState_partial_generate(self, obj);
968
976
  VALUE re, args[2];
969
- args[0] = rb_str_new2("\\A\\s*(?:\\[.*\\]|\\{.*\\})\\s*\\Z");
970
- args[1] = CRegexp_MULTILINE;
971
- re = rb_class_new_instance(2, args, rb_cRegexp);
972
- if (NIL_P(rb_funcall(re, i_match, 1, result))) {
973
- rb_raise(eGeneratorError, "only generation of JSON objects or arrays allowed");
977
+ GET_STATE(self);
978
+ if (!state->quirks_mode) {
979
+ args[0] = rb_str_new2("\\A\\s*(?:\\[.*\\]|\\{.*\\})\\s*\\Z");
980
+ args[1] = CRegexp_MULTILINE;
981
+ re = rb_class_new_instance(2, args, rb_cRegexp);
982
+ if (NIL_P(rb_funcall(re, i_match, 1, result))) {
983
+ rb_raise(eGeneratorError, "only generation of JSON objects or arrays allowed");
984
+ }
974
985
  }
975
986
  return result;
976
987
  }
@@ -985,11 +996,13 @@ static VALUE cState_generate(VALUE self, VALUE obj)
985
996
  * * *indent*: a string used to indent levels (default: ''),
986
997
  * * *space*: a string that is put after, a : or , delimiter (default: ''),
987
998
  * * *space_before*: a string that is put before a : pair delimiter (default: ''),
988
- * * *object_nl*: a string that is put at the end of a JSON object (default: ''),
999
+ * * *object_nl*: a string that is put at the end of a JSON object (default: ''),
989
1000
  * * *array_nl*: a string that is put at the end of a JSON array (default: ''),
990
1001
  * * *allow_nan*: true if NaN, Infinity, and -Infinity should be
991
1002
  * generated, otherwise an exception is thrown, if these values are
992
1003
  * encountered. This options defaults to false.
1004
+ * * *quirks_mode*: Enables quirks_mode for parser, that is for example
1005
+ * generating single JSON values instead of documents is possible.
993
1006
  */
994
1007
  static VALUE cState_initialize(int argc, VALUE *argv, VALUE self)
995
1008
  {
@@ -1292,6 +1305,29 @@ static VALUE cState_ascii_only_p(VALUE self)
1292
1305
  return state->ascii_only ? Qtrue : Qfalse;
1293
1306
  }
1294
1307
 
1308
+ /*
1309
+ * call-seq: quirks_mode?
1310
+ *
1311
+ * Returns true, if quirks mode is enabled. Otherwise returns false.
1312
+ */
1313
+ static VALUE cState_quirks_mode_p(VALUE self)
1314
+ {
1315
+ GET_STATE(self);
1316
+ return state->quirks_mode ? Qtrue : Qfalse;
1317
+ }
1318
+
1319
+ /*
1320
+ * call-seq: quirks_mode=(enable)
1321
+ *
1322
+ * If set to true, enables the quirks_mode mode.
1323
+ */
1324
+ static VALUE cState_quirks_mode_set(VALUE self, VALUE enable)
1325
+ {
1326
+ GET_STATE(self);
1327
+ state->quirks_mode = RTEST(enable);
1328
+ return Qnil;
1329
+ }
1330
+
1295
1331
  /*
1296
1332
  * call-seq: depth
1297
1333
  *
@@ -1350,6 +1386,9 @@ void Init_generator()
1350
1386
  rb_define_method(cState, "check_circular?", cState_check_circular_p, 0);
1351
1387
  rb_define_method(cState, "allow_nan?", cState_allow_nan_p, 0);
1352
1388
  rb_define_method(cState, "ascii_only?", cState_ascii_only_p, 0);
1389
+ rb_define_method(cState, "quirks_mode?", cState_quirks_mode_p, 0);
1390
+ rb_define_method(cState, "quirks_mode", cState_quirks_mode_p, 0);
1391
+ rb_define_method(cState, "quirks_mode=", cState_quirks_mode_set, 1);
1353
1392
  rb_define_method(cState, "depth", cState_depth, 0);
1354
1393
  rb_define_method(cState, "depth=", cState_depth_set, 1);
1355
1394
  rb_define_method(cState, "configure", cState_configure, 1);
@@ -1397,6 +1436,7 @@ void Init_generator()
1397
1436
  i_max_nesting = rb_intern("max_nesting");
1398
1437
  i_allow_nan = rb_intern("allow_nan");
1399
1438
  i_ascii_only = rb_intern("ascii_only");
1439
+ i_quirks_mode = rb_intern("quirks_mode");
1400
1440
  i_depth = rb_intern("depth");
1401
1441
  i_pack = rb_intern("pack");
1402
1442
  i_unpack = rb_intern("unpack");
@@ -45,7 +45,10 @@
45
45
  #define RSTRING_LEN(string) RSTRING(string)->len
46
46
  #endif
47
47
 
48
- #define RSTRING_PAIR(string) RSTRING_PTR(string), RSTRING_LEN(string)
48
+ /* We don't need to guard objects for rbx, so let's do nothing at all. */
49
+ #ifndef RB_GC_GUARD
50
+ #define RB_GC_GUARD(object)
51
+ #endif
49
52
 
50
53
  /* fbuffer implementation */
51
54
 
@@ -67,7 +70,6 @@ static char *fstrndup(const char *ptr, unsigned long len);
67
70
  static FBuffer *fbuffer_alloc();
68
71
  static FBuffer *fbuffer_alloc_with_length(unsigned long initial_length);
69
72
  static void fbuffer_free(FBuffer *fb);
70
- static void fbuffer_free_only_buffer(FBuffer *fb);
71
73
  static void fbuffer_clear(FBuffer *fb);
72
74
  static void fbuffer_append(FBuffer *fb, const char *newstr, unsigned long len);
73
75
  static void fbuffer_append_long(FBuffer *fb, long number);
@@ -124,6 +126,7 @@ typedef struct JSON_Generator_StateStruct {
124
126
  long max_nesting;
125
127
  char allow_nan;
126
128
  char ascii_only;
129
+ char quirks_mode;
127
130
  long depth;
128
131
  } JSON_Generator_State;
129
132
 
@@ -4,7 +4,7 @@
4
4
 
5
5
  /* unicode */
6
6
 
7
- static const char digit_values[256] = {
7
+ static const char digit_values[256] = {
8
8
  -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
9
9
  -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
10
10
  -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, -1,
@@ -40,7 +40,7 @@ static UTF32 unescape_unicode(const unsigned char *p)
40
40
  return result;
41
41
  }
42
42
 
43
- static int convert_UTF32_to_UTF8(char *buf, UTF32 ch)
43
+ static int convert_UTF32_to_UTF8(char *buf, UTF32 ch)
44
44
  {
45
45
  int len = 1;
46
46
  if (ch <= 0x7F) {
@@ -69,7 +69,7 @@ static int convert_UTF32_to_UTF8(char *buf, UTF32 ch)
69
69
  #ifdef HAVE_RUBY_ENCODING_H
70
70
  static VALUE CEncoding_ASCII_8BIT, CEncoding_UTF_8, CEncoding_UTF_16BE,
71
71
  CEncoding_UTF_16LE, CEncoding_UTF_32BE, CEncoding_UTF_32LE;
72
- static ID i_encoding, i_encode, i_encode_bang, i_force_encoding;
72
+ static ID i_encoding, i_encode;
73
73
  #else
74
74
  static ID i_iconv;
75
75
  #endif
@@ -78,15 +78,16 @@ static VALUE mJSON, mExt, cParser, eParserError, eNestingError;
78
78
  static VALUE CNaN, CInfinity, CMinusInfinity;
79
79
 
80
80
  static ID i_json_creatable_p, i_json_create, i_create_id, i_create_additions,
81
- i_chr, i_max_nesting, i_allow_nan, i_symbolize_names, i_object_class,
82
- i_array_class, i_key_p, i_deep_const_get, i_match, i_match_string, i_aset, i_leftshift;
81
+ i_chr, i_max_nesting, i_allow_nan, i_symbolize_names, i_quirks_mode,
82
+ i_object_class, i_array_class, i_key_p, i_deep_const_get, i_match,
83
+ i_match_string, i_aset, i_leftshift;
83
84
 
84
85
 
85
- #line 108 "parser.rl"
86
+ #line 109 "parser.rl"
86
87
 
87
88
 
88
89
 
89
- #line 90 "parser.c"
90
+ #line 91 "parser.c"
90
91
  static const int JSON_object_start = 1;
91
92
  static const int JSON_object_first_final = 27;
92
93
  static const int JSON_object_error = 0;
@@ -94,7 +95,7 @@ static const int JSON_object_error = 0;
94
95
  static const int JSON_object_en_main = 1;
95
96
 
96
97
 
97
- #line 148 "parser.rl"
98
+ #line 150 "parser.rl"
98
99
 
99
100
 
100
101
  static char *JSON_parse_object(JSON_Parser *json, char *p, char *pe, VALUE *result)
@@ -109,15 +110,15 @@ static char *JSON_parse_object(JSON_Parser *json, char *p, char *pe, VALUE *resu
109
110
 
110
111
  *result = NIL_P(object_class) ? rb_hash_new() : rb_class_new_instance(0, 0, object_class);
111
112
 
112
-
113
- #line 114 "parser.c"
113
+
114
+ #line 115 "parser.c"
114
115
  {
115
116
  cs = JSON_object_start;
116
117
  }
117
118
 
118
- #line 163 "parser.rl"
119
-
120
- #line 121 "parser.c"
119
+ #line 165 "parser.rl"
120
+
121
+ #line 122 "parser.c"
121
122
  {
122
123
  if ( p == pe )
123
124
  goto _test_eof;
@@ -145,7 +146,7 @@ case 2:
145
146
  goto st2;
146
147
  goto st0;
147
148
  tr2:
148
- #line 131 "parser.rl"
149
+ #line 132 "parser.rl"
149
150
  {
150
151
  char *np;
151
152
  json->parsing_name = 1;
@@ -158,7 +159,7 @@ st3:
158
159
  if ( ++p == pe )
159
160
  goto _test_eof3;
160
161
  case 3:
161
- #line 162 "parser.c"
162
+ #line 163 "parser.c"
162
163
  switch( (*p) ) {
163
164
  case 13: goto st3;
164
165
  case 32: goto st3;
@@ -225,17 +226,17 @@ case 8:
225
226
  goto st8;
226
227
  goto st0;
227
228
  tr11:
228
- #line 116 "parser.rl"
229
+ #line 117 "parser.rl"
229
230
  {
230
231
  VALUE v = Qnil;
231
- char *np = JSON_parse_value(json, p, pe, &v);
232
+ char *np = JSON_parse_value(json, p, pe, &v);
232
233
  if (np == NULL) {
233
234
  p--; {p++; cs = 9; goto _out;}
234
235
  } else {
235
236
  if (NIL_P(json->object_class)) {
236
- rb_hash_aset(*result, last_name, v);
237
+ rb_hash_aset(*result, last_name, v);
237
238
  } else {
238
- rb_funcall(*result, i_aset, 2, last_name, v);
239
+ rb_funcall(*result, i_aset, 2, last_name, v);
239
240
  }
240
241
  {p = (( np))-1;}
241
242
  }
@@ -245,7 +246,7 @@ st9:
245
246
  if ( ++p == pe )
246
247
  goto _test_eof9;
247
248
  case 9:
248
- #line 249 "parser.c"
249
+ #line 250 "parser.c"
249
250
  switch( (*p) ) {
250
251
  case 13: goto st9;
251
252
  case 32: goto st9;
@@ -334,14 +335,14 @@ case 18:
334
335
  goto st9;
335
336
  goto st18;
336
337
  tr4:
337
- #line 139 "parser.rl"
338
+ #line 140 "parser.rl"
338
339
  { p--; {p++; cs = 27; goto _out;} }
339
340
  goto st27;
340
341
  st27:
341
342
  if ( ++p == pe )
342
343
  goto _test_eof27;
343
344
  case 27:
344
- #line 345 "parser.c"
345
+ #line 346 "parser.c"
345
346
  goto st0;
346
347
  st19:
347
348
  if ( ++p == pe )
@@ -408,38 +409,38 @@ case 26:
408
409
  goto st2;
409
410
  goto st26;
410
411
  }
411
- _test_eof2: cs = 2; goto _test_eof;
412
- _test_eof3: cs = 3; goto _test_eof;
413
- _test_eof4: cs = 4; goto _test_eof;
414
- _test_eof5: cs = 5; goto _test_eof;
415
- _test_eof6: cs = 6; goto _test_eof;
416
- _test_eof7: cs = 7; goto _test_eof;
417
- _test_eof8: cs = 8; goto _test_eof;
418
- _test_eof9: cs = 9; goto _test_eof;
419
- _test_eof10: cs = 10; goto _test_eof;
420
- _test_eof11: cs = 11; goto _test_eof;
421
- _test_eof12: cs = 12; goto _test_eof;
422
- _test_eof13: cs = 13; goto _test_eof;
423
- _test_eof14: cs = 14; goto _test_eof;
424
- _test_eof15: cs = 15; goto _test_eof;
425
- _test_eof16: cs = 16; goto _test_eof;
426
- _test_eof17: cs = 17; goto _test_eof;
427
- _test_eof18: cs = 18; goto _test_eof;
428
- _test_eof27: cs = 27; goto _test_eof;
429
- _test_eof19: cs = 19; goto _test_eof;
430
- _test_eof20: cs = 20; goto _test_eof;
431
- _test_eof21: cs = 21; goto _test_eof;
432
- _test_eof22: cs = 22; goto _test_eof;
433
- _test_eof23: cs = 23; goto _test_eof;
434
- _test_eof24: cs = 24; goto _test_eof;
435
- _test_eof25: cs = 25; goto _test_eof;
436
- _test_eof26: cs = 26; goto _test_eof;
412
+ _test_eof2: cs = 2; goto _test_eof;
413
+ _test_eof3: cs = 3; goto _test_eof;
414
+ _test_eof4: cs = 4; goto _test_eof;
415
+ _test_eof5: cs = 5; goto _test_eof;
416
+ _test_eof6: cs = 6; goto _test_eof;
417
+ _test_eof7: cs = 7; goto _test_eof;
418
+ _test_eof8: cs = 8; goto _test_eof;
419
+ _test_eof9: cs = 9; goto _test_eof;
420
+ _test_eof10: cs = 10; goto _test_eof;
421
+ _test_eof11: cs = 11; goto _test_eof;
422
+ _test_eof12: cs = 12; goto _test_eof;
423
+ _test_eof13: cs = 13; goto _test_eof;
424
+ _test_eof14: cs = 14; goto _test_eof;
425
+ _test_eof15: cs = 15; goto _test_eof;
426
+ _test_eof16: cs = 16; goto _test_eof;
427
+ _test_eof17: cs = 17; goto _test_eof;
428
+ _test_eof18: cs = 18; goto _test_eof;
429
+ _test_eof27: cs = 27; goto _test_eof;
430
+ _test_eof19: cs = 19; goto _test_eof;
431
+ _test_eof20: cs = 20; goto _test_eof;
432
+ _test_eof21: cs = 21; goto _test_eof;
433
+ _test_eof22: cs = 22; goto _test_eof;
434
+ _test_eof23: cs = 23; goto _test_eof;
435
+ _test_eof24: cs = 24; goto _test_eof;
436
+ _test_eof25: cs = 25; goto _test_eof;
437
+ _test_eof26: cs = 26; goto _test_eof;
437
438
 
438
439
  _test_eof: {}
439
440
  _out: {}
440
441
  }
441
442
 
442
- #line 164 "parser.rl"
443
+ #line 166 "parser.rl"
443
444
 
444
445
  if (cs >= JSON_object_first_final) {
445
446
  if (json->create_additions) {
@@ -458,7 +459,8 @@ case 26:
458
459
  }
459
460
 
460
461
 
461
- #line 462 "parser.c"
462
+
463
+ #line 464 "parser.c"
462
464
  static const int JSON_value_start = 1;
463
465
  static const int JSON_value_first_final = 21;
464
466
  static const int JSON_value_error = 0;
@@ -466,22 +468,22 @@ static const int JSON_value_error = 0;
466
468
  static const int JSON_value_en_main = 1;
467
469
 
468
470
 
469
- #line 262 "parser.rl"
471
+ #line 265 "parser.rl"
470
472
 
471
473
 
472
474
  static char *JSON_parse_value(JSON_Parser *json, char *p, char *pe, VALUE *result)
473
475
  {
474
476
  int cs = EVIL;
475
477
 
476
-
477
- #line 478 "parser.c"
478
+
479
+ #line 480 "parser.c"
478
480
  {
479
481
  cs = JSON_value_start;
480
482
  }
481
483
 
482
- #line 269 "parser.rl"
483
-
484
- #line 485 "parser.c"
484
+ #line 272 "parser.rl"
485
+
486
+ #line 487 "parser.c"
485
487
  {
486
488
  if ( p == pe )
487
489
  goto _test_eof;
@@ -506,17 +508,17 @@ st0:
506
508
  cs = 0;
507
509
  goto _out;
508
510
  tr0:
509
- #line 210 "parser.rl"
511
+ #line 213 "parser.rl"
510
512
  {
511
513
  char *np = JSON_parse_string(json, p, pe, result);
512
514
  if (np == NULL) { p--; {p++; cs = 21; goto _out;} } else {p = (( np))-1;}
513
515
  }
514
516
  goto st21;
515
517
  tr2:
516
- #line 215 "parser.rl"
518
+ #line 218 "parser.rl"
517
519
  {
518
520
  char *np;
519
- if(pe > p + 9 && !strncmp(MinusInfinity, p, 9)) {
521
+ if(pe > p + 9 - json->quirks_mode && !strncmp(MinusInfinity, p, 9)) {
520
522
  if (json->allow_nan) {
521
523
  *result = CMinusInfinity;
522
524
  {p = (( p + 10))-1;}
@@ -533,8 +535,8 @@ tr2:
533
535
  }
534
536
  goto st21;
535
537
  tr5:
536
- #line 233 "parser.rl"
537
- {
538
+ #line 236 "parser.rl"
539
+ {
538
540
  char *np;
539
541
  json->current_nesting++;
540
542
  np = JSON_parse_array(json, p, pe, result);
@@ -543,8 +545,8 @@ tr5:
543
545
  }
544
546
  goto st21;
545
547
  tr9:
546
- #line 241 "parser.rl"
547
- {
548
+ #line 244 "parser.rl"
549
+ {
548
550
  char *np;
549
551
  json->current_nesting++;
550
552
  np = JSON_parse_object(json, p, pe, result);
@@ -553,7 +555,7 @@ tr9:
553
555
  }
554
556
  goto st21;
555
557
  tr16:
556
- #line 203 "parser.rl"
558
+ #line 206 "parser.rl"
557
559
  {
558
560
  if (json->allow_nan) {
559
561
  *result = CInfinity;
@@ -563,7 +565,7 @@ tr16:
563
565
  }
564
566
  goto st21;
565
567
  tr18:
566
- #line 196 "parser.rl"
568
+ #line 199 "parser.rl"
567
569
  {
568
570
  if (json->allow_nan) {
569
571
  *result = CNaN;
@@ -573,19 +575,19 @@ tr18:
573
575
  }
574
576
  goto st21;
575
577
  tr22:
576
- #line 190 "parser.rl"
578
+ #line 193 "parser.rl"
577
579
  {
578
580
  *result = Qfalse;
579
581
  }
580
582
  goto st21;
581
583
  tr25:
582
- #line 187 "parser.rl"
584
+ #line 190 "parser.rl"
583
585
  {
584
586
  *result = Qnil;
585
587
  }
586
588
  goto st21;
587
589
  tr28:
588
- #line 193 "parser.rl"
590
+ #line 196 "parser.rl"
589
591
  {
590
592
  *result = Qtrue;
591
593
  }
@@ -594,9 +596,9 @@ st21:
594
596
  if ( ++p == pe )
595
597
  goto _test_eof21;
596
598
  case 21:
597
- #line 249 "parser.rl"
599
+ #line 252 "parser.rl"
598
600
  { p--; {p++; cs = 21; goto _out;} }
599
- #line 600 "parser.c"
601
+ #line 602 "parser.c"
600
602
  goto st0;
601
603
  st2:
602
604
  if ( ++p == pe )
@@ -732,32 +734,32 @@ case 20:
732
734
  goto tr28;
733
735
  goto st0;
734
736
  }
735
- _test_eof21: cs = 21; goto _test_eof;
736
- _test_eof2: cs = 2; goto _test_eof;
737
- _test_eof3: cs = 3; goto _test_eof;
738
- _test_eof4: cs = 4; goto _test_eof;
739
- _test_eof5: cs = 5; goto _test_eof;
740
- _test_eof6: cs = 6; goto _test_eof;
741
- _test_eof7: cs = 7; goto _test_eof;
742
- _test_eof8: cs = 8; goto _test_eof;
743
- _test_eof9: cs = 9; goto _test_eof;
744
- _test_eof10: cs = 10; goto _test_eof;
745
- _test_eof11: cs = 11; goto _test_eof;
746
- _test_eof12: cs = 12; goto _test_eof;
747
- _test_eof13: cs = 13; goto _test_eof;
748
- _test_eof14: cs = 14; goto _test_eof;
749
- _test_eof15: cs = 15; goto _test_eof;
750
- _test_eof16: cs = 16; goto _test_eof;
751
- _test_eof17: cs = 17; goto _test_eof;
752
- _test_eof18: cs = 18; goto _test_eof;
753
- _test_eof19: cs = 19; goto _test_eof;
754
- _test_eof20: cs = 20; goto _test_eof;
737
+ _test_eof21: cs = 21; goto _test_eof;
738
+ _test_eof2: cs = 2; goto _test_eof;
739
+ _test_eof3: cs = 3; goto _test_eof;
740
+ _test_eof4: cs = 4; goto _test_eof;
741
+ _test_eof5: cs = 5; goto _test_eof;
742
+ _test_eof6: cs = 6; goto _test_eof;
743
+ _test_eof7: cs = 7; goto _test_eof;
744
+ _test_eof8: cs = 8; goto _test_eof;
745
+ _test_eof9: cs = 9; goto _test_eof;
746
+ _test_eof10: cs = 10; goto _test_eof;
747
+ _test_eof11: cs = 11; goto _test_eof;
748
+ _test_eof12: cs = 12; goto _test_eof;
749
+ _test_eof13: cs = 13; goto _test_eof;
750
+ _test_eof14: cs = 14; goto _test_eof;
751
+ _test_eof15: cs = 15; goto _test_eof;
752
+ _test_eof16: cs = 16; goto _test_eof;
753
+ _test_eof17: cs = 17; goto _test_eof;
754
+ _test_eof18: cs = 18; goto _test_eof;
755
+ _test_eof19: cs = 19; goto _test_eof;
756
+ _test_eof20: cs = 20; goto _test_eof;
755
757
 
756
758
  _test_eof: {}
757
759
  _out: {}
758
760
  }
759
761
 
760
- #line 270 "parser.rl"
762
+ #line 273 "parser.rl"
761
763
 
762
764
  if (cs >= JSON_value_first_final) {
763
765
  return p;
@@ -767,31 +769,31 @@ case 20:
767
769
  }
768
770
 
769
771
 
770
- #line 771 "parser.c"
772
+ #line 773 "parser.c"
771
773
  static const int JSON_integer_start = 1;
772
- static const int JSON_integer_first_final = 5;
774
+ static const int JSON_integer_first_final = 3;
773
775
  static const int JSON_integer_error = 0;
774
776
 
775
777
  static const int JSON_integer_en_main = 1;
776
778
 
777
779
 
778
- #line 286 "parser.rl"
780
+ #line 289 "parser.rl"
779
781
 
780
782
 
781
783
  static char *JSON_parse_integer(JSON_Parser *json, char *p, char *pe, VALUE *result)
782
784
  {
783
785
  int cs = EVIL;
784
786
 
785
-
786
- #line 787 "parser.c"
787
+
788
+ #line 789 "parser.c"
787
789
  {
788
790
  cs = JSON_integer_start;
789
791
  }
790
792
 
791
- #line 293 "parser.rl"
793
+ #line 296 "parser.rl"
792
794
  json->memo = p;
793
-
794
- #line 795 "parser.c"
795
+
796
+ #line 797 "parser.c"
795
797
  {
796
798
  if ( p == pe )
797
799
  goto _test_eof;
@@ -803,7 +805,7 @@ case 1:
803
805
  case 48: goto st3;
804
806
  }
805
807
  if ( 49 <= (*p) && (*p) <= 57 )
806
- goto st4;
808
+ goto st5;
807
809
  goto st0;
808
810
  st0:
809
811
  cs = 0;
@@ -815,7 +817,7 @@ case 2:
815
817
  if ( (*p) == 48 )
816
818
  goto st3;
817
819
  if ( 49 <= (*p) && (*p) <= 57 )
818
- goto st4;
820
+ goto st5;
819
821
  goto st0;
820
822
  st3:
821
823
  if ( ++p == pe )
@@ -825,33 +827,33 @@ case 3:
825
827
  goto st0;
826
828
  goto tr4;
827
829
  tr4:
828
- #line 283 "parser.rl"
829
- { p--; {p++; cs = 5; goto _out;} }
830
- goto st5;
831
- st5:
832
- if ( ++p == pe )
833
- goto _test_eof5;
834
- case 5:
835
- #line 836 "parser.c"
836
- goto st0;
830
+ #line 286 "parser.rl"
831
+ { p--; {p++; cs = 4; goto _out;} }
832
+ goto st4;
837
833
  st4:
838
834
  if ( ++p == pe )
839
835
  goto _test_eof4;
840
836
  case 4:
837
+ #line 838 "parser.c"
838
+ goto st0;
839
+ st5:
840
+ if ( ++p == pe )
841
+ goto _test_eof5;
842
+ case 5:
841
843
  if ( 48 <= (*p) && (*p) <= 57 )
842
- goto st4;
844
+ goto st5;
843
845
  goto tr4;
844
846
  }
845
- _test_eof2: cs = 2; goto _test_eof;
846
- _test_eof3: cs = 3; goto _test_eof;
847
- _test_eof5: cs = 5; goto _test_eof;
848
- _test_eof4: cs = 4; goto _test_eof;
847
+ _test_eof2: cs = 2; goto _test_eof;
848
+ _test_eof3: cs = 3; goto _test_eof;
849
+ _test_eof4: cs = 4; goto _test_eof;
850
+ _test_eof5: cs = 5; goto _test_eof;
849
851
 
850
852
  _test_eof: {}
851
853
  _out: {}
852
854
  }
853
855
 
854
- #line 295 "parser.rl"
856
+ #line 298 "parser.rl"
855
857
 
856
858
  if (cs >= JSON_integer_first_final) {
857
859
  long len = p - json->memo;
@@ -863,31 +865,31 @@ case 4:
863
865
  }
864
866
 
865
867
 
866
- #line 867 "parser.c"
868
+ #line 869 "parser.c"
867
869
  static const int JSON_float_start = 1;
868
- static const int JSON_float_first_final = 10;
870
+ static const int JSON_float_first_final = 8;
869
871
  static const int JSON_float_error = 0;
870
872
 
871
873
  static const int JSON_float_en_main = 1;
872
874
 
873
875
 
874
- #line 317 "parser.rl"
876
+ #line 320 "parser.rl"
875
877
 
876
878
 
877
879
  static char *JSON_parse_float(JSON_Parser *json, char *p, char *pe, VALUE *result)
878
880
  {
879
881
  int cs = EVIL;
880
882
 
881
-
882
- #line 883 "parser.c"
883
+
884
+ #line 885 "parser.c"
883
885
  {
884
886
  cs = JSON_float_start;
885
887
  }
886
888
 
887
- #line 324 "parser.rl"
889
+ #line 327 "parser.rl"
888
890
  json->memo = p;
889
-
890
- #line 891 "parser.c"
891
+
892
+ #line 893 "parser.c"
891
893
  {
892
894
  if ( p == pe )
893
895
  goto _test_eof;
@@ -899,7 +901,7 @@ case 1:
899
901
  case 48: goto st3;
900
902
  }
901
903
  if ( 49 <= (*p) && (*p) <= 57 )
902
- goto st9;
904
+ goto st7;
903
905
  goto st0;
904
906
  st0:
905
907
  cs = 0;
@@ -911,7 +913,7 @@ case 2:
911
913
  if ( (*p) == 48 )
912
914
  goto st3;
913
915
  if ( 49 <= (*p) && (*p) <= 57 )
914
- goto st9;
916
+ goto st7;
915
917
  goto st0;
916
918
  st3:
917
919
  if ( ++p == pe )
@@ -919,8 +921,8 @@ st3:
919
921
  case 3:
920
922
  switch( (*p) ) {
921
923
  case 46: goto st4;
922
- case 69: goto st6;
923
- case 101: goto st6;
924
+ case 69: goto st5;
925
+ case 101: goto st5;
924
926
  }
925
927
  goto st0;
926
928
  st4:
@@ -928,92 +930,92 @@ st4:
928
930
  goto _test_eof4;
929
931
  case 4:
930
932
  if ( 48 <= (*p) && (*p) <= 57 )
931
- goto st5;
933
+ goto st8;
932
934
  goto st0;
933
- st5:
935
+ st8:
934
936
  if ( ++p == pe )
935
- goto _test_eof5;
936
- case 5:
937
+ goto _test_eof8;
938
+ case 8:
937
939
  switch( (*p) ) {
938
- case 69: goto st6;
939
- case 101: goto st6;
940
+ case 69: goto st5;
941
+ case 101: goto st5;
940
942
  }
941
943
  if ( (*p) > 46 ) {
942
944
  if ( 48 <= (*p) && (*p) <= 57 )
943
- goto st5;
945
+ goto st8;
944
946
  } else if ( (*p) >= 45 )
945
947
  goto st0;
946
- goto tr7;
947
- tr7:
948
- #line 311 "parser.rl"
949
- { p--; {p++; cs = 10; goto _out;} }
950
- goto st10;
951
- st10:
948
+ goto tr9;
949
+ tr9:
950
+ #line 314 "parser.rl"
951
+ { p--; {p++; cs = 9; goto _out;} }
952
+ goto st9;
953
+ st9:
952
954
  if ( ++p == pe )
953
- goto _test_eof10;
954
- case 10:
955
- #line 956 "parser.c"
955
+ goto _test_eof9;
956
+ case 9:
957
+ #line 958 "parser.c"
956
958
  goto st0;
957
- st6:
959
+ st5:
958
960
  if ( ++p == pe )
959
- goto _test_eof6;
960
- case 6:
961
+ goto _test_eof5;
962
+ case 5:
961
963
  switch( (*p) ) {
962
- case 43: goto st7;
963
- case 45: goto st7;
964
+ case 43: goto st6;
965
+ case 45: goto st6;
964
966
  }
965
967
  if ( 48 <= (*p) && (*p) <= 57 )
966
- goto st8;
968
+ goto st10;
967
969
  goto st0;
968
- st7:
970
+ st6:
969
971
  if ( ++p == pe )
970
- goto _test_eof7;
971
- case 7:
972
+ goto _test_eof6;
973
+ case 6:
972
974
  if ( 48 <= (*p) && (*p) <= 57 )
973
- goto st8;
975
+ goto st10;
974
976
  goto st0;
975
- st8:
977
+ st10:
976
978
  if ( ++p == pe )
977
- goto _test_eof8;
978
- case 8:
979
+ goto _test_eof10;
980
+ case 10:
979
981
  switch( (*p) ) {
980
982
  case 69: goto st0;
981
983
  case 101: goto st0;
982
984
  }
983
985
  if ( (*p) > 46 ) {
984
986
  if ( 48 <= (*p) && (*p) <= 57 )
985
- goto st8;
987
+ goto st10;
986
988
  } else if ( (*p) >= 45 )
987
989
  goto st0;
988
- goto tr7;
989
- st9:
990
+ goto tr9;
991
+ st7:
990
992
  if ( ++p == pe )
991
- goto _test_eof9;
992
- case 9:
993
+ goto _test_eof7;
994
+ case 7:
993
995
  switch( (*p) ) {
994
996
  case 46: goto st4;
995
- case 69: goto st6;
996
- case 101: goto st6;
997
+ case 69: goto st5;
998
+ case 101: goto st5;
997
999
  }
998
1000
  if ( 48 <= (*p) && (*p) <= 57 )
999
- goto st9;
1001
+ goto st7;
1000
1002
  goto st0;
1001
1003
  }
1002
- _test_eof2: cs = 2; goto _test_eof;
1003
- _test_eof3: cs = 3; goto _test_eof;
1004
- _test_eof4: cs = 4; goto _test_eof;
1005
- _test_eof5: cs = 5; goto _test_eof;
1006
- _test_eof10: cs = 10; goto _test_eof;
1007
- _test_eof6: cs = 6; goto _test_eof;
1008
- _test_eof7: cs = 7; goto _test_eof;
1009
- _test_eof8: cs = 8; goto _test_eof;
1010
- _test_eof9: cs = 9; goto _test_eof;
1004
+ _test_eof2: cs = 2; goto _test_eof;
1005
+ _test_eof3: cs = 3; goto _test_eof;
1006
+ _test_eof4: cs = 4; goto _test_eof;
1007
+ _test_eof8: cs = 8; goto _test_eof;
1008
+ _test_eof9: cs = 9; goto _test_eof;
1009
+ _test_eof5: cs = 5; goto _test_eof;
1010
+ _test_eof6: cs = 6; goto _test_eof;
1011
+ _test_eof10: cs = 10; goto _test_eof;
1012
+ _test_eof7: cs = 7; goto _test_eof;
1011
1013
 
1012
1014
  _test_eof: {}
1013
1015
  _out: {}
1014
1016
  }
1015
1017
 
1016
- #line 326 "parser.rl"
1018
+ #line 329 "parser.rl"
1017
1019
 
1018
1020
  if (cs >= JSON_float_first_final) {
1019
1021
  long len = p - json->memo;
@@ -1026,7 +1028,7 @@ case 9:
1026
1028
 
1027
1029
 
1028
1030
 
1029
- #line 1030 "parser.c"
1031
+ #line 1032 "parser.c"
1030
1032
  static const int JSON_array_start = 1;
1031
1033
  static const int JSON_array_first_final = 17;
1032
1034
  static const int JSON_array_error = 0;
@@ -1034,7 +1036,7 @@ static const int JSON_array_error = 0;
1034
1036
  static const int JSON_array_en_main = 1;
1035
1037
 
1036
1038
 
1037
- #line 366 "parser.rl"
1039
+ #line 369 "parser.rl"
1038
1040
 
1039
1041
 
1040
1042
  static char *JSON_parse_array(JSON_Parser *json, char *p, char *pe, VALUE *result)
@@ -1047,15 +1049,15 @@ static char *JSON_parse_array(JSON_Parser *json, char *p, char *pe, VALUE *resul
1047
1049
  }
1048
1050
  *result = NIL_P(array_class) ? rb_ary_new() : rb_class_new_instance(0, 0, array_class);
1049
1051
 
1050
-
1051
- #line 1052 "parser.c"
1052
+
1053
+ #line 1054 "parser.c"
1052
1054
  {
1053
1055
  cs = JSON_array_start;
1054
1056
  }
1055
1057
 
1056
- #line 379 "parser.rl"
1057
-
1058
- #line 1059 "parser.c"
1058
+ #line 382 "parser.rl"
1059
+
1060
+ #line 1061 "parser.c"
1059
1061
  {
1060
1062
  if ( p == pe )
1061
1063
  goto _test_eof;
@@ -1094,10 +1096,10 @@ case 2:
1094
1096
  goto st2;
1095
1097
  goto st0;
1096
1098
  tr2:
1097
- #line 343 "parser.rl"
1099
+ #line 346 "parser.rl"
1098
1100
  {
1099
1101
  VALUE v = Qnil;
1100
- char *np = JSON_parse_value(json, p, pe, &v);
1102
+ char *np = JSON_parse_value(json, p, pe, &v);
1101
1103
  if (np == NULL) {
1102
1104
  p--; {p++; cs = 3; goto _out;}
1103
1105
  } else {
@@ -1114,7 +1116,7 @@ st3:
1114
1116
  if ( ++p == pe )
1115
1117
  goto _test_eof3;
1116
1118
  case 3:
1117
- #line 1118 "parser.c"
1119
+ #line 1120 "parser.c"
1118
1120
  switch( (*p) ) {
1119
1121
  case 13: goto st3;
1120
1122
  case 32: goto st3;
@@ -1214,14 +1216,14 @@ case 12:
1214
1216
  goto st3;
1215
1217
  goto st12;
1216
1218
  tr4:
1217
- #line 358 "parser.rl"
1219
+ #line 361 "parser.rl"
1218
1220
  { p--; {p++; cs = 17; goto _out;} }
1219
1221
  goto st17;
1220
1222
  st17:
1221
1223
  if ( ++p == pe )
1222
1224
  goto _test_eof17;
1223
1225
  case 17:
1224
- #line 1225 "parser.c"
1226
+ #line 1227 "parser.c"
1225
1227
  goto st0;
1226
1228
  st13:
1227
1229
  if ( ++p == pe )
@@ -1256,28 +1258,28 @@ case 16:
1256
1258
  goto st2;
1257
1259
  goto st16;
1258
1260
  }
1259
- _test_eof2: cs = 2; goto _test_eof;
1260
- _test_eof3: cs = 3; goto _test_eof;
1261
- _test_eof4: cs = 4; goto _test_eof;
1262
- _test_eof5: cs = 5; goto _test_eof;
1263
- _test_eof6: cs = 6; goto _test_eof;
1264
- _test_eof7: cs = 7; goto _test_eof;
1265
- _test_eof8: cs = 8; goto _test_eof;
1266
- _test_eof9: cs = 9; goto _test_eof;
1267
- _test_eof10: cs = 10; goto _test_eof;
1268
- _test_eof11: cs = 11; goto _test_eof;
1269
- _test_eof12: cs = 12; goto _test_eof;
1270
- _test_eof17: cs = 17; goto _test_eof;
1271
- _test_eof13: cs = 13; goto _test_eof;
1272
- _test_eof14: cs = 14; goto _test_eof;
1273
- _test_eof15: cs = 15; goto _test_eof;
1274
- _test_eof16: cs = 16; goto _test_eof;
1261
+ _test_eof2: cs = 2; goto _test_eof;
1262
+ _test_eof3: cs = 3; goto _test_eof;
1263
+ _test_eof4: cs = 4; goto _test_eof;
1264
+ _test_eof5: cs = 5; goto _test_eof;
1265
+ _test_eof6: cs = 6; goto _test_eof;
1266
+ _test_eof7: cs = 7; goto _test_eof;
1267
+ _test_eof8: cs = 8; goto _test_eof;
1268
+ _test_eof9: cs = 9; goto _test_eof;
1269
+ _test_eof10: cs = 10; goto _test_eof;
1270
+ _test_eof11: cs = 11; goto _test_eof;
1271
+ _test_eof12: cs = 12; goto _test_eof;
1272
+ _test_eof17: cs = 17; goto _test_eof;
1273
+ _test_eof13: cs = 13; goto _test_eof;
1274
+ _test_eof14: cs = 14; goto _test_eof;
1275
+ _test_eof15: cs = 15; goto _test_eof;
1276
+ _test_eof16: cs = 16; goto _test_eof;
1275
1277
 
1276
1278
  _test_eof: {}
1277
1279
  _out: {}
1278
1280
  }
1279
1281
 
1280
- #line 380 "parser.rl"
1282
+ #line 383 "parser.rl"
1281
1283
 
1282
1284
  if(cs >= JSON_array_first_final) {
1283
1285
  return p + 1;
@@ -1320,7 +1322,7 @@ static VALUE json_string_unescape(VALUE result, char *string, char *stringEnd)
1320
1322
  unescape = (char *) "\f";
1321
1323
  break;
1322
1324
  case 'u':
1323
- if (pe > stringEnd - 4) {
1325
+ if (pe > stringEnd - 4) {
1324
1326
  return Qnil;
1325
1327
  } else {
1326
1328
  char buf[4];
@@ -1358,7 +1360,7 @@ static VALUE json_string_unescape(VALUE result, char *string, char *stringEnd)
1358
1360
  }
1359
1361
 
1360
1362
 
1361
- #line 1362 "parser.c"
1363
+ #line 1364 "parser.c"
1362
1364
  static const int JSON_string_start = 1;
1363
1365
  static const int JSON_string_first_final = 8;
1364
1366
  static const int JSON_string_error = 0;
@@ -1366,7 +1368,7 @@ static const int JSON_string_error = 0;
1366
1368
  static const int JSON_string_en_main = 1;
1367
1369
 
1368
1370
 
1369
- #line 479 "parser.rl"
1371
+ #line 482 "parser.rl"
1370
1372
 
1371
1373
 
1372
1374
  static int
@@ -1387,16 +1389,16 @@ static char *JSON_parse_string(JSON_Parser *json, char *p, char *pe, VALUE *resu
1387
1389
  VALUE match_string;
1388
1390
 
1389
1391
  *result = rb_str_buf_new(0);
1390
-
1391
- #line 1392 "parser.c"
1392
+
1393
+ #line 1394 "parser.c"
1392
1394
  {
1393
1395
  cs = JSON_string_start;
1394
1396
  }
1395
1397
 
1396
- #line 500 "parser.rl"
1398
+ #line 503 "parser.rl"
1397
1399
  json->memo = p;
1398
-
1399
- #line 1400 "parser.c"
1400
+
1401
+ #line 1402 "parser.c"
1400
1402
  {
1401
1403
  if ( p == pe )
1402
1404
  goto _test_eof;
@@ -1421,7 +1423,7 @@ case 2:
1421
1423
  goto st0;
1422
1424
  goto st2;
1423
1425
  tr2:
1424
- #line 465 "parser.rl"
1426
+ #line 468 "parser.rl"
1425
1427
  {
1426
1428
  *result = json_string_unescape(*result, json->memo + 1, p);
1427
1429
  if (NIL_P(*result)) {
@@ -1432,14 +1434,14 @@ tr2:
1432
1434
  {p = (( p + 1))-1;}
1433
1435
  }
1434
1436
  }
1435
- #line 476 "parser.rl"
1437
+ #line 479 "parser.rl"
1436
1438
  { p--; {p++; cs = 8; goto _out;} }
1437
1439
  goto st8;
1438
1440
  st8:
1439
1441
  if ( ++p == pe )
1440
1442
  goto _test_eof8;
1441
1443
  case 8:
1442
- #line 1443 "parser.c"
1444
+ #line 1445 "parser.c"
1443
1445
  goto st0;
1444
1446
  st3:
1445
1447
  if ( ++p == pe )
@@ -1503,19 +1505,19 @@ case 7:
1503
1505
  goto st2;
1504
1506
  goto st0;
1505
1507
  }
1506
- _test_eof2: cs = 2; goto _test_eof;
1507
- _test_eof8: cs = 8; goto _test_eof;
1508
- _test_eof3: cs = 3; goto _test_eof;
1509
- _test_eof4: cs = 4; goto _test_eof;
1510
- _test_eof5: cs = 5; goto _test_eof;
1511
- _test_eof6: cs = 6; goto _test_eof;
1512
- _test_eof7: cs = 7; goto _test_eof;
1508
+ _test_eof2: cs = 2; goto _test_eof;
1509
+ _test_eof8: cs = 8; goto _test_eof;
1510
+ _test_eof3: cs = 3; goto _test_eof;
1511
+ _test_eof4: cs = 4; goto _test_eof;
1512
+ _test_eof5: cs = 5; goto _test_eof;
1513
+ _test_eof6: cs = 6; goto _test_eof;
1514
+ _test_eof7: cs = 7; goto _test_eof;
1513
1515
 
1514
1516
  _test_eof: {}
1515
1517
  _out: {}
1516
1518
  }
1517
1519
 
1518
- #line 502 "parser.rl"
1520
+ #line 505 "parser.rl"
1519
1521
 
1520
1522
  if (json->create_additions && RTEST(match_string = json->match_string)) {
1521
1523
  VALUE klass;
@@ -1538,20 +1540,7 @@ case 7:
1538
1540
  }
1539
1541
  }
1540
1542
 
1541
-
1542
-
1543
- #line 1544 "parser.c"
1544
- static const int JSON_start = 1;
1545
- static const int JSON_first_final = 10;
1546
- static const int JSON_error = 0;
1547
-
1548
- static const int JSON_en_main = 1;
1549
-
1550
-
1551
- #line 550 "parser.rl"
1552
-
1553
-
1554
- /*
1543
+ /*
1555
1544
  * Document-class: JSON::Ext::Parser
1556
1545
  *
1557
1546
  * This is the JSON parser implemented as a C extension. It can be configured
@@ -1575,22 +1564,15 @@ static VALUE convert_encoding(VALUE source)
1575
1564
  VALUE encoding = rb_funcall(source, i_encoding, 0);
1576
1565
  if (encoding == CEncoding_ASCII_8BIT) {
1577
1566
  if (len >= 4 && ptr[0] == 0 && ptr[1] == 0 && ptr[2] == 0) {
1578
- source = rb_str_dup(source);
1579
- rb_funcall(source, i_force_encoding, 1, CEncoding_UTF_32BE);
1580
- source = rb_funcall(source, i_encode_bang, 1, CEncoding_UTF_8);
1567
+ source = rb_funcall(source, i_encode, 2, CEncoding_UTF_8, CEncoding_UTF_32BE);
1581
1568
  } else if (len >= 4 && ptr[0] == 0 && ptr[2] == 0) {
1582
- source = rb_str_dup(source);
1583
- rb_funcall(source, i_force_encoding, 1, CEncoding_UTF_16BE);
1584
- source = rb_funcall(source, i_encode_bang, 1, CEncoding_UTF_8);
1569
+ source = rb_funcall(source, i_encode, 2, CEncoding_UTF_8, CEncoding_UTF_16BE);
1585
1570
  } else if (len >= 4 && ptr[1] == 0 && ptr[2] == 0 && ptr[3] == 0) {
1586
- source = rb_str_dup(source);
1587
- rb_funcall(source, i_force_encoding, 1, CEncoding_UTF_32LE);
1588
- source = rb_funcall(source, i_encode_bang, 1, CEncoding_UTF_8);
1571
+ source = rb_funcall(source, i_encode, 2, CEncoding_UTF_8, CEncoding_UTF_32LE);
1589
1572
  } else if (len >= 4 && ptr[1] == 0 && ptr[3] == 0) {
1590
- source = rb_str_dup(source);
1591
- rb_funcall(source, i_force_encoding, 1, CEncoding_UTF_16LE);
1592
- source = rb_funcall(source, i_encode_bang, 1, CEncoding_UTF_8);
1573
+ source = rb_funcall(source, i_encode, 2, CEncoding_UTF_8, CEncoding_UTF_16LE);
1593
1574
  } else {
1575
+ source = rb_str_dup(source);
1594
1576
  FORCE_UTF8(source);
1595
1577
  }
1596
1578
  } else {
@@ -1636,17 +1618,19 @@ static VALUE convert_encoding(VALUE source)
1636
1618
  * defaults to true.
1637
1619
  * * *object_class*: Defaults to Hash
1638
1620
  * * *array_class*: Defaults to Array
1621
+ * * *quirks_mode*: Enables quirks_mode for parser, that is for example
1622
+ * parsing single JSON values instead of documents is possible.
1623
+ *
1639
1624
  */
1640
1625
  static VALUE cParser_initialize(int argc, VALUE *argv, VALUE self)
1641
1626
  {
1642
- char *ptr;
1643
- long len;
1644
1627
  VALUE source, opts;
1645
- GET_PARSER;
1628
+ GET_PARSER_INIT;
1629
+
1630
+ if (json->Vsource) {
1631
+ rb_raise(rb_eTypeError, "already initialized instance");
1632
+ }
1646
1633
  rb_scan_args(argc, argv, "11", &source, &opts);
1647
- source = convert_encoding(StringValue(source));
1648
- ptr = RSTRING_PTR(source);
1649
- len = RSTRING_LEN(source);
1650
1634
  if (!NIL_P(opts)) {
1651
1635
  opts = rb_convert_type(opts, T_HASH, "Hash", "to_hash");
1652
1636
  if (NIL_P(opts)) {
@@ -1676,6 +1660,13 @@ static VALUE cParser_initialize(int argc, VALUE *argv, VALUE self)
1676
1660
  } else {
1677
1661
  json->symbolize_names = 0;
1678
1662
  }
1663
+ tmp = ID2SYM(i_quirks_mode);
1664
+ if (option_given_p(opts, tmp)) {
1665
+ VALUE quirks_mode = rb_hash_aref(opts, tmp);
1666
+ json->quirks_mode = RTEST(quirks_mode) ? 1 : 0;
1667
+ } else {
1668
+ json->quirks_mode = 0;
1669
+ }
1679
1670
  tmp = ID2SYM(i_create_additions);
1680
1671
  if (option_given_p(opts, tmp)) {
1681
1672
  json->create_additions = RTEST(rb_hash_aref(opts, tmp));
@@ -1716,37 +1707,46 @@ static VALUE cParser_initialize(int argc, VALUE *argv, VALUE self)
1716
1707
  json->object_class = Qnil;
1717
1708
  json->array_class = Qnil;
1718
1709
  }
1710
+ if (!json->quirks_mode) {
1711
+ source = convert_encoding(StringValue(source));
1712
+ }
1719
1713
  json->current_nesting = 0;
1720
- json->len = len;
1721
- json->source = ptr;
1714
+ json->len = RSTRING_LEN(source);
1715
+ json->source = RSTRING_PTR(source);;
1722
1716
  json->Vsource = source;
1723
1717
  return self;
1724
1718
  }
1725
1719
 
1726
- /*
1727
- * call-seq: parse()
1728
- *
1729
- * Parses the current JSON text _source_ and returns the complete data
1730
- * structure as a result.
1731
- */
1732
- static VALUE cParser_parse(VALUE self)
1720
+
1721
+ #line 1719 "parser.c"
1722
+ static const int JSON_start = 1;
1723
+ static const int JSON_first_final = 10;
1724
+ static const int JSON_error = 0;
1725
+
1726
+ static const int JSON_en_main = 1;
1727
+
1728
+
1729
+ #line 726 "parser.rl"
1730
+
1731
+
1732
+ static VALUE cParser_parse_strict(VALUE self)
1733
1733
  {
1734
1734
  char *p, *pe;
1735
1735
  int cs = EVIL;
1736
1736
  VALUE result = Qnil;
1737
1737
  GET_PARSER;
1738
1738
 
1739
-
1740
- #line 1741 "parser.c"
1739
+
1740
+ #line 1738 "parser.c"
1741
1741
  {
1742
1742
  cs = JSON_start;
1743
1743
  }
1744
1744
 
1745
- #line 738 "parser.rl"
1745
+ #line 736 "parser.rl"
1746
1746
  p = json->source;
1747
1747
  pe = p + json->len;
1748
-
1749
- #line 1750 "parser.c"
1748
+
1749
+ #line 1747 "parser.c"
1750
1750
  {
1751
1751
  if ( p == pe )
1752
1752
  goto _test_eof;
@@ -1802,7 +1802,7 @@ case 5:
1802
1802
  goto st1;
1803
1803
  goto st5;
1804
1804
  tr3:
1805
- #line 539 "parser.rl"
1805
+ #line 715 "parser.rl"
1806
1806
  {
1807
1807
  char *np;
1808
1808
  json->current_nesting = 1;
@@ -1811,7 +1811,7 @@ tr3:
1811
1811
  }
1812
1812
  goto st10;
1813
1813
  tr4:
1814
- #line 532 "parser.rl"
1814
+ #line 708 "parser.rl"
1815
1815
  {
1816
1816
  char *np;
1817
1817
  json->current_nesting = 1;
@@ -1823,7 +1823,7 @@ st10:
1823
1823
  if ( ++p == pe )
1824
1824
  goto _test_eof10;
1825
1825
  case 10:
1826
- #line 1827 "parser.c"
1826
+ #line 1824 "parser.c"
1827
1827
  switch( (*p) ) {
1828
1828
  case 13: goto st10;
1829
1829
  case 32: goto st10;
@@ -1865,22 +1865,22 @@ case 9:
1865
1865
  goto st10;
1866
1866
  goto st9;
1867
1867
  }
1868
- _test_eof1: cs = 1; goto _test_eof;
1869
- _test_eof2: cs = 2; goto _test_eof;
1870
- _test_eof3: cs = 3; goto _test_eof;
1871
- _test_eof4: cs = 4; goto _test_eof;
1872
- _test_eof5: cs = 5; goto _test_eof;
1873
- _test_eof10: cs = 10; goto _test_eof;
1874
- _test_eof6: cs = 6; goto _test_eof;
1875
- _test_eof7: cs = 7; goto _test_eof;
1876
- _test_eof8: cs = 8; goto _test_eof;
1877
- _test_eof9: cs = 9; goto _test_eof;
1868
+ _test_eof1: cs = 1; goto _test_eof;
1869
+ _test_eof2: cs = 2; goto _test_eof;
1870
+ _test_eof3: cs = 3; goto _test_eof;
1871
+ _test_eof4: cs = 4; goto _test_eof;
1872
+ _test_eof5: cs = 5; goto _test_eof;
1873
+ _test_eof10: cs = 10; goto _test_eof;
1874
+ _test_eof6: cs = 6; goto _test_eof;
1875
+ _test_eof7: cs = 7; goto _test_eof;
1876
+ _test_eof8: cs = 8; goto _test_eof;
1877
+ _test_eof9: cs = 9; goto _test_eof;
1878
1878
 
1879
1879
  _test_eof: {}
1880
1880
  _out: {}
1881
1881
  }
1882
1882
 
1883
- #line 741 "parser.rl"
1883
+ #line 739 "parser.rl"
1884
1884
 
1885
1885
  if (cs >= JSON_first_final && p == pe) {
1886
1886
  return result;
@@ -1890,6 +1890,197 @@ case 9:
1890
1890
  }
1891
1891
  }
1892
1892
 
1893
+
1894
+
1895
+ #line 1893 "parser.c"
1896
+ static const int JSON_quirks_mode_start = 1;
1897
+ static const int JSON_quirks_mode_first_final = 10;
1898
+ static const int JSON_quirks_mode_error = 0;
1899
+
1900
+ static const int JSON_quirks_mode_en_main = 1;
1901
+
1902
+
1903
+ #line 764 "parser.rl"
1904
+
1905
+
1906
+ static VALUE cParser_parse_quirks_mode(VALUE self)
1907
+ {
1908
+ char *p, *pe;
1909
+ int cs = EVIL;
1910
+ VALUE result = Qnil;
1911
+ GET_PARSER;
1912
+
1913
+
1914
+ #line 1912 "parser.c"
1915
+ {
1916
+ cs = JSON_quirks_mode_start;
1917
+ }
1918
+
1919
+ #line 774 "parser.rl"
1920
+ p = json->source;
1921
+ pe = p + json->len;
1922
+
1923
+ #line 1921 "parser.c"
1924
+ {
1925
+ if ( p == pe )
1926
+ goto _test_eof;
1927
+ switch ( cs )
1928
+ {
1929
+ st1:
1930
+ if ( ++p == pe )
1931
+ goto _test_eof1;
1932
+ case 1:
1933
+ switch( (*p) ) {
1934
+ case 13: goto st1;
1935
+ case 32: goto st1;
1936
+ case 34: goto tr2;
1937
+ case 45: goto tr2;
1938
+ case 47: goto st6;
1939
+ case 73: goto tr2;
1940
+ case 78: goto tr2;
1941
+ case 91: goto tr2;
1942
+ case 102: goto tr2;
1943
+ case 110: goto tr2;
1944
+ case 116: goto tr2;
1945
+ case 123: goto tr2;
1946
+ }
1947
+ if ( (*p) > 10 ) {
1948
+ if ( 48 <= (*p) && (*p) <= 57 )
1949
+ goto tr2;
1950
+ } else if ( (*p) >= 9 )
1951
+ goto st1;
1952
+ goto st0;
1953
+ st0:
1954
+ cs = 0;
1955
+ goto _out;
1956
+ tr2:
1957
+ #line 756 "parser.rl"
1958
+ {
1959
+ char *np = JSON_parse_value(json, p, pe, &result);
1960
+ if (np == NULL) { p--; {p++; cs = 10; goto _out;} } else {p = (( np))-1;}
1961
+ }
1962
+ goto st10;
1963
+ st10:
1964
+ if ( ++p == pe )
1965
+ goto _test_eof10;
1966
+ case 10:
1967
+ #line 1965 "parser.c"
1968
+ switch( (*p) ) {
1969
+ case 13: goto st10;
1970
+ case 32: goto st10;
1971
+ case 47: goto st2;
1972
+ }
1973
+ if ( 9 <= (*p) && (*p) <= 10 )
1974
+ goto st10;
1975
+ goto st0;
1976
+ st2:
1977
+ if ( ++p == pe )
1978
+ goto _test_eof2;
1979
+ case 2:
1980
+ switch( (*p) ) {
1981
+ case 42: goto st3;
1982
+ case 47: goto st5;
1983
+ }
1984
+ goto st0;
1985
+ st3:
1986
+ if ( ++p == pe )
1987
+ goto _test_eof3;
1988
+ case 3:
1989
+ if ( (*p) == 42 )
1990
+ goto st4;
1991
+ goto st3;
1992
+ st4:
1993
+ if ( ++p == pe )
1994
+ goto _test_eof4;
1995
+ case 4:
1996
+ switch( (*p) ) {
1997
+ case 42: goto st4;
1998
+ case 47: goto st10;
1999
+ }
2000
+ goto st3;
2001
+ st5:
2002
+ if ( ++p == pe )
2003
+ goto _test_eof5;
2004
+ case 5:
2005
+ if ( (*p) == 10 )
2006
+ goto st10;
2007
+ goto st5;
2008
+ st6:
2009
+ if ( ++p == pe )
2010
+ goto _test_eof6;
2011
+ case 6:
2012
+ switch( (*p) ) {
2013
+ case 42: goto st7;
2014
+ case 47: goto st9;
2015
+ }
2016
+ goto st0;
2017
+ st7:
2018
+ if ( ++p == pe )
2019
+ goto _test_eof7;
2020
+ case 7:
2021
+ if ( (*p) == 42 )
2022
+ goto st8;
2023
+ goto st7;
2024
+ st8:
2025
+ if ( ++p == pe )
2026
+ goto _test_eof8;
2027
+ case 8:
2028
+ switch( (*p) ) {
2029
+ case 42: goto st8;
2030
+ case 47: goto st1;
2031
+ }
2032
+ goto st7;
2033
+ st9:
2034
+ if ( ++p == pe )
2035
+ goto _test_eof9;
2036
+ case 9:
2037
+ if ( (*p) == 10 )
2038
+ goto st1;
2039
+ goto st9;
2040
+ }
2041
+ _test_eof1: cs = 1; goto _test_eof;
2042
+ _test_eof10: cs = 10; goto _test_eof;
2043
+ _test_eof2: cs = 2; goto _test_eof;
2044
+ _test_eof3: cs = 3; goto _test_eof;
2045
+ _test_eof4: cs = 4; goto _test_eof;
2046
+ _test_eof5: cs = 5; goto _test_eof;
2047
+ _test_eof6: cs = 6; goto _test_eof;
2048
+ _test_eof7: cs = 7; goto _test_eof;
2049
+ _test_eof8: cs = 8; goto _test_eof;
2050
+ _test_eof9: cs = 9; goto _test_eof;
2051
+
2052
+ _test_eof: {}
2053
+ _out: {}
2054
+ }
2055
+
2056
+ #line 777 "parser.rl"
2057
+
2058
+ if (cs >= JSON_quirks_mode_first_final && p == pe) {
2059
+ return result;
2060
+ } else {
2061
+ rb_raise(eParserError, "%u: unexpected token at '%s'", __LINE__, p);
2062
+ return Qnil;
2063
+ }
2064
+ }
2065
+
2066
+ /*
2067
+ * call-seq: parse()
2068
+ *
2069
+ * Parses the current JSON text _source_ and returns the complete data
2070
+ * structure as a result.
2071
+ */
2072
+ static VALUE cParser_parse(VALUE self)
2073
+ {
2074
+ GET_PARSER;
2075
+
2076
+ if (json->quirks_mode) {
2077
+ return cParser_parse_quirks_mode(self);
2078
+ } else {
2079
+ return cParser_parse_strict(self);
2080
+ }
2081
+ }
2082
+
2083
+
1893
2084
  static JSON_Parser *JSON_allocate()
1894
2085
  {
1895
2086
  JSON_Parser *json = ALLOC(JSON_Parser);
@@ -1929,6 +2120,18 @@ static VALUE cParser_source(VALUE self)
1929
2120
  return rb_str_dup(json->Vsource);
1930
2121
  }
1931
2122
 
2123
+ /*
2124
+ * call-seq: quirks_mode?()
2125
+ *
2126
+ * Returns a true, if this parser is in quirks_mode, false otherwise.
2127
+ */
2128
+ static VALUE cParser_quirks_mode_p(VALUE self)
2129
+ {
2130
+ GET_PARSER;
2131
+ return json->quirks_mode ? Qtrue : Qfalse;
2132
+ }
2133
+
2134
+
1932
2135
  void Init_parser()
1933
2136
  {
1934
2137
  rb_require("json/common");
@@ -1941,6 +2144,7 @@ void Init_parser()
1941
2144
  rb_define_method(cParser, "initialize", cParser_initialize, -1);
1942
2145
  rb_define_method(cParser, "parse", cParser_parse, 0);
1943
2146
  rb_define_method(cParser, "source", cParser_source, 0);
2147
+ rb_define_method(cParser, "quirks_mode?", cParser_quirks_mode_p, 0);
1944
2148
 
1945
2149
  CNaN = rb_const_get(mJSON, rb_intern("NaN"));
1946
2150
  CInfinity = rb_const_get(mJSON, rb_intern("Infinity"));
@@ -1954,6 +2158,7 @@ void Init_parser()
1954
2158
  i_max_nesting = rb_intern("max_nesting");
1955
2159
  i_allow_nan = rb_intern("allow_nan");
1956
2160
  i_symbolize_names = rb_intern("symbolize_names");
2161
+ i_quirks_mode = rb_intern("quirks_mode");
1957
2162
  i_object_class = rb_intern("object_class");
1958
2163
  i_array_class = rb_intern("array_class");
1959
2164
  i_match = rb_intern("match");
@@ -1971,9 +2176,15 @@ void Init_parser()
1971
2176
  CEncoding_ASCII_8BIT = rb_funcall(rb_path2class("Encoding"), rb_intern("find"), 1, rb_str_new2("ascii-8bit"));
1972
2177
  i_encoding = rb_intern("encoding");
1973
2178
  i_encode = rb_intern("encode");
1974
- i_encode_bang = rb_intern("encode!");
1975
- i_force_encoding = rb_intern("force_encoding");
1976
2179
  #else
1977
2180
  i_iconv = rb_intern("iconv");
1978
2181
  #endif
1979
2182
  }
2183
+
2184
+ /*
2185
+ * Local variables:
2186
+ * mode: c
2187
+ * c-file-style: ruby
2188
+ * indent-tabs-mode: nil
2189
+ * End:
2190
+ */