turn_types/attribute/
data.rs1use stun_types::{attribute::*, message::StunParseError};
10
11#[derive(Debug, Clone)]
13pub struct Data<'a> {
14 data: stun_types::data::Data<'a>,
15}
16
17impl AttributeStaticType for Data<'_> {
18 const TYPE: AttributeType = AttributeType::new(0x0013);
19}
20
21impl Attribute for Data<'_> {
22 fn get_type(&self) -> AttributeType {
23 Self::TYPE
24 }
25
26 fn length(&self) -> u16 {
27 self.data.len() as u16
28 }
29}
30
31impl AttributeWrite for Data<'_> {
32 fn to_raw(&self) -> RawAttribute {
33 RawAttribute::new(self.get_type(), &self.data)
34 }
35
36 fn write_into_unchecked(&self, dest: &mut [u8]) {
37 self.write_header_unchecked(dest);
38 dest[4..4 + self.data.len()].copy_from_slice(&self.data);
39 }
40}
41
42impl<'a> AttributeFromRaw<'a> for Data<'a> {
43 fn from_raw_ref(raw: &RawAttribute) -> Result<Self, StunParseError>
44 where
45 Self: Sized,
46 {
47 raw.check_type_and_len(Self::TYPE, ..)?;
48 Ok(Self {
49 data: raw.value.clone().into_owned(),
50 })
51 }
52
53 fn from_raw(raw: RawAttribute<'a>) -> Result<Self, StunParseError>
54 where
55 Self: Sized,
56 {
57 Self::try_from(raw)
58 }
59}
60
61impl<'a> TryFrom<RawAttribute<'a>> for Data<'a> {
62 type Error = StunParseError;
63
64 fn try_from(raw: RawAttribute<'a>) -> Result<Self, Self::Error> {
65 raw.check_type_and_len(Self::TYPE, ..)?;
66 Ok(Self { data: raw.value })
67 }
68}
69
70impl<'a> Data<'a> {
71 pub fn new(data: &'a [u8]) -> Self {
82 if data.len() > u16::MAX as usize {
83 panic!(
84 "Attempt made to create a Data attribute larger than {}",
85 u16::MAX
86 );
87 }
88 Self {
89 data: stun_types::data::Data::from(data),
90 }
91 }
92
93 pub fn data(&self) -> &[u8] {
104 &self.data
105 }
106}
107
108impl std::fmt::Display for Data<'_> {
109 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
110 write!(f, "{}: len:{}", self.get_type(), self.data.len())
111 }
112}
113
114#[cfg(test)]
115mod tests {
116 use super::*;
117 use byteorder::{BigEndian, ByteOrder};
118
119 #[test]
120 fn data() {
121 let _log = crate::tests::test_init_log();
122 let bytes = vec![0, 1, 2, 3, 4, 5];
123 let data = Data::new(&bytes);
124 assert_eq!(data.get_type(), Data::TYPE);
125 assert_eq!(data.data(), &bytes);
126 let raw: RawAttribute = data.to_raw();
127 println!("{}", raw);
128 assert_eq!(raw.get_type(), Data::TYPE);
129 let data2 = Data::try_from(raw.clone()).unwrap();
130 assert_eq!(data2.get_type(), Data::TYPE);
131 assert_eq!(data2.data(), &bytes);
132 let mut data: Vec<_> = raw.into();
134 BigEndian::write_u16(&mut data[0..2], 0);
135 assert!(matches!(
136 Data::try_from(RawAttribute::from_bytes(data.as_ref()).unwrap()),
137 Err(StunParseError::WrongAttributeImplementation)
138 ));
139 }
140}