🔨 changed an exception

This commit is contained in:
Niels Lohmann 2017-03-08 18:07:21 +01:00
parent 8fcd01631f
commit fc9b528ec9
No known key found for this signature in database
GPG key ID: 7F3CEA63AE251B69
6 changed files with 106 additions and 77 deletions

View file

@ -7374,10 +7374,11 @@ class basic_json
template<typename T> template<typename T>
static T get_from_vector(const std::vector<uint8_t>& vec, const size_t current_index) static T get_from_vector(const std::vector<uint8_t>& vec, const size_t current_index)
{ {
if (current_index + sizeof(T) + 1 > vec.size()) check_length(vec.size(), sizeof(T), current_index + 1);
{ //if (current_index + sizeof(T) + 1 > vec.size())
JSON_THROW(parse_error(110, current_index + 1, "cannot read " + std::to_string(sizeof(T)) + " bytes from vector")); //{
} // JSON_THROW(parse_error(110, current_index + 1, "cannot read " + std::to_string(sizeof(T)) + " bytes from vector"));
//}
T result; T result;
auto* ptr = reinterpret_cast<uint8_t*>(&result); auto* ptr = reinterpret_cast<uint8_t*>(&result);
@ -7926,19 +7927,19 @@ class basic_json
// simple case: requested length is greater than the vector's length // simple case: requested length is greater than the vector's length
if (len > size or offset > size) if (len > size or offset > size)
{ {
JSON_THROW(std::out_of_range("len out of range")); JSON_THROW(parse_error(110, offset + 1, "cannot read " + std::to_string(len) + " bytes from vector"));
} }
// second case: adding offset would result in overflow // second case: adding offset would result in overflow
if ((size > (std::numeric_limits<size_t>::max() - offset))) if ((size > (std::numeric_limits<size_t>::max() - offset)))
{ {
JSON_THROW(std::out_of_range("len+offset out of range")); JSON_THROW(parse_error(110, offset + 1, "cannot read " + std::to_string(len) + " bytes from vector"));
} }
// last case: reading past the end of the vector // last case: reading past the end of the vector
if (len + offset > size) if (len + offset > size)
{ {
JSON_THROW(std::out_of_range("len+offset out of range")); JSON_THROW(parse_error(110, offset + 1, "cannot read " + std::to_string(len) + " bytes from vector"));
} }
} }

View file

@ -7374,10 +7374,8 @@ class basic_json
template<typename T> template<typename T>
static T get_from_vector(const std::vector<uint8_t>& vec, const size_t current_index) static T get_from_vector(const std::vector<uint8_t>& vec, const size_t current_index)
{ {
if (current_index + sizeof(T) + 1 > vec.size()) // check if we can read sizeof(T) bytes starting the next index
{ check_length(vec.size(), sizeof(T), current_index + 1);
JSON_THROW(parse_error(110, current_index + 1, "cannot read " + std::to_string(sizeof(T)) + " bytes from vector"));
}
T result; T result;
auto* ptr = reinterpret_cast<uint8_t*>(&result); auto* ptr = reinterpret_cast<uint8_t*>(&result);
@ -7926,19 +7924,19 @@ class basic_json
// simple case: requested length is greater than the vector's length // simple case: requested length is greater than the vector's length
if (len > size or offset > size) if (len > size or offset > size)
{ {
JSON_THROW(std::out_of_range("len out of range")); JSON_THROW(parse_error(110, offset + 1, "cannot read " + std::to_string(len) + " bytes from vector"));
} }
// second case: adding offset would result in overflow // second case: adding offset would result in overflow
if ((size > (std::numeric_limits<size_t>::max() - offset))) if ((size > (std::numeric_limits<size_t>::max() - offset)))
{ {
JSON_THROW(std::out_of_range("len+offset out of range")); JSON_THROW(parse_error(110, offset + 1, "cannot read " + std::to_string(len) + " bytes from vector"));
} }
// last case: reading past the end of the vector // last case: reading past the end of the vector
if (len + offset > size) if (len + offset > size)
{ {
JSON_THROW(std::out_of_range("len+offset out of range")); JSON_THROW(parse_error(110, offset + 1, "cannot read " + std::to_string(len) + " bytes from vector"));
} }
} }

View file

@ -49,13 +49,13 @@ extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size)
// serializations must match // serializations must match
assert(s1 == s2); assert(s1 == s2);
} }
catch (const std::invalid_argument&) catch (const json::parse_error&)
{ {
// parsing a JSON serialization must not fail // parsing a JSON serialization must not fail
assert(false); assert(false);
} }
} }
catch (const std::invalid_argument&) catch (const json::parse_error&)
{ {
// parse errors are ok, because input may be random bytes // parse errors are ok, because input may be random bytes
} }

