| #![cfg(feature = "borsh")] | ||
| use std::fmt; | ||
| extern crate arrayvec; | ||
| extern crate borsh; | ||
| fn assert_ser<T: borsh::BorshSerialize>(v: &T, expected_bytes: &[u8]) { | ||
| let mut actual_bytes = Vec::new(); | ||
| v.serialize(&mut actual_bytes).unwrap(); | ||
| assert_eq!(actual_bytes, expected_bytes); | ||
| } | ||
| fn assert_roundtrip<T: borsh::BorshSerialize + borsh::BorshDeserialize + PartialEq + fmt::Debug>(v: &T) { | ||
| let mut bytes = Vec::new(); | ||
| v.serialize(&mut bytes).unwrap(); | ||
| let v_de = T::try_from_slice(&bytes).unwrap(); | ||
| assert_eq!(*v, v_de); | ||
| } | ||
| mod array_vec { | ||
| use arrayvec::ArrayVec; | ||
| use super::{assert_ser, assert_roundtrip}; | ||
| #[test] | ||
| fn test_empty() { | ||
| let vec = ArrayVec::<u32, 0>::new(); | ||
| assert_ser(&vec, b"\0\0\0\0"); | ||
| assert_roundtrip(&vec); | ||
| } | ||
| #[test] | ||
| fn test_full() { | ||
| let mut vec = ArrayVec::<u32, 3>::new(); | ||
| vec.push(0xdeadbeef); | ||
| vec.push(0x123); | ||
| vec.push(0x456); | ||
| assert_ser(&vec, b"\x03\0\0\0\xef\xbe\xad\xde\x23\x01\0\0\x56\x04\0\0"); | ||
| assert_roundtrip(&vec); | ||
| } | ||
| #[test] | ||
| fn test_with_free_capacity() { | ||
| let mut vec = ArrayVec::<u32, 3>::new(); | ||
| vec.push(0xdeadbeef); | ||
| assert_ser(&vec, b"\x01\0\0\0\xef\xbe\xad\xde"); | ||
| assert_roundtrip(&vec); | ||
| } | ||
| } | ||
| mod array_string { | ||
| use arrayvec::ArrayString; | ||
| use super::{assert_ser, assert_roundtrip}; | ||
| #[test] | ||
| fn test_empty() { | ||
| let string = ArrayString::<0>::new(); | ||
| assert_ser(&string, b"\0\0\0\0"); | ||
| assert_roundtrip(&string); | ||
| } | ||
| #[test] | ||
| fn test_full() { | ||
| let string = ArrayString::from_byte_string(b"hello world").unwrap(); | ||
| assert_ser(&string, b"\x0b\0\0\0hello world"); | ||
| assert_roundtrip(&string); | ||
| } | ||
| #[test] | ||
| fn test_with_free_capacity() { | ||
| let string = ArrayString::<16>::from("hello world").unwrap(); | ||
| assert_ser(&string, b"\x0b\0\0\0hello world"); | ||
| assert_roundtrip(&string); | ||
| } | ||
| } |
| { | ||
| "git": { | ||
| "sha1": "2c92a59bed0d1669cede3806000d2e61d5994c4e" | ||
| "sha1": "f3732a0b4c9d5f2a20f3d5221afe75a0c66430dc" | ||
| }, | ||
| "path_in_vcs": "" | ||
| } |
@@ -23,2 +23,5 @@ on: | ||
| experimental: false | ||
| - rust: 1.70.0 | ||
| features: serde | ||
| experimental: false | ||
| - rust: stable | ||
@@ -32,12 +35,15 @@ features: | ||
| - rust: nightly | ||
| features: serde, zeroize | ||
| features: serde, borsh, zeroize | ||
| experimental: false | ||
| steps: | ||
| - uses: actions/checkout@v2 | ||
| - uses: actions-rs/toolchain@v1 | ||
| - uses: actions/checkout@v4 | ||
| - uses: dtolnay/rust-toolchain@master | ||
| with: | ||
| profile: minimal | ||
| toolchain: ${{ matrix.rust }} | ||
| override: true | ||
| - name: Pin versions for MSRV | ||
| if: "${{ matrix.rust == '1.51.0' }}" | ||
| run: | | ||
| cargo update -p serde_test --precise 1.0.163 | ||
| cargo update -p serde --precise 1.0.69 | ||
| - name: Tests | ||
@@ -56,3 +62,3 @@ run: | | ||
| steps: | ||
| - uses: actions/checkout@v2 | ||
| - uses: actions/checkout@v4 | ||
| - name: Install Miri | ||
@@ -59,0 +65,0 @@ run: | |
+33
-3
@@ -14,5 +14,11 @@ # THIS FILE IS AUTOMATICALLY GENERATED BY CARGO | ||
| edition = "2018" | ||
| rust-version = "1.51" | ||
| name = "arrayvec" | ||
| version = "0.7.4" | ||
| version = "0.7.5" | ||
| authors = ["bluss"] | ||
| build = false | ||
| autobins = false | ||
| autoexamples = false | ||
| autotests = false | ||
| autobenches = false | ||
| description = "A vector with fixed capacity, backed by an array (it can be stored on the stack too). Implements fixed capacity ArrayVec and ArrayString." | ||
@@ -37,2 +43,3 @@ documentation = "https://docs.rs/arrayvec/" | ||
| features = [ | ||
| "borsh", | ||
| "serde", | ||
@@ -52,10 +59,33 @@ "zeroize", | ||
| [lib] | ||
| name = "arrayvec" | ||
| path = "src/lib.rs" | ||
| [[test]] | ||
| name = "borsh" | ||
| path = "tests/borsh.rs" | ||
| [[test]] | ||
| name = "serde" | ||
| path = "tests/serde.rs" | ||
| [[test]] | ||
| name = "tests" | ||
| path = "tests/tests.rs" | ||
| [[bench]] | ||
| name = "extend" | ||
| name = "arraystring" | ||
| path = "benches/arraystring.rs" | ||
| harness = false | ||
| [[bench]] | ||
| name = "arraystring" | ||
| name = "extend" | ||
| path = "benches/extend.rs" | ||
| harness = false | ||
| [dependencies.borsh] | ||
| version = "1.2.0" | ||
| optional = true | ||
| default-features = false | ||
| [dependencies.serde] | ||
@@ -62,0 +92,0 @@ version = "1.0" |
+13
-2
| Recent Changes (arrayvec) | ||
| ========================= | ||
| ## 0.7.5 | ||
| - Add `as_ptr` and `as_mut_ptr` to `ArrayString` [@YuhanLiin](https://github.com/YuhanLiin) [#260](https://github.com/bluss/arrayvec/pull/260) | ||
| - Add borsh serialization support by @honzasp and @Fuuzetsu [#259](https://github.com/bluss/arrayvec/pull/259) | ||
| - Move length field before before data in ArrayVec and ArrayString by @JakkuSakura [#255](https://github.com/bluss/arrayvec/pull/255) | ||
| - Fix miri error for ZST case in extend by @bluss | ||
| - implement AsRef<Path> for ArrayString by [@Zoybean](https://github.com/Zoybean) [#218](https://github.com/bluss/arrayvec/pull/218) | ||
| - Fix typos in changelog by [@striezel](https://github.com/striezel) [#241](https://github.com/bluss/arrayvec/pull/241) | ||
| - Add `as_slice`, `as_mut_slice` methods to `IntoIter` by [@clarfonthey](https://github.com/clarfonthey) [#224](https://github.com/bluss/arrayvec/pull/224) | ||
| ## 0.7.4 | ||
@@ -121,3 +132,3 @@ | ||
| - Add method `try_extend_from_slice` to `ArrayVec`, which is always | ||
| effecient by @Thomasdezeeuw. | ||
| efficient by @Thomasdezeeuw. | ||
| - Add method `remaining_capacity` by @Thomasdezeeuw | ||
@@ -173,3 +184,3 @@ - Improve performance of the `extend` method. | ||
| - Use `drop_in_place` when dropping the arrayvec by-value iterator | ||
| - Decrease mininum Rust version (see docs) by @jeehoonkang | ||
| - Decrease minimum Rust version (see docs) by @jeehoonkang | ||
@@ -176,0 +187,0 @@ - 0.3.25 |
+44
-3
@@ -8,2 +8,3 @@ use std::borrow::{Borrow, BorrowMut}; | ||
| use std::ops::{Deref, DerefMut}; | ||
| use std::path::Path; | ||
| use std::ptr; | ||
@@ -35,6 +36,7 @@ use std::slice; | ||
| #[derive(Copy)] | ||
| #[repr(C)] | ||
| pub struct ArrayString<const CAP: usize> { | ||
| // the `len` first elements of the array are initialized | ||
| len: LenUint, | ||
| xs: [MaybeUninit<u8>; CAP], | ||
| len: LenUint, | ||
| } | ||
@@ -419,7 +421,9 @@ | ||
| fn as_ptr(&self) -> *const u8 { | ||
| /// Return a raw pointer to the string's buffer. | ||
| pub fn as_ptr(&self) -> *const u8 { | ||
| self.xs.as_ptr() as *const u8 | ||
| } | ||
| fn as_mut_ptr(&mut self) -> *mut u8 { | ||
| /// Return a raw mutable pointer to the string's buffer. | ||
| pub fn as_mut_ptr(&mut self) -> *mut u8 { | ||
| self.xs.as_mut_ptr() as *mut u8 | ||
@@ -504,2 +508,8 @@ } | ||
| impl<const CAP: usize> AsRef<Path> for ArrayString<CAP> { | ||
| fn as_ref(&self) -> &Path { | ||
| self.as_str().as_ref() | ||
| } | ||
| } | ||
| impl<const CAP: usize> fmt::Display for ArrayString<CAP> | ||
@@ -632,2 +642,33 @@ { | ||
| #[cfg(feature = "borsh")] | ||
| /// Requires crate feature `"borsh"` | ||
| impl<const CAP: usize> borsh::BorshSerialize for ArrayString<CAP> { | ||
| fn serialize<W: borsh::io::Write>(&self, writer: &mut W) -> borsh::io::Result<()> { | ||
| <str as borsh::BorshSerialize>::serialize(&*self, writer) | ||
| } | ||
| } | ||
| #[cfg(feature = "borsh")] | ||
| /// Requires crate feature `"borsh"` | ||
| impl<const CAP: usize> borsh::BorshDeserialize for ArrayString<CAP> { | ||
| fn deserialize_reader<R: borsh::io::Read>(reader: &mut R) -> borsh::io::Result<Self> { | ||
| let len = <u32 as borsh::BorshDeserialize>::deserialize_reader(reader)? as usize; | ||
| if len > CAP { | ||
| return Err(borsh::io::Error::new( | ||
| borsh::io::ErrorKind::InvalidData, | ||
| format!("Expected a string no more than {} bytes long", CAP), | ||
| )) | ||
| } | ||
| let mut buf = [0u8; CAP]; | ||
| let buf = &mut buf[..len]; | ||
| reader.read_exact(buf)?; | ||
| let s = str::from_utf8(&buf).map_err(|err| { | ||
| borsh::io::Error::new(borsh::io::ErrorKind::InvalidData, err.to_string()) | ||
| })?; | ||
| Ok(Self::from(s).unwrap()) | ||
| } | ||
| } | ||
| impl<'a, const CAP: usize> TryFrom<&'a str> for ArrayString<CAP> | ||
@@ -634,0 +675,0 @@ { |
+51
-3
@@ -42,6 +42,7 @@ | ||
| /// available. The ArrayVec can be converted into a by value iterator. | ||
| #[repr(C)] | ||
| pub struct ArrayVec<T, const CAP: usize> { | ||
| len: LenUint, | ||
| // the `len` first elements of the array are initialized | ||
| xs: [MaybeUninit<T>; CAP], | ||
| len: LenUint, | ||
| } | ||
@@ -883,3 +884,14 @@ | ||
| } | ||
| impl<T, const CAP: usize> IntoIter<T, CAP> { | ||
| /// Returns the remaining items of this iterator as a slice. | ||
| pub fn as_slice(&self) -> &[T] { | ||
| &self.v[self.index..] | ||
| } | ||
| /// Returns the remaining items of this iterator as a mutable slice. | ||
| pub fn as_mut_slice(&mut self) -> &mut [T] { | ||
| &mut self.v[self.index..] | ||
| } | ||
| } | ||
| impl<T, const CAP: usize> Iterator for IntoIter<T, CAP> { | ||
@@ -1093,3 +1105,5 @@ type Item = T; | ||
| debug_assert_ne!(ptr, end_ptr); | ||
| ptr.write(elt); | ||
| if mem::size_of::<T>() != 0 { | ||
| ptr.write(elt); | ||
| } | ||
| ptr = raw_ptr_add(ptr, 1); | ||
@@ -1121,3 +1135,3 @@ guard.data += 1; | ||
| // Special case for ZST | ||
| ptr.cast::<u8>().wrapping_add(offset).cast() | ||
| ptr.cast::<u8>().wrapping_add(offset).cast::<T>() | ||
| } else { | ||
@@ -1305,1 +1319,35 @@ ptr.add(offset) | ||
| } | ||
| #[cfg(feature = "borsh")] | ||
| /// Requires crate feature `"borsh"` | ||
| impl<T, const CAP: usize> borsh::BorshSerialize for ArrayVec<T, CAP> | ||
| where | ||
| T: borsh::BorshSerialize, | ||
| { | ||
| fn serialize<W: borsh::io::Write>(&self, writer: &mut W) -> borsh::io::Result<()> { | ||
| <[T] as borsh::BorshSerialize>::serialize(self.as_slice(), writer) | ||
| } | ||
| } | ||
| #[cfg(feature = "borsh")] | ||
| /// Requires crate feature `"borsh"` | ||
| impl<T, const CAP: usize> borsh::BorshDeserialize for ArrayVec<T, CAP> | ||
| where | ||
| T: borsh::BorshDeserialize, | ||
| { | ||
| fn deserialize_reader<R: borsh::io::Read>(reader: &mut R) -> borsh::io::Result<Self> { | ||
| let mut values = Self::new(); | ||
| let len = <u32 as borsh::BorshDeserialize>::deserialize_reader(reader)?; | ||
| for _ in 0..len { | ||
| let elem = <T as borsh::BorshDeserialize>::deserialize_reader(reader)?; | ||
| if let Err(_) = values.try_push(elem) { | ||
| return Err(borsh::io::Error::new( | ||
| borsh::io::ErrorKind::InvalidData, | ||
| format!("Expected an array with no more than {} items", CAP), | ||
| )); | ||
| } | ||
| } | ||
| Ok(values) | ||
| } | ||
| } |
+1
-15
@@ -698,17 +698,3 @@ extern crate arrayvec; | ||
| #[cfg(feature="array-sizes-33-128")] | ||
| #[test] | ||
| fn test_sizes_33_128() { | ||
| ArrayVec::from([0u8; 52]); | ||
| ArrayVec::from([0u8; 127]); | ||
| } | ||
| #[cfg(feature="array-sizes-129-255")] | ||
| #[test] | ||
| fn test_sizes_129_255() { | ||
| ArrayVec::from([0u8; 237]); | ||
| ArrayVec::from([0u8; 255]); | ||
| } | ||
| #[test] | ||
| fn test_extend_zst() { | ||
@@ -794,2 +780,2 @@ let mut range = 0..10; | ||
| assert_eq!(string.len(), 4); | ||
| } | ||
| } |
Sorry, the diff of this file is not supported yet