Skip to content

Commit

Permalink
RUST-713 Fix underflow on BSON array and binary deserialization (#244)
Browse files Browse the repository at this point in the history
  • Loading branch information
gperinazzo authored and patrickfreed committed Apr 6, 2021
1 parent 0fc08b7 commit f696f8c
Show file tree
Hide file tree
Showing 2 changed files with 41 additions and 0 deletions.
19 changes: 19 additions & 0 deletions src/de/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -176,6 +176,17 @@ fn deserialize_array<R: Read + ?Sized>(reader: &mut R, utf8_lossy: bool) -> Resu
let mut arr = Array::new();
let length = read_i32(reader)?;

if !(MIN_BSON_DOCUMENT_SIZE..=MAX_BSON_SIZE).contains(&length) {
return Err(Error::invalid_length(
length as usize,
&format!(
"array length must be between {} and {}",
MIN_BSON_DOCUMENT_SIZE, MAX_BSON_SIZE
)
.as_str(),
));
}

ensure_read_exactly(
reader,
(length as usize) - 4,
Expand Down Expand Up @@ -224,6 +235,14 @@ pub(crate) fn deserialize_bson_kvp<R: Read + ?Sized>(
if let BinarySubtype::BinaryOld = subtype {
let data_len = read_i32(reader)?;

if !(0..=(MAX_BSON_SIZE - 4)).contains(&data_len) {
return Err(Error::invalid_length(
data_len as usize,
&format!("0x02 length must be between 0 and {}", MAX_BSON_SIZE - 4)
.as_str(),
));
}

if data_len + 4 != len {
return Err(Error::invalid_length(
data_len as usize,
Expand Down
22 changes: 22 additions & 0 deletions src/tests/modules/serializer_deserializer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -540,3 +540,25 @@ fn test_serialize_deserialize_document() {
let bad_point: Result<Point, crate::de::Error> = from_document(bad_point);
assert!(bad_point.is_err());
}

/// [RUST-713](https://jira.mongodb.org/browse/RUST-713)
#[test]
fn test_deserialize_invalid_array_length() {
let _guard = LOCK.run_concurrently();
let buffer = b"\n\x00\x00\x00\x04\x00\x00\x00\x00\x00";
Document::from_reader(&mut std::io::Cursor::new(buffer))
.expect_err("expected deserialization to fail");
}

/// [RUST-713](https://jira.mongodb.org/browse/RUST-713)
#[test]
fn test_deserialize_invalid_old_binary_length() {
let _guard = LOCK.run_concurrently();
let buffer = b"\x0F\x00\x00\x00\x05\x00\x00\x00\x00\x00\x02\xFC\xFF\xFF\xFF";
Document::from_reader(&mut std::io::Cursor::new(buffer))
.expect_err("expected deserialization to fail");

let buffer = b".\x00\x00\x00\x05\x01\x00\x00\x00\x00\x00\x02\xfc\xff\xff\xff\xff\xff\xff\xff\x00\x00*\x00h\x0e\x10++\x00h\x0e++\x00\x00\t\x00\x00\x00\x00\x00*\x0e\x10++";
Document::from_reader(&mut std::io::Cursor::new(buffer))
.expect_err("expected deserialization to fail");
}

0 comments on commit f696f8c

Please sign in to comment.