From c8d2ea0c8608a5bf1866a78b6405ac5d545a70df Mon Sep 17 00:00:00 2001 From: Sebastian Date: Fri, 9 Aug 2024 23:52:38 +0200 Subject: [PATCH] Ensure that blobs match the length of arrays they're being deserialized into and otherwise fail. --- libsql/src/value.rs | 38 ++++++++++++++++++++++++++++++++++++-- 1 file changed, 36 insertions(+), 2 deletions(-) diff --git a/libsql/src/value.rs b/libsql/src/value.rs index fd3719b8ce..578d7541c2 100644 --- a/libsql/src/value.rs +++ b/libsql/src/value.rs @@ -630,7 +630,7 @@ mod serde_ { serde::forward_to_deserialize_any! { i8 i16 i32 i64 i128 u8 u16 u32 u64 u128 f32 f64 char str string - bytes byte_buf unit_struct newtype_struct seq tuple tuple_struct + bytes byte_buf unit_struct newtype_struct seq tuple_struct map struct identifier ignored_any } @@ -668,6 +668,31 @@ mod serde_ { } } + fn deserialize_tuple( + self, + len: usize, + visitor: V, + ) -> std::result::Result + where + V: Visitor<'de>, + { + match self.value { + Value::Blob(b) => { + if len != b.len() { + return Err(de::Error::invalid_value( + de::Unexpected::Other(&format!("{:?}", Value::Blob(b))), + &"expected and provided buffers don't match in length", + )); + } + visitor.visit_seq(SeqDeserializer::new(b.into_iter())) + } + _ => Err(de::Error::invalid_value( + de::Unexpected::Other(&format!("{:?}", self.value)), + &"a blob of a certain length", + )), + } + } + fn deserialize_any(self, visitor: V) -> std::result::Result where V: Visitor<'de>, @@ -814,7 +839,16 @@ mod serde_ { assert!(de::(Value::Blob(b"abc".to_vec())).is_err()); assert!(de::(Value::Text("C".to_string())).is_err()); - assert_eq!(de::<[u8; 2]>(Value::Blob(b"aa".to_vec())), Ok([97, 97])); + assert_eq!( + de::<[u8; 0]>(Value::Blob(b"".to_vec())).unwrap(), + [] as [u8; 0] + ); + assert_eq!( + de::<[u8; 2]>(Value::Blob(b"aa".to_vec())).unwrap(), + [97, 97] + ); + assert!(de::<[u8; 2]>(Value::Blob(b"aaa".to_vec())).is_err()); + assert!(de::<[u8; 3]>(Value::Blob(b"aa".to_vec())).is_err()); } } }