On Wed, Jun 28, 2017 at 09:40:08AM +0800, JingPiao Chen wrote:
> * netlink_sock_diag.c: Include <linux/filter.h>
> and "xlat/packet_diag_info_flags.h".
> (packet_diag_msg_nla_decoders): New array.
> (decode_packet_diag_msg): Use it.
> * linux/packet_diag.h (packet_diag_info, packet_diag_mclist,
> packet_diag_ring): New structures.
> (PDI_*): New macros.
> * xlat/packet_diag_info_flags.in: New file.
> ---
>  linux/packet_diag.h            |  33 +++++++++++
>  netlink_sock_diag.c            | 126 
> ++++++++++++++++++++++++++++++++++++++++-
>  xlat/packet_diag_info_flags.in |   5 ++
>  3 files changed, 163 insertions(+), 1 deletion(-)
>  create mode 100644 xlat/packet_diag_info_flags.in
> 
> diff --git a/linux/packet_diag.h b/linux/packet_diag.h
> index 3e8120b..368e26f 100644
> --- a/linux/packet_diag.h
> +++ b/linux/packet_diag.h
> @@ -37,4 +37,37 @@ enum {
>       PACKET_DIAG_FILTER,
>  };
>  
> +struct packet_diag_info {
> +     uint32_t pdi_index;
> +     uint32_t pdi_version;
> +     uint32_t pdi_reserve;
> +     uint32_t pdi_copy_thresh;
> +     uint32_t pdi_tstamp;
> +     uint32_t pdi_flags;
> +
> +#define PDI_RUNNING  0x1
> +#define PDI_AUXDATA  0x2
> +#define PDI_ORIGDEV  0x4
> +#define PDI_VNETHDR  0x8
> +#define PDI_LOSS     0x10
> +};
> +
> +struct packet_diag_mclist {
> +     uint32_t pdmc_index;
> +     uint32_t pdmc_count;
> +     uint16_t pdmc_type;
> +     uint16_t pdmc_alen;
> +     uint8_t pdmc_addr[32]; /* MAX_ADDR_LEN */
> +};
> +
> +struct packet_diag_ring {
> +     uint32_t pdr_block_size;
> +     uint32_t pdr_block_nr;
> +     uint32_t pdr_frame_size;
> +     uint32_t pdr_frame_nr;
> +     uint32_t pdr_retire_tmo;
> +     uint32_t pdr_sizeof_priv;
> +     uint32_t pdr_features;
> +};
> +
>  #endif /* !STRACE_LINUX_PACKET_DIAG_H */
> diff --git a/netlink_sock_diag.c b/netlink_sock_diag.c
> index f5b53b5..c0709c0 100644
> --- a/netlink_sock_diag.c
> +++ b/netlink_sock_diag.c
> @@ -32,6 +32,7 @@
>  #include "nlattr.h"
>  
>  #include <arpa/inet.h>
> +#include <linux/filter.h>

<linux/filter.h> is not universally available yet, on other parts
of strace we wrap its use in #ifdef HAVE_LINUX_FILTER_H/#endif.