View file

@ -1162,35 +1162,35 @@ TEST_CASE("CBOR")
CHECK_THROWS_AS(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})), json::parse_error); CHECK_THROWS_AS(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x18})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x18})),
"[json.exception.parse_error.110] parse error at 1: cannot read 1 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 1 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x19})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x19})),
"[json.exception.parse_error.110] parse error at 1: cannot read 2 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 2 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x19, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x19, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 2 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 2 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1a})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1a})),
"[json.exception.parse_error.110] parse error at 1: cannot read 4 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 4 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1a, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1a, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 4 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 4 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1a, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1a, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 4 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 4 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1a, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1a, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 4 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 4 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_cbor(std::vector<uint8_t>({0x1b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
} }
SECTION("unsupported bytes") SECTION("unsupported bytes")
@ -1341,21 +1341,13 @@ TEST_CASE("CBOR regressions", "[!throws]")
// deserializations must match // deserializations must match
CHECK(j1 == j2); CHECK(j1 == j2);
} }
catch (const std::invalid_argument&) catch (const json::parse_error&)
{ {
// parsing a CBOR serialization must not fail // parsing a CBOR serialization must not fail
CHECK(false); CHECK(false);
} }
} }
catch (const std::invalid_argument&) catch (const json::parse_error&)
{
// parse errors are ok, because input may be random bytes
}
catch (const std::out_of_range&)
{
// parse errors are ok, because input may be random bytes
}
catch (const std::domain_error&)
{ {
// parse errors are ok, because input may be random bytes // parse errors are ok, because input may be random bytes
} }
@ -1365,7 +1357,9 @@ TEST_CASE("CBOR regressions", "[!throws]")
SECTION("improve code coverage") SECTION("improve code coverage")
{ {
// exotic edge case // exotic edge case
CHECK_THROWS_AS(json::check_length(0xffffffffffffffffull, 0xfffffffffffffff0ull, 0xff), std::out_of_range); CHECK_THROWS_AS(json::check_length(0xffffffffffffffffull, 0xfffffffffffffff0ull, 0xff), json::parse_error);
CHECK_THROWS_WITH(json::check_length(0xffffffffffffffffull, 0xfffffffffffffff0ull, 0xff),
"[json.exception.parse_error.110] parse error at 256: cannot read 18446744073709551600 bytes from vector");
} }
} }

View file

@ -1038,35 +1038,35 @@ TEST_CASE("MessagePack")
CHECK_THROWS_AS(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})), json::parse_error); CHECK_THROWS_AS(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})), json::parse_error);
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcc})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcc})),
"[json.exception.parse_error.110] parse error at 1: cannot read 1 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 1 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcd})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcd})),
"[json.exception.parse_error.110] parse error at 1: cannot read 2 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 2 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcd, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcd, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 2 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 2 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xce})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xce})),
"[json.exception.parse_error.110] parse error at 1: cannot read 4 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 4 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xce, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xce, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 4 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 4 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xce, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xce, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 4 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 4 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xce, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xce, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 4 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 4 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})), CHECK_THROWS_WITH(json::from_msgpack(std::vector<uint8_t>({0xcf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00})),
"[json.exception.parse_error.110] parse error at 1: cannot read 8 bytes from vector"); "[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
} }
SECTION("unsupported bytes") SECTION("unsupported bytes")

View file

