rtnetlink/link/
xfrm.rs

1// SPDX-License-Identifier: MIT
2
3use crate::{
4    link::LinkMessageBuilder,
5    packet_route::link::{InfoData, InfoKind, InfoXfrm},
6};
7
8/// Represent XFRM interface.
9/// Example code on creating a XFRM interface
10/// ```no_run
11/// use rtnetlink::{new_connection, LinkXfrm};
12/// #[tokio::main]
13/// async fn main() -> Result<(), String> {
14///     let (connection, handle, _) = new_connection().unwrap();
15///     tokio::spawn(connection);
16///
17///     handle
18///         .link()
19///         .add(LinkXfrm::new("xfrm8", 9, 0x08).build())
20///         .execute()
21///         .await
22///         .map_err(|e| format!("{e}"))
23/// }
24/// ```
25///
26/// Please check LinkMessageBuilder::<LinkXfrm> for more detail.
27#[derive(Debug)]
28pub struct LinkXfrm;
29
30impl LinkXfrm {
31    /// Equal to `LinkMessageBuilder::<LinkXfrm>::new().dev().if_id()`
32    pub fn new(
33        name: &str,
34        base_iface_index: u32,
35        if_id: u32,
36    ) -> LinkMessageBuilder<Self> {
37        LinkMessageBuilder::<LinkXfrm>::new(name)
38            .dev(base_iface_index)
39            .if_id(if_id)
40    }
41}
42
43impl LinkMessageBuilder<LinkXfrm> {
44    /// Create [LinkMessageBuilder] for XFRM
45    pub fn new(name: &str) -> Self {
46        LinkMessageBuilder::<LinkXfrm>::new_with_info_kind(InfoKind::Xfrm)
47            .name(name.to_string())
48    }
49
50    pub fn append_info_data(mut self, info: InfoXfrm) -> Self {
51        if let InfoData::Xfrm(infos) = self
52            .info_data
53            .get_or_insert_with(|| InfoData::Xfrm(Vec::new()))
54        {
55            infos.push(info);
56        }
57        self
58    }
59
60    /// This is equivalent to the `if_id IF_ID` in command
61    /// `ip link add name NAME type xfrm if_id IF_ID`.
62    pub fn if_id(self, if_id: u32) -> Self {
63        self.append_info_data(InfoXfrm::IfId(if_id))
64    }
65
66    /// This is equivalent to the `dev PHYS_DEV` in command
67    /// `ip link add name NAME type xfm dev PHYS_DEV`, only take the interface
68    /// index.
69    pub fn dev(self, iface_index: u32) -> Self {
70        self.append_info_data(InfoXfrm::Link(iface_index))
71    }
72}