diff --git a/CHANGELOG.md b/CHANGELOG.md index 8148ae3..dbfa298 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -8,6 +8,15 @@ and this project adheres to [Semantic Versioning](http://semver.org/). # [unreleased] +# [v0.10.0] 2024-02-17 + +## Added + +- Added `value` and `to_vec` methods for the `UnsignedEnum` trait. The value is returned as + as `u64`. Renamed former `value` method on `GenericUnsignedByteField` to `value_typed`. +- Added `value_const` const function for `UnsignedByteField` type. +- Added `value_typed` const functions for `GenericUnsignedByteField` and `GenericEcssEnumWrapper`. + # [v0.9.0] 2024-02-07 ## Added diff --git a/Cargo.toml b/Cargo.toml index 108e3d5..cb5f35e 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "spacepackets" -version = "0.9.0" +version = "0.10.0" edition = "2021" rust-version = "1.61" authors = ["Robin Mueller "] diff --git a/src/cfdp/pdu/finished.rs b/src/cfdp/pdu/finished.rs index 529984c..6dd1d0a 100644 --- a/src/cfdp/pdu/finished.rs +++ b/src/cfdp/pdu/finished.rs @@ -581,7 +581,7 @@ mod tests { assert_eq!(finished_pdu_vec.len(), 12); assert_eq!(finished_pdu_vec[9], TlvType::EntityId.into()); assert_eq!(finished_pdu_vec[10], 1); - assert_eq!(finished_pdu_vec[11], TEST_DEST_ID.value()); + assert_eq!(finished_pdu_vec[11], TEST_DEST_ID.value_typed()); assert_eq!( finished_pdu.fault_location().unwrap().entity_id(), &TEST_DEST_ID.into() diff --git a/src/ecss/mod.rs b/src/ecss/mod.rs index 19d44a6..29b1e96 100644 --- a/src/ecss/mod.rs +++ b/src/ecss/mod.rs @@ -315,15 +315,19 @@ pub trait EcssEnumerationExt: EcssEnumeration + Debug + Copy + Clone + PartialEq #[derive(Debug, Copy, Clone, Eq, PartialEq)] #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))] -pub struct GenericEcssEnumWrapper { +pub struct GenericEcssEnumWrapper> { field: GenericUnsignedByteField, } -impl GenericEcssEnumWrapper { +impl> GenericEcssEnumWrapper { pub const fn ptc() -> PacketTypeCodes { PacketTypeCodes::Enumerated } + pub const fn value_typed(&self) -> TYPE { + self.field.value_typed() + } + pub fn new(val: TYPE) -> Self { Self { field: GenericUnsignedByteField::new(val), @@ -331,7 +335,7 @@ impl GenericEcssEnumWrapper { } } -impl UnsignedEnum for GenericEcssEnumWrapper { +impl> UnsignedEnum for GenericEcssEnumWrapper { fn size(&self) -> usize { (self.pfc() / 8) as usize } @@ -339,15 +343,19 @@ impl UnsignedEnum for GenericEcssEnumWrapper { fn write_to_be_bytes(&self, buf: &mut [u8]) -> Result { self.field.write_to_be_bytes(buf) } + + fn value(&self) -> u64 { + self.field.value() + } } -impl EcssEnumeration for GenericEcssEnumWrapper { +impl> EcssEnumeration for GenericEcssEnumWrapper { fn pfc(&self) -> u8 { size_of::() as u8 * 8_u8 } } -impl EcssEnumerationExt +impl> EcssEnumerationExt for GenericEcssEnumWrapper { } @@ -396,6 +404,8 @@ mod tests { .write_to_be_bytes(&mut buf[1..2]) .expect("To byte conversion of u8 failed"); assert_eq!(buf[1], 1); + assert_eq!(my_enum.value(), 1); + assert_eq!(my_enum.value_typed(), 1); } #[test] @@ -409,6 +419,8 @@ mod tests { assert_eq!(my_enum.pfc(), 16); assert_eq!(buf[1], 0x1f); assert_eq!(buf[2], 0x2f); + assert_eq!(my_enum.value(), 0x1f2f); + assert_eq!(my_enum.value_typed(), 0x1f2f); } #[test] @@ -440,6 +452,8 @@ mod tests { assert_eq!(buf[2], 0x2f); assert_eq!(buf[3], 0x3f); assert_eq!(buf[4], 0x4f); + assert_eq!(my_enum.value(), 0x1f2f3f4f); + assert_eq!(my_enum.value_typed(), 0x1f2f3f4f); } #[test] @@ -460,6 +474,23 @@ mod tests { } } + #[test] + fn test_enum_u64() { + let mut buf = [0; 8]; + let my_enum = EcssEnumU64::new(0x1f2f3f4f5f); + my_enum + .write_to_be_bytes(&mut buf) + .expect("To byte conversion of u64 failed"); + assert_eq!(buf[3], 0x1f); + assert_eq!(buf[4], 0x2f); + assert_eq!(buf[5], 0x3f); + assert_eq!(buf[6], 0x4f); + assert_eq!(buf[7], 0x5f); + assert_eq!(my_enum.value(), 0x1f2f3f4f5f); + assert_eq!(my_enum.value_typed(), 0x1f2f3f4f5f); + assert_eq!(u64::from_be_bytes(buf), 0x1f2f3f4f5f); + } + #[test] fn test_pus_error_display() { let unsupport_version = PusError::VersionNotSupported(super::PusVersion::EsaPus); diff --git a/src/util.rs b/src/util.rs index 88298f4..44f15dd 100644 --- a/src/util.rs +++ b/src/util.rs @@ -73,6 +73,15 @@ pub trait UnsignedEnum { fn size(&self) -> usize; /// Write the unsigned enumeration to a raw buffer. Returns the written size on success. fn write_to_be_bytes(&self, buf: &mut [u8]) -> Result; + + fn value(&self) -> u64; + + #[cfg(feature = "alloc")] + fn to_vec(&self) -> alloc::vec::Vec { + let mut buf = alloc::vec![0; self.size()]; + self.write_to_be_bytes(&mut buf).unwrap(); + buf + } } pub trait UnsignedEnumExt: UnsignedEnum + Debug + Copy + Clone + PartialEq + Eq {} @@ -132,7 +141,7 @@ impl UnsignedByteField { Self { width, value } } - pub fn value(&self) -> u64 { + pub const fn value_const(&self) -> u64 { self.value } @@ -172,6 +181,10 @@ impl UnsignedEnum for UnsignedByteField { self.width } + fn value(&self) -> u64 { + self.value_const() + } + fn write_to_be_bytes(&self, buf: &mut [u8]) -> Result { if buf.len() < self.size() { return Err(ByteConversionError::ToSliceTooSmall { @@ -207,21 +220,21 @@ impl UnsignedEnum for UnsignedByteField { #[derive(Debug, Copy, Clone, Eq, PartialEq)] #[cfg_attr(feature = "serde", derive(Serialize, Deserialize))] -pub struct GenericUnsignedByteField { +pub struct GenericUnsignedByteField> { value: TYPE, } -impl GenericUnsignedByteField { +impl> GenericUnsignedByteField { pub const fn new(val: TYPE) -> Self { Self { value: val } } - pub const fn value(&self) -> TYPE { + pub const fn value_typed(&self) -> TYPE { self.value } } -impl UnsignedEnum for GenericUnsignedByteField { +impl> UnsignedEnum for GenericUnsignedByteField { fn size(&self) -> usize { self.value.written_len() } @@ -233,9 +246,13 @@ impl UnsignedEnum for GenericUnsignedByteField { expected: self.size(), }); } - buf[0..self.size()].copy_from_slice(self.value.to_be_bytes().as_ref()); + buf[..self.size()].copy_from_slice(self.value.to_be_bytes().as_ref()); Ok(self.value.written_len()) } + + fn value(&self) -> u64 { + self.value_typed().into() + } } pub type UnsignedByteFieldEmpty = GenericUnsignedByteField<()>; @@ -351,6 +368,8 @@ pub mod tests { for val in buf.iter().skip(1) { assert_eq!(*val, 0); } + assert_eq!(u8.value_typed(), 5); + assert_eq!(u8.value(), 5); } #[test] @@ -367,6 +386,8 @@ pub mod tests { for val in buf.iter().skip(2) { assert_eq!(*val, 0); } + assert_eq!(u16.value_typed(), 3823); + assert_eq!(u16.value(), 3823); } #[test] @@ -383,6 +404,8 @@ pub mod tests { (4..8).for_each(|i| { assert_eq!(buf[i], 0); }); + assert_eq!(u32.value_typed(), 80932); + assert_eq!(u32.value(), 80932); } #[test] @@ -396,6 +419,8 @@ pub mod tests { assert_eq!(len, 8); let raw_val = u64::from_be_bytes(buf[0..8].try_into().unwrap()); assert_eq!(raw_val, 5999999); + assert_eq!(u64.value_typed(), 5999999); + assert_eq!(u64.value(), 5999999); } #[test] @@ -534,9 +559,9 @@ pub mod tests { u8.write_to_be_bytes(&mut buf) .expect("writing to raw buffer failed"); assert_eq!(buf[0], 5); - for i in 1..8 { + (1..8).for_each(|i| { assert_eq!(buf[i], 0); - } + }); } #[test] @@ -562,9 +587,9 @@ pub mod tests { .expect("writing to raw buffer failed"); let raw_val = u32::from_be_bytes(buf[0..4].try_into().unwrap()); assert_eq!(raw_val, 80932); - for i in 4..8 { + (4..8).for_each(|i| { assert_eq!(buf[i], 0); - } + }); } #[test]