// // json_binder.cpp // json // // Created by Sam Jaffe on 4/23/16. // #include "json_common.hpp" namespace json { namespace helper { namespace { std::string get_no_end_error(char expected, char found) { char str[64] = { '\0' }; snprintf(str, sizeof(str), "Expected delimeter: ',' or '%c', got '%c' instead", expected, found); return str; } } numeric_token_info::numeric_token_info(char const * start) : val(0) , it(start) , end(start) , is_double(false) , is_negative(*start == '-') { if ( is_negative ) { ++it; ++end; } for (char c = *end; strchr(",]}", c) == NULL && !isspace(c); c = *++end) { is_double |= !isdigit(*end); } if (end == it) { throw malformed_json_exception("Expected any token, got nothing"); } } numeric_state numeric_token_info::parse_numeric() { static uint_jt const threshold = (UINT_JT_MAX / 10); val = 0; for (char c = *it; it != end; c = *++it) { int_jt digit = static_cast(c - '0'); if (val > threshold || ( val == threshold && ((it + 1) < end || digit > INT_JT_MAX_LAST_DIGIT))) { return DOUBLE; } val = (10 * val) + digit; } return INTEGER; } const char get_next_element(char const*& data) { while (isspace(*data)) ++data; return *data; } void advance_to_boundary(char const endtok, char const*& data) { char const next = get_next_element(data); if (next == ',') { ++data; } else if (next != endtok) { throw json::malformed_json_exception(get_no_end_error(endtok, *data)); } } std::string parse_string(char const * & data) { char const* start = data; while (*++data) { if (*data == '"' && *(data-1) != '\\') { return std::string(start+1, data++); } } throw json::malformed_json_exception("Could not locate end of string"); } } }