From 37519cc782115269c84f80162565c8a6a5c55751 Mon Sep 17 00:00:00 2001 From: Emil Fresk Date: Mon, 5 Aug 2024 08:16:39 +0200 Subject: [PATCH] Fix error in `impl Value for [T; N]` and update tests for API change --- src/map.rs | 70 ++++++++++++++++++++++++++++-------------------------- 1 file changed, 36 insertions(+), 34 deletions(-) diff --git a/src/map.rs b/src/map.rs index 8ba24bd..d3bc7e0 100644 --- a/src/map.rs +++ b/src/map.rs @@ -97,7 +97,7 @@ //! For your convenience there are premade implementations for the [Key] and [Value] traits. //! -use core::mem::MaybeUninit; +use core::mem::{size_of, MaybeUninit}; use embedded_storage_async::nor_flash::MultiwriteNorFlash; @@ -688,7 +688,7 @@ macro_rules! impl_key_num { ($int:ty) => { impl Key for $int { fn serialize_into(&self, buffer: &mut [u8]) -> Result { - let len = core::mem::size_of::(); + let len = size_of::(); if buffer.len() < len { return Err(SerializationError::BufferTooSmall); } @@ -697,19 +697,19 @@ macro_rules! impl_key_num { } fn deserialize_from(buffer: &[u8]) -> Result<(Self, usize), SerializationError> { - let len = core::mem::size_of::(); + let len = size_of::(); if buffer.len() < len { return Err(SerializationError::BufferTooSmall); } Ok(( Self::from_le_bytes(buffer[..len].try_into().unwrap()), - core::mem::size_of::(), + size_of::(), )) } fn get_len(_buffer: &[u8]) -> Result { - Ok(core::mem::size_of::()) + Ok(size_of::()) } } }; @@ -767,24 +767,6 @@ pub trait Value<'a> { Self: Sized; } -impl<'a> Value<'a> for &'a [u8] { - fn serialize_into(&self, buffer: &mut [u8]) -> Result { - if buffer.len() < self.len() { - return Err(SerializationError::BufferTooSmall); - } - - buffer[..self.len()].copy_from_slice(self); - Ok(self.len()) - } - - fn deserialize_from(buffer: &'a [u8]) -> Result - where - Self: Sized, - { - Ok(buffer) - } -} - impl<'a> Value<'a> for bool { fn serialize_into(&self, buffer: &mut [u8]) -> Result { ::serialize_into(&(*self as u8), buffer) @@ -822,9 +804,13 @@ impl<'a, T: Value<'a>> Value<'a> for Option { impl<'a, T: Value<'a>, const N: usize> Value<'a> for [T; N] { fn serialize_into(&self, buffer: &mut [u8]) -> Result { + if buffer.len() < size_of::() * N { + return Err(SerializationError::BufferTooSmall); + } + let mut size = 0; for v in self { - size += ::serialize_into(v, buffer)?; + size += ::serialize_into(v, &mut buffer[size..])?; } Ok(size) @@ -841,24 +827,40 @@ impl<'a, T: Value<'a>, const N: usize> Value<'a> for [T; N] { return Ok(unsafe { array.assume_init() }); } - let mut ptr = array.as_mut_ptr() as *mut T; + let ptr = array.as_mut_ptr() as *mut T; // SAFETY: // 1. The pointers are all inside the array via knowing `N`. // 2. `ptr.add(1)` does never point outside the array. // 3. `MaybeUninit::assume_init` is upheld with all values being filled. unsafe { - for _ in 0..N - 1 { - *ptr = ::deserialize_from(buffer)?; - ptr = ptr.add(1); + for i in 0..N { + *ptr.add(i) = ::deserialize_from(&buffer[i * size_of::()..])?; } - *ptr = ::deserialize_from(buffer)?; Ok(array.assume_init()) } } } +impl<'a> Value<'a> for &'a [u8] { + fn serialize_into(&self, buffer: &mut [u8]) -> Result { + if buffer.len() < self.len() { + return Err(SerializationError::BufferTooSmall); + } + + buffer[..self.len()].copy_from_slice(self); + Ok(self.len()) + } + + fn deserialize_from(buffer: &'a [u8]) -> Result + where + Self: Sized, + { + Ok(buffer) + } +} + macro_rules! impl_map_item_num { ($int:ty) => { impl<'a> Value<'a> for $int { @@ -1082,7 +1084,7 @@ mod tests { &mut cache::NoCache::new(), &mut data_buffer, &0u8, - &[5], + &[5u8], ) .await .unwrap(); @@ -1092,7 +1094,7 @@ mod tests { &mut cache::NoCache::new(), &mut data_buffer, &0u8, - &[5, 6], + &[5u8, 6], ) .await .unwrap(); @@ -1115,7 +1117,7 @@ mod tests { &mut cache::NoCache::new(), &mut data_buffer, &1u8, - &[2, 2, 2, 2, 2, 2], + &[2u8, 2, 2, 2, 2, 2], ) .await .unwrap(); @@ -1504,7 +1506,7 @@ mod tests { &mut cache::NoCache::new(), &mut [0; 1024], &0u8, - &[0; 1024 - 4 * 2 - 8 - 1], + &[0u8; 1024 - 4 * 2 - 8 - 1], ) .await .unwrap(); @@ -1516,7 +1518,7 @@ mod tests { &mut cache::NoCache::new(), &mut [0; 1024], &0u8, - &[0; 1024 - 4 * 2 - 8 - 1 + 1], + &[0u8; 1024 - 4 * 2 - 8 - 1 + 1], ) .await, Err(Error::ItemTooBig)