Made deserializeJson() more picky about trailing characters (closes #980)

This commit is contained in:
Benoit Blanchon
2019-05-16 20:41:07 +02:00
parent 2af003e4e2
commit 90c1d549a8
12 changed files with 98 additions and 85 deletions

View File

@@ -28,19 +28,14 @@ class JsonDeserializer {
_nestingLimit(nestingLimit),
_loaded(false) {}
DeserializationError parse(VariantData &variant) {
DeserializationError err = skipSpacesAndComments();
if (err) return err;
DeserializationError err = parseVariant(variant);
switch (current()) {
case '[':
return parseArray(variant.toArray());
case '{':
return parseObject(variant.toObject());
default:
return parseValue(variant);
if (!err && _current != 0 && !variant.isEnclosed()) {
// We don't detect trailing characters earlier, so we need to check now
err = DeserializationError::InvalidInput;
}
return err;
}
private:
@@ -48,10 +43,8 @@ class JsonDeserializer {
char current() {
if (!_loaded) {
if (_reader.ended())
_current = 0;
else
_current = _reader.read();
int c = _reader.read();
_current = static_cast<char>(c > 0 ? c : 0);
_loaded = true;
}
return _current;
@@ -67,6 +60,26 @@ class JsonDeserializer {
return true;
}
DeserializationError parseVariant(VariantData &variant) {
DeserializationError err = skipSpacesAndComments();
if (err) return err;
switch (current()) {
case '[':
return parseArray(variant.toArray());
case '{':
return parseObject(variant.toObject());
case '\"':
case '\'':
return parseStringValue(variant);
default:
return parseNumericValue(variant);
}
}
DeserializationError parseArray(CollectionData &array) {
if (_nestingLimit == 0) return DeserializationError::TooDeep;
@@ -88,7 +101,7 @@ class JsonDeserializer {
// 1 - Parse value
_nestingLimit--;
err = parse(*value);
err = parseVariant(*value);
_nestingLimit++;
if (err) return err;
@@ -134,7 +147,7 @@ class JsonDeserializer {
// Parse value
_nestingLimit--;
err = parse(*slot->data());
err = parseVariant(*slot->data());
_nestingLimit++;
if (err) return err;
@@ -152,14 +165,6 @@ class JsonDeserializer {
}
}
DeserializationError parseValue(VariantData &variant) {
if (isQuote(current())) {
return parseStringValue(variant);
} else {
return parseNumericValue(variant);
}
}
DeserializationError parseKey(const char *&key) {
if (isQuote(current())) {
return parseQuotedString(key);