| 109 | } |
| 110 | |
| 111 | int JSONParser::ParseValue(JSONValue& val){ |
| 112 | EatWhitespace(); |
| 113 | |
| 114 | char c = Peek(); |
| 115 | JSONValue& v = val; |
| 116 | |
| 117 | if(isdigit(c) || c == '-'){ |
| 118 | bool negative = false; |
| 119 | if(c == '-'){ |
| 120 | negative = true; |
| 121 | Eat(); |
| 122 | c = Peek(); |
| 123 | } |
| 124 | |
| 125 | if(c == '0' && Peek(1) != '.'){ // Number, Leading zeros are not allowed unless value == 0 or is a decimal |
| 126 | v = JSONValue(0L); |
| 127 | } else { |
| 128 | std::string_view num = EatWhile([] (char c) -> bool { return isdigit(c) || c == '.'; }); |
| 129 | |
| 130 | if(size_t pt = num.find('.'); pt != num.npos){ // Check for a decimal point |
| 131 | if(num.find('.', pt + 1) != num.npos){ |
| 132 | #ifdef LIBLEMON_DEBUG_JSON |
| 133 | printf("Expected no more than one '.', line %d.\n", line); |
| 134 | #endif |
| 135 | return 1; // We can't have more than one decimal point |
| 136 | } |
| 137 | |
| 138 | if(!negative){ |
| 139 | v = JSONValue(std::stof(std::string(num))); |
| 140 | } else { |
| 141 | v = JSONValue(-std::stof(std::string(num))); |
| 142 | } |
| 143 | } else { |
| 144 | |
| 145 | if(!negative){ |
| 146 | v = JSONValue(std::stoul(std::string(num))); |
| 147 | } else { |
| 148 | v = JSONValue(-std::stol(std::string(num))); |
| 149 | } |
| 150 | } |
| 151 | } |
| 152 | } else if(c == '"'){ // String |
| 153 | v = JSONValue(ParseString()); |
| 154 | } else if(c == '{'){ // Object |
| 155 | v = ParseObject(); |
| 156 | |
| 157 | if(v.IsNull()){ |
| 158 | return 1; // Should not be null |
| 159 | } |
| 160 | } else if(c == '['){ // Array |
| 161 | v = ParseArray(); |
| 162 | |
| 163 | if(v.IsNull()){ |
| 164 | return 1; // Should not be null |
| 165 | } |
| 166 | } else if(c == 't'){ |
| 167 | if(!EatWord("true")){ |
| 168 | return 1; // Unknown word |