netlink_packet_route/neighbour_table/
param.rs1use netlink_packet_core::{
4 emit_u32, emit_u64, parse_u32, parse_u64, DecodeError, DefaultNla,
5 ErrorContext, Nla, NlaBuffer, NlasIterator, Parseable,
6};
7
8const NDTPA_IFINDEX: u16 = 1;
9const NDTPA_REFCNT: u16 = 2;
10const NDTPA_REACHABLE_TIME: u16 = 3;
11const NDTPA_BASE_REACHABLE_TIME: u16 = 4;
12const NDTPA_RETRANS_TIME: u16 = 5;
13const NDTPA_GC_STALETIME: u16 = 6;
14const NDTPA_DELAY_PROBE_TIME: u16 = 7;
15const NDTPA_QUEUE_LEN: u16 = 8;
16const NDTPA_APP_PROBES: u16 = 9;
17const NDTPA_UCAST_PROBES: u16 = 10;
18const NDTPA_MCAST_PROBES: u16 = 11;
19const NDTPA_ANYCAST_DELAY: u16 = 12;
20const NDTPA_PROXY_DELAY: u16 = 13;
21const NDTPA_PROXY_QLEN: u16 = 14;
22const NDTPA_LOCKTIME: u16 = 15;
23const NDTPA_QUEUE_LENBYTES: u16 = 16;
24const NDTPA_MCAST_REPROBES: u16 = 17;
25const NDTPA_INTERVAL_PROBE_TIME_MS: u16 = 19;
27
28#[derive(Debug, PartialEq, Eq, Clone)]
29#[non_exhaustive]
30pub enum NeighbourTableParameter {
31 Ifindex(u32),
32 ReferenceCount(u32),
33 ReachableTime(u64),
34 BaseReachableTime(u64),
35 RetransTime(u64),
36 GcStaletime(u64),
37 DelayProbeTime(u64),
38 QueueLen(u32),
39 AppProbes(u32),
40 UcastProbes(u32),
41 McastProbes(u32),
42 AnycastDelay(u64),
43 ProxyDelay(u64),
44 ProxyQlen(u32),
45 Locktime(u64),
46 QueueLenbytes(u32),
47 McastReprobes(u32),
48 IntervalProbeTimeMs(u64),
49 Other(DefaultNla),
50}
51
52impl Nla for NeighbourTableParameter {
53 fn value_len(&self) -> usize {
54 match self {
55 Self::Ifindex(_)
56 | Self::ReferenceCount(_)
57 | Self::QueueLen(_)
58 | Self::AppProbes(_)
59 | Self::UcastProbes(_)
60 | Self::McastProbes(_)
61 | Self::ProxyQlen(_)
62 | Self::QueueLenbytes(_)
63 | Self::McastReprobes(_) => 4,
64
65 Self::ReachableTime(_)
66 | Self::BaseReachableTime(_)
67 | Self::RetransTime(_)
68 | Self::GcStaletime(_)
69 | Self::DelayProbeTime(_)
70 | Self::AnycastDelay(_)
71 | Self::ProxyDelay(_)
72 | Self::Locktime(_)
73 | Self::IntervalProbeTimeMs(_) => 8,
74
75 Self::Other(nla) => nla.value_len(),
76 }
77 }
78
79 fn emit_value(&self, buffer: &mut [u8]) {
80 match self {
81 Self::Ifindex(v)
82 | Self::ReferenceCount(v)
83 | Self::QueueLen(v)
84 | Self::AppProbes(v)
85 | Self::UcastProbes(v)
86 | Self::McastProbes(v)
87 | Self::ProxyQlen(v)
88 | Self::QueueLenbytes(v)
89 | Self::McastReprobes(v) => emit_u32(buffer, *v).unwrap(),
90
91 Self::ReachableTime(v)
92 | Self::BaseReachableTime(v)
93 | Self::RetransTime(v)
94 | Self::GcStaletime(v)
95 | Self::DelayProbeTime(v)
96 | Self::AnycastDelay(v)
97 | Self::ProxyDelay(v)
98 | Self::Locktime(v)
99 | Self::IntervalProbeTimeMs(v) => emit_u64(buffer, *v).unwrap(),
100
101 Self::Other(nla) => nla.emit_value(buffer),
102 }
103 }
104
105 fn kind(&self) -> u16 {
106 match self {
107 Self::Ifindex(_) => NDTPA_IFINDEX,
108 Self::ReferenceCount(_) => NDTPA_REFCNT,
109 Self::ReachableTime(_) => NDTPA_REACHABLE_TIME,
110 Self::BaseReachableTime(_) => NDTPA_BASE_REACHABLE_TIME,
111 Self::RetransTime(_) => NDTPA_RETRANS_TIME,
112 Self::GcStaletime(_) => NDTPA_GC_STALETIME,
113 Self::DelayProbeTime(_) => NDTPA_DELAY_PROBE_TIME,
114 Self::QueueLen(_) => NDTPA_QUEUE_LEN,
115 Self::AppProbes(_) => NDTPA_APP_PROBES,
116 Self::UcastProbes(_) => NDTPA_UCAST_PROBES,
117 Self::McastProbes(_) => NDTPA_MCAST_PROBES,
118 Self::AnycastDelay(_) => NDTPA_ANYCAST_DELAY,
119 Self::ProxyDelay(_) => NDTPA_PROXY_DELAY,
120 Self::ProxyQlen(_) => NDTPA_PROXY_QLEN,
121 Self::Locktime(_) => NDTPA_LOCKTIME,
122 Self::QueueLenbytes(_) => NDTPA_QUEUE_LENBYTES,
123 Self::McastReprobes(_) => NDTPA_MCAST_REPROBES,
124 Self::IntervalProbeTimeMs(_) => NDTPA_INTERVAL_PROBE_TIME_MS,
125 Self::Other(nla) => nla.kind(),
126 }
127 }
128}
129
130impl<'a, T: AsRef<[u8]> + ?Sized> Parseable<NlaBuffer<&'a T>>
131 for NeighbourTableParameter
132{
133 fn parse(buf: &NlaBuffer<&'a T>) -> Result<Self, DecodeError> {
134 let payload = buf.value();
135 Ok(match buf.kind() {
136 NDTPA_IFINDEX => {
137 Self::Ifindex(parse_u32(payload).context(format!(
138 "invalid NDTPA_IFINDEX value {payload:?}"
139 ))?)
140 }
141 NDTPA_REFCNT => {
142 Self::ReferenceCount(parse_u32(payload).context(format!(
143 "invalid NDTPA_REFCNT value {payload:?}"
144 ))?)
145 }
146 NDTPA_REACHABLE_TIME => {
147 Self::ReachableTime(parse_u64(payload).context(format!(
148 "invalid NDTPA_REACHABLE_TIME value {payload:?}"
149 ))?)
150 }
151 NDTPA_BASE_REACHABLE_TIME => {
152 Self::BaseReachableTime(parse_u64(payload).context(format!(
153 "invalid NDTPA_BASE_REACHABLE_TIME value {payload:?}"
154 ))?)
155 }
156 NDTPA_RETRANS_TIME => {
157 Self::RetransTime(parse_u64(payload).context(format!(
158 "invalid NDTPA_RETRANS_TIME value {payload:?}"
159 ))?)
160 }
161 NDTPA_GC_STALETIME => {
162 Self::GcStaletime(parse_u64(payload).context(format!(
163 "invalid NDTPA_GC_STALE_TIME value {payload:?}"
164 ))?)
165 }
166 NDTPA_DELAY_PROBE_TIME => {
167 Self::DelayProbeTime(parse_u64(payload).context(format!(
168 "invalid NDTPA_DELAY_PROBE_TIME value {payload:?}"
169 ))?)
170 }
171 NDTPA_QUEUE_LEN => Self::QueueLen(parse_u32(payload).context(
172 format!("invalid NDTPA_QUEUE_LEN value {payload:?}"),
173 )?),
174 NDTPA_APP_PROBES => Self::AppProbes(parse_u32(payload).context(
175 format!("invalid NDTPA_APP_PROBES value {payload:?}"),
176 )?),
177 NDTPA_UCAST_PROBES => {
178 Self::UcastProbes(parse_u32(payload).context(format!(
179 "invalid NDTPA_UCAST_PROBES value {payload:?}"
180 ))?)
181 }
182 NDTPA_MCAST_PROBES => {
183 Self::McastProbes(parse_u32(payload).context(format!(
184 "invalid NDTPA_MCAST_PROBES value {payload:?}"
185 ))?)
186 }
187 NDTPA_ANYCAST_DELAY => {
188 Self::AnycastDelay(parse_u64(payload).context(format!(
189 "invalid NDTPA_ANYCAST_DELAY value {payload:?}"
190 ))?)
191 }
192 NDTPA_PROXY_DELAY => Self::ProxyDelay(parse_u64(payload).context(
193 format!("invalid NDTPA_PROXY_DELAY value {payload:?}"),
194 )?),
195 NDTPA_PROXY_QLEN => Self::ProxyQlen(parse_u32(payload).context(
196 format!("invalid NDTPA_PROXY_QLEN value {payload:?}"),
197 )?),
198 NDTPA_LOCKTIME => Self::Locktime(parse_u64(payload).context(
199 format!("invalid NDTPA_LOCKTIME value {payload:?}"),
200 )?),
201 NDTPA_QUEUE_LENBYTES => {
202 Self::QueueLenbytes(parse_u32(payload).context(format!(
203 "invalid NDTPA_QUEUE_LENBYTES value {payload:?}"
204 ))?)
205 }
206 NDTPA_MCAST_REPROBES => {
207 Self::McastReprobes(parse_u32(payload).context(format!(
208 "invalid NDTPA_MCAST_PROBES value {payload:?}"
209 ))?)
210 }
211 NDTPA_INTERVAL_PROBE_TIME_MS => Self::IntervalProbeTimeMs(
212 parse_u64(payload).context(format!(
213 "invalid NDTPA_INTERVAL_PROBE_TIME_MS value {payload:?}"
214 ))?,
215 ),
216 _ => Self::Other(DefaultNla::parse(buf).context(format!(
217 "invalid NDTA_PARMS attribute {payload:?}"
218 ))?),
219 })
220 }
221}
222
223#[derive(Debug, PartialEq, Eq, Clone)]
224pub(crate) struct VecNeighbourTableParameter(
225 pub(crate) Vec<NeighbourTableParameter>,
226);
227
228impl<'a, T: AsRef<[u8]> + ?Sized> Parseable<NlaBuffer<&'a T>>
229 for VecNeighbourTableParameter
230{
231 fn parse(buf: &NlaBuffer<&'a T>) -> Result<Self, DecodeError> {
232 let mut nlas = vec![];
233 let err = "invalid NDTA_PARMS attribute";
234 for nla in NlasIterator::new(buf.into_inner()) {
235 let nla = nla.context(err)?;
236 nlas.push(NeighbourTableParameter::parse(&nla).context(err)?);
237 }
238 Ok(Self(nlas))
239 }
240}