1
2pub mod address;
3pub mod link;
4pub mod neighbor;
5pub mod route;
6
7pub use ipnet::{Ipv4Net, Ipv6Net, IpNet};
8
9
10use ftth_common::channel::create_pair;
11
12use futures::{future::join_all, FutureExt};
13
14
15#[derive(Debug, Clone)]
16pub struct RtnlClient {
17 address: address::RtnlAddressClient,
18 link: link::RtnlLinkClient,
19 neighbor: neighbor::RtnlNeighborClient,
20 route: route::RtnlRouteClient,
21}
22
23impl RtnlClient {
24 pub fn new() -> Self {
25 let (address_tx, address_rx) = create_pair();
26 let (link_tx, link_rx) = create_pair();
27 let (neighbor_tx, neighbor_rx) = create_pair();
28 let (route_tx, route_rx) = create_pair();
29
30 std::thread::spawn(move || {
31 let rt = match tokio::runtime::Builder::new_multi_thread().enable_all().build() {
32 Ok(rt) => rt,
33 Err(e) => {
34 log::error!("Tokio runtime building error: {}", e);
35 return;
36 }
37 };
38
39 let _ = rt.block_on(async {
40 #[allow(unused_variables)]
41 let (connection, handle, receiver) = rtnetlink::new_connection()?;
42
43 tokio::spawn(connection);
44
45 let mut futures = Vec::new();
46 futures.push(address::run_server(address_rx, handle.address()).boxed());
47 futures.push(link::run_server(link_rx, handle.link()).boxed());
48 futures.push(neighbor::run_server(neighbor_rx, handle.neighbours()).boxed());
49 futures.push(route::run_server(route_rx, handle.route()).boxed());
50
51 join_all(futures).await;
52
53 Ok::<(), std::io::Error>(())
54 });
55 });
56
57 Self {
58 address: address::RtnlAddressClient::new(address_tx),
59 link: link::RtnlLinkClient::new(link_tx),
60 neighbor: neighbor::RtnlNeighborClient::new(neighbor_tx),
61 route: route::RtnlRouteClient::new(route_tx),
62 }
63 }
64
65 pub fn address(&self) -> address::RtnlAddressClient {
66 self.address.clone()
67 }
68
69 pub fn link(&self) -> link::RtnlLinkClient {
70 self.link.clone()
71 }
72
73 pub fn neighbor(&self) -> neighbor::RtnlNeighborClient {
74 self.neighbor.clone()
75 }
76
77 pub fn route(&self) -> route::RtnlRouteClient {
78 self.route.clone()
79 }
80}