oj 1.2.0 → 1.2.1

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

Potentially problematic release.


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

@@ -1,7 +1,37 @@
1
1
  require 'mkmf'
2
2
 
3
- $CPPFLAGS += ' -Wall'
4
- #puts "*** $CPPFLAGS: #{$CPPFLAGS}"
5
3
  extension_name = 'oj'
6
4
  dir_config(extension_name)
5
+
6
+ parts = RUBY_DESCRIPTION.split(' ')
7
+ type = parts[0]
8
+ type = 'ree' if 'ruby' == type && RUBY_DESCRIPTION.include?('Ruby Enterprise Edition')
9
+ version = RUBY_VERSION.split('.')
10
+ puts ">>>>> Creating Makefile for #{type} version #{RUBY_VERSION} <<<<<"
11
+
12
+ dflags = {
13
+ 'RUBY_TYPE' => type,
14
+ (type.upcase + '_RUBY') => nil,
15
+ 'RUBY_VERSION' => RUBY_VERSION,
16
+ 'RUBY_VERSION_MAJOR' => version[0],
17
+ 'RUBY_VERSION_MINOR' => version[1],
18
+ 'RUBY_VERSION_MICRO' => version[2],
19
+ 'HAS_RB_TIME_TIMESPEC' => ('ruby' == type && '1.9.3' == RUBY_VERSION) ? 1 : 0,
20
+ 'HAS_ENCODING_SUPPORT' => ('ruby' == type && '1' == version[0] && '9' == version[1]) ? 1 : 0,
21
+ 'HAS_NANO_TIME' => ('ruby' == type && '1' == version[0] && '9' == version[1]) ? 1 : 0,
22
+ 'HAS_RSTRUCT' => ('ruby' == type || 'ree' == type) ? 1 : 0,
23
+ 'HAS_IVAR_HELPERS' => ('ruby' == type && '1' == version[0] && '9' == version[1]) ? 1 : 0,
24
+ 'HAS_PROC_WITH_BLOCK' => ('ruby' == type && '1' == version[0] && '9' == version[1]) ? 1 : 0,
25
+ 'HAS_TOP_LEVEL_ST_H' => ('ree' == type || ('ruby' == type && '1' == version[0] && '8' == version[1])) ? 1 : 0,
26
+ }
27
+
28
+ dflags.each do |k,v|
29
+ if v.nil?
30
+ $CPPFLAGS += " -D#{k}"
31
+ else
32
+ $CPPFLAGS += " -D#{k}=#{v}"
33
+ end
34
+ end
35
+ $CPPFLAGS += ' -Wall'
36
+ #puts "*** $CPPFLAGS: #{$CPPFLAGS}"
7
37
  create_makefile(extension_name)