>  #include <linux/inet_diag.h>
>  #include <linux/netlink_diag.h>
>  #include <linux/packet_diag.h>
> @@ -54,6 +55,7 @@
>  #include "xlat/netlink_states.h"
>  
>  #include "xlat/packet_diag_attrs.h"
> +#include "xlat/packet_diag_info_flags.h"
>  #include "xlat/packet_diag_show.h"
>  
>  #ifdef AF_SMC
> @@ -451,6 +453,127 @@ decode_packet_diag_req(struct tcb *const tcp,
>       tprints("}");
>  }
>  
> +static bool
> +decode_packet_diag_info(struct tcb *tcp, kernel_ulong_t addr,
> +                     kernel_ulong_t len, const void *const opaque_data)
> +{
> +     struct packet_diag_info pinfo;
> +
> +     if (len < sizeof(pinfo))
> +             return false;
> +     if (umove_or_printaddr(tcp, addr, &pinfo))
> +             return true;
> +
> +     tprintf("{pdi_index=%" PRIu32 ", pdi_version=%" PRIu32
> +             ", pdi_reserve=%" PRIu32 ", pdi_copy_thresh=%" PRIu32
> +             ", pdi_tstamp=%" PRIu32 ", pdi_flags=",
> +             pinfo.pdi_index, pinfo.pdi_version, pinfo.pdi_reserve,
> +             pinfo.pdi_copy_thresh, pinfo.pdi_tstamp);
> +     printflags(packet_diag_info_flags, pinfo.pdi_flags, "PDI_???");
> +     tprints("}");
> +
> +     return true;
> +}
> +
> +static bool
> +print_packet_diag_mclist(struct tcb *tcp, void *elem_buf,
> +                      size_t elem_size, void *opaque_data)
> +{
> +     struct packet_diag_mclist *dml;
> +
> +     dml = (struct packet_diag_mclist *) elem_buf;
> +
> +     tprintf("{pdmc_index=%" PRIu32 ", pdmc_count=%" PRIu32
> +             ", pdmc_type=%" PRIu16 ", pdmc_alen=%" PRIu16
> +             ", pdmc_addr=",
> +             dml->pdmc_index, dml->pdmc_count, dml->pdmc_type,
> +             dml->pdmc_alen);
> +     print_quoted_string((char *) dml->pdmc_addr, sizeof(dml->pdmc_addr),
> +                         QUOTE_0_TERMINATED);

I don't think packet_diag_mclist is printed properly here.

For example, pdmc_index seems to be an interface index we print using
print_ifindex; pdmc_addr is an address, not nul-terminated string, and
pdmc_alen is its actual length.

Please investigate what would be a correct representation of this
structure.

> +     tprints("}");
> +
> +     return true;
> +}
> +
> +static bool
> +decode_packet_diag_mclist(struct tcb *tcp, kernel_ulong_t addr,
> +                       kernel_ulong_t len, const void *const opaque_data)
> +{
> +     struct packet_diag_mclist dml;
> +     size_t nmemb = len / sizeof(dml);
> +
> +     if (!nmemb)
> +             return false;
> +
> +     print_array(tcp, addr, nmemb, &dml, sizeof(dml),
> +                 umoven_or_printaddr, print_packet_diag_mclist, 0);
> +
> +     return true;
> +}
> +
> +static bool
> +decode_packet_diag_ring(struct tcb *tcp, kernel_ulong_t addr,
> +                     kernel_ulong_t len, const void *const opaque_data)
> +{
> +     struct packet_diag_ring pdr;
> +
> +     if (len < sizeof(pdr))
> +             return false;
> +     if (umove_or_printaddr(tcp, addr, &pdr))
> +             return true;
> +
> +     tprintf("{pdr_block_size=%" PRIu32 ", pdr_block_nr=%" PRIu32
> +             ", pdr_frame_size=%" PRIu32 ", pdr_frame_nr=%" PRIu32
> +             ", pdr_retire_tmo=%" PRIu32 ", pdr_sizeof_priv=%" PRIu32
> +             ", pdr_features=%" PRIu32 "}",
> +             pdr.pdr_block_size, pdr.pdr_block_nr,
> +             pdr.pdr_frame_size, pdr.pdr_frame_nr,
> +             pdr.pdr_retire_tmo, pdr.pdr_sizeof_priv,
> +             pdr.pdr_features);
> +
> +     return true;
> +}
> +
> +static bool
> +print_sock_filter(struct tcb *tcp, void *elem_buf,
> +               size_t elem_size, void *opaque_data)
> +{
> +     struct sock_filter *filter = (struct sock_filter *)elem_buf;

No need to cast.

> +     tprintf("{code=%" PRIu16 ", jt=%" PRIu8 ", jf=%" PRIu8 ", k=%" PRIu32,
> +             filter->code, filter->jt, filter->jf, filter->k);
> +     tprints("}");
> +
> +     return true;
> +}

Note that this is a very primitive parser compared to print_bpf_filter
in seccomp.c.

> +
> +static bool
> +decode_sock_filter(struct tcb *tcp, kernel_ulong_t addr,
> +                kernel_ulong_t len, const void *const opaque_data)
> +{
> +     struct sock_filter filter;
> +     size_t nmemb = len / sizeof(filter);
> +
> +     if (!nmemb)
> +             return false;
> +
> +     print_array(tcp, addr, nmemb, &filter, sizeof(filter),
> +                 umoven_or_printaddr, print_sock_filter, 0);
> +
> +     return true;
> +}
> +
> +static const nla_decoder_t packet_diag_msg_nla_decoders[] = {
> +     [PACKET_DIAG_INFO]      = decode_packet_diag_info,
> +     [PACKET_DIAG_MCLIST]    = decode_packet_diag_mclist,
> +     [PACKET_DIAG_RX_RING]   = decode_packet_diag_ring,
> +     [PACKET_DIAG_TX_RING]   = decode_packet_diag_ring,
> +     [PACKET_DIAG_FANOUT]    = decode_nla_u32,
> +     [PACKET_DIAG_UID]       = decode_nla_u32,
> +     [PACKET_DIAG_MEMINFO]   = decode_meminfo,
> +     [PACKET_DIAG_FILTER]    = decode_sock_filter
> +};
> +
>  static void
>  decode_packet_diag_msg(struct tcb *const tcp,
>                      const struct nlmsghdr *const nlmsghdr,
> @@ -487,7 +610,8 @@ decode_packet_diag_msg(struct tcb *const tcp,
>               tprints(", ");
>               decode_nlattr(tcp, addr + offset, len - offset,
>                             packet_diag_attrs, "PACKET_DIAG_???",
> -                           NULL, 0, NULL);
> +                           packet_diag_msg_nla_decoders,
> +                           ARRAY_SIZE(packet_diag_msg_nla_decoders), NULL);
>       }
>  }
>  
> diff --git a/xlat/packet_diag_info_flags.in b/xlat/packet_diag_info_flags.in
> new file mode 100644
> index 0000000..30a47b1
> --- /dev/null
> +++ b/xlat/packet_diag_info_flags.in
> @@ -0,0 +1,5 @@
> +PDI_RUNNING  0x1
> +PDI_AUXDATA  0x2
> +PDI_ORIGDEV  0x4
> +PDI_VNETHDR  0x8
> +PDI_LOSS     0x10

These constants are defined in local linux/packet_diag.h already,
no fallback definitions are needed.


-- 
ldv

Attachment: signature.asc
Description: PGP signature

------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
_______________________________________________
Strace-devel mailing list
Strace-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/strace-devel

Reply via email to