@ -613,37 +613,51 @@ TEST_CASE("regression tests")
{ {
// original test case // original test case
std::vector<uint8_t> vec {0x65, 0xf5, 0x0a, 0x48, 0x21}; std::vector<uint8_t> vec {0x65, 0xf5, 0x0a, 0x48, 0x21};
CHECK_THROWS_AS(json::from_cbor(vec), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec),
"[json.exception.parse_error.110] parse error at 2: cannot read 5 bytes from vector");
} }
SECTION("issue #407 - Heap-buffer-overflow (OSS-Fuzz issue 343)") SECTION("issue #407 - Heap-buffer-overflow (OSS-Fuzz issue 343)")
{ {
// original test case: incomplete float64 // original test case: incomplete float64
std::vector<uint8_t> vec1 {0xcb, 0x8f, 0x0a}; std::vector<uint8_t> vec1 {0xcb, 0x8f, 0x0a};
CHECK_THROWS_AS(json::from_msgpack(vec1), std::out_of_range); CHECK_THROWS_AS(json::from_msgpack(vec1), json::parse_error);
CHECK_THROWS_WITH(json::from_msgpack(vec1),
"[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
// related test case: incomplete float32 // related test case: incomplete float32
std::vector<uint8_t> vec2 {0xca, 0x8f, 0x0a}; std::vector<uint8_t> vec2 {0xca, 0x8f, 0x0a};
CHECK_THROWS_AS(json::from_msgpack(vec2), std::out_of_range); CHECK_THROWS_AS(json::from_msgpack(vec2), json::parse_error);
CHECK_THROWS_WITH(json::from_msgpack(vec2),
"[json.exception.parse_error.110] parse error at 2: cannot read 4 bytes from vector");
// related test case: incomplete Half-Precision Float (CBOR) // related test case: incomplete Half-Precision Float (CBOR)
std::vector<uint8_t> vec3 {0xf9, 0x8f}; std::vector<uint8_t> vec3 {0xf9, 0x8f};
CHECK_THROWS_AS(json::from_cbor(vec3), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec3), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec3),
"[json.exception.parse_error.110] parse error at 2: cannot read 2 bytes from vector");
// related test case: incomplete Single-Precision Float (CBOR) // related test case: incomplete Single-Precision Float (CBOR)
std::vector<uint8_t> vec4 {0xfa, 0x8f, 0x0a}; std::vector<uint8_t> vec4 {0xfa, 0x8f, 0x0a};
CHECK_THROWS_AS(json::from_cbor(vec4), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec4), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec4),
"[json.exception.parse_error.110] parse error at 2: cannot read 4 bytes from vector");
// related test case: incomplete Double-Precision Float (CBOR) // related test case: incomplete Double-Precision Float (CBOR)
std::vector<uint8_t> vec5 {0xfb, 0x8f, 0x0a}; std::vector<uint8_t> vec5 {0xfb, 0x8f, 0x0a};
CHECK_THROWS_AS(json::from_cbor(vec5), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec5), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec5),
"[json.exception.parse_error.110] parse error at 2: cannot read 8 bytes from vector");
} }
SECTION("issue #408 - Heap-buffer-overflow (OSS-Fuzz issue 344)") SECTION("issue #408 - Heap-buffer-overflow (OSS-Fuzz issue 344)")
{ {
// original test case // original test case
std::vector<uint8_t> vec1 {0x87}; std::vector<uint8_t> vec1 {0x87};
CHECK_THROWS_AS(json::from_msgpack(vec1), std::out_of_range); CHECK_THROWS_AS(json::from_msgpack(vec1), json::parse_error);
CHECK_THROWS_WITH(json::from_msgpack(vec1),
"[json.exception.parse_error.110] parse error at 2: cannot read 1 bytes from vector");
// more test cases for MessagePack // more test cases for MessagePack
for (auto b : for (auto b :
@ -655,7 +669,7 @@ TEST_CASE("regression tests")
}) })
{ {
std::vector<uint8_t> vec(1, static_cast<uint8_t>(b)); std::vector<uint8_t> vec(1, static_cast<uint8_t>(b));
CHECK_THROWS_AS(json::from_msgpack(vec), std::out_of_range); CHECK_THROWS_AS(json::from_msgpack(vec), json::parse_error);
} }
// more test cases for CBOR // more test cases for CBOR
@ -670,28 +684,38 @@ TEST_CASE("regression tests")
}) })
{ {
std::vector<uint8_t> vec(1, static_cast<uint8_t>(b)); std::vector<uint8_t> vec(1, static_cast<uint8_t>(b));
CHECK_THROWS_AS(json::from_cbor(vec), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec), json::parse_error);
} }
// special case: empty input // special case: empty input
std::vector<uint8_t> vec2; std::vector<uint8_t> vec2;
CHECK_THROWS_AS(json::from_cbor(vec2), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec2), json::parse_error);
CHECK_THROWS_AS(json::from_msgpack(vec2), std::out_of_range); CHECK_THROWS_WITH(json::from_cbor(vec2),
"[json.exception.parse_error.110] parse error at 1: cannot read 1 bytes from vector");
CHECK_THROWS_AS(json::from_msgpack(vec2), json::parse_error);
CHECK_THROWS_WITH(json::from_msgpack(vec2),
"[json.exception.parse_error.110] parse error at 1: cannot read 1 bytes from vector");
} }
SECTION("issue #411 - Heap-buffer-overflow (OSS-Fuzz issue 366)") SECTION("issue #411 - Heap-buffer-overflow (OSS-Fuzz issue 366)")
{ {
// original test case: empty UTF-8 string (indefinite length) // original test case: empty UTF-8 string (indefinite length)
std::vector<uint8_t> vec1 {0x7f}; std::vector<uint8_t> vec1 {0x7f};
CHECK_THROWS_AS(json::from_cbor(vec1), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec1), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec1),
"[json.exception.parse_error.110] parse error at 2: cannot read 1 bytes from vector");
// related test case: empty array (indefinite length) // related test case: empty array (indefinite length)
std::vector<uint8_t> vec2 {0x9f}; std::vector<uint8_t> vec2 {0x9f};
CHECK_THROWS_AS(json::from_cbor(vec2), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec2), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec2),
"[json.exception.parse_error.110] parse error at 2: cannot read 1 bytes from vector");
// related test case: empty map (indefinite length) // related test case: empty map (indefinite length)
std::vector<uint8_t> vec3 {0xbf}; std::vector<uint8_t> vec3 {0xbf};
CHECK_THROWS_AS(json::from_cbor(vec3), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec3), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec3),
"[json.exception.parse_error.110] parse error at 2: cannot read 1 bytes from vector");
} }
SECTION("issue #412 - Heap-buffer-overflow (OSS-Fuzz issue 367)") SECTION("issue #412 - Heap-buffer-overflow (OSS-Fuzz issue 367)")
@ -717,19 +741,27 @@ TEST_CASE("regression tests")
0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60,
0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60, 0x60
}; };
CHECK_THROWS_AS(json::from_cbor(vec), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec),
"[json.exception.parse_error.110] parse error at 137: cannot read 1 bytes from vector");
// related test case: nonempty UTF-8 string (indefinite length) // related test case: nonempty UTF-8 string (indefinite length)
std::vector<uint8_t> vec1 {0x7f, 0x61, 0x61}; std::vector<uint8_t> vec1 {0x7f, 0x61, 0x61};
CHECK_THROWS_AS(json::from_cbor(vec1), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec1), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec1),
"[json.exception.parse_error.110] parse error at 4: cannot read 1 bytes from vector");
// related test case: nonempty array (indefinite length) // related test case: nonempty array (indefinite length)
std::vector<uint8_t> vec2 {0x9f, 0x01}; std::vector<uint8_t> vec2 {0x9f, 0x01};
CHECK_THROWS_AS(json::from_cbor(vec2), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec2), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec2),
"[json.exception.parse_error.110] parse error at 3: cannot read 1 bytes from vector");
// related test case: nonempty map (indefinite length) // related test case: nonempty map (indefinite length)
std::vector<uint8_t> vec3 {0xbf, 0x61, 0x61, 0x01}; std::vector<uint8_t> vec3 {0xbf, 0x61, 0x61, 0x01};
CHECK_THROWS_AS(json::from_cbor(vec3), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec3), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec3),
"[json.exception.parse_error.110] parse error at 5: cannot read 1 bytes from vector");
} }
SECTION("issue #414 - compare with literal 0)") SECTION("issue #414 - compare with literal 0)")
@ -762,7 +794,9 @@ TEST_CASE("regression tests")
0x96, 0x96, 0xb4, 0xb4, 0xfa, 0x94, 0x94, 0x61, 0x96, 0x96, 0xb4, 0xb4, 0xfa, 0x94, 0x94, 0x61,
0x61, 0x61, 0x61, 0x61, 0x61, 0x61, 0x61, 0xfa 0x61, 0x61, 0x61, 0x61, 0x61, 0x61, 0x61, 0xfa
}; };
CHECK_THROWS_AS(json::from_cbor(vec1), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec1), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec1),
"[json.exception.parse_error.110] parse error at 49: cannot read 4 bytes from vector");
// related test case: double-precision // related test case: double-precision
std::vector<uint8_t> vec2 std::vector<uint8_t> vec2
@ -774,7 +808,9 @@ TEST_CASE("regression tests")
0x96, 0x96, 0xb4, 0xb4, 0xfa, 0x94, 0x94, 0x61, 0x96, 0x96, 0xb4, 0xb4, 0xfa, 0x94, 0x94, 0x61,
0x61, 0x61, 0x61, 0x61, 0x61, 0x61, 0x61, 0xfb 0x61, 0x61, 0x61, 0x61, 0x61, 0x61, 0x61, 0xfb
}; };
CHECK_THROWS_AS(json::from_cbor(vec2), std::out_of_range); CHECK_THROWS_AS(json::from_cbor(vec2), json::parse_error);
CHECK_THROWS_WITH(json::from_cbor(vec2),
"[json.exception.parse_error.110] parse error at 49: cannot read 8 bytes from vector");
} }
SECTION("issue #452 - Heap-buffer-overflow (OSS-Fuzz issue 585)") SECTION("issue #452 - Heap-buffer-overflow (OSS-Fuzz issue 585)")