int main ( int argc, char* argv[] ) { int count = 0, result = 0; FILE* input; us_malloc_allocator_t malloc_allocator; us_allocator_t *allocator; us_json_config_t config; us_json_parser_t jc = NULL; allocator = us_malloc_allocator_init ( &malloc_allocator ); us_json_config_init ( &config ); config.depth = 20; config.callback = &print; config.allow_comments = 1; config.handle_floats_manually = 0; /* Important! Set locale before parser is created.*/ #if 0 if ( argc >= 2 ) { if ( !setlocale ( LC_ALL, argv[1] ) ) { fprintf ( stderr, "Failed to set locale to '%s'\n", argv[1] ); } } else { fprintf ( stderr, "No locale provided, C locale is used\n" ); } #endif jc = us_json_parser_create ( allocator, &config ); if ( argc > 1 ) { input = fopen ( argv[1], "rt" ); } else { input = stdin; } for ( ; input ; ++count ) { int next_char = fgetc ( input ); if ( next_char <= 0 ) { break; } if ( !us_json_parser_char ( jc, next_char ) ) { fprintf ( stderr, "JSON_parser_char: syntax error, byte %d\n", count ); result = 1; goto done; } } if ( !us_json_parser_done ( jc ) ) { fprintf ( stderr, "JSON_parser_end: syntax error\n" ); result = 1; goto done; } done: us_json_parser_destroy ( jc ); if ( input != stdin ) fclose ( input ); return result; }
us_json_parser_t us_json_parser_create( us_allocator_t *allocator, us_json_config_t *config ) { /* new_json_parser starts the checking process by constructing a us_json_parser object. It takes a depth parameter that restricts the level of maximum nesting. To continue the process, call us_json_parser_char for each character in the JSON text, and then call us_json_parser_done to obtain the final result. These functions are fully reentrant. */ int depth = 0; us_json_config_t default_config; us_json_parser_t jc = us_new( allocator, struct us_json_parser_struct ); memset( jc, 0, sizeof( *jc ) ); jc->allocator = allocator; /* initialize configuration */ us_json_config_init( &default_config ); /* set to default configuration if none was provided */ if ( config == NULL ) { config = &default_config; } depth = config->depth; /* We need to be able to push at least one object */ if ( depth == 0 ) { depth = 1; } jc->state = GO; jc->top = -1; /* Do we want non-bound stack? */ if ( depth > 0 ) { jc->stack_capacity = depth; jc->depth = depth; if ( depth <= (int)US_COUNTOF( jc->static_stack ) ) { jc->stack = &jc->static_stack[0]; } else { jc->stack = (signed char *)malloc( jc->stack_capacity * sizeof( jc->static_stack[0] ) ); } } else { jc->stack_capacity = US_COUNTOF( jc->static_stack ); jc->depth = -1; jc->stack = &jc->static_stack[0]; } /* set parser to start */ push( jc, MODE_DONE ); /* set up the parse buffer */ jc->parse_buffer = &jc->static_parse_buffer[0]; jc->parse_buffer_capacity = US_COUNTOF( jc->static_parse_buffer ); parse_buffer_clear( jc ); /* set up callback, comment & float handling */ jc->callback = config->callback; jc->ctx = config->callback_ctx; jc->allow_comments = config->allow_comments != 0; jc->handle_floats_manually = config->handle_floats_manually != 0; /* set up decimal point */ /* jc->decimal_point = *localeconv()->decimal_point; */ jc->decimal_point = '.'; return jc; }