Commit dc341a3c authored by Adam Langley's avatar Adam Langley Committed by Commit Bot

cbor: ensure that error codes are set iff parsing fails.

Bug: 827551
Change-Id: I134199ca4538f469fc29d0b315a9e36f72e8df80
Reviewed-on: https://chromium-review.googlesource.com/982611Reviewed-by: default avatarBalazs Engedy <engedy@chromium.org>
Commit-Queue: Adam Langley <agl@chromium.org>
Cr-Commit-Position: refs/heads/master@{#548108}
parent c3dd28e8
...@@ -51,6 +51,7 @@ const char kUnsupportedFloatingPointValue[] = ...@@ -51,6 +51,7 @@ const char kUnsupportedFloatingPointValue[] =
"Floating point numbers are not supported."; "Floating point numbers are not supported.";
const char kOutOfRangeIntegerValue[] = const char kOutOfRangeIntegerValue[] =
"Integer values must be between INT64_MIN and INT64_MAX."; "Integer values must be between INT64_MIN and INT64_MAX.";
const char kUnknownError[] = "An unknown error occured.";
} // namespace } // namespace
...@@ -88,15 +89,16 @@ base::Optional<CBORValue> CBORReader::Read(base::span<uint8_t const> data, ...@@ -88,15 +89,16 @@ base::Optional<CBORValue> CBORReader::Read(base::span<uint8_t const> data,
base::Optional<CBORValue> decoded_cbor = base::Optional<CBORValue> decoded_cbor =
reader.DecodeCompleteDataItem(max_nesting_level); reader.DecodeCompleteDataItem(max_nesting_level);
if (error_code_out) auto error_code = reader.GetErrorCode();
*error_code_out = reader.GetErrorCode(); const bool failed = !decoded_cbor.has_value();
if (reader.GetErrorCode() != DecoderError::CBOR_NO_ERROR) { // An error code must be set iff parsing failed.
*num_bytes_consumed = 0; DCHECK_EQ(failed, error_code != DecoderError::CBOR_NO_ERROR);
return base::nullopt;
}
*num_bytes_consumed = reader.num_bytes_consumed(); if (error_code_out)
*error_code_out = error_code;
*num_bytes_consumed = failed ? 0 : reader.num_bytes_consumed();
return decoded_cbor; return decoded_cbor;
} }
...@@ -395,6 +397,8 @@ const char* CBORReader::ErrorCodeToString(DecoderError error) { ...@@ -395,6 +397,8 @@ const char* CBORReader::ErrorCodeToString(DecoderError error) {
return kUnsupportedFloatingPointValue; return kUnsupportedFloatingPointValue;
case DecoderError::OUT_OF_RANGE_INTEGER_VALUE: case DecoderError::OUT_OF_RANGE_INTEGER_VALUE:
return kOutOfRangeIntegerValue; return kOutOfRangeIntegerValue;
case DecoderError::UNKNOWN_ERROR:
return kUnknownError;
default: default:
NOTREACHED(); NOTREACHED();
return "Unknown error code."; return "Unknown error code.";
......
...@@ -66,6 +66,7 @@ class CBOR_EXPORT CBORReader { ...@@ -66,6 +66,7 @@ class CBOR_EXPORT CBORReader {
UNSUPPORTED_SIMPLE_VALUE, UNSUPPORTED_SIMPLE_VALUE,
UNSUPPORTED_FLOATING_POINT_VALUE, UNSUPPORTED_FLOATING_POINT_VALUE,
OUT_OF_RANGE_INTEGER_VALUE, OUT_OF_RANGE_INTEGER_VALUE,
UNKNOWN_ERROR,
}; };
// Encapsulates information extracted from the header of a CBOR data item, // Encapsulates information extracted from the header of a CBOR data item,
...@@ -96,7 +97,7 @@ class CBOR_EXPORT CBORReader { ...@@ -96,7 +97,7 @@ class CBOR_EXPORT CBORReader {
// formats is violated -including unknown additional info and incomplete // formats is violated -including unknown additional info and incomplete
// CBOR data- then an empty optional is returned. Optional |error_code_out| // CBOR data- then an empty optional is returned. Optional |error_code_out|
// can be provided by the caller to obtain additional information about // can be provided by the caller to obtain additional information about
// decoding failures. // decoding failures, which is always available if an empty value is returned.
// //
// Fails if not all the data was consumed and sets |error_code_out| to // Fails if not all the data was consumed and sets |error_code_out| to
// EXTRANEOUS_DATA in this case. // EXTRANEOUS_DATA in this case.
...@@ -113,9 +114,10 @@ class CBOR_EXPORT CBORReader { ...@@ -113,9 +114,10 @@ class CBOR_EXPORT CBORReader {
// Reads and parses the header of CBOR data item from |input_data|. Optional // Reads and parses the header of CBOR data item from |input_data|. Optional
// |error_code_out| can be provided by the caller to obtain additional // |error_code_out| can be provided by the caller to obtain additional
// information about decoding failures. Never fails with EXTRANEOUS_DATA, but // information about decoding failures, which is always available if an empty
// informs the caller of how many bytes were consumed through // value is returned. Never fails with EXTRANEOUS_DATA, but informs the
// |num_bytes_consumed|. // caller of how many bytes were consumed through |num_bytes_consumed|, which
// is set to zero on error.
static base::Optional<DataItemHeader> ReadDataItemHeader( static base::Optional<DataItemHeader> ReadDataItemHeader(
base::span<const uint8_t> input_data, base::span<const uint8_t> input_data,
size_t* num_bytes_consumed = nullptr, size_t* num_bytes_consumed = nullptr,
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment