Skip to content

Commit f8ce9d5

Browse files
ppiaoldv-alt
andcommitted
netlink: decode AF_PACKET packet_diag_msg attributes
* linux/packet_diag.h (packet_diag_info, packet_diag_mclist, packet_diag_ring): New structures. (PDI_*): New macros. * netlink_sock_diag.c: Include <linux/filter.h> and "xlat/packet_diag_info_flags.h". (decode_packet_diag_info, decode_packet_diag_mclist, decode_packet_diag_ring, decode_packet_diag_filter): New functions. (packet_diag_msg_nla_decoders): New array. (decode_packet_diag_msg): Use it. * print_fields.h (PRINT_FIELD_QUOTED_STRING): New macro. * xlat/packet_diag_info_flags.in: New file. Co-authored-by: Dmitry V. Levin <[email protected]>
1 parent fd81796 commit f8ce9d5

File tree

4 files changed

+162
-1
lines changed

4 files changed

+162
-1
lines changed

linux/packet_diag.h

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,4 +37,37 @@ enum {
3737
PACKET_DIAG_FILTER,
3838
};
3939

40+
struct packet_diag_info {
41+
uint32_t pdi_index;
42+
uint32_t pdi_version;
43+
uint32_t pdi_reserve;
44+
uint32_t pdi_copy_thresh;
45+
uint32_t pdi_tstamp;
46+
uint32_t pdi_flags;
47+
48+
#define PDI_RUNNING 0x1
49+
#define PDI_AUXDATA 0x2
50+
#define PDI_ORIGDEV 0x4
51+
#define PDI_VNETHDR 0x8
52+
#define PDI_LOSS 0x10
53+
};
54+
55+
struct packet_diag_mclist {
56+
uint32_t pdmc_index;
57+
uint32_t pdmc_count;
58+
uint16_t pdmc_type;
59+
uint16_t pdmc_alen;
60+
uint8_t pdmc_addr[32]; /* MAX_ADDR_LEN */
61+
};
62+
63+
struct packet_diag_ring {
64+
uint32_t pdr_block_size;
65+
uint32_t pdr_block_nr;
66+
uint32_t pdr_frame_size;
67+
uint32_t pdr_frame_nr;
68+
uint32_t pdr_retire_tmo;
69+
uint32_t pdr_sizeof_priv;
70+
uint32_t pdr_features;
71+
};
72+
4073
#endif /* !STRACE_LINUX_PACKET_DIAG_H */

netlink_sock_diag.c

Lines changed: 118 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,8 @@
3333
#include "print_fields.h"
3434

3535
#include <arpa/inet.h>
36+
#include <linux/filter.h>
37+
3638
#include <linux/inet_diag.h>
3739
#include <linux/netlink_diag.h>
3840
#include <linux/packet_diag.h>
@@ -55,6 +57,7 @@
5557
#include "xlat/netlink_states.h"
5658

5759
#include "xlat/packet_diag_attrs.h"
60+
#include "xlat/packet_diag_info_flags.h"
5861
#include "xlat/packet_diag_show.h"
5962

6063
#ifdef AF_SMC
@@ -447,6 +450,119 @@ decode_packet_diag_req(struct tcb *const tcp,
447450
tprints("}");
448451
}
449452

453+
static bool
454+
decode_packet_diag_info(struct tcb *const tcp,
455+
const kernel_ulong_t addr,
456+
const kernel_ulong_t len,
457+
const void *const opaque_data)
458+
{
459+
struct packet_diag_info pinfo;
460+
461+
if (len < sizeof(pinfo))
462+
return false;
463+
if (umove_or_printaddr(tcp, addr, &pinfo))
464+
return true;
465+
466+
PRINT_FIELD_U("{", pinfo, pdi_index);
467+
PRINT_FIELD_U(", ", pinfo, pdi_version);
468+
PRINT_FIELD_U(", ", pinfo, pdi_reserve);
469+
PRINT_FIELD_U(", ", pinfo, pdi_copy_thresh);
470+
PRINT_FIELD_U(", ", pinfo, pdi_tstamp);
471+
PRINT_FIELD_FLAGS(", ", pinfo, pdi_flags,
472+
packet_diag_info_flags, "PDI_???");
473+
tprints("}");
474+
475+
return true;
476+
}
477+
478+
static bool
479+
print_packet_diag_mclist(struct tcb *const tcp, void *const elem_buf,
480+
const size_t elem_size, void *const opaque_data)
481+
{
482+
struct packet_diag_mclist *dml = elem_buf;
483+
uint16_t alen = dml->pdmc_alen > sizeof(dml->pdmc_addr) ?
484+
sizeof(dml->pdmc_addr) : dml->pdmc_alen;
485+
486+
tprints("{pdmc_index=");
487+
print_ifindex(dml->pdmc_index);
488+
PRINT_FIELD_U(", ", *dml, pdmc_count);
489+
PRINT_FIELD_U(", ", *dml, pdmc_type);
490+
PRINT_FIELD_U(", ", *dml, pdmc_alen);
491+
PRINT_FIELD_QUOTED_STRING(", ", *dml, pdmc_addr, alen, QUOTE_FORCE_HEX);
492+
tprints("}");
493+
494+
return true;
495+
}
496+
497+
static bool
498+
decode_packet_diag_mclist(struct tcb *const tcp,
499+
const kernel_ulong_t addr,
500+
const kernel_ulong_t len,
501+
const void *const opaque_data)
502+
{
503+
struct packet_diag_mclist dml;
504+
const size_t nmemb = len / sizeof(dml);
505+
506+
if (!nmemb)
507+
return false;
508+
509+
print_array(tcp, addr, nmemb, &dml, sizeof(dml),
510+
umoven_or_printaddr, print_packet_diag_mclist, 0);
511+
512+
return true;
513+
}
514+
515+
static bool
516+
decode_packet_diag_ring(struct tcb *const tcp,
517+
const kernel_ulong_t addr,
518+
const kernel_ulong_t len,
519+
const void *const opaque_data)
520+
{
521+
struct packet_diag_ring pdr;
522+
523+
if (len < sizeof(pdr))
524+
return false;
525+
if (umove_or_printaddr(tcp, addr, &pdr))
526+
return true;
527+
528+
PRINT_FIELD_U("{", pdr, pdr_block_size);
529+
PRINT_FIELD_U(", ", pdr, pdr_block_nr);
530+
PRINT_FIELD_U(", ", pdr, pdr_frame_size);
531+
PRINT_FIELD_U(", ", pdr, pdr_frame_nr);
532+
PRINT_FIELD_U(", ", pdr, pdr_retire_tmo);
533+
PRINT_FIELD_U(", ", pdr, pdr_sizeof_priv);
534+
PRINT_FIELD_U(", ", pdr, pdr_features);
535+
tprints("}");
536+
537+
return true;
538+
}
539+
540+
static bool
541+
decode_packet_diag_filter(struct tcb *const tcp,
542+
const kernel_ulong_t addr,
543+
const kernel_ulong_t len,
544+
const void *const opaque_data)
545+
{
546+
const kernel_ulong_t nmemb = len / sizeof(struct sock_filter);
547+
if (!nmemb || (unsigned short) nmemb != nmemb)
548+
return false;
549+
550+
print_sock_fprog(tcp, addr, nmemb);
551+
552+
return true;
553+
}
554+
555+
static const nla_decoder_t packet_diag_msg_nla_decoders[] = {
556+
[PACKET_DIAG_INFO] = decode_packet_diag_info,
557+
[PACKET_DIAG_MCLIST] = decode_packet_diag_mclist,
558+
[PACKET_DIAG_RX_RING] = decode_packet_diag_ring,
559+
[PACKET_DIAG_TX_RING] = decode_packet_diag_ring,
560+
[PACKET_DIAG_FANOUT] = decode_nla_u32,
561+
[PACKET_DIAG_UID] = decode_nla_u32,
562+
[PACKET_DIAG_MEMINFO] = decode_meminfo,
563+
[PACKET_DIAG_FILTER] = decode_packet_diag_filter
564+
};
565+
450566
static void
451567
decode_packet_diag_msg(struct tcb *const tcp,
452568
const struct nlmsghdr *const nlmsghdr,
@@ -480,7 +596,8 @@ decode_packet_diag_msg(struct tcb *const tcp,
480596
tprints(", ");
481597
decode_nlattr(tcp, addr + offset, len - offset,
482598
packet_diag_attrs, "PACKET_DIAG_???",
483-
NULL, 0, NULL);
599+
packet_diag_msg_nla_decoders,
600+
ARRAY_SIZE(packet_diag_msg_nla_decoders), NULL);
484601
}
485602
}
486603

print_fields.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,4 +74,10 @@
7474
zero_extend_signed_to_ull((where_).field_)); \
7575
} while (0)
7676

77+
#define PRINT_FIELD_QUOTED_STRING(prefix_, where_, field_, len_, style_) \
78+
do { \
79+
STRACE_PRINTF("%s%s=", (prefix_), #field_); \
80+
print_quoted_string((const char *)(where_).field_, len_, style_); \
81+
} while (0)
82+
7783
#endif /* !STRACE_PRINT_FIELDS_H */

xlat/packet_diag_info_flags.in

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
PDI_RUNNING
2+
PDI_AUXDATA
3+
PDI_ORIGDEV
4+
PDI_VNETHDR
5+
PDI_LOSS

0 commit comments

Comments
 (0)