From 6ef3cb51a4d49d24fe94f255643f8932b1545f4f Mon Sep 17 00:00:00 2001 From: Niels Date: Sat, 14 Feb 2015 17:34:06 +0100 Subject: [PATCH] some reorganization --- src/json.hpp | 1207 ++++++++++++++++++++++----------------------- src/json.hpp.re2c | 130 ++--- test/unit.cpp | 18 + 3 files changed, 687 insertions(+), 668 deletions(-) diff --git a/src/json.hpp b/src/json.hpp index 9ac648c0f..077f605e4 100644 --- a/src/json.hpp +++ b/src/json.hpp @@ -2516,722 +2516,724 @@ class basic_json // pointer for backtracking information const char* m_marker = nullptr; - // remember the begin of the token - m_start = m_cursor; - - + while (true) { - char yych; - unsigned int yyaccept = 0; - static const unsigned char yybm[] = - { - 0, 64, 64, 64, 64, 64, 64, 64, - 64, 96, 96, 64, 64, 96, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 96, 64, 0, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 192, 192, 192, 192, 192, 192, 192, 192, - 192, 192, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 0, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - 64, 64, 64, 64, 64, 64, 64, 64, - }; + // remember the begin of the token + m_start = m_cursor; + - yych = *m_cursor; - if (yych <= '9') { - if (yych <= ' ') + char yych; + unsigned int yyaccept = 0; + static const unsigned char yybm[] = { - if (yych <= '\n') + 0, 64, 64, 64, 64, 64, 64, 64, + 64, 96, 96, 64, 64, 96, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 96, 64, 0, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 192, 192, 192, 192, 192, 192, 192, 192, + 192, 192, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 0, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + 64, 64, 64, 64, 64, 64, 64, 64, + }; + + yych = *m_cursor; + if (yych <= '9') + { + if (yych <= ' ') { - if (yych <= 0x00) + if (yych <= '\n') { - goto json_parser_27; + if (yych <= 0x00) + { + goto basic_json_parser_27; + } + if (yych <= 0x08) + { + goto basic_json_parser_29; + } + if (yych >= '\n') + { + goto basic_json_parser_4; + } } - if (yych <= 0x08) + else { - goto json_parser_29; + if (yych == '\r') + { + goto basic_json_parser_2; + } + if (yych <= 0x1F) + { + goto basic_json_parser_29; + } } - if (yych <= '\t') - { - goto json_parser_3; - } - goto json_parser_4; } else { - if (yych == '\r') + if (yych <= ',') { - goto json_parser_3; + if (yych == '"') + { + goto basic_json_parser_26; + } + if (yych <= '+') + { + goto basic_json_parser_29; + } + goto basic_json_parser_14; } - if (yych <= 0x1F) + else { - goto json_parser_29; + if (yych <= '-') + { + goto basic_json_parser_22; + } + if (yych <= '/') + { + goto basic_json_parser_29; + } + if (yych <= '0') + { + goto basic_json_parser_23; + } + goto basic_json_parser_25; } - goto json_parser_3; } } else { - if (yych <= ',') + if (yych <= 'm') + { + if (yych <= '\\') + { + if (yych <= ':') + { + goto basic_json_parser_16; + } + if (yych == '[') + { + goto basic_json_parser_6; + } + goto basic_json_parser_29; + } + else + { + if (yych <= ']') + { + goto basic_json_parser_8; + } + if (yych == 'f') + { + goto basic_json_parser_21; + } + goto basic_json_parser_29; + } + } + else + { + if (yych <= 'z') + { + if (yych <= 'n') + { + goto basic_json_parser_18; + } + if (yych == 't') + { + goto basic_json_parser_20; + } + goto basic_json_parser_29; + } + else + { + if (yych <= '{') + { + goto basic_json_parser_10; + } + if (yych == '}') + { + goto basic_json_parser_12; + } + goto basic_json_parser_29; + } + } + } +basic_json_parser_2: + ++m_cursor; + yych = *m_cursor; + goto basic_json_parser_5; +basic_json_parser_3: + { + continue; + } +basic_json_parser_4: + ++m_cursor; + yych = *m_cursor; +basic_json_parser_5: + if (yybm[0 + yych] & 32) + { + goto basic_json_parser_4; + } + goto basic_json_parser_3; +basic_json_parser_6: + ++m_cursor; + { + return token_type::begin_array; + } +basic_json_parser_8: + ++m_cursor; + { + return token_type::end_array; + } +basic_json_parser_10: + ++m_cursor; + { + return token_type::begin_object; + } +basic_json_parser_12: + ++m_cursor; + { + return token_type::end_object; + } +basic_json_parser_14: + ++m_cursor; + { + return token_type::value_separator; + } +basic_json_parser_16: + ++m_cursor; + { + return token_type::name_separator; + } +basic_json_parser_18: + yyaccept = 0; + yych = *(m_marker = ++m_cursor); + if (yych == 'u') + { + goto basic_json_parser_59; + } +basic_json_parser_19: + { + return token_type::parse_error; + } +basic_json_parser_20: + yyaccept = 0; + yych = *(m_marker = ++m_cursor); + if (yych == 'r') + { + goto basic_json_parser_55; + } + goto basic_json_parser_19; +basic_json_parser_21: + yyaccept = 0; + yych = *(m_marker = ++m_cursor); + if (yych == 'a') + { + goto basic_json_parser_50; + } + goto basic_json_parser_19; +basic_json_parser_22: + yych = *++m_cursor; + if (yych <= '/') + { + goto basic_json_parser_19; + } + if (yych <= '0') + { + goto basic_json_parser_49; + } + if (yych <= '9') + { + goto basic_json_parser_40; + } + goto basic_json_parser_19; +basic_json_parser_23: + yyaccept = 1; + yych = *(m_marker = ++m_cursor); + if (yych <= 'D') + { + if (yych == '.') + { + goto basic_json_parser_42; + } + } + else + { + if (yych <= 'E') + { + goto basic_json_parser_43; + } + if (yych == 'e') + { + goto basic_json_parser_43; + } + } +basic_json_parser_24: + { + return token_type::value_number; + } +basic_json_parser_25: + yyaccept = 1; + yych = *(m_marker = ++m_cursor); + goto basic_json_parser_41; +basic_json_parser_26: + yyaccept = 0; + yych = *(m_marker = ++m_cursor); + if (yych <= 0x00) + { + goto basic_json_parser_19; + } + goto basic_json_parser_31; +basic_json_parser_27: + ++m_cursor; + { + return token_type::end_of_input; + } +basic_json_parser_29: + yych = *++m_cursor; + goto basic_json_parser_19; +basic_json_parser_30: + ++m_cursor; + yych = *m_cursor; +basic_json_parser_31: + if (yybm[0 + yych] & 64) + { + goto basic_json_parser_30; + } + if (yych <= 0x00) + { + goto basic_json_parser_32; + } + if (yych <= '"') + { + goto basic_json_parser_34; + } + goto basic_json_parser_33; +basic_json_parser_32: + m_cursor = m_marker; + if (yyaccept == 0) + { + goto basic_json_parser_19; + } + else + { + goto basic_json_parser_24; + } +basic_json_parser_33: + ++m_cursor; + yych = *m_cursor; + if (yych <= 'e') + { + if (yych <= '/') { if (yych == '"') { - goto json_parser_26; + goto basic_json_parser_30; } - if (yych <= '+') + if (yych <= '.') { - goto json_parser_29; + goto basic_json_parser_32; } - goto json_parser_14; + goto basic_json_parser_30; } else { - if (yych <= '-') + if (yych <= '\\') { - goto json_parser_22; + if (yych <= '[') + { + goto basic_json_parser_32; + } + goto basic_json_parser_30; } - if (yych <= '/') + else { - goto json_parser_29; + if (yych == 'b') + { + goto basic_json_parser_30; + } + goto basic_json_parser_32; } - if (yych <= '0') - { - goto json_parser_23; - } - goto json_parser_25; - } - } - } - else - { - if (yych <= 'm') - { - if (yych <= '\\') - { - if (yych <= ':') - { - goto json_parser_16; - } - if (yych == '[') - { - goto json_parser_6; - } - goto json_parser_29; - } - else - { - if (yych <= ']') - { - goto json_parser_8; - } - if (yych == 'f') - { - goto json_parser_21; - } - goto json_parser_29; } } else { - if (yych <= 'z') + if (yych <= 'q') { - if (yych <= 'n') + if (yych <= 'f') { - goto json_parser_18; + goto basic_json_parser_30; } - if (yych == 't') + if (yych == 'n') { - goto json_parser_20; + goto basic_json_parser_30; } - goto json_parser_29; + goto basic_json_parser_32; } else { - if (yych <= '{') + if (yych <= 's') { - goto json_parser_10; + if (yych <= 'r') + { + goto basic_json_parser_30; + } + goto basic_json_parser_32; } - if (yych == '}') + else { - goto json_parser_12; + if (yych <= 't') + { + goto basic_json_parser_30; + } + if (yych <= 'u') + { + goto basic_json_parser_36; + } + goto basic_json_parser_32; } - goto json_parser_29; } } - } -json_parser_2: - { - return scan(); - } -json_parser_3: - yych = *++m_cursor; - goto json_parser_5; -json_parser_4: - ++m_cursor; - yych = *m_cursor; -json_parser_5: - if (yybm[0 + yych] & 32) - { - goto json_parser_4; - } - goto json_parser_2; -json_parser_6: - ++m_cursor; - { - return token_type::begin_array; - } -json_parser_8: - ++m_cursor; - { - return token_type::end_array; - } -json_parser_10: - ++m_cursor; - { - return token_type::begin_object; - } -json_parser_12: - ++m_cursor; - { - return token_type::end_object; - } -json_parser_14: - ++m_cursor; - { - return token_type::value_separator; - } -json_parser_16: - ++m_cursor; - { - return token_type::name_separator; - } -json_parser_18: - yyaccept = 0; - yych = *(m_marker = ++m_cursor); - if (yych == 'u') - { - goto json_parser_59; - } -json_parser_19: - { - return token_type::parse_error; - } -json_parser_20: - yyaccept = 0; - yych = *(m_marker = ++m_cursor); - if (yych == 'r') - { - goto json_parser_55; - } - goto json_parser_19; -json_parser_21: - yyaccept = 0; - yych = *(m_marker = ++m_cursor); - if (yych == 'a') - { - goto json_parser_50; - } - goto json_parser_19; -json_parser_22: - yych = *++m_cursor; - if (yych <= '/') - { - goto json_parser_19; - } - if (yych <= '0') - { - goto json_parser_49; - } - if (yych <= '9') - { - goto json_parser_40; - } - goto json_parser_19; -json_parser_23: - yyaccept = 1; - yych = *(m_marker = ++m_cursor); - if (yych <= 'D') - { - if (yych == '.') +basic_json_parser_34: + ++m_cursor; { - goto json_parser_42; + return token_type::value_string; } - } - else - { - if (yych <= 'E') +basic_json_parser_36: + ++m_cursor; + yych = *m_cursor; + if (yych <= '@') { - goto json_parser_43; - } - if (yych == 'e') - { - goto json_parser_43; - } - } -json_parser_24: - { - return token_type::value_number; - } -json_parser_25: - yyaccept = 1; - yych = *(m_marker = ++m_cursor); - goto json_parser_41; -json_parser_26: - yyaccept = 0; - yych = *(m_marker = ++m_cursor); - if (yych <= 0x00) - { - goto json_parser_19; - } - goto json_parser_31; -json_parser_27: - ++m_cursor; - { - return token_type::end_of_input; - } -json_parser_29: - yych = *++m_cursor; - goto json_parser_19; -json_parser_30: - ++m_cursor; - yych = *m_cursor; -json_parser_31: - if (yybm[0 + yych] & 64) - { - goto json_parser_30; - } - if (yych <= 0x00) - { - goto json_parser_32; - } - if (yych <= '"') - { - goto json_parser_34; - } - goto json_parser_33; -json_parser_32: - m_cursor = m_marker; - if (yyaccept == 0) - { - goto json_parser_19; - } - else - { - goto json_parser_24; - } -json_parser_33: - ++m_cursor; - yych = *m_cursor; - if (yych <= 'e') - { - if (yych <= '/') - { - if (yych == '"') + if (yych <= '/') { - goto json_parser_30; + goto basic_json_parser_32; } - if (yych <= '.') + if (yych >= ':') { - goto json_parser_32; + goto basic_json_parser_32; } - goto json_parser_30; } else { - if (yych <= '\\') + if (yych <= 'F') { - if (yych <= '[') - { - goto json_parser_32; - } - goto json_parser_30; + goto basic_json_parser_37; } - else + if (yych <= '`') { - if (yych == 'b') - { - goto json_parser_30; - } - goto json_parser_32; + goto basic_json_parser_32; + } + if (yych >= 'g') + { + goto basic_json_parser_32; } } - } - else - { - if (yych <= 'q') +basic_json_parser_37: + ++m_cursor; + yych = *m_cursor; + if (yych <= '@') { + if (yych <= '/') + { + goto basic_json_parser_32; + } + if (yych >= ':') + { + goto basic_json_parser_32; + } + } + else + { + if (yych <= 'F') + { + goto basic_json_parser_38; + } + if (yych <= '`') + { + goto basic_json_parser_32; + } + if (yych >= 'g') + { + goto basic_json_parser_32; + } + } +basic_json_parser_38: + ++m_cursor; + yych = *m_cursor; + if (yych <= '@') + { + if (yych <= '/') + { + goto basic_json_parser_32; + } + if (yych >= ':') + { + goto basic_json_parser_32; + } + } + else + { + if (yych <= 'F') + { + goto basic_json_parser_39; + } + if (yych <= '`') + { + goto basic_json_parser_32; + } + if (yych >= 'g') + { + goto basic_json_parser_32; + } + } +basic_json_parser_39: + ++m_cursor; + yych = *m_cursor; + if (yych <= '@') + { + if (yych <= '/') + { + goto basic_json_parser_32; + } + if (yych <= '9') + { + goto basic_json_parser_30; + } + goto basic_json_parser_32; + } + else + { + if (yych <= 'F') + { + goto basic_json_parser_30; + } + if (yych <= '`') + { + goto basic_json_parser_32; + } if (yych <= 'f') { - goto json_parser_30; + goto basic_json_parser_30; } - if (yych == 'n') + goto basic_json_parser_32; + } +basic_json_parser_40: + yyaccept = 1; + m_marker = ++m_cursor; + yych = *m_cursor; +basic_json_parser_41: + if (yybm[0 + yych] & 128) + { + goto basic_json_parser_40; + } + if (yych <= 'D') + { + if (yych != '.') { - goto json_parser_30; + goto basic_json_parser_24; } - goto json_parser_32; } else { - if (yych <= 's') + if (yych <= 'E') { - if (yych <= 'r') - { - goto json_parser_30; - } - goto json_parser_32; + goto basic_json_parser_43; } - else + if (yych == 'e') { - if (yych <= 't') - { - goto json_parser_30; - } - if (yych <= 'u') - { - goto json_parser_36; - } - goto json_parser_32; + goto basic_json_parser_43; + } + goto basic_json_parser_24; + } +basic_json_parser_42: + yych = *++m_cursor; + if (yych <= '/') + { + goto basic_json_parser_32; + } + if (yych <= '9') + { + goto basic_json_parser_47; + } + goto basic_json_parser_32; +basic_json_parser_43: + yych = *++m_cursor; + if (yych <= ',') + { + if (yych != '+') + { + goto basic_json_parser_32; } } - } -json_parser_34: - ++m_cursor; - { - return token_type::value_string; - } -json_parser_36: - ++m_cursor; - yych = *m_cursor; - if (yych <= '@') - { + else + { + if (yych <= '-') + { + goto basic_json_parser_44; + } + if (yych <= '/') + { + goto basic_json_parser_32; + } + if (yych <= '9') + { + goto basic_json_parser_45; + } + goto basic_json_parser_32; + } +basic_json_parser_44: + yych = *++m_cursor; if (yych <= '/') { - goto json_parser_32; + goto basic_json_parser_32; } if (yych >= ':') { - goto json_parser_32; + goto basic_json_parser_32; } - } - else - { - if (yych <= 'F') - { - goto json_parser_37; - } - if (yych <= '`') - { - goto json_parser_32; - } - if (yych >= 'g') - { - goto json_parser_32; - } - } -json_parser_37: - ++m_cursor; - yych = *m_cursor; - if (yych <= '@') - { +basic_json_parser_45: + ++m_cursor; + yych = *m_cursor; if (yych <= '/') { - goto json_parser_32; - } - if (yych >= ':') - { - goto json_parser_32; - } - } - else - { - if (yych <= 'F') - { - goto json_parser_38; - } - if (yych <= '`') - { - goto json_parser_32; - } - if (yych >= 'g') - { - goto json_parser_32; - } - } -json_parser_38: - ++m_cursor; - yych = *m_cursor; - if (yych <= '@') - { - if (yych <= '/') - { - goto json_parser_32; - } - if (yych >= ':') - { - goto json_parser_32; - } - } - else - { - if (yych <= 'F') - { - goto json_parser_39; - } - if (yych <= '`') - { - goto json_parser_32; - } - if (yych >= 'g') - { - goto json_parser_32; - } - } -json_parser_39: - ++m_cursor; - yych = *m_cursor; - if (yych <= '@') - { - if (yych <= '/') - { - goto json_parser_32; + goto basic_json_parser_24; } if (yych <= '9') { - goto json_parser_30; + goto basic_json_parser_45; } - goto json_parser_32; - } - else - { - if (yych <= 'F') + goto basic_json_parser_24; +basic_json_parser_47: + yyaccept = 1; + m_marker = ++m_cursor; + yych = *m_cursor; + if (yych <= 'D') { - goto json_parser_30; + if (yych <= '/') + { + goto basic_json_parser_24; + } + if (yych <= '9') + { + goto basic_json_parser_47; + } + goto basic_json_parser_24; } - if (yych <= '`') + else { - goto json_parser_32; + if (yych <= 'E') + { + goto basic_json_parser_43; + } + if (yych == 'e') + { + goto basic_json_parser_43; + } + goto basic_json_parser_24; } - if (yych <= 'f') +basic_json_parser_49: + yyaccept = 1; + yych = *(m_marker = ++m_cursor); + if (yych <= 'D') { - goto json_parser_30; + if (yych == '.') + { + goto basic_json_parser_42; + } + goto basic_json_parser_24; } - goto json_parser_32; - } -json_parser_40: - yyaccept = 1; - m_marker = ++m_cursor; - yych = *m_cursor; -json_parser_41: - if (yybm[0 + yych] & 128) - { - goto json_parser_40; - } - if (yych <= 'D') - { - if (yych != '.') + else { - goto json_parser_24; + if (yych <= 'E') + { + goto basic_json_parser_43; + } + if (yych == 'e') + { + goto basic_json_parser_43; + } + goto basic_json_parser_24; } - } - else - { - if (yych <= 'E') +basic_json_parser_50: + yych = *++m_cursor; + if (yych != 'l') { - goto json_parser_43; + goto basic_json_parser_32; } - if (yych == 'e') + yych = *++m_cursor; + if (yych != 's') { - goto json_parser_43; + goto basic_json_parser_32; } - goto json_parser_24; - } -json_parser_42: - yych = *++m_cursor; - if (yych <= '/') - { - goto json_parser_32; - } - if (yych <= '9') - { - goto json_parser_47; - } - goto json_parser_32; -json_parser_43: - yych = *++m_cursor; - if (yych <= ',') - { - if (yych != '+') + yych = *++m_cursor; + if (yych != 'e') { - goto json_parser_32; + goto basic_json_parser_32; } - } - else - { - if (yych <= '-') + ++m_cursor; { - goto json_parser_44; + return token_type::literal_false; } - if (yych <= '/') +basic_json_parser_55: + yych = *++m_cursor; + if (yych != 'u') { - goto json_parser_32; + goto basic_json_parser_32; } - if (yych <= '9') + yych = *++m_cursor; + if (yych != 'e') { - goto json_parser_45; + goto basic_json_parser_32; } - goto json_parser_32; - } -json_parser_44: - yych = *++m_cursor; - if (yych <= '/') - { - goto json_parser_32; - } - if (yych >= ':') - { - goto json_parser_32; - } -json_parser_45: - ++m_cursor; - yych = *m_cursor; - if (yych <= '/') - { - goto json_parser_24; - } - if (yych <= '9') - { - goto json_parser_45; - } - goto json_parser_24; -json_parser_47: - yyaccept = 1; - m_marker = ++m_cursor; - yych = *m_cursor; - if (yych <= 'D') - { - if (yych <= '/') + ++m_cursor; { - goto json_parser_24; + return token_type::literal_true; } - if (yych <= '9') +basic_json_parser_59: + yych = *++m_cursor; + if (yych != 'l') { - goto json_parser_47; + goto basic_json_parser_32; } - goto json_parser_24; - } - else - { - if (yych <= 'E') + yych = *++m_cursor; + if (yych != 'l') { - goto json_parser_43; + goto basic_json_parser_32; } - if (yych == 'e') + ++m_cursor; { - goto json_parser_43; + return token_type::literal_null; } - goto json_parser_24; } -json_parser_49: - yyaccept = 1; - yych = *(m_marker = ++m_cursor); - if (yych <= 'D') - { - if (yych == '.') - { - goto json_parser_42; - } - goto json_parser_24; - } - else - { - if (yych <= 'E') - { - goto json_parser_43; - } - if (yych == 'e') - { - goto json_parser_43; - } - goto json_parser_24; - } -json_parser_50: - yych = *++m_cursor; - if (yych != 'l') - { - goto json_parser_32; - } - yych = *++m_cursor; - if (yych != 's') - { - goto json_parser_32; - } - yych = *++m_cursor; - if (yych != 'e') - { - goto json_parser_32; - } - ++m_cursor; - { - return token_type::literal_false; - } -json_parser_55: - yych = *++m_cursor; - if (yych != 'u') - { - goto json_parser_32; - } - yych = *++m_cursor; - if (yych != 'e') - { - goto json_parser_32; - } - ++m_cursor; - { - return token_type::literal_true; - } -json_parser_59: - yych = *++m_cursor; - if (yych != 'l') - { - goto json_parser_32; - } - yych = *++m_cursor; - if (yych != 'l') - { - goto json_parser_32; - } - ++m_cursor; - { - return token_type::literal_null; - } - } + } } - inline std::string get_string_value() const + inline std::string get_token() const { return std::string(m_start, static_cast(m_cursor - m_start)); } @@ -3266,15 +3268,9 @@ json_parser_59: char* endptr; const auto float_val = std::strtod(reinterpret_cast(m_start), &endptr); - // check if strtod read beyond the end of the lexem - if (endptr != m_cursor) - { - return NAN; - } - else - { - return float_val; - } + // return float_val if the whole number was translated and NAN + // otherwise + return (endptr == m_cursor) ? float_val : NAN; } private: @@ -3441,10 +3437,12 @@ json_parser_59: { auto float_val = m_lexer.get_number(); + // NAN is returned if token could not be translated + // completely if (std::isnan(float_val)) { throw std::invalid_argument(std::string("parse error - ") + - m_lexer.get_string_value() + " is not a number"); + m_lexer.get_token() + " is not a number"); } get_token(); @@ -3466,7 +3464,7 @@ json_parser_59: default: { std::string error_msg = "parse error - unexpected \'"; - error_msg += m_lexer.get_string_value(); + error_msg += m_lexer.get_token(); error_msg += "\' ("; error_msg += lexer::token_type_name(last_token) + ")"; throw std::invalid_argument(error_msg); @@ -3486,7 +3484,7 @@ json_parser_59: if (t != last_token) { std::string error_msg = "parse error - unexpected \'"; - error_msg += m_lexer.get_string_value(); + error_msg += m_lexer.get_token(); error_msg += "\' (" + lexer::token_type_name(last_token); error_msg += "); expected " + lexer::token_type_name(t); throw std::invalid_argument(error_msg); @@ -3498,6 +3496,7 @@ json_parser_59: std::string m_buffer; /// the type of the last read token typename lexer::token_type last_token = lexer::token_type::uninitialized; + /// the lexer lexer m_lexer; }; }; diff --git a/src/json.hpp.re2c b/src/json.hpp.re2c index f59985eb7..3ac3a4c03 100644 --- a/src/json.hpp.re2c +++ b/src/json.hpp.re2c @@ -2516,68 +2516,73 @@ class basic_json // pointer for backtracking information const char* m_marker = nullptr; - // remember the begin of the token - m_start = m_cursor; + while (true) + { + // remember the begin of the token + m_start = m_cursor; - /*!re2c - re2c:define:YYCTYPE = char; - re2c:define:YYCURSOR = m_cursor; - re2c:define:YYLIMIT = m_limit; - re2c:define:YYMARKER = m_marker; - re2c:indent:string = " "; - re2c:indent:top = 1; - re2c:labelprefix = "json_parser_"; - re2c:yyfill:enable = 0; + /*!re2c + re2c:define:YYCTYPE = char; + re2c:define:YYCURSOR = m_cursor; + re2c:define:YYLIMIT = m_limit; + re2c:define:YYMARKER = m_marker; + re2c:indent:string = " "; + re2c:indent:top = 1; + re2c:labelprefix = "basic_json_parser_"; + re2c:yyfill:enable = 0; - // whitespace - ws = [ \t\n\r]*; - ws { return scan(); } + // whitespace + ws = [ \t\n\r]+; + ws { continue; } - // structural characters - "[" { return token_type::begin_array; } - "]" { return token_type::end_array; } - "{" { return token_type::begin_object; } - "}" { return token_type::end_object; } - "," { return token_type::value_separator; } - ":" { return token_type::name_separator; } + // structural characters + "[" { return token_type::begin_array; } + "]" { return token_type::end_array; } + "{" { return token_type::begin_object; } + "}" { return token_type::end_object; } + "," { return token_type::value_separator; } + ":" { return token_type::name_separator; } - // literal names - "null" { return token_type::literal_null; } - "true" { return token_type::literal_true; } - "false" { return token_type::literal_false; } + // literal names + "null" { return token_type::literal_null; } + "true" { return token_type::literal_true; } + "false" { return token_type::literal_false; } - // number - decimal_point = [.]; - digit = [0-9]; - digit_1_9 = [1-9]; - e = [eE]; - minus = [-]; - plus = [+]; - zero = [0]; - exp = e (minus|plus)? digit+; - frac = decimal_point digit+; - int = (zero|digit_1_9 digit*); - number = minus? int frac? exp?; - number { return token_type::value_number; } + // number + decimal_point = [.]; + digit = [0-9]; + digit_1_9 = [1-9]; + e = [eE]; + minus = [-]; + plus = [+]; + zero = [0]; + exp = e (minus|plus)? digit+; + frac = decimal_point digit+; + int = (zero|digit_1_9 digit*); + number = minus? int frac? exp?; + number { return token_type::value_number; } - // string - quotation_mark = [\"]; - escape = [\\]; - unescaped = [^\"\\\000]; - escaped = escape ([\"\\/bfnrt] | [u][0-9a-fA-F]{4}); - char = unescaped | escaped; - string = quotation_mark char* quotation_mark; - string { return token_type::value_string; } + // string + quotation_mark = [\"]; + escape = [\\]; + unescaped = [^\"\\\000]; + single_escaped = [\"\\/bfnrt]; + unicode_escaped = [u][0-9a-fA-F]{4}; + escaped = escape (single_escaped | unicode_escaped); + char = unescaped | escaped; + string = quotation_mark char* quotation_mark; + string { return token_type::value_string; } - // end of file - '\000' { return token_type::end_of_input; } + // end of file + '\000' { return token_type::end_of_input; } - // anything else is an error - . { return token_type::parse_error; } - */ + // anything else is an error + . { return token_type::parse_error; } + */ + } } - inline std::string get_string_value() const + inline std::string get_token() const { return std::string(m_start, static_cast(m_cursor - m_start)); } @@ -2612,15 +2617,9 @@ class basic_json char* endptr; const auto float_val = std::strtod(reinterpret_cast(m_start), &endptr); - // check if strtod read beyond the end of the lexem - if (endptr != m_cursor) - { - return NAN; - } - else - { - return float_val; - } + // return float_val if the whole number was translated and NAN + // otherwise + return (endptr == m_cursor) ? float_val : NAN; } private: @@ -2787,10 +2786,12 @@ class basic_json { auto float_val = m_lexer.get_number(); + // NAN is returned if token could not be translated + // completely if (std::isnan(float_val)) { throw std::invalid_argument(std::string("parse error - ") + - m_lexer.get_string_value() + " is not a number"); + m_lexer.get_token() + " is not a number"); } get_token(); @@ -2812,7 +2813,7 @@ class basic_json default: { std::string error_msg = "parse error - unexpected \'"; - error_msg += m_lexer.get_string_value(); + error_msg += m_lexer.get_token(); error_msg += "\' ("; error_msg += lexer::token_type_name(last_token) + ")"; throw std::invalid_argument(error_msg); @@ -2832,7 +2833,7 @@ class basic_json if (t != last_token) { std::string error_msg = "parse error - unexpected \'"; - error_msg += m_lexer.get_string_value(); + error_msg += m_lexer.get_token(); error_msg += "\' (" + lexer::token_type_name(last_token); error_msg += "); expected " + lexer::token_type_name(t); throw std::invalid_argument(error_msg); @@ -2844,6 +2845,7 @@ class basic_json std::string m_buffer; /// the type of the last read token typename lexer::token_type last_token = lexer::token_type::uninitialized; + /// the lexer lexer m_lexer; }; }; diff --git a/test/unit.cpp b/test/unit.cpp index 575015547..e85cf1f06 100644 --- a/test/unit.cpp +++ b/test/unit.cpp @@ -3630,6 +3630,8 @@ TEST_CASE("capacity") { CHECK(std::distance(j.begin(), j.end()) == j.size()); CHECK(std::distance(j_const.begin(), j_const.end()) == j_const.size()); + CHECK(std::distance(j.rbegin(), j.rend()) == j.size()); + CHECK(std::distance(j_const.crbegin(), j_const.crend()) == j_const.size()); } } @@ -3648,6 +3650,8 @@ TEST_CASE("capacity") { CHECK(std::distance(j.begin(), j.end()) == j.size()); CHECK(std::distance(j_const.begin(), j_const.end()) == j_const.size()); + CHECK(std::distance(j.rbegin(), j.rend()) == j.size()); + CHECK(std::distance(j_const.crbegin(), j_const.crend()) == j_const.size()); } } @@ -3668,6 +3672,8 @@ TEST_CASE("capacity") { CHECK(std::distance(j.begin(), j.end()) == j.size()); CHECK(std::distance(j_const.begin(), j_const.end()) == j_const.size()); + CHECK(std::distance(j.rbegin(), j.rend()) == j.size()); + CHECK(std::distance(j_const.crbegin(), j_const.crend()) == j_const.size()); } } @@ -3686,6 +3692,8 @@ TEST_CASE("capacity") { CHECK(std::distance(j.begin(), j.end()) == j.size()); CHECK(std::distance(j_const.begin(), j_const.end()) == j_const.size()); + CHECK(std::distance(j.rbegin(), j.rend()) == j.size()); + CHECK(std::distance(j_const.crbegin(), j_const.crend()) == j_const.size()); } } } @@ -3707,6 +3715,8 @@ TEST_CASE("capacity") { CHECK(std::distance(j.begin(), j.end()) == j.size()); CHECK(std::distance(j_const.begin(), j_const.end()) == j_const.size()); + CHECK(std::distance(j.rbegin(), j.rend()) == j.size()); + CHECK(std::distance(j_const.crbegin(), j_const.crend()) == j_const.size()); } } @@ -3725,6 +3735,8 @@ TEST_CASE("capacity") { CHECK(std::distance(j.begin(), j.end()) == j.size()); CHECK(std::distance(j_const.begin(), j_const.end()) == j_const.size()); + CHECK(std::distance(j.rbegin(), j.rend()) == j.size()); + CHECK(std::distance(j_const.crbegin(), j_const.crend()) == j_const.size()); } } } @@ -3744,6 +3756,8 @@ TEST_CASE("capacity") { CHECK(std::distance(j.begin(), j.end()) == j.size()); CHECK(std::distance(j_const.begin(), j_const.end()) == j_const.size()); + CHECK(std::distance(j.rbegin(), j.rend()) == j.size()); + CHECK(std::distance(j_const.crbegin(), j_const.crend()) == j_const.size()); } } @@ -3762,6 +3776,8 @@ TEST_CASE("capacity") { CHECK(std::distance(j.begin(), j.end()) == j.size()); CHECK(std::distance(j_const.begin(), j_const.end()) == j_const.size()); + CHECK(std::distance(j.rbegin(), j.rend()) == j.size()); + CHECK(std::distance(j_const.crbegin(), j_const.crend()) == j_const.size()); } } @@ -3780,6 +3796,8 @@ TEST_CASE("capacity") { CHECK(std::distance(j.begin(), j.end()) == j.size()); CHECK(std::distance(j_const.begin(), j_const.end()) == j_const.size()); + CHECK(std::distance(j.rbegin(), j.rend()) == j.size()); + CHECK(std::distance(j_const.crbegin(), j_const.crend()) == j_const.size()); } } }