dot15d4_frame/repr/
addressing.rs

1use super::FrameControlRepr;
2
3use crate::{Address, AddressingFields, AddressingMode, Error, FrameType, Result};
4
5/// A high-level representation of the IEEE 802.15.4 Addressing Fields.
6#[derive(Debug, Default)]
7#[cfg_attr(feature = "fuzz", derive(arbitrary::Arbitrary))]
8pub struct AddressingFieldsRepr {
9    /// Destination PAN identifier.
10    pub dst_pan_id: Option<u16>,
11    /// Destination address.
12    pub dst_address: Option<Address>,
13    /// Source PAN identifier.
14    pub src_pan_id: Option<u16>,
15    /// Source address.
16    pub src_address: Option<Address>,
17}
18
19impl AddressingFieldsRepr {
20    /// Parse the Addressing Fields from the given buffer.
21    pub fn parse(addressing: AddressingFields<&'_ [u8], &'_ [u8]>) -> Self {
22        Self {
23            dst_pan_id: addressing.dst_pan_id(),
24            dst_address: addressing.dst_address(),
25            src_pan_id: addressing.src_pan_id(),
26            src_address: addressing.src_address(),
27        }
28    }
29
30    /// Validate the Addressing Fields.
31    pub fn validate(&self, fc: &FrameControlRepr) -> Result<()> {
32        if fc.frame_type == FrameType::Data
33            && matches!(
34                (
35                    self.dst_pan_id,
36                    self.dst_address,
37                    self.src_pan_id,
38                    self.src_address
39                ),
40                (None, None, None, None)
41            )
42        {
43            return Err(Error);
44        }
45        Ok(())
46    }
47
48    /// Return the length of the Addressing Fields in octets.
49    pub fn buffer_len(&self, fc: &FrameControlRepr) -> usize {
50        (match self.dst_pan_id {
51            Some(_) => 2,
52            None => 0,
53        }) + match fc.dst_addressing_mode {
54            AddressingMode::Absent => 0,
55            AddressingMode::Short => 2,
56            AddressingMode::Extended => 8,
57            _ => unreachable!(),
58        } + match self.src_pan_id {
59            Some(_) => 2,
60            None => 0,
61        } + match fc.src_addressing_mode {
62            AddressingMode::Absent => 0,
63            AddressingMode::Short => 2,
64            AddressingMode::Extended => 8,
65            _ => unreachable!(),
66        }
67    }
68
69    /// Emit the Addressing Fields into the given buffer.
70    pub fn emit(&self, _buffer: &AddressingFields<&'_ mut [u8], &'_ [u8]>) {
71        todo!();
72    }
73}