netlink_packet_route/rtnl/address/
message.rs

1// SPDX-License-Identifier: MIT
2
3use anyhow::Context;
4use netlink_packet_utils::{
5    traits::{Emitable, Parseable},
6    DecodeError,
7};
8
9use crate::{nlas::address::Nla, AddressMessageBuffer, ADDRESS_HEADER_LEN};
10
11#[derive(Debug, PartialEq, Eq, Clone, Default)]
12#[non_exhaustive]
13pub struct AddressMessage {
14    pub header: AddressHeader,
15    pub nlas: Vec<Nla>,
16}
17
18#[derive(Debug, PartialEq, Eq, Clone, Default)]
19pub struct AddressHeader {
20    pub family: u8,
21    pub prefix_len: u8,
22    pub flags: u8,
23    pub scope: u8,
24    pub index: u32,
25}
26
27impl Emitable for AddressHeader {
28    fn buffer_len(&self) -> usize {
29        ADDRESS_HEADER_LEN
30    }
31
32    fn emit(&self, buffer: &mut [u8]) {
33        let mut packet = AddressMessageBuffer::new(buffer);
34        packet.set_family(self.family);
35        packet.set_prefix_len(self.prefix_len);
36        packet.set_flags(self.flags);
37        packet.set_scope(self.scope);
38        packet.set_index(self.index);
39    }
40}
41
42impl Emitable for AddressMessage {
43    fn buffer_len(&self) -> usize {
44        self.header.buffer_len() + self.nlas.as_slice().buffer_len()
45    }
46
47    fn emit(&self, buffer: &mut [u8]) {
48        self.header.emit(buffer);
49        self.nlas
50            .as_slice()
51            .emit(&mut buffer[self.header.buffer_len()..]);
52    }
53}
54
55impl<T: AsRef<[u8]>> Parseable<AddressMessageBuffer<T>> for AddressHeader {
56    fn parse(buf: &AddressMessageBuffer<T>) -> Result<Self, DecodeError> {
57        Ok(Self {
58            family: buf.family(),
59            prefix_len: buf.prefix_len(),
60            flags: buf.flags(),
61            scope: buf.scope(),
62            index: buf.index(),
63        })
64    }
65}
66
67impl<'a, T: AsRef<[u8]> + 'a> Parseable<AddressMessageBuffer<&'a T>>
68    for AddressMessage
69{
70    fn parse(buf: &AddressMessageBuffer<&'a T>) -> Result<Self, DecodeError> {
71        Ok(AddressMessage {
72            header: AddressHeader::parse(buf)
73                .context("failed to parse address message header")?,
74            nlas: Vec::<Nla>::parse(buf)
75                .context("failed to parse address message NLAs")?,
76        })
77    }
78}
79
80impl<'a, T: AsRef<[u8]> + 'a> Parseable<AddressMessageBuffer<&'a T>>
81    for Vec<Nla>
82{
83    fn parse(buf: &AddressMessageBuffer<&'a T>) -> Result<Self, DecodeError> {
84        let mut nlas = vec![];
85        for nla_buf in buf.nlas() {
86            nlas.push(Nla::parse(&nla_buf?)?);
87        }
88        Ok(nlas)
89    }
90}