netlink_packet_route/neighbour_discovery_user_option/
buffer.rs1use netlink_packet_utils::nla::{NlaBuffer, NlasIterator};
4use netlink_packet_utils::DecodeError;
5
6pub const NEIGHBOUR_DISCOVERY_USER_OPTION_HEADER_LEN: usize = 16;
7
8buffer!(NeighbourDiscoveryUserOptionMessageBuffer {
9 address_family: (u8, 0),
10 padding_1: (u8, 1),
11 options_length: (u16, 2..4),
12 interface_index: (u32, 4..8),
13 icmp_type: (u8, 8),
14 icmp_code: (u8, 9),
15 padding_2: (u16, 10..12),
16 padding_3: (u32, 12..16),
17 payload: (slice, NEIGHBOUR_DISCOVERY_USER_OPTION_HEADER_LEN..),
18});
19
20impl<T: AsRef<[u8]>> NeighbourDiscoveryUserOptionMessageBuffer<T> {
21 pub fn new_checked(buffer: T) -> Result<Self, DecodeError> {
22 let packet = Self::new(buffer);
23 packet.check_buffer_length()?;
24 Ok(packet)
25 }
26
27 fn check_buffer_length(&self) -> Result<(), DecodeError> {
28 let len = self.buffer.as_ref().len();
29 let required_len =
30 NEIGHBOUR_DISCOVERY_USER_OPTION_HEADER_LEN + self.options_length() as usize;
31 if len < required_len {
32 Err(DecodeError::InvalidBufferLength {
33 name: "NeighbourDiscoveryUserOptionMessageBuffer",
34 len,
35 buffer_len: required_len,
36 })
37 } else {
38 Ok(())
39 }
40 }
41}
42
43impl<'a, T: AsRef<[u8]> + ?Sized> NeighbourDiscoveryUserOptionMessageBuffer<&'a T> {
44 pub fn option_body(&self) -> &[u8] {
45 &self.payload()[..self.options_length() as usize]
46 }
47
48 pub fn nlas(&self) -> impl Iterator<Item = Result<NlaBuffer<&'a [u8]>, DecodeError>> {
49 NlasIterator::new(&self.payload()[self.options_length() as usize..])
50 .map(|result| result.map_err(DecodeError::from))
51 }
52}