json 1.8.3 → 2.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +5 -5
- data/.gitignore +2 -0
- data/.travis.yml +9 -11
- data/{CHANGES → CHANGES.md} +186 -90
- data/Gemfile +10 -6
- data/{COPYING-json-jruby → LICENSE} +5 -6
- data/{README-json-jruby.markdown → README-json-jruby.md} +0 -0
- data/{README.rdoc → README.md} +185 -134
- data/Rakefile +41 -40
- data/VERSION +1 -1
- data/ext/json/ext/fbuffer/fbuffer.h +0 -3
- data/ext/json/ext/generator/generator.c +142 -101
- data/ext/json/ext/generator/generator.h +7 -2
- data/ext/json/ext/parser/extconf.rb +3 -0
- data/ext/json/ext/parser/parser.c +383 -463
- data/ext/json/ext/parser/parser.h +4 -5
- data/ext/json/ext/parser/parser.rl +141 -184
- data/ext/json/extconf.rb +0 -1
- data/java/src/json/ext/ByteListTranscoder.java +1 -2
- data/java/src/json/ext/Generator.java +44 -22
- data/java/src/json/ext/GeneratorMethods.java +1 -2
- data/java/src/json/ext/GeneratorService.java +1 -2
- data/java/src/json/ext/GeneratorState.java +3 -56
- data/java/src/json/ext/OptionsReader.java +2 -3
- data/java/src/json/ext/Parser.java +132 -415
- data/java/src/json/ext/Parser.rl +48 -124
- data/java/src/json/ext/ParserService.java +1 -2
- data/java/src/json/ext/RuntimeInfo.java +1 -6
- data/java/src/json/ext/StringDecoder.java +1 -2
- data/java/src/json/ext/StringEncoder.java +5 -0
- data/java/src/json/ext/Utils.java +1 -2
- data/json-java.gemspec +16 -2
- data/json.gemspec +0 -0
- data/json_pure.gemspec +24 -26
- data/lib/json/add/bigdecimal.rb +3 -2
- data/lib/json/add/complex.rb +4 -3
- data/lib/json/add/core.rb +1 -0
- data/lib/json/add/date.rb +1 -1
- data/lib/json/add/date_time.rb +1 -1
- data/lib/json/add/exception.rb +1 -1
- data/lib/json/add/ostruct.rb +3 -3
- data/lib/json/add/range.rb +1 -1
- data/lib/json/add/rational.rb +3 -2
- data/lib/json/add/regexp.rb +3 -3
- data/lib/json/add/set.rb +29 -0
- data/lib/json/add/struct.rb +1 -1
- data/lib/json/add/symbol.rb +1 -1
- data/lib/json/add/time.rb +1 -1
- data/lib/json/common.rb +26 -54
- data/lib/json/ext.rb +0 -6
- data/lib/json/generic_object.rb +5 -4
- data/lib/json/pure/generator.rb +63 -126
- data/lib/json/pure/parser.rb +41 -81
- data/lib/json/pure.rb +2 -8
- data/lib/json/version.rb +2 -1
- data/lib/json.rb +1 -0
- data/references/rfc7159.txt +899 -0
- data/tests/fixtures/obsolete_fail1.json +1 -0
- data/tests/{test_json_addition.rb → json_addition_test.rb} +32 -25
- data/tests/json_common_interface_test.rb +126 -0
- data/tests/json_encoding_test.rb +107 -0
- data/tests/json_ext_parser_test.rb +15 -0
- data/tests/{test_json_fixtures.rb → json_fixtures_test.rb} +5 -8
- data/tests/{test_json_generate.rb → json_generator_test.rb} +123 -39
- data/tests/{test_json_generic_object.rb → json_generic_object_test.rb} +15 -8
- data/tests/json_parser_test.rb +472 -0
- data/tests/json_string_matching_test.rb +38 -0
- data/tests/{setup_variant.rb → test_helper.rb} +6 -0
- data/tools/diff.sh +18 -0
- data/tools/fuzz.rb +1 -9
- metadata +30 -47
- data/COPYING +0 -58
- data/GPL +0 -340
- data/TODO +0 -1
- data/data/example.json +0 -1
- data/data/index.html +0 -38
- data/data/prototype.js +0 -4184
- data/tests/fixtures/fail1.json +0 -1
- data/tests/test_json.rb +0 -553
- data/tests/test_json_encoding.rb +0 -65
- data/tests/test_json_string_matching.rb +0 -39
- data/tests/test_json_unicode.rb +0 -72
@@ -7,14 +7,20 @@ static ID i_encoding, i_encode;
|
|
7
7
|
#endif
|
8
8
|
|
9
9
|
static VALUE mJSON, mExt, mGenerator, cState, mGeneratorMethods, mObject,
|
10
|
-
mHash, mArray,
|
10
|
+
mHash, mArray,
|
11
|
+
#ifdef RUBY_INTEGER_UNIFICATION
|
12
|
+
mInteger,
|
13
|
+
#else
|
14
|
+
mFixnum, mBignum,
|
15
|
+
#endif
|
16
|
+
mFloat, mString, mString_Extend,
|
11
17
|
mTrueClass, mFalseClass, mNilClass, eGeneratorError,
|
12
|
-
eNestingError,
|
18
|
+
eNestingError,
|
13
19
|
i_SAFE_STATE_PROTOTYPE;
|
14
20
|
|
15
21
|
static ID i_to_s, i_to_json, i_new, i_indent, i_space, i_space_before,
|
16
22
|
i_object_nl, i_array_nl, i_max_nesting, i_allow_nan, i_ascii_only,
|
17
|
-
|
23
|
+
i_pack, i_unpack, i_create_id, i_extend, i_key_p,
|
18
24
|
i_aref, i_send, i_respond_to_p, i_match, i_keys, i_depth,
|
19
25
|
i_buffer_initial_length, i_dup;
|
20
26
|
|
@@ -216,6 +222,7 @@ static void convert_UTF8_to_JSON_ASCII(FBuffer *buffer, VALUE string)
|
|
216
222
|
unicode_escape_to_buffer(buffer, buf, (UTF16)((ch & halfMask) + UNI_SUR_LOW_START));
|
217
223
|
}
|
218
224
|
}
|
225
|
+
RB_GC_GUARD(string);
|
219
226
|
}
|
220
227
|
|
221
228
|
/* Converts string to a JSON string in FBuffer buffer, where only the
|
@@ -230,6 +237,7 @@ static void convert_UTF8_to_JSON(FBuffer *buffer, VALUE string)
|
|
230
237
|
int escape_len;
|
231
238
|
unsigned char c;
|
232
239
|
char buf[6] = { '\\', 'u' };
|
240
|
+
int ascii_only = rb_enc_str_asciionly_p(string);
|
233
241
|
|
234
242
|
for (start = 0, end = 0; end < len;) {
|
235
243
|
p = ptr + end;
|
@@ -274,14 +282,17 @@ static void convert_UTF8_to_JSON(FBuffer *buffer, VALUE string)
|
|
274
282
|
break;
|
275
283
|
default:
|
276
284
|
{
|
277
|
-
unsigned short clen =
|
278
|
-
if (
|
279
|
-
|
280
|
-
|
281
|
-
|
282
|
-
|
283
|
-
|
284
|
-
|
285
|
+
unsigned short clen = 1;
|
286
|
+
if (!ascii_only) {
|
287
|
+
clen += trailingBytesForUTF8[c];
|
288
|
+
if (end + clen > len) {
|
289
|
+
rb_raise(rb_path2class("JSON::GeneratorError"),
|
290
|
+
"partial character in source, but hit end");
|
291
|
+
}
|
292
|
+
if (!isLegalUTF8((UTF8 *) p, clen)) {
|
293
|
+
rb_raise(rb_path2class("JSON::GeneratorError"),
|
294
|
+
"source sequence is illegal/malformed utf-8");
|
295
|
+
}
|
285
296
|
}
|
286
297
|
end += clen;
|
287
298
|
}
|
@@ -301,7 +312,7 @@ static char *fstrndup(const char *ptr, unsigned long len) {
|
|
301
312
|
char *result;
|
302
313
|
if (len <= 0) return NULL;
|
303
314
|
result = ALLOC_N(char, len);
|
304
|
-
|
315
|
+
memcpy(result, ptr, len);
|
305
316
|
return result;
|
306
317
|
}
|
307
318
|
|
@@ -342,6 +353,18 @@ static VALUE mArray_to_json(int argc, VALUE *argv, VALUE self) {
|
|
342
353
|
GENERATE_JSON(array);
|
343
354
|
}
|
344
355
|
|
356
|
+
#ifdef RUBY_INTEGER_UNIFICATION
|
357
|
+
/*
|
358
|
+
* call-seq: to_json(*)
|
359
|
+
*
|
360
|
+
* Returns a JSON string representation for this Integer number.
|
361
|
+
*/
|
362
|
+
static VALUE mInteger_to_json(int argc, VALUE *argv, VALUE self)
|
363
|
+
{
|
364
|
+
GENERATE_JSON(integer);
|
365
|
+
}
|
366
|
+
|
367
|
+
#else
|
345
368
|
/*
|
346
369
|
* call-seq: to_json(*)
|
347
370
|
*
|
@@ -361,6 +384,7 @@ static VALUE mBignum_to_json(int argc, VALUE *argv, VALUE self)
|
|
361
384
|
{
|
362
385
|
GENERATE_JSON(bignum);
|
363
386
|
}
|
387
|
+
#endif
|
364
388
|
|
365
389
|
/*
|
366
390
|
* call-seq: to_json(*)
|
@@ -622,8 +646,6 @@ static VALUE cState_configure(VALUE self, VALUE opts)
|
|
622
646
|
state->allow_nan = RTEST(tmp);
|
623
647
|
tmp = rb_hash_aref(opts, ID2SYM(i_ascii_only));
|
624
648
|
state->ascii_only = RTEST(tmp);
|
625
|
-
tmp = rb_hash_aref(opts, ID2SYM(i_quirks_mode));
|
626
|
-
state->quirks_mode = RTEST(tmp);
|
627
649
|
return self;
|
628
650
|
}
|
629
651
|
|
@@ -657,7 +679,6 @@ static VALUE cState_to_h(VALUE self)
|
|
657
679
|
rb_hash_aset(result, ID2SYM(i_array_nl), rb_str_new(state->array_nl, state->array_nl_len));
|
658
680
|
rb_hash_aset(result, ID2SYM(i_allow_nan), state->allow_nan ? Qtrue : Qfalse);
|
659
681
|
rb_hash_aset(result, ID2SYM(i_ascii_only), state->ascii_only ? Qtrue : Qfalse);
|
660
|
-
rb_hash_aset(result, ID2SYM(i_quirks_mode), state->quirks_mode ? Qtrue : Qfalse);
|
661
682
|
rb_hash_aset(result, ID2SYM(i_max_nesting), LONG2FIX(state->max_nesting));
|
662
683
|
rb_hash_aset(result, ID2SYM(i_depth), LONG2FIX(state->depth));
|
663
684
|
rb_hash_aset(result, ID2SYM(i_buffer_initial_length), LONG2FIX(state->buffer_initial_length));
|
@@ -675,7 +696,7 @@ static VALUE cState_aref(VALUE self, VALUE name)
|
|
675
696
|
if (RTEST(rb_funcall(self, i_respond_to_p, 1, name))) {
|
676
697
|
return rb_funcall(self, i_send, 1, name);
|
677
698
|
} else {
|
678
|
-
return
|
699
|
+
return rb_attr_get(self, rb_intern_str(rb_str_concat(rb_str_new2("@"), name)));
|
679
700
|
}
|
680
701
|
}
|
681
702
|
|
@@ -698,43 +719,83 @@ static VALUE cState_aset(VALUE self, VALUE name, VALUE value)
|
|
698
719
|
return Qnil;
|
699
720
|
}
|
700
721
|
|
701
|
-
|
722
|
+
struct hash_foreach_arg {
|
723
|
+
FBuffer *buffer;
|
724
|
+
JSON_Generator_State *state;
|
725
|
+
VALUE Vstate;
|
726
|
+
int iter;
|
727
|
+
};
|
728
|
+
|
729
|
+
static int
|
730
|
+
json_object_i(VALUE key, VALUE val, VALUE _arg)
|
702
731
|
{
|
732
|
+
struct hash_foreach_arg *arg = (struct hash_foreach_arg *)_arg;
|
733
|
+
FBuffer *buffer = arg->buffer;
|
734
|
+
JSON_Generator_State *state = arg->state;
|
735
|
+
VALUE Vstate = arg->Vstate;
|
736
|
+
|
703
737
|
char *object_nl = state->object_nl;
|
704
738
|
long object_nl_len = state->object_nl_len;
|
705
739
|
char *indent = state->indent;
|
706
740
|
long indent_len = state->indent_len;
|
707
|
-
long max_nesting = state->max_nesting;
|
708
741
|
char *delim = FBUFFER_PTR(state->object_delim);
|
709
742
|
long delim_len = FBUFFER_LEN(state->object_delim);
|
710
743
|
char *delim2 = FBUFFER_PTR(state->object_delim2);
|
711
744
|
long delim2_len = FBUFFER_LEN(state->object_delim2);
|
745
|
+
long depth = state->depth;
|
746
|
+
int j;
|
747
|
+
VALUE klass, key_to_s;
|
748
|
+
|
749
|
+
if (arg->iter > 0) fbuffer_append(buffer, delim, delim_len);
|
750
|
+
if (object_nl) {
|
751
|
+
fbuffer_append(buffer, object_nl, object_nl_len);
|
752
|
+
}
|
753
|
+
if (indent) {
|
754
|
+
for (j = 0; j < depth; j++) {
|
755
|
+
fbuffer_append(buffer, indent, indent_len);
|
756
|
+
}
|
757
|
+
}
|
758
|
+
|
759
|
+
klass = CLASS_OF(key);
|
760
|
+
if (klass == rb_cString) {
|
761
|
+
key_to_s = key;
|
762
|
+
} else if (klass == rb_cSymbol) {
|
763
|
+
key_to_s = rb_id2str(SYM2ID(key));
|
764
|
+
} else {
|
765
|
+
key_to_s = rb_funcall(key, i_to_s, 0);
|
766
|
+
}
|
767
|
+
Check_Type(key_to_s, T_STRING);
|
768
|
+
generate_json(buffer, Vstate, state, key_to_s);
|
769
|
+
fbuffer_append(buffer, delim2, delim2_len);
|
770
|
+
generate_json(buffer, Vstate, state, val);
|
771
|
+
|
772
|
+
arg->iter++;
|
773
|
+
return ST_CONTINUE;
|
774
|
+
}
|
775
|
+
|
776
|
+
static void generate_json_object(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj)
|
777
|
+
{
|
778
|
+
char *object_nl = state->object_nl;
|
779
|
+
long object_nl_len = state->object_nl_len;
|
780
|
+
char *indent = state->indent;
|
781
|
+
long indent_len = state->indent_len;
|
782
|
+
long max_nesting = state->max_nesting;
|
712
783
|
long depth = ++state->depth;
|
713
|
-
int
|
714
|
-
|
784
|
+
int j;
|
785
|
+
struct hash_foreach_arg arg;
|
786
|
+
|
715
787
|
if (max_nesting != 0 && depth > max_nesting) {
|
716
788
|
fbuffer_free(buffer);
|
717
789
|
rb_raise(eNestingError, "nesting of %ld is too deep", --state->depth);
|
718
790
|
}
|
719
791
|
fbuffer_append_char(buffer, '{');
|
720
|
-
|
721
|
-
|
722
|
-
|
723
|
-
|
724
|
-
|
725
|
-
|
726
|
-
|
727
|
-
for (j = 0; j < depth; j++) {
|
728
|
-
fbuffer_append(buffer, indent, indent_len);
|
729
|
-
}
|
730
|
-
}
|
731
|
-
key = rb_ary_entry(keys, i);
|
732
|
-
key_to_s = rb_funcall(key, i_to_s, 0);
|
733
|
-
Check_Type(key_to_s, T_STRING);
|
734
|
-
generate_json(buffer, Vstate, state, key_to_s);
|
735
|
-
fbuffer_append(buffer, delim2, delim2_len);
|
736
|
-
generate_json(buffer, Vstate, state, rb_hash_aref(obj, key));
|
737
|
-
}
|
792
|
+
|
793
|
+
arg.buffer = buffer;
|
794
|
+
arg.state = state;
|
795
|
+
arg.Vstate = Vstate;
|
796
|
+
arg.iter = 0;
|
797
|
+
rb_hash_foreach(obj, json_object_i, (VALUE)&arg);
|
798
|
+
|
738
799
|
depth = --state->depth;
|
739
800
|
if (object_nl) {
|
740
801
|
fbuffer_append(buffer, object_nl, object_nl_len);
|
@@ -785,11 +846,22 @@ static void generate_json_array(FBuffer *buffer, VALUE Vstate, JSON_Generator_St
|
|
785
846
|
fbuffer_append_char(buffer, ']');
|
786
847
|
}
|
787
848
|
|
849
|
+
#ifdef HAVE_RUBY_ENCODING_H
|
850
|
+
static int enc_utf8_compatible_p(rb_encoding *enc)
|
851
|
+
{
|
852
|
+
if (enc == rb_usascii_encoding()) return 1;
|
853
|
+
if (enc == rb_utf8_encoding()) return 1;
|
854
|
+
return 0;
|
855
|
+
}
|
856
|
+
#endif
|
857
|
+
|
788
858
|
static void generate_json_string(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj)
|
789
859
|
{
|
790
860
|
fbuffer_append_char(buffer, '"');
|
791
861
|
#ifdef HAVE_RUBY_ENCODING_H
|
792
|
-
|
862
|
+
if (!enc_utf8_compatible_p(rb_enc_get(obj))) {
|
863
|
+
obj = rb_str_encode(obj, CEncoding_UTF_8, 0, Qnil);
|
864
|
+
}
|
793
865
|
#endif
|
794
866
|
if (state->ascii_only) {
|
795
867
|
convert_UTF8_to_JSON_ASCII(buffer, obj);
|
@@ -825,6 +897,15 @@ static void generate_json_bignum(FBuffer *buffer, VALUE Vstate, JSON_Generator_S
|
|
825
897
|
fbuffer_append_str(buffer, tmp);
|
826
898
|
}
|
827
899
|
|
900
|
+
#ifdef RUBY_INTEGER_UNIFICATION
|
901
|
+
static void generate_json_integer(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj)
|
902
|
+
{
|
903
|
+
if (FIXNUM_P(obj))
|
904
|
+
generate_json_fixnum(buffer, Vstate, state, obj);
|
905
|
+
else
|
906
|
+
generate_json_bignum(buffer, Vstate, state, obj);
|
907
|
+
}
|
908
|
+
#endif
|
828
909
|
static void generate_json_float(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj)
|
829
910
|
{
|
830
911
|
double value = RFLOAT_VALUE(obj);
|
@@ -858,9 +939,9 @@ static void generate_json(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *s
|
|
858
939
|
generate_json_false(buffer, Vstate, state, obj);
|
859
940
|
} else if (obj == Qtrue) {
|
860
941
|
generate_json_true(buffer, Vstate, state, obj);
|
861
|
-
} else if (
|
942
|
+
} else if (FIXNUM_P(obj)) {
|
862
943
|
generate_json_fixnum(buffer, Vstate, state, obj);
|
863
|
-
} else if (
|
944
|
+
} else if (RB_TYPE_P(obj, T_BIGNUM)) {
|
864
945
|
generate_json_bignum(buffer, Vstate, state, obj);
|
865
946
|
} else if (klass == rb_cFloat) {
|
866
947
|
generate_json_float(buffer, Vstate, state, obj);
|
@@ -871,7 +952,7 @@ static void generate_json(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *s
|
|
871
952
|
} else {
|
872
953
|
tmp = rb_funcall(obj, i_to_s, 0);
|
873
954
|
Check_Type(tmp, T_STRING);
|
874
|
-
|
955
|
+
generate_json_string(buffer, Vstate, state, tmp);
|
875
956
|
}
|
876
957
|
}
|
877
958
|
|
@@ -914,21 +995,6 @@ static VALUE cState_partial_generate(VALUE self, VALUE obj)
|
|
914
995
|
return fbuffer_to_s(buffer);
|
915
996
|
}
|
916
997
|
|
917
|
-
/*
|
918
|
-
* This function returns true if string is either a JSON array or JSON object.
|
919
|
-
* It might suffer from false positives, e. g. syntactically incorrect JSON in
|
920
|
-
* the string or certain UTF-8 characters on the right hand side.
|
921
|
-
*/
|
922
|
-
static int isArrayOrObject(VALUE string)
|
923
|
-
{
|
924
|
-
long string_len = RSTRING_LEN(string);
|
925
|
-
char *p = RSTRING_PTR(string), *q = p + string_len - 1;
|
926
|
-
if (string_len < 2) return 0;
|
927
|
-
for (; p < q && isspace((unsigned char)*p); p++);
|
928
|
-
for (; q > p && isspace((unsigned char)*q); q--);
|
929
|
-
return (*p == '[' && *q == ']') || (*p == '{' && *q == '}');
|
930
|
-
}
|
931
|
-
|
932
998
|
/*
|
933
999
|
* call-seq: generate(obj)
|
934
1000
|
*
|
@@ -940,9 +1006,7 @@ static VALUE cState_generate(VALUE self, VALUE obj)
|
|
940
1006
|
{
|
941
1007
|
VALUE result = cState_partial_generate(self, obj);
|
942
1008
|
GET_STATE(self);
|
943
|
-
|
944
|
-
rb_raise(eGeneratorError, "only generation of JSON objects or arrays allowed");
|
945
|
-
}
|
1009
|
+
(void)state;
|
946
1010
|
return result;
|
947
1011
|
}
|
948
1012
|
|
@@ -961,8 +1025,8 @@ static VALUE cState_generate(VALUE self, VALUE obj)
|
|
961
1025
|
* * *allow_nan*: true if NaN, Infinity, and -Infinity should be
|
962
1026
|
* generated, otherwise an exception is thrown, if these values are
|
963
1027
|
* encountered. This options defaults to false.
|
964
|
-
* * *
|
965
|
-
*
|
1028
|
+
* * *ascii_only*: true if only ASCII characters should be generated. This
|
1029
|
+
* ontions defaults to false.
|
966
1030
|
* * *buffer_initial_length*: sets the initial length of the generator's
|
967
1031
|
* internal buffer.
|
968
1032
|
*/
|
@@ -1018,10 +1082,8 @@ static VALUE cState_from_state_s(VALUE self, VALUE opts)
|
|
1018
1082
|
} else if (rb_obj_is_kind_of(opts, rb_cHash)) {
|
1019
1083
|
return rb_funcall(self, i_new, 1, opts);
|
1020
1084
|
} else {
|
1021
|
-
|
1022
|
-
|
1023
|
-
}
|
1024
|
-
return rb_funcall(CJSON_SAFE_STATE_PROTOTYPE, i_dup, 0);
|
1085
|
+
VALUE prototype = rb_const_get(mJSON, i_SAFE_STATE_PROTOTYPE);
|
1086
|
+
return rb_funcall(prototype, i_dup, 0);
|
1025
1087
|
}
|
1026
1088
|
}
|
1027
1089
|
|
@@ -1055,7 +1117,7 @@ static VALUE cState_indent_set(VALUE self, VALUE indent)
|
|
1055
1117
|
}
|
1056
1118
|
} else {
|
1057
1119
|
if (state->indent) ruby_xfree(state->indent);
|
1058
|
-
state->indent =
|
1120
|
+
state->indent = fstrndup(RSTRING_PTR(indent), len);
|
1059
1121
|
state->indent_len = len;
|
1060
1122
|
}
|
1061
1123
|
return Qnil;
|
@@ -1093,7 +1155,7 @@ static VALUE cState_space_set(VALUE self, VALUE space)
|
|
1093
1155
|
}
|
1094
1156
|
} else {
|
1095
1157
|
if (state->space) ruby_xfree(state->space);
|
1096
|
-
state->space =
|
1158
|
+
state->space = fstrndup(RSTRING_PTR(space), len);
|
1097
1159
|
state->space_len = len;
|
1098
1160
|
}
|
1099
1161
|
return Qnil;
|
@@ -1129,7 +1191,7 @@ static VALUE cState_space_before_set(VALUE self, VALUE space_before)
|
|
1129
1191
|
}
|
1130
1192
|
} else {
|
1131
1193
|
if (state->space_before) ruby_xfree(state->space_before);
|
1132
|
-
state->space_before =
|
1194
|
+
state->space_before = fstrndup(RSTRING_PTR(space_before), len);
|
1133
1195
|
state->space_before_len = len;
|
1134
1196
|
}
|
1135
1197
|
return Qnil;
|
@@ -1166,7 +1228,7 @@ static VALUE cState_object_nl_set(VALUE self, VALUE object_nl)
|
|
1166
1228
|
}
|
1167
1229
|
} else {
|
1168
1230
|
if (state->object_nl) ruby_xfree(state->object_nl);
|
1169
|
-
state->object_nl =
|
1231
|
+
state->object_nl = fstrndup(RSTRING_PTR(object_nl), len);
|
1170
1232
|
state->object_nl_len = len;
|
1171
1233
|
}
|
1172
1234
|
return Qnil;
|
@@ -1201,7 +1263,7 @@ static VALUE cState_array_nl_set(VALUE self, VALUE array_nl)
|
|
1201
1263
|
}
|
1202
1264
|
} else {
|
1203
1265
|
if (state->array_nl) ruby_xfree(state->array_nl);
|
1204
|
-
state->array_nl =
|
1266
|
+
state->array_nl = fstrndup(RSTRING_PTR(array_nl), len);
|
1205
1267
|
state->array_nl_len = len;
|
1206
1268
|
}
|
1207
1269
|
return Qnil;
|
@@ -1260,7 +1322,7 @@ static VALUE cState_allow_nan_p(VALUE self)
|
|
1260
1322
|
/*
|
1261
1323
|
* call-seq: ascii_only?
|
1262
1324
|
*
|
1263
|
-
* Returns true, if
|
1325
|
+
* Returns true, if only ASCII characters should be generated. Otherwise
|
1264
1326
|
* returns false.
|
1265
1327
|
*/
|
1266
1328
|
static VALUE cState_ascii_only_p(VALUE self)
|
@@ -1269,29 +1331,6 @@ static VALUE cState_ascii_only_p(VALUE self)
|
|
1269
1331
|
return state->ascii_only ? Qtrue : Qfalse;
|
1270
1332
|
}
|
1271
1333
|
|
1272
|
-
/*
|
1273
|
-
* call-seq: quirks_mode?
|
1274
|
-
*
|
1275
|
-
* Returns true, if quirks mode is enabled. Otherwise returns false.
|
1276
|
-
*/
|
1277
|
-
static VALUE cState_quirks_mode_p(VALUE self)
|
1278
|
-
{
|
1279
|
-
GET_STATE(self);
|
1280
|
-
return state->quirks_mode ? Qtrue : Qfalse;
|
1281
|
-
}
|
1282
|
-
|
1283
|
-
/*
|
1284
|
-
* call-seq: quirks_mode=(enable)
|
1285
|
-
*
|
1286
|
-
* If set to true, enables the quirks_mode mode.
|
1287
|
-
*/
|
1288
|
-
static VALUE cState_quirks_mode_set(VALUE self, VALUE enable)
|
1289
|
-
{
|
1290
|
-
GET_STATE(self);
|
1291
|
-
state->quirks_mode = RTEST(enable);
|
1292
|
-
return Qnil;
|
1293
|
-
}
|
1294
|
-
|
1295
1334
|
/*
|
1296
1335
|
* call-seq: depth
|
1297
1336
|
*
|
@@ -1351,6 +1390,7 @@ static VALUE cState_buffer_initial_length_set(VALUE self, VALUE buffer_initial_l
|
|
1351
1390
|
*/
|
1352
1391
|
void Init_generator(void)
|
1353
1392
|
{
|
1393
|
+
#undef rb_intern
|
1354
1394
|
rb_require("json/common");
|
1355
1395
|
|
1356
1396
|
mJSON = rb_define_module("JSON");
|
@@ -1359,6 +1399,8 @@ void Init_generator(void)
|
|
1359
1399
|
|
1360
1400
|
eGeneratorError = rb_path2class("JSON::GeneratorError");
|
1361
1401
|
eNestingError = rb_path2class("JSON::NestingError");
|
1402
|
+
rb_gc_register_mark_object(eGeneratorError);
|
1403
|
+
rb_gc_register_mark_object(eNestingError);
|
1362
1404
|
|
1363
1405
|
cState = rb_define_class_under(mGenerator, "State", rb_cObject);
|
1364
1406
|
rb_define_alloc_func(cState, cState_s_allocate);
|
@@ -1380,9 +1422,6 @@ void Init_generator(void)
|
|
1380
1422
|
rb_define_method(cState, "check_circular?", cState_check_circular_p, 0);
|
1381
1423
|
rb_define_method(cState, "allow_nan?", cState_allow_nan_p, 0);
|
1382
1424
|
rb_define_method(cState, "ascii_only?", cState_ascii_only_p, 0);
|
1383
|
-
rb_define_method(cState, "quirks_mode?", cState_quirks_mode_p, 0);
|
1384
|
-
rb_define_method(cState, "quirks_mode", cState_quirks_mode_p, 0);
|
1385
|
-
rb_define_method(cState, "quirks_mode=", cState_quirks_mode_set, 1);
|
1386
1425
|
rb_define_method(cState, "depth", cState_depth, 0);
|
1387
1426
|
rb_define_method(cState, "depth=", cState_depth_set, 1);
|
1388
1427
|
rb_define_method(cState, "buffer_initial_length", cState_buffer_initial_length, 0);
|
@@ -1402,10 +1441,15 @@ void Init_generator(void)
|
|
1402
1441
|
rb_define_method(mHash, "to_json", mHash_to_json, -1);
|
1403
1442
|
mArray = rb_define_module_under(mGeneratorMethods, "Array");
|
1404
1443
|
rb_define_method(mArray, "to_json", mArray_to_json, -1);
|
1444
|
+
#ifdef RUBY_INTEGER_UNIFICATION
|
1445
|
+
mInteger = rb_define_module_under(mGeneratorMethods, "Integer");
|
1446
|
+
rb_define_method(mInteger, "to_json", mInteger_to_json, -1);
|
1447
|
+
#else
|
1405
1448
|
mFixnum = rb_define_module_under(mGeneratorMethods, "Fixnum");
|
1406
1449
|
rb_define_method(mFixnum, "to_json", mFixnum_to_json, -1);
|
1407
1450
|
mBignum = rb_define_module_under(mGeneratorMethods, "Bignum");
|
1408
1451
|
rb_define_method(mBignum, "to_json", mBignum_to_json, -1);
|
1452
|
+
#endif
|
1409
1453
|
mFloat = rb_define_module_under(mGeneratorMethods, "Float");
|
1410
1454
|
rb_define_method(mFloat, "to_json", mFloat_to_json, -1);
|
1411
1455
|
mString = rb_define_module_under(mGeneratorMethods, "String");
|
@@ -1422,7 +1466,6 @@ void Init_generator(void)
|
|
1422
1466
|
mNilClass = rb_define_module_under(mGeneratorMethods, "NilClass");
|
1423
1467
|
rb_define_method(mNilClass, "to_json", mNilClass_to_json, -1);
|
1424
1468
|
|
1425
|
-
CRegexp_MULTILINE = rb_const_get(rb_cRegexp, rb_intern("MULTILINE"));
|
1426
1469
|
i_to_s = rb_intern("to_s");
|
1427
1470
|
i_to_json = rb_intern("to_json");
|
1428
1471
|
i_new = rb_intern("new");
|
@@ -1434,7 +1477,6 @@ void Init_generator(void)
|
|
1434
1477
|
i_max_nesting = rb_intern("max_nesting");
|
1435
1478
|
i_allow_nan = rb_intern("allow_nan");
|
1436
1479
|
i_ascii_only = rb_intern("ascii_only");
|
1437
|
-
i_quirks_mode = rb_intern("quirks_mode");
|
1438
1480
|
i_depth = rb_intern("depth");
|
1439
1481
|
i_buffer_initial_length = rb_intern("buffer_initial_length");
|
1440
1482
|
i_pack = rb_intern("pack");
|
@@ -1454,5 +1496,4 @@ void Init_generator(void)
|
|
1454
1496
|
i_encode = rb_intern("encode");
|
1455
1497
|
#endif
|
1456
1498
|
i_SAFE_STATE_PROTOTYPE = rb_intern("SAFE_STATE_PROTOTYPE");
|
1457
|
-
CJSON_SAFE_STATE_PROTOTYPE = Qnil;
|
1458
1499
|
}
|
@@ -1,7 +1,6 @@
|
|
1
1
|
#ifndef _GENERATOR_H_
|
2
2
|
#define _GENERATOR_H_
|
3
3
|
|
4
|
-
#include <string.h>
|
5
4
|
#include <math.h>
|
6
5
|
#include <ctype.h>
|
7
6
|
|
@@ -73,7 +72,6 @@ typedef struct JSON_Generator_StateStruct {
|
|
73
72
|
long max_nesting;
|
74
73
|
char allow_nan;
|
75
74
|
char ascii_only;
|
76
|
-
char quirks_mode;
|
77
75
|
long depth;
|
78
76
|
long buffer_initial_length;
|
79
77
|
} JSON_Generator_State;
|
@@ -99,8 +97,12 @@ typedef struct JSON_Generator_StateStruct {
|
|
99
97
|
|
100
98
|
static VALUE mHash_to_json(int argc, VALUE *argv, VALUE self);
|
101
99
|
static VALUE mArray_to_json(int argc, VALUE *argv, VALUE self);
|
100
|
+
#ifdef RUBY_INTEGER_UNIFICATION
|
101
|
+
static VALUE mInteger_to_json(int argc, VALUE *argv, VALUE self);
|
102
|
+
#else
|
102
103
|
static VALUE mFixnum_to_json(int argc, VALUE *argv, VALUE self);
|
103
104
|
static VALUE mBignum_to_json(int argc, VALUE *argv, VALUE self);
|
105
|
+
#endif
|
104
106
|
static VALUE mFloat_to_json(int argc, VALUE *argv, VALUE self);
|
105
107
|
static VALUE mString_included_s(VALUE self, VALUE modul);
|
106
108
|
static VALUE mString_to_json(int argc, VALUE *argv, VALUE self);
|
@@ -122,6 +124,9 @@ static void generate_json_string(FBuffer *buffer, VALUE Vstate, JSON_Generator_S
|
|
122
124
|
static void generate_json_null(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj);
|
123
125
|
static void generate_json_false(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj);
|
124
126
|
static void generate_json_true(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj);
|
127
|
+
#ifdef RUBY_INTEGER_UNIFICATION
|
128
|
+
static void generate_json_integer(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj);
|
129
|
+
#endif
|
125
130
|
static void generate_json_fixnum(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj);
|
126
131
|
static void generate_json_bignum(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj);
|
127
132
|
static void generate_json_float(FBuffer *buffer, VALUE Vstate, JSON_Generator_State *state, VALUE obj);
|