@@ -50,15 +50,10 @@ typedef struct _Batch {
50
50
 
51
51
  typedef struct _Doc {
52
52
  Leaf data;
53
- Leaf *where; // points to current location
53
+ Leaf *where; // points to current location
54
54
  Leaf where_path[MAX_STACK]; // points to head of path
55
- #ifdef HAVE_RUBY_ENCODING_H
56
- rb_encoding *encoding;
57
- #else
58
- void *encoding;
59
- #endif
60
55
  char *json;
61
- unsigned long size; // number of leaves/branches in the doc
56
+ unsigned long size; // number of leaves/branches in the doc
62
57
  VALUE self;
63
58
  Batch batches;
64
59
  struct _Batch batch0;
@@ -156,11 +151,11 @@ next_white(ParseInfo pi) {
156
151
  inline static char*
157
152
  ulong_fill(char *s, size_t num) {
158
153
  char buf[32];
159
- char *b = buf + sizeof(buf) - 1;
154
+ char *b = buf + sizeof(buf) - 1;
160
155
 
161
156
  *b-- = '\0';
162
157
  for (; 0 < num; num /= 10, b--) {
163
- *b = (num % 10) + '0';
158
+ *b = (num % 10) + '0';
164
159
  }
165
160
  b++;
166
161
  if ('\0' == *b) {
@@ -256,10 +251,8 @@ leaf_value(Doc doc, Leaf leaf) {
256
251
  break;
257
252
  case T_STRING:
258
253
  leaf->value = rb_str_new2(leaf->str);
259
- #ifdef HAVE_RUBY_ENCODING_H
260
- if (0 != doc->encoding) {
261
- rb_enc_associate(leaf->value, doc->encoding);
262
- }
254
+ #if HAS_ENCODING_SUPPORT
255
+ rb_enc_associate(leaf->value, oj_utf8_encoding);
263
256
  #endif
264
257
  leaf->value_type = RUBY_VAL;
265
258
  break;
@@ -317,7 +310,7 @@ skip_comment(ParseInfo pi) {
317
310
  }
318
311
  }
319
312
 
320
- #ifdef RUBINIUS
313
+ #ifdef RUBINIUS_RUBY
321
314
  #define NUM_MAX 0x07FFFFFF
322
315
  #else
323
316
  #define NUM_MAX (FIXNUM_MAX >> 8)
@@ -358,13 +351,7 @@ leaf_fixnum_value(Leaf leaf) {
358
351
  leaf->value_type = RUBY_VAL;
359
352
  }
360
353
 
361
- #if 1
362
- static void
363
- leaf_float_value(Leaf leaf) {
364
- leaf->value = rb_float_new(rb_cstr_to_dbl(leaf->str, 1));
365
- leaf->value_type = RUBY_VAL;
366
- }
367
- #else
354
+ #ifdef JRUBY_RUBY
368
355
  static void
369
356
  leaf_float_value(Leaf leaf) {
370
357
  char *s = leaf->str;
@@ -426,10 +413,16 @@ leaf_float_value(Leaf leaf) {
426
413
  }
427
414
  d *= pow(10.0, e);
428
415
  }
429
- leaf->value = DBL2NUM(d);
416
+ leaf->value = rb_float_new(d);
430
417
  }
431
418
  leaf->value_type = RUBY_VAL;
432
419
  }
420
+ #else
421
+ static void
422
+ leaf_float_value(Leaf leaf) {
423
+ leaf->value = rb_float_new(rb_cstr_to_dbl(leaf->str, 1));
424
+ leaf->value_type = RUBY_VAL;
425
+ }
433
426
  #endif
434
427
 
435
428
  static VALUE
@@ -459,10 +452,8 @@ leaf_hash_value(Doc doc, Leaf leaf) {
459
452
 
460
453
  do {
461
454
  key = rb_str_new2(e->key);
462
- #ifdef HAVE_RUBY_ENCODING_H
463
- if (0 != doc->encoding) {
464
- rb_enc_associate(key, doc->encoding);
465
- }
455
+ #if HAS_ENCODING_SUPPORT
456
+ rb_enc_associate(key, oj_utf8_encoding);
466
457
  #endif
467
458
  rb_hash_aset(h, key, leaf_value(doc, e));
468
459
  e = e->next;
@@ -722,7 +713,7 @@ static char*
722
713
  read_quoted_value(ParseInfo pi) {
723
714
  char *value = 0;
724
715
  char *h = pi->s; // head
725
- char *t = h; // tail
716
+ char *t = h; // tail
726
717
 
727
718
  h++; // skip quote character
728
719
  t++;
@@ -1138,7 +1129,7 @@ doc_open_file(VALUE clas, VALUE filename) {
1138
1129
  Check_Type(filename, T_STRING);
1139
1130
  path = StringValuePtr(filename);
1140
1131
  if (0 == (f = fopen(path, "r"))) {
1141
- rb_raise(rb_eIOError, "%s\n", strerror(errno));
1132
+ rb_raise(rb_eIOError, "%s\n", strerror(errno));
1142
1133
  }
1143
1134
  fseek(f, 0, SEEK_END);
1144
1135
  len = ftell(f);
@@ -1150,8 +1141,8 @@ doc_open_file(VALUE clas, VALUE filename) {
1150
1141
  }
1151
1142
  fseek(f, 0, SEEK_SET);
1152
1143
  if (len != fread(json, 1, len, f)) {
1153
- fclose(f);
1154
- rb_raise(rb_eLoadError, "Failed to read %lu bytes from %s.\n", (unsigned long)len, path);
1144
+ fclose(f);
1145
+ rb_raise(rb_eLoadError, "Failed to read %lu bytes from %s.\n", (unsigned long)len, path);
1155
1146
  }
1156
1147
  fclose(f);
1157
1148
  json[len] = '\0';
@@ -1212,9 +1203,9 @@ doc_where(VALUE self) {
1212
1203
  *
1213
1204
  * Returns the final key to the current location.
1214
1205
  * @example
1215
- * Oj::Doc.open('[1,2,3]') { |doc| doc.move('/2'); doc.local_key() } #=> 2
1206
+ * Oj::Doc.open('[1,2,3]') { |doc| doc.move('/2'); doc.local_key() } #=> 2
1216
1207
  * Oj::Doc.open('{"one":3}') { |doc| doc.move('/one'); doc.local_key() } #=> "one"
1217
- * Oj::Doc.open('[1,2,3]') { |doc| doc.local_key() } #=> nil
1208
+ * Oj::Doc.open('[1,2,3]') { |doc| doc.local_key() } #=> nil
1218
1209
  */
1219
1210
  static VALUE
1220
1211
  doc_local_key(VALUE self) {
@@ -1224,10 +1215,8 @@ doc_local_key(VALUE self) {
1224
1215
 
1225
1216
  if (T_HASH == leaf->parent_type) {
1226
1217
  key = rb_str_new2(leaf->key);
1227
- #ifdef HAVE_RUBY_ENCODING_H
1228
- if (0 != doc->encoding) {
1229
- rb_enc_associate(key, doc->encoding);
1230
- }
1218
+ #if HAS_ENCODING_SUPPORT
1219
+ rb_enc_associate(key, oj_utf8_encoding);
1231
1220
  #endif
1232
1221
  } else if (T_ARRAY == leaf->parent_type) {
1233
1222
  key = LONG2NUM(leaf->index);
@@ -1260,7 +1249,7 @@ doc_home(VALUE self) {
1260
1249
  * is low.
1261
1250
  * @param [String] path path to the location to get the type of if provided
1262
1251
  * @example
1263
- * Oj::Doc.open('[1,2]') { |doc| doc.type() } #=> Array
1252
+ * Oj::Doc.open('[1,2]') { |doc| doc.type() } #=> Array
1264
1253
  * Oj::Doc.open('[1,2]') { |doc| doc.type('/1') } #=> Fixnum
1265
1254
  */
1266
1255
  static VALUE
@@ -40,10 +40,10 @@ enum {
40
40
  };
41
41
 
42
42
  typedef struct _CircArray {
43
- VALUE obj_array[1024];
44
- VALUE *objs;
45
- unsigned long size; // allocated size or initial array size
46
- unsigned long cnt;
43
+ VALUE obj_array[1024];
44
+ VALUE *objs;
45
+ unsigned long size; // allocated size or initial array size
46
+ unsigned long cnt;
47
47
  } *CircArray;
48
48
 
49
49
  typedef struct _ParseInfo {
@@ -124,8 +124,8 @@ next_white(ParseInfo pi) {
124
124
 
125
125
  inline static VALUE
126
126
  resolve_classname(VALUE mod, const char *class_name, int auto_define) {
127
- VALUE clas;
128
- ID ci = rb_intern(class_name);
127
+ VALUE clas;
128
+ ID ci = rb_intern(class_name);
129
129
 
130
130
  if (rb_const_defined_at(mod, ci) || !auto_define) {
131
131
  clas = rb_const_get_at(mod, ci);
@@ -140,55 +140,55 @@ classname2obj(const char *name, ParseInfo pi) {
140
140
  VALUE clas = classname2class(name, pi);
141
141
 
142
142
  if (Qundef == clas) {
143
- return Qnil;
143
+ return Qnil;
144
144
  } else {
145
- return rb_obj_alloc(clas);
145
+ return rb_obj_alloc(clas);
146
146
  }
147
147
  }
148
148
 
149
149
  static VALUE
150
150
  classname2class(const char *name, ParseInfo pi) {
151
- VALUE clas;
152
- VALUE *slot;
151
+ VALUE clas;
152
+ VALUE *slot;
153
153
  int auto_define = (Yes == pi->options->auto_define);
154
154
 
155
155
  if (Qundef == (clas = oj_cache_get(oj_class_cache, name, &slot))) {
156
- char class_name[1024];
157
- char *s;
158
- const char *n = name;
159
-
160
- clas = rb_cObject;
161
- for (s = class_name; '\0' != *n; n++) {
162
- if (':' == *n) {
163
- *s = '\0';
164
- n++;
156
+ char class_name[1024];
157
+ char *s;
158
+ const char *n = name;
159
+
160
+ clas = rb_cObject;
161
+ for (s = class_name; '\0' != *n; n++) {
162
+ if (':' == *n) {
163
+ *s = '\0';
164
+ n++;
165
165
  if (':' != *n) {
166
- raise_error("Invalid classname, expected another ':'", pi->str, pi->s);
166
+ raise_error("Invalid classname, expected another ':'", pi->str, pi->s);
167
167
  }
168
- if (Qundef == (clas = resolve_classname(clas, class_name, auto_define))) {
169
- return Qundef;
170
- }
171
- s = class_name;
172
- } else {
173
- *s++ = *n;
174
- }
175
- }
176
- *s = '\0';
177
- if (Qundef != (clas = resolve_classname(clas, class_name, auto_define))) {
178
- *slot = clas;
179
- }
168
+ if (Qundef == (clas = resolve_classname(clas, class_name, auto_define))) {
169
+ return Qundef;
170
+ }
171
+ s = class_name;
172
+ } else {
173
+ *s++ = *n;
174
+ }
175
+ }
176
+ *s = '\0';
177
+ if (Qundef != (clas = resolve_classname(clas, class_name, auto_define))) {
178
+ *slot = clas;
179
+ }
180
180
  }
181
181
  return clas;
182
182
  }
183
183
 
184
- #ifndef NO_RSTRUCT
184
+ #if HAS_RSTRUCT
185
185
  inline static VALUE
186
186
  structname2obj(const char *name) {
187
- VALUE ost;
187
+ VALUE ost;
188
188
 
189
189
  ost = rb_const_get(oj_struct_class, rb_intern(name));
190
190
  // use encoding as the indicator for Ruby 1.8.7 or 1.9.x
191
- #ifdef HAVE_RUBY_ENCODING_H
191
+ #if HAS_ENCODING_SUPPORT
192
192
  return rb_struct_alloc_noinit(ost);
193
193
  #else
194
194
  return rb_struct_new(ost);
@@ -212,10 +212,10 @@ read_ulong(const char *s, ParseInfo pi) {
212
212
 
213
213
  static CircArray
214
214
  circ_array_new() {
215
- CircArray ca;
215
+ CircArray ca;
216
216
 
217
217
  if (0 == (ca = ALLOC(struct _CircArray))) {
218
- rb_raise(rb_eNoMemError, "not enough memory\n");
218
+ rb_raise(rb_eNoMemError, "not enough memory\n");
219
219
  }
220
220
  ca->objs = ca->obj_array;
221
221
  ca->size = sizeof(ca->obj_array) / sizeof(VALUE);
@@ -227,7 +227,7 @@ circ_array_new() {
227
227
  static void
228
228
  circ_array_free(CircArray ca) {
229
229
  if (ca->objs != ca->obj_array) {
230
- xfree(ca->objs);
230
+ xfree(ca->objs);
231
231
  }
232
232
  xfree(ca);
233
233
  }
@@ -235,41 +235,41 @@ circ_array_free(CircArray ca) {
235
235
  static void
236
236
  circ_array_set(CircArray ca, VALUE obj, unsigned long id) {
237
237
  if (0 < id && 0 != ca) {
238
- unsigned long i;
239
-
240
- if (ca->size < id) {
241
- unsigned long cnt = id + 512;
242
-
243
- if (ca->objs == ca->obj_array) {
244
- if (0 == (ca->objs = ALLOC_N(VALUE, cnt))) {
245
- rb_raise(rb_eNoMemError, "not enough memory\n");
246
- }
247
- memcpy(ca->objs, ca->obj_array, sizeof(VALUE) * ca->cnt);
248
- } else {
249
- ca->objs = REALLOC_N(ca->objs, VALUE, cnt);
250
- if (0 == ca->objs) {
251
- rb_raise(rb_eNoMemError, "not enough memory\n");
252
- }
253
- }
254
- ca->size = cnt;
255
- }
256
- id--;
257
- for (i = ca->cnt; i < id; i++) {
258
- ca->objs[i] = Qnil;
259
- }
260
- ca->objs[id] = obj;
261
- if (ca->cnt <= id) {
262
- ca->cnt = id + 1;
263
- }
238
+ unsigned long i;
239
+
240
+ if (ca->size < id) {
241
+ unsigned long cnt = id + 512;
242
+
243
+ if (ca->objs == ca->obj_array) {
244
+ if (0 == (ca->objs = ALLOC_N(VALUE, cnt))) {
245
+ rb_raise(rb_eNoMemError, "not enough memory\n");
246
+ }
247
+ memcpy(ca->objs, ca->obj_array, sizeof(VALUE) * ca->cnt);
248
+ } else {
249
+ ca->objs = REALLOC_N(ca->objs, VALUE, cnt);
250
+ if (0 == ca->objs) {
251
+ rb_raise(rb_eNoMemError, "not enough memory\n");
252
+ }
253
+ }
254
+ ca->size = cnt;
255
+ }
256
+ id--;
257
+ for (i = ca->cnt; i < id; i++) {
258
+ ca->objs[i] = Qnil;
259
+ }
260
+ ca->objs[id] = obj;
261
+ if (ca->cnt <= id) {
262
+ ca->cnt = id + 1;
263
+ }
264
264
  }
265
265
  }
266
266
 
267
267
  static VALUE
268
268
  circ_array_get(CircArray ca, unsigned long id) {
269
- VALUE obj = Qnil;
269
+ VALUE obj = Qnil;
270
270
 
271
271
  if (id <= ca->cnt && 0 != ca) {
272
- obj = ca->objs[id - 1];
272
+ obj = ca->objs[id - 1];
273
273
  }
274
274
  return obj;
275
275
  }
@@ -454,8 +454,8 @@ read_obj(ParseInfo pi) {
454
454
  }
455
455
  if (Qundef != key) {
456
456
  if (T_OBJECT == obj_type) {
457
- VALUE *slot;
458
- ID var_id;
457
+ VALUE *slot;
458
+ ID var_id;
459
459
 
460
460
  if (Qundef == (var_id = oj_cache_get(oj_attr_cache, ks, &slot))) {
461
461
  char attr[1024];
@@ -516,7 +516,7 @@ read_array(ParseInfo pi, int hint) {
516
516
  int type = T_NONE;
517
517
  int cnt = 0;
518
518
  int a_str;
519
- #ifndef NO_RSTRUCT
519
+ #if HAS_RSTRUCT
520
520
  long slen = 0;
521
521
  #endif
522
522
 
@@ -532,7 +532,7 @@ read_array(ParseInfo pi, int hint) {
532
532
  if (Qundef == (e = read_next(pi, 0))) {
533
533
  raise_error("unexpected character", pi->str, pi->s);
534
534
  }
535
- #ifndef NO_RSTRUCT
535
+ #if HAS_RSTRUCT
536
536
  if (Qundef == a && T_STRUCT == hint && T_STRING == rb_type(e)) {
537
537
  a = structname2obj(StringValuePtr(e));
538
538
  type = T_STRUCT;
@@ -550,13 +550,13 @@ read_array(ParseInfo pi, int hint) {
550
550
  }
551
551
  if (Qundef != e) {
552
552
  if (T_STRUCT == type) {
553
- #ifdef NO_RSTRUCT
554
- raise_error("Ruby structs not supported with this version of Ruby", pi->str, pi->s);
555
- #else
553
+ #if HAS_RSTRUCT
556
554
  if (slen <= cnt) {
557
555
  raise_error("Too many elements for Struct", pi->str, pi->s);
558
556
  }
559
557
  RSTRUCT_PTR(a)[cnt] = e;
558
+ #else
559
+ raise_error("Ruby structs not supported with this version of Ruby", pi->str, pi->s);
560
560
  #endif
561
561
  } else {
562
562
  rb_ary_push(a, e);
@@ -596,12 +596,12 @@ read_str(ParseInfo pi, int hint) {
596
596
  break;
597
597
  case T_STRING:
598
598
  obj = rb_str_new2(text);
599
- #ifdef HAVE_RUBY_ENCODING_H
599
+ #if HAS_ENCODING_SUPPORT
600
600
  rb_enc_associate(obj, oj_utf8_encoding);
601
601
  #endif
602
602
  break;
603
603
  case T_SYMBOL:
604
- #ifdef HAVE_RUBY_ENCODING_H
604
+ #if HAS_ENCODING_SUPPORT
605
605
  obj = rb_str_new2(text);
606
606
  rb_enc_associate(obj, oj_utf8_encoding);
607
607
  obj = rb_funcall(obj, oj_to_sym_id, 0);
@@ -613,7 +613,7 @@ read_str(ParseInfo pi, int hint) {
613
613
  default:
614
614
  obj = Qundef;
615
615
  if (':' == *text && !escaped) { // Symbol
616
- #ifdef HAVE_RUBY_ENCODING_H
616
+ #if HAS_ENCODING_SUPPORT
617
617
  obj = rb_str_new2(text + 1);
618
618
  rb_enc_associate(obj, oj_utf8_encoding);
619
619
  obj = rb_funcall(obj, oj_to_sym_id, 0);
@@ -631,7 +631,7 @@ read_str(ParseInfo pi, int hint) {
631
631
  }
632
632
  if (Qundef == obj) {
633
633
  obj = rb_str_new2(text);
634
- #ifdef HAVE_RUBY_ENCODING_H
634
+ #if HAS_ENCODING_SUPPORT
635
635
  rb_enc_associate(obj, oj_utf8_encoding);
636
636
  #endif
637
637
  }
@@ -640,7 +640,7 @@ read_str(ParseInfo pi, int hint) {
640
640
  return obj;
641
641
  }
642
642
 
643
- #ifdef RUBINIUS
643
+ #ifdef RUBINIUS_RUBY
644
644
  #define NUM_MAX 0x07FFFFFF
645
645
  #else
646
646
  #define NUM_MAX (FIXNUM_MAX >> 8)
@@ -749,7 +749,11 @@ read_time(ParseInfo pi) {
749
749
  v2 *= 10;
750
750
  }
751
751
  }
752
+ #if HAS_NANO_TIME
752
753
  return rb_time_nano_new(v, v2);
754
+ #else
755
+ return rb_time_new(v, v2 / 1000);
756
+ #endif
753
757
  }
754
758
 
755
759
  static VALUE
@@ -849,7 +853,7 @@ static char*
849
853
  read_quoted_value(ParseInfo pi) {
850
854
  char *value = 0;
851
855
  char *h = pi->s; // head
852
- char *t = h; // tail
856
+ char *t = h; // tail
853
857
  uint32_t code;
854
858
 
855
859
  h++; // skip quote character