~ubuntu-branches/ubuntu/intrepid/ruby1.9/intrepid-updates

« back to all changes in this revision

Viewing changes to ext/json/ext/parser/parser.rl

  • Committer: Bazaar Package Importer
  • Author(s): Matthias Klose
  • Date: 2007-09-04 16:01:17 UTC
  • mfrom: (1.1.8 upstream)
  • Revision ID: james.westby@ubuntu.com-20070904160117-i15zckg2nhxe9fyw
Tags: 1.9.0+20070830-2ubuntu1
* Sync from Debian; remaining changes:
  - Add -g to CFLAGS.
* Fixes build failure on ia64.
* Fixes build failure with gcc-4.2 on lpia.
* Robustify check for target_os, fixing build failure on lpia.
* Set Ubuntu maintainer address.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/* vim: set cin et sw=4 ts=4: */
 
1
/* -*-c-*- vim: set cin et sw=4 ts=4: */
2
2
 
3
 
#include "ruby.h"
4
 
#include "re.h"
5
 
#include "st.h"
 
3
#include "ruby/ruby.h"
 
4
#include "ruby/re.h"
 
5
#include "ruby/st.h"
6
6
#include "unicode.h"
7
7
 
8
8
#define EVIL 0x666
9
9
 
10
10
static VALUE mJSON, mExt, cParser, eParserError, eNestingError;
11
 
 
12
 
static ID i_json_creatable_p, i_json_create, i_create_id, i_chr, i_max_nesting; 
 
11
static VALUE CNaN, CInfinity, CMinusInfinity;
 
12
 
 
13
static ID i_json_creatable_p, i_json_create, i_create_id, i_chr, i_max_nesting,
 
14
          i_allow_nan; 
 
15
 
 
16
#define MinusInfinity "-Infinity"
13
17
 
14
18
typedef struct JSON_ParserStruct {
15
19
    VALUE Vsource;
19
23
    VALUE create_id;
20
24
    int max_nesting;
21
25
    int current_nesting;
 
26
    int allow_nan;
22
27
} JSON_Parser;
23
28
 
24
29
static char *JSON_parse_object(JSON_Parser *json, char *p, char *pe, VALUE *result);
47
52
    Vnull               = 'null';
48
53
    Vfalse              = 'false';
49
54
    Vtrue               = 'true';
50
 
    begin_value         = [nft"\-[{] | digit;
 
55
    VNaN                = 'NaN';
 
56
    VInfinity           = 'Infinity';
 
57
    VMinusInfinity      = '-Infinity';
 
58
    begin_value         = [nft"\-[{NI] | digit;
51
59
    begin_object        = '{';
52
60
    end_object          = '}';
53
61
    begin_array         = '[';
133
141
    action parse_true {
134
142
        *result = Qtrue;
135
143
    }
 
144
    action parse_nan {
 
145
        if (json->allow_nan) {
 
146
            *result = CNaN;
 
147
        } else {
 
148
            rb_raise(eParserError, "unexpected token at '%s'", p - 2);
 
149
        }
 
150
    }
 
151
    action parse_infinity {
 
152
        if (json->allow_nan) {
 
153
            *result = CInfinity;
 
154
        } else {
 
155
            rb_raise(eParserError, "unexpected token at '%s'", p - 8);
 
156
        }
 
157
    }
136
158
    action parse_string {
137
159
        char *np = JSON_parse_string(json, fpc, pe, result);
138
160
        if (np == NULL) fbreak; else fexec np;
140
162
 
141
163
    action parse_number {
142
164
        char *np;
 
165
        if(pe > fpc + 9 && !strncmp(MinusInfinity, fpc, 9)) {
 
166
            if (json->allow_nan) {
 
167
                *result = CMinusInfinity;
 
168
                fexec p + 10;
 
169
                fbreak;
 
170
            } else {
 
171
                rb_raise(eParserError, "unexpected token at '%s'", p);
 
172
            }
 
173
        }
143
174
        np = JSON_parse_float(json, fpc, pe, result);
144
175
        if (np != NULL) fexec np;
145
176
        np = JSON_parse_integer(json, fpc, pe, result);
169
200
              Vnull @parse_null |
170
201
              Vfalse @parse_false |
171
202
              Vtrue @parse_true |
 
203
              VNaN @parse_nan |
 
204
              VInfinity @parse_infinity |
172
205
              begin_number >parse_number |
173
206
              begin_string >parse_string |
174
207
              begin_array >parse_array |
435
468
 *
436
469
 * _opts_ can have the following keys:
437
470
 * * *max_nesting*: The maximum depth of nesting allowed in the parsed data
438
 
 *   structures. Disable depth checking with :max_nesting => false.
 
471
 *   structures. Disable depth checking with :max_nesting => false|nil|0, it
 
472
 *   defaults to 19.
 
473
 * * *allow_nan*: If set to true, allow NaN, Infinity and -Infinity in
 
474
 *   defiance of RFC 4627 to be parsed by the Parser. This option defaults to
 
475
 *   false.
439
476
 */
440
477
static VALUE cParser_initialize(int argc, VALUE *argv, VALUE self)
441
478
{
451
488
        rb_raise(eParserError, "A JSON text must at least contain two octets!");
452
489
    }
453
490
    json->max_nesting = 19;
 
491
    json->allow_nan = 0;
454
492
    if (!NIL_P(opts)) {
455
493
        opts = rb_convert_type(opts, T_HASH, "Hash", "to_hash");
456
494
        if (NIL_P(opts)) {
457
495
            rb_raise(rb_eArgError, "opts needs to be like a hash");
458
496
        } else {
459
 
            VALUE s_max_nesting = ID2SYM(i_max_nesting);
460
 
            if (st_lookup(RHASH(opts)->tbl, s_max_nesting, 0)) {
461
 
                VALUE max_nesting = rb_hash_aref(opts, s_max_nesting);
 
497
            VALUE tmp = ID2SYM(i_max_nesting);
 
498
            if (st_lookup(RHASH_TBL(opts), tmp, 0)) {
 
499
                VALUE max_nesting = rb_hash_aref(opts, tmp);
462
500
                if (RTEST(max_nesting)) {
463
501
                    Check_Type(max_nesting, T_FIXNUM);
464
502
                    json->max_nesting = FIX2INT(max_nesting);
466
504
                    json->max_nesting = 0;
467
505
                }
468
506
            }
 
507
            tmp = ID2SYM(i_allow_nan);
 
508
            if (st_lookup(RHASH_TBL(opts), tmp, 0)) {
 
509
                VALUE allow_nan = rb_hash_aref(opts, tmp);
 
510
                if (RTEST(allow_nan)) json->allow_nan = 1;
 
511
            }
469
512
        }
470
513
    }
471
514
    json->current_nesting = 0;
561
604
    rb_define_method(cParser, "parse", cParser_parse, 0);
562
605
    rb_define_method(cParser, "source", cParser_source, 0);
563
606
 
 
607
    CNaN = rb_const_get(mJSON, rb_intern("NaN"));
 
608
    CInfinity = rb_const_get(mJSON, rb_intern("Infinity"));
 
609
    CMinusInfinity = rb_const_get(mJSON, rb_intern("MinusInfinity"));
 
610
 
564
611
    i_json_creatable_p = rb_intern("json_creatable?");
565
612
    i_json_create = rb_intern("json_create");
566
613
    i_create_id = rb_intern("create_id");
567
614
    i_chr = rb_intern("chr");
568
615
    i_max_nesting = rb_intern("max_nesting");
 
616
    i_allow_nan = rb_intern("allow_nan");
569
617
}