2 * Copyright (c) 2016 Fabien Siron <fabien.siron@epita.fr>
3 * Copyright (c) 2017 JingPiao Chen <chenjingpiao@gmail.com>
4 * Copyright (c) 2016-2018 The strace developers.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * 3. The name of the author may not be used to endorse or promote products
16 * derived from this software without specific prior written permission.
18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
19 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
20 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
21 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
22 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
23 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31 #include "netlink_route.h"
33 #include "print_fields.h"
37 #include <netinet/in.h>
39 #ifdef HAVE_LINUX_IF_LINK_H
40 # include <linux/if_link.h>
42 #include <linux/rtnetlink.h>
44 #include "xlat/in6_addr_gen_mode.h"
45 #include "xlat/inet_devconf_indices.h"
46 #include "xlat/inet6_devconf_indices.h"
47 #include "xlat/inet6_if_flags.h"
48 #include "xlat/rtnl_ifla_af_spec_inet_attrs.h"
49 #include "xlat/rtnl_ifla_af_spec_inet6_attrs.h"
50 #include "xlat/rtnl_ifla_brport_attrs.h"
51 #include "xlat/rtnl_ifla_events.h"
52 #include "xlat/rtnl_ifla_info_attrs.h"
53 #include "xlat/rtnl_ifla_info_data_bridge_attrs.h"
54 #include "xlat/rtnl_ifla_info_data_tun_attrs.h"
55 #include "xlat/rtnl_ifla_port_attrs.h"
56 #include "xlat/rtnl_ifla_vf_port_attrs.h"
57 #include "xlat/rtnl_ifla_xdp_attrs.h"
58 #include "xlat/rtnl_link_attrs.h"
59 #include "xlat/snmp_icmp6_stats.h"
60 #include "xlat/snmp_ip_stats.h"
61 #include "xlat/tun_device_types.h"
62 #include "xlat/xdp_flags.h"
65 decode_rtnl_link_stats(struct tcb *const tcp,
66 const kernel_ulong_t addr,
67 const unsigned int len,
68 const void *const opaque_data)
70 struct rtnl_link_stats st;
71 const unsigned int min_size =
72 offsetofend(struct rtnl_link_stats, tx_compressed);
73 const unsigned int def_size = sizeof(st);
74 const unsigned int size =
75 (len >= def_size) ? def_size :
76 ((len == min_size) ? min_size : 0);
81 if (!umoven_or_printaddr(tcp, addr, size, &st)) {
82 PRINT_FIELD_U("{", st, rx_packets);
83 PRINT_FIELD_U(", ", st, tx_packets);
84 PRINT_FIELD_U(", ", st, rx_bytes);
85 PRINT_FIELD_U(", ", st, tx_bytes);
86 PRINT_FIELD_U(", ", st, rx_errors);
87 PRINT_FIELD_U(", ", st, tx_errors);
88 PRINT_FIELD_U(", ", st, rx_dropped);
89 PRINT_FIELD_U(", ", st, tx_dropped);
90 PRINT_FIELD_U(", ", st, multicast);
91 PRINT_FIELD_U(", ", st, collisions);
93 PRINT_FIELD_U(", ", st, rx_length_errors);
94 PRINT_FIELD_U(", ", st, rx_over_errors);
95 PRINT_FIELD_U(", ", st, rx_crc_errors);
96 PRINT_FIELD_U(", ", st, rx_frame_errors);
97 PRINT_FIELD_U(", ", st, rx_fifo_errors);
98 PRINT_FIELD_U(", ", st, rx_missed_errors);
100 PRINT_FIELD_U(", ", st, tx_aborted_errors);
101 PRINT_FIELD_U(", ", st, tx_carrier_errors);
102 PRINT_FIELD_U(", ", st, tx_fifo_errors);
103 PRINT_FIELD_U(", ", st, tx_heartbeat_errors);
104 PRINT_FIELD_U(", ", st, tx_window_errors);
106 PRINT_FIELD_U(", ", st, rx_compressed);
107 PRINT_FIELD_U(", ", st, tx_compressed);
108 #ifdef HAVE_STRUCT_RTNL_LINK_STATS_RX_NOHANDLER
110 PRINT_FIELD_U(", ", st, rx_nohandler);
119 decode_ifla_bridge_id(struct tcb *const tcp,
120 const kernel_ulong_t addr,
121 const unsigned int len,
122 const void *const opaque_data)
129 if (len < sizeof(id))
131 else if (!umove_or_printaddr(tcp, addr, &id)) {
132 tprintf("{prio=[%u, %u]", id.prio[0], id.prio[1]);
133 PRINT_FIELD_MAC(", ", id, addr);
140 static const nla_decoder_t ifla_brport_nla_decoders[] = {
141 [IFLA_BRPORT_STATE] = decode_nla_u8,
142 [IFLA_BRPORT_PRIORITY] = decode_nla_u16,
143 [IFLA_BRPORT_COST] = decode_nla_u32,
144 [IFLA_BRPORT_MODE] = decode_nla_u8,
145 [IFLA_BRPORT_GUARD] = decode_nla_u8,
146 [IFLA_BRPORT_PROTECT] = decode_nla_u8,
147 [IFLA_BRPORT_FAST_LEAVE] = decode_nla_u8,
148 [IFLA_BRPORT_LEARNING] = decode_nla_u8,
149 [IFLA_BRPORT_UNICAST_FLOOD] = decode_nla_u8,
150 [IFLA_BRPORT_PROXYARP] = decode_nla_u8,
151 [IFLA_BRPORT_LEARNING_SYNC] = decode_nla_u8,
152 [IFLA_BRPORT_PROXYARP_WIFI] = decode_nla_u8,
153 [IFLA_BRPORT_ROOT_ID] = decode_ifla_bridge_id,
154 [IFLA_BRPORT_BRIDGE_ID] = decode_ifla_bridge_id,
155 [IFLA_BRPORT_DESIGNATED_PORT] = decode_nla_u16,
156 [IFLA_BRPORT_DESIGNATED_COST] = decode_nla_u16,
157 [IFLA_BRPORT_ID] = decode_nla_u16,
158 [IFLA_BRPORT_NO] = decode_nla_u16,
159 [IFLA_BRPORT_TOPOLOGY_CHANGE_ACK] = decode_nla_u8,
160 [IFLA_BRPORT_CONFIG_PENDING] = decode_nla_u8,
161 [IFLA_BRPORT_MESSAGE_AGE_TIMER] = decode_nla_u64,
162 [IFLA_BRPORT_FORWARD_DELAY_TIMER] = decode_nla_u64,
163 [IFLA_BRPORT_HOLD_TIMER] = decode_nla_u64,
164 [IFLA_BRPORT_FLUSH] = NULL,
165 [IFLA_BRPORT_MULTICAST_ROUTER] = decode_nla_u8,
166 [IFLA_BRPORT_PAD] = NULL,
167 [IFLA_BRPORT_MCAST_FLOOD] = decode_nla_u8,
168 [IFLA_BRPORT_MCAST_TO_UCAST] = decode_nla_u8,
169 [IFLA_BRPORT_VLAN_TUNNEL] = decode_nla_u8,
170 [IFLA_BRPORT_BCAST_FLOOD] = decode_nla_u8
174 decode_ifla_protinfo(struct tcb *const tcp,
175 const kernel_ulong_t addr,
176 const unsigned int len,
177 const void *const opaque_data)
179 decode_nlattr(tcp, addr, len, rtnl_ifla_brport_attrs,
181 ARRSZ_PAIR(ifla_brport_nla_decoders), opaque_data);
187 decode_rtnl_link_ifmap(struct tcb *const tcp,
188 const kernel_ulong_t addr,
189 const unsigned int len,
190 const void *const opaque_data)
192 struct rtnl_link_ifmap map;
193 const unsigned int sizeof_ifmap =
194 offsetofend(struct rtnl_link_ifmap, port);
196 if (len < sizeof_ifmap)
198 else if (!umoven_or_printaddr(tcp, addr, sizeof_ifmap, &map)) {
199 PRINT_FIELD_X("{", map, mem_start);
200 PRINT_FIELD_X(", ", map, mem_end);
201 PRINT_FIELD_X(", ", map, base_addr);
202 PRINT_FIELD_U(", ", map, irq);
203 PRINT_FIELD_U(", ", map, dma);
204 PRINT_FIELD_U(", ", map, port);
212 decode_nla_linkinfo_kind(struct tcb *const tcp,
213 const kernel_ulong_t addr,
214 const unsigned int len,
215 const void *const opaque_data)
217 struct ifla_linkinfo_ctx *ctx = (void *) opaque_data;
219 memset(ctx->kind, '\0', sizeof(ctx->kind));
221 if (umovestr(tcp, addr, sizeof(ctx->kind), ctx->kind) <= 0) {
223 * If we haven't seen NUL or an error occurred, set kind to
229 printstr_ex(tcp, addr, len, QUOTE_0_TERMINATED);
235 decode_nla_linkinfo_xstats_can(struct tcb *const tcp,
236 const kernel_ulong_t addr,
237 const unsigned int len,
238 const void *const opaque_data)
240 struct strace_can_device_stats {
242 uint32_t error_warning;
243 uint32_t error_passive;
245 uint32_t arbitration_lost;
248 const unsigned int def_size = sizeof(st);
249 const unsigned int size = (len >= def_size) ? def_size : 0;
254 if (umoven_or_printaddr(tcp, addr, size, &st))
257 PRINT_FIELD_U("{", st, bus_error);
258 PRINT_FIELD_U(", ", st, error_warning);
259 PRINT_FIELD_U(", ", st, error_passive);
260 PRINT_FIELD_U(", ", st, bus_off);
261 PRINT_FIELD_U(", ", st, arbitration_lost);
262 PRINT_FIELD_U(", ", st, restarts);
269 decode_nla_linkinfo_xstats(struct tcb *const tcp,
270 const kernel_ulong_t addr,
271 const unsigned int len,
272 const void *const opaque_data)
274 struct ifla_linkinfo_ctx *ctx = (void *) opaque_data;
275 nla_decoder_t func = NULL;
277 if (!strcmp(ctx->kind, "can"))
278 func = decode_nla_linkinfo_xstats_can;
281 return func(tcp, addr, len, opaque_data);
286 static const nla_decoder_t ifla_info_data_bridge_nla_decoders[] = {
287 [IFLA_BR_UNSPEC] = NULL,
288 [IFLA_BR_FORWARD_DELAY] = decode_nla_u32,
289 [IFLA_BR_HELLO_TIME] = decode_nla_u32,
290 [IFLA_BR_MAX_AGE] = decode_nla_u32,
291 [IFLA_BR_AGEING_TIME] = decode_nla_u32,
292 [IFLA_BR_STP_STATE] = decode_nla_u32,
293 [IFLA_BR_PRIORITY] = decode_nla_u16,
294 [IFLA_BR_VLAN_FILTERING] = decode_nla_u8,
295 [IFLA_BR_VLAN_PROTOCOL] = decode_nla_ether_proto,
296 [IFLA_BR_GROUP_FWD_MASK] = decode_nla_x16,
297 [IFLA_BR_ROOT_ID] = decode_ifla_bridge_id,
298 [IFLA_BR_BRIDGE_ID] = decode_ifla_bridge_id,
299 [IFLA_BR_ROOT_PORT] = decode_nla_u16,
300 [IFLA_BR_ROOT_PATH_COST] = decode_nla_u32,
301 [IFLA_BR_TOPOLOGY_CHANGE] = decode_nla_u8,
302 [IFLA_BR_TOPOLOGY_CHANGE_DETECTED] = decode_nla_u8,
303 [IFLA_BR_HELLO_TIMER] = decode_nla_u64,
304 [IFLA_BR_TCN_TIMER] = decode_nla_u64,
305 [IFLA_BR_TOPOLOGY_CHANGE_TIMER] = decode_nla_u64,
306 [IFLA_BR_GC_TIMER] = decode_nla_u64,
307 [IFLA_BR_GROUP_ADDR] = NULL, /* MAC address */
308 [IFLA_BR_FDB_FLUSH] = NULL, /* unspecified */
309 [IFLA_BR_MCAST_ROUTER] = decode_nla_u8,
310 [IFLA_BR_MCAST_SNOOPING] = decode_nla_u8,
311 [IFLA_BR_MCAST_QUERY_USE_IFADDR] = decode_nla_u8,
312 [IFLA_BR_MCAST_QUERIER] = decode_nla_u8,
313 [IFLA_BR_MCAST_HASH_ELASTICITY] = decode_nla_u32,
314 [IFLA_BR_MCAST_HASH_MAX] = decode_nla_u32,
315 [IFLA_BR_MCAST_LAST_MEMBER_CNT] = decode_nla_u32,
316 [IFLA_BR_MCAST_STARTUP_QUERY_CNT] = decode_nla_u32,
317 [IFLA_BR_MCAST_LAST_MEMBER_INTVL] = decode_nla_u64,
318 [IFLA_BR_MCAST_MEMBERSHIP_INTVL] = decode_nla_u64,
319 [IFLA_BR_MCAST_QUERIER_INTVL] = decode_nla_u64,
320 [IFLA_BR_MCAST_QUERY_INTVL] = decode_nla_u64,
321 [IFLA_BR_MCAST_QUERY_RESPONSE_INTVL] = decode_nla_u64,
322 [IFLA_BR_MCAST_STARTUP_QUERY_INTVL] = decode_nla_u64,
323 [IFLA_BR_NF_CALL_IPTABLES] = decode_nla_u8,
324 [IFLA_BR_NF_CALL_IP6TABLES] = decode_nla_u8,
325 [IFLA_BR_NF_CALL_ARPTABLES] = decode_nla_u8,
326 [IFLA_BR_VLAN_DEFAULT_PVID] = decode_nla_u16,
327 [IFLA_BR_PAD] = NULL,
328 [IFLA_BR_VLAN_STATS_ENABLED] = decode_nla_u8,
329 [IFLA_BR_MCAST_STATS_ENABLED] = decode_nla_u8,
330 [IFLA_BR_MCAST_IGMP_VERSION] = decode_nla_u8,
331 [IFLA_BR_MCAST_MLD_VERSION] = decode_nla_u8,
335 decode_nla_linkinfo_data_bridge(struct tcb *const tcp,
336 const kernel_ulong_t addr,
337 const unsigned int len,
338 const void *const opaque_data)
340 decode_nlattr(tcp, addr, len, rtnl_ifla_info_data_bridge_attrs,
342 ARRSZ_PAIR(ifla_info_data_bridge_nla_decoders),
349 decode_nla_tun_type(struct tcb *const tcp,
350 const kernel_ulong_t addr,
351 const unsigned int len,
352 const void *const opaque_data)
354 const struct decode_nla_xlat_opts opts = {
355 .xlat = tun_device_types,
356 .xlat_size = ARRAY_SIZE(tun_device_types),
362 return decode_nla_xval(tcp, addr, len, &opts);
365 static const nla_decoder_t ifla_info_data_tun_nla_decoders[] = {
366 [IFLA_TUN_UNSPEC] = NULL,
367 [IFLA_TUN_OWNER] = decode_nla_uid,
368 [IFLA_TUN_GROUP] = decode_nla_gid,
369 [IFLA_TUN_TYPE] = decode_nla_tun_type,
370 [IFLA_TUN_PI] = decode_nla_u8,
371 [IFLA_TUN_VNET_HDR] = decode_nla_u8,
372 [IFLA_TUN_PERSIST] = decode_nla_u8,
373 [IFLA_TUN_MULTI_QUEUE] = decode_nla_u8,
374 [IFLA_TUN_NUM_QUEUES] = decode_nla_u32,
375 [IFLA_TUN_NUM_DISABLED_QUEUES] = decode_nla_u32,
379 decode_nla_linkinfo_data_tun(struct tcb *const tcp,
380 const kernel_ulong_t addr,
381 const unsigned int len,
382 const void *const opaque_data)
384 decode_nlattr(tcp, addr, len, rtnl_ifla_info_data_tun_attrs,
386 ARRSZ_PAIR(ifla_info_data_tun_nla_decoders),
393 decode_nla_linkinfo_data(struct tcb *const tcp,
394 const kernel_ulong_t addr,
395 const unsigned int len,
396 const void *const opaque_data)
398 struct ifla_linkinfo_ctx *ctx = (void *) opaque_data;
399 nla_decoder_t func = NULL;
401 if (!strcmp(ctx->kind, "bridge"))
402 func = decode_nla_linkinfo_data_bridge;
403 else if (!strcmp(ctx->kind, "tun"))
404 func = decode_nla_linkinfo_data_tun;
407 return func(tcp, addr, len, opaque_data);
412 static const nla_decoder_t ifla_linkinfo_nla_decoders[] = {
413 [IFLA_INFO_KIND] = decode_nla_linkinfo_kind,
414 [IFLA_INFO_DATA] = decode_nla_linkinfo_data,
415 [IFLA_INFO_XSTATS] = decode_nla_linkinfo_xstats,
416 [IFLA_INFO_SLAVE_KIND] = decode_nla_str,
417 [IFLA_INFO_SLAVE_DATA] = NULL, /* unimplemented */
421 decode_ifla_linkinfo(struct tcb *const tcp,
422 const kernel_ulong_t addr,
423 const unsigned int len,
424 const void *const opaque_data)
426 struct ifla_linkinfo_ctx ctx = { .kind = "", };
428 decode_nlattr(tcp, addr, len, rtnl_ifla_info_attrs,
429 "IFLA_INFO_???", ARRSZ_PAIR(ifla_linkinfo_nla_decoders),
436 decode_rtnl_link_stats64(struct tcb *const tcp,
437 const kernel_ulong_t addr,
438 const unsigned int len,
439 const void *const opaque_data)
441 #ifdef HAVE_STRUCT_RTNL_LINK_STATS64
442 struct rtnl_link_stats64 st;
443 const unsigned int min_size =
444 offsetofend(struct rtnl_link_stats64, tx_compressed);
445 const unsigned int def_size = sizeof(st);
446 const unsigned int size =
447 (len >= def_size) ? def_size :
448 ((len == min_size) ? min_size : 0);
453 if (!umoven_or_printaddr(tcp, addr, size, &st)) {
454 PRINT_FIELD_U("{", st, rx_packets);
455 PRINT_FIELD_U(", ", st, tx_packets);
456 PRINT_FIELD_U(", ", st, rx_bytes);
457 PRINT_FIELD_U(", ", st, tx_bytes);
458 PRINT_FIELD_U(", ", st, rx_errors);
459 PRINT_FIELD_U(", ", st, tx_errors);
460 PRINT_FIELD_U(", ", st, rx_dropped);
461 PRINT_FIELD_U(", ", st, tx_dropped);
462 PRINT_FIELD_U(", ", st, multicast);
463 PRINT_FIELD_U(", ", st, collisions);
465 PRINT_FIELD_U(", ", st, rx_length_errors);
466 PRINT_FIELD_U(", ", st, rx_over_errors);
467 PRINT_FIELD_U(", ", st, rx_crc_errors);
468 PRINT_FIELD_U(", ", st, rx_frame_errors);
469 PRINT_FIELD_U(", ", st, rx_fifo_errors);
470 PRINT_FIELD_U(", ", st, rx_missed_errors);
472 PRINT_FIELD_U(", ", st, tx_aborted_errors);
473 PRINT_FIELD_U(", ", st, tx_carrier_errors);
474 PRINT_FIELD_U(", ", st, tx_fifo_errors);
475 PRINT_FIELD_U(", ", st, tx_heartbeat_errors);
476 PRINT_FIELD_U(", ", st, tx_window_errors);
478 PRINT_FIELD_U(", ", st, rx_compressed);
479 PRINT_FIELD_U(", ", st, tx_compressed);
480 #ifdef HAVE_STRUCT_RTNL_LINK_STATS64_RX_NOHANDLER
482 PRINT_FIELD_U(", ", st, rx_nohandler);
494 decode_ifla_port_vsi(struct tcb *const tcp,
495 const kernel_ulong_t addr,
496 const unsigned int len,
497 const void *const opaque_data)
499 #ifdef HAVE_STRUCT_IFLA_PORT_VSI
500 struct ifla_port_vsi vsi;
502 if (len < sizeof(vsi))
504 else if (!umove_or_printaddr(tcp, addr, &vsi)) {
505 PRINT_FIELD_U("{", vsi, vsi_mgr_id);
506 PRINT_FIELD_STRING(", ", vsi, vsi_type_id,
507 sizeof(vsi.vsi_type_id), QUOTE_FORCE_HEX);
508 PRINT_FIELD_U(", ", vsi, vsi_type_version);
518 static const nla_decoder_t ifla_port_nla_decoders[] = {
519 [IFLA_PORT_VF] = decode_nla_u32,
520 [IFLA_PORT_PROFILE] = decode_nla_str,
521 [IFLA_PORT_VSI_TYPE] = decode_ifla_port_vsi,
522 [IFLA_PORT_INSTANCE_UUID] = NULL, /* default parser */
523 [IFLA_PORT_HOST_UUID] = NULL, /* default parser */
524 [IFLA_PORT_REQUEST] = decode_nla_u8,
525 [IFLA_PORT_RESPONSE] = decode_nla_u16
529 decode_ifla_port(struct tcb *const tcp,
530 const kernel_ulong_t addr,
531 const unsigned int len,
532 const void *const opaque_data)
534 decode_nlattr(tcp, addr, len, rtnl_ifla_port_attrs,
535 "IFLA_VF_PORT_???", ARRSZ_PAIR(ifla_port_nla_decoders),
541 static const nla_decoder_t ifla_vf_port_nla_decoders[] = {
542 [IFLA_VF_PORT] = decode_ifla_port
546 decode_ifla_vf_ports(struct tcb *const tcp,
547 const kernel_ulong_t addr,
548 const unsigned int len,
549 const void *const opaque_data)
551 decode_nlattr(tcp, addr, len, rtnl_ifla_vf_port_attrs,
552 "IFLA_VF_PORT_???", ARRSZ_PAIR(ifla_vf_port_nla_decoders),
559 decode_ifla_xdp_flags(struct tcb *const tcp,
560 const kernel_ulong_t addr,
561 const unsigned int len,
562 const void *const opaque_data)
566 if (len < sizeof(flags))
568 else if (!umove_or_printaddr(tcp, addr, &flags))
569 printflags(xdp_flags, flags, "XDP_FLAGS_???");
574 static const nla_decoder_t ifla_xdp_nla_decoders[] = {
575 [IFLA_XDP_FD] = decode_nla_fd,
576 [IFLA_XDP_ATTACHED] = decode_nla_u8,
577 [IFLA_XDP_FLAGS] = decode_ifla_xdp_flags,
578 [IFLA_XDP_PROG_ID] = decode_nla_u32
582 decode_ifla_xdp(struct tcb *const tcp,
583 const kernel_ulong_t addr,
584 const unsigned int len,
585 const void *const opaque_data)
587 decode_nlattr(tcp, addr, len, rtnl_ifla_xdp_attrs,
588 "IFLA_XDP_???", ARRSZ_PAIR(ifla_xdp_nla_decoders),
595 decode_ifla_event(struct tcb *const tcp,
596 const kernel_ulong_t addr,
597 const unsigned int len,
598 const void *const opaque_data)
602 if (len < sizeof(ev))
604 else if (!umove_or_printaddr(tcp, addr, &ev))
605 printxval(rtnl_ifla_events, ev, "IFLA_EVENT_???");
612 decode_ifla_inet_conf(struct tcb *const tcp,
613 const kernel_ulong_t addr,
614 const unsigned int len,
615 const void *const opaque_data)
618 size_t cnt = len / sizeof(elem);
623 print_array_ex(tcp, addr, cnt, &elem, sizeof(elem),
624 tfetch_mem, print_int32_array_member, NULL,
625 PAF_PRINT_INDICES | PAF_INDEX_XLAT_VALUE_INDEXED
626 | XLAT_STYLE_FMT_D, ARRSZ_PAIR(inet_devconf_indices),
632 static const nla_decoder_t ifla_inet_nla_decoders[] = {
633 [IFLA_INET_CONF] = decode_ifla_inet_conf,
637 decode_ifla_inet6_flags(struct tcb *const tcp,
638 const kernel_ulong_t addr,
639 const unsigned int len,
640 const void *const opaque_data)
642 const struct decode_nla_xlat_opts opts = {
643 ARRSZ_PAIR(inet6_if_flags), "IF_???",
647 return decode_nla_flags(tcp, addr, len, &opts);
651 decode_ifla_inet6_conf(struct tcb *const tcp,
652 const kernel_ulong_t addr,
653 const unsigned int len,
654 const void *const opaque_data)
657 size_t cnt = len / sizeof(elem);
662 print_array_ex(tcp, addr, cnt, &elem, sizeof(elem),
663 tfetch_mem, print_int32_array_member, NULL,
664 PAF_PRINT_INDICES | PAF_INDEX_XLAT_VALUE_INDEXED
665 | XLAT_STYLE_FMT_D, ARRSZ_PAIR(inet6_devconf_indices),
672 decode_ifla_inet6_stats(struct tcb *const tcp,
673 const kernel_ulong_t addr,
674 const unsigned int len,
675 const void *const opaque_data)
678 size_t cnt = len / sizeof(elem);
683 print_array_ex(tcp, addr, cnt, &elem, sizeof(elem),
684 tfetch_mem, print_uint64_array_member, NULL,
685 PAF_PRINT_INDICES | PAF_INDEX_XLAT_VALUE_INDEXED
686 | XLAT_STYLE_FMT_U, ARRSZ_PAIR(snmp_ip_stats),
693 decode_ifla_inet6_cacheinfo(struct tcb *const tcp,
694 const kernel_ulong_t addr,
695 const unsigned int len,
696 const void *const opaque_data)
699 uint32_t max_reasm_len;
701 uint32_t reachable_time;
702 uint32_t retrans_time;
705 if (len < sizeof(ci))
707 else if (!umove_or_printaddr(tcp, addr, &ci)) {
708 PRINT_FIELD_U("{", ci, max_reasm_len);
709 PRINT_FIELD_U(", ", ci, tstamp);
710 PRINT_FIELD_U(", ", ci, reachable_time);
711 PRINT_FIELD_U(", ", ci, retrans_time);
719 decode_ifla_inet6_icmp6_stats(struct tcb *const tcp,
720 const kernel_ulong_t addr,
721 const unsigned int len,
722 const void *const opaque_data)
725 size_t cnt = len / sizeof(elem);
730 print_array_ex(tcp, addr, cnt, &elem, sizeof(elem),
731 tfetch_mem, print_uint64_array_member, NULL,
732 PAF_PRINT_INDICES | PAF_INDEX_XLAT_VALUE_INDEXED
733 | XLAT_STYLE_FMT_U, ARRSZ_PAIR(snmp_icmp6_stats),
740 decode_ifla_inet6_token(struct tcb *const tcp,
741 const kernel_ulong_t addr,
742 const unsigned int len,
743 const void *const opaque_data)
747 if (len < sizeof(in6))
749 else if (!umove_or_printaddr(tcp, addr, &in6))
750 print_inet_addr(AF_INET6, &in6, sizeof(in6), NULL);
756 decode_ifla_inet6_agm(struct tcb *const tcp,
757 const kernel_ulong_t addr,
758 const unsigned int len,
759 const void *const opaque_data)
761 const struct decode_nla_xlat_opts opts = {
762 ARRSZ_PAIR(in6_addr_gen_mode), "IN6_ADDR_GEN_MODE_???",
767 return decode_nla_xval(tcp, addr, len, &opts);
770 static const nla_decoder_t ifla_inet6_nla_decoders[] = {
771 [IFLA_INET6_FLAGS] = decode_ifla_inet6_flags,
772 [IFLA_INET6_CONF] = decode_ifla_inet6_conf,
773 [IFLA_INET6_STATS] = decode_ifla_inet6_stats,
774 [IFLA_INET6_MCAST] = NULL, /* unused */
775 [IFLA_INET6_CACHEINFO] = decode_ifla_inet6_cacheinfo,
776 [IFLA_INET6_ICMP6STATS] = decode_ifla_inet6_icmp6_stats,
777 [IFLA_INET6_TOKEN] = decode_ifla_inet6_token,
778 [IFLA_INET6_ADDR_GEN_MODE] = decode_ifla_inet6_agm,
781 static const struct nla_decoder_table_desc {
782 const struct xlat *xlat;
784 const nla_decoder_t *table;
786 } ifla_af_spec_protos[] = {
788 rtnl_ifla_af_spec_inet_attrs, "IFLA_INET_???",
789 ARRSZ_PAIR(ifla_inet_nla_decoders),
792 rtnl_ifla_af_spec_inet6_attrs, "IFLA_INET6_???",
793 ARRSZ_PAIR(ifla_inet6_nla_decoders),
798 decode_ifla_af(struct tcb *const tcp,
799 const kernel_ulong_t addr,
800 const unsigned int len,
801 const void *const opaque_data)
803 uintptr_t proto = (uintptr_t) opaque_data;
804 const struct nla_decoder_table_desc *desc
805 = proto < ARRAY_SIZE(ifla_af_spec_protos)
806 ? ifla_af_spec_protos + proto : NULL;
808 if (!desc || !desc->table)
811 decode_nlattr(tcp, addr, len,
812 desc->xlat, desc->dflt, desc->table, desc->size, NULL);
818 decode_ifla_af_spec(struct tcb *const tcp,
819 const kernel_ulong_t addr,
820 const unsigned int len,
821 const void *const opaque_data)
823 nla_decoder_t af_spec_decoder = &decode_ifla_af;
825 decode_nlattr(tcp, addr, len, addrfams, "AF_???",
826 &af_spec_decoder, 0, opaque_data);
831 static const nla_decoder_t ifinfomsg_nla_decoders[] = {
832 [IFLA_ADDRESS] = NULL, /* unimplemented */
833 [IFLA_BROADCAST] = NULL, /* unimplemented */
834 [IFLA_IFNAME] = decode_nla_str,
835 [IFLA_MTU] = decode_nla_u32,
836 [IFLA_LINK] = decode_nla_u32,
837 [IFLA_QDISC] = decode_nla_str,
838 [IFLA_STATS] = decode_rtnl_link_stats,
839 [IFLA_COST] = NULL, /* unused */
840 [IFLA_PRIORITY] = NULL, /* unused */
841 [IFLA_MASTER] = decode_nla_u32,
842 [IFLA_WIRELESS] = NULL, /* unimplemented */
843 [IFLA_PROTINFO] = decode_ifla_protinfo,
844 [IFLA_TXQLEN] = decode_nla_u32,
845 [IFLA_MAP] = decode_rtnl_link_ifmap,
846 [IFLA_WEIGHT] = decode_nla_u32,
847 [IFLA_OPERSTATE] = decode_nla_u8,
848 [IFLA_LINKMODE] = decode_nla_u8,
849 [IFLA_LINKINFO] = decode_ifla_linkinfo,
850 [IFLA_NET_NS_PID] = decode_nla_u32,
851 [IFLA_IFALIAS] = decode_nla_str,
852 [IFLA_NUM_VF] = decode_nla_u32,
853 [IFLA_VFINFO_LIST] = NULL, /* unimplemented */
854 [IFLA_STATS64] = decode_rtnl_link_stats64,
855 [IFLA_VF_PORTS] = decode_ifla_vf_ports,
856 [IFLA_PORT_SELF] = decode_ifla_port,
857 [IFLA_AF_SPEC] = decode_ifla_af_spec,
858 [IFLA_GROUP] = decode_nla_u32,
859 [IFLA_NET_NS_FD] = decode_nla_fd,
860 [IFLA_EXT_MASK] = decode_nla_u32,
861 [IFLA_PROMISCUITY] = decode_nla_u32,
862 [IFLA_NUM_TX_QUEUES] = decode_nla_u32,
863 [IFLA_NUM_RX_QUEUES] = decode_nla_u32,
864 [IFLA_CARRIER] = decode_nla_u8,
865 [IFLA_PHYS_PORT_ID] = NULL, /* default parser */
866 [IFLA_CARRIER_CHANGES] = decode_nla_u32,
867 [IFLA_PHYS_SWITCH_ID] = NULL, /* default parser */
868 [IFLA_LINK_NETNSID] = decode_nla_s32,
869 [IFLA_PHYS_PORT_NAME] = decode_nla_str,
870 [IFLA_PROTO_DOWN] = decode_nla_u8,
871 [IFLA_GSO_MAX_SEGS] = decode_nla_u32,
872 [IFLA_GSO_MAX_SIZE] = decode_nla_u32,
874 [IFLA_XDP] = decode_ifla_xdp,
875 [IFLA_EVENT] = decode_ifla_event,
876 [IFLA_NEW_NETNSID] = decode_nla_s32,
877 [IFLA_IF_NETNSID] = decode_nla_s32,
878 [IFLA_CARRIER_UP_COUNT] = decode_nla_u32,
879 [IFLA_CARRIER_DOWN_COUNT] = decode_nla_u32,
880 [IFLA_NEW_IFINDEX] = decode_nla_ifindex,
883 DECL_NETLINK_ROUTE_DECODER(decode_ifinfomsg)
885 struct ifinfomsg ifinfo = { .ifi_family = family };
886 size_t offset = sizeof(ifinfo.ifi_family);
887 bool decode_nla = false;
889 PRINT_FIELD_XVAL("{", ifinfo, ifi_family, addrfams, "AF_???");
892 if (len >= sizeof(ifinfo)) {
893 if (!umoven_or_printaddr(tcp, addr + offset,
894 sizeof(ifinfo) - offset,
895 (char *) &ifinfo + offset)) {
896 PRINT_FIELD_XVAL_SORTED_SIZED("", ifinfo, ifi_type,
898 arp_hardware_types_size,
900 PRINT_FIELD_IFINDEX(", ", ifinfo, ifi_index);
901 PRINT_FIELD_FLAGS(", ", ifinfo, ifi_flags,
902 iffflags, "IFF_???");
903 PRINT_FIELD_X(", ", ifinfo, ifi_change);
910 offset = NLMSG_ALIGN(sizeof(ifinfo));
911 if (decode_nla && len > offset) {
913 decode_nlattr(tcp, addr + offset, len - offset,
914 rtnl_link_attrs, "IFLA_???",
915 ARRSZ_PAIR(ifinfomsg_nla_decoders), NULL);