netdev.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Michal Kubecek <mkubecek@suse.cz>
To: John Linville <linville@tuxdriver.com>, netdev@vger.kernel.org
Cc: Andrew Lunn <andrew@lunn.ch>, Florian Fainelli <f.fainelli@gmail.com>
Subject: [PATCH ethtool v2 25/25] netlink: use pretty printing for ethtool netlink messages
Date: Wed,  4 Mar 2020 21:26:41 +0100 (CET)	[thread overview]
Message-ID: <5d787f17d58fb66c671a90d2cfc8f47eaaf730e8.1583347351.git.mkubecek@suse.cz> (raw)
In-Reply-To: <cover.1583347351.git.mkubecek@suse.cz>

Introduce new debugging flag DEBUG_NL_PRETTY_MSG (0x10) which has two
effects:

  - show request messages embedded in extack error messages in human
    readable form; if failing attribute offset is provided, highlight the
    attribute
  - if DEBUG_NL_MSGS is also set, show structure of all outgoing and
    incoming ethtool netlink messages in addition to their summary

Signed-off-by: Michal Kubecek <mkubecek@suse.cz>
---
 internal.h       |  1 +
 netlink/nlsock.c | 71 +++++++++++++++++++++++++++++++++++++-----------
 2 files changed, 56 insertions(+), 16 deletions(-)

diff --git a/internal.h b/internal.h
index a518bfa99380..edb07bddd073 100644
--- a/internal.h
+++ b/internal.h
@@ -122,6 +122,7 @@ enum {
 	DEBUG_NL_MSGS,		/* incoming/outgoing netlink messages */
 	DEBUG_NL_DUMP_SND,	/* dump outgoing netlink messages */
 	DEBUG_NL_DUMP_RCV,	/* dump incoming netlink messages */
+	DEBUG_NL_PRETTY_MSG,	/* pretty print of messages and errors */
 };
 
 static inline bool debug_on(unsigned long debug, unsigned int bit)
diff --git a/netlink/nlsock.c b/netlink/nlsock.c
index 4366c52ce390..22abb68b6646 100644
--- a/netlink/nlsock.c
+++ b/netlink/nlsock.c
@@ -10,6 +10,7 @@
 #include "../internal.h"
 #include "nlsock.h"
 #include "netlink.h"
+#include "prettymsg.h"
 
 #define NLSOCK_RECV_BUFFSIZE 65536
 
@@ -43,10 +44,12 @@ static void ctrl_msg_summary(const struct nlmsghdr *nlhdr)
 }
 
 static void genl_msg_summary(const struct nlmsghdr *nlhdr, int ethnl_fam,
-			     bool outgoing)
+			     bool outgoing, bool pretty)
 {
 	if (nlhdr->nlmsg_type == ethnl_fam) {
+		const struct pretty_nlmsg_desc *msg_desc;
 		const struct genlmsghdr *ghdr;
+		unsigned int n_desc;
 
 		printf(" ethool");
 		if (nlhdr->nlmsg_len < NLMSG_HDRLEN + GENL_HDRLEN) {
@@ -55,27 +58,46 @@ static void genl_msg_summary(const struct nlmsghdr *nlhdr, int ethnl_fam,
 		}
 		ghdr = mnl_nlmsg_get_payload(nlhdr);
 
-		printf(" cmd %u", ghdr->cmd);
+		msg_desc = outgoing ? ethnl_umsg_desc : ethnl_kmsg_desc;
+		n_desc = outgoing ? ethnl_umsg_n_desc : ethnl_kmsg_n_desc;
+		if (ghdr->cmd < n_desc && msg_desc[ghdr->cmd].name)
+			printf(" %s", msg_desc[ghdr->cmd].name);
+		else
+			printf(" cmd %u", ghdr->cmd);
 		fputc('\n', stdout);
 
+		if (pretty)
+			pretty_print_genlmsg(nlhdr, msg_desc, n_desc, 0);
 		return;
 	}
 
-	if (nlhdr->nlmsg_type == GENL_ID_CTRL)
+	if (nlhdr->nlmsg_type == GENL_ID_CTRL) {
 		printf(" genl-ctrl\n");
-	else
+		if (pretty)
+			pretty_print_genlmsg(nlhdr, genlctrl_msg_desc,
+					     genlctrl_msg_n_desc, 0);
+	} else {
 		fputc('\n', stdout);
+		if (pretty)
+			pretty_print_genlmsg(nlhdr, NULL, 0, 0);
+	}
 }
 
-static void rtnl_msg_summary(const struct nlmsghdr *nlhdr)
+static void rtnl_msg_summary(const struct nlmsghdr *nlhdr, bool pretty)
 {
 	unsigned int type = nlhdr->nlmsg_type;
 
-	printf(" type %u\n", type);
+	if (type < rtnl_msg_n_desc && rtnl_msg_desc[type].name)
+		printf(" %s\n", rtnl_msg_desc[type].name);
+	else
+		printf(" type %u\n", type);
+
+	if (pretty)
+		pretty_print_rtnlmsg(nlhdr, 0);
 }
 
 static void debug_msg_summary(const struct nlmsghdr *nlhdr, int ethnl_fam,
-			      int nl_fam, bool outgoing)
+			      int nl_fam, bool outgoing, bool pretty)
 {
 	printf("    msg length %u", nlhdr->nlmsg_len);
 
@@ -86,10 +108,10 @@ static void debug_msg_summary(const struct nlmsghdr *nlhdr, int ethnl_fam,
 
 	switch(nl_fam) {
 	case NETLINK_GENERIC:
-		genl_msg_summary(nlhdr, ethnl_fam, outgoing);
+		genl_msg_summary(nlhdr, ethnl_fam, outgoing, pretty);
 		break;
 	case NETLINK_ROUTE:
-		rtnl_msg_summary(nlhdr);
+		rtnl_msg_summary(nlhdr, pretty);
 		break;
 	default:
 		fputc('\n', stdout);
@@ -103,13 +125,14 @@ static void debug_msg(struct nl_socket *nlsk, const void *msg, unsigned int len,
 	const char *dirlabel = outgoing ? "sending" : "received";
 	uint32_t debug = nlsk->nlctx->ctx->debug;
 	const struct nlmsghdr *nlhdr = msg;
-	bool summary, dump;
+	bool summary, dump, pretty;
 	const char *nl_fam_label;
 	int left = len;
 
 	summary = debug_on(debug, DEBUG_NL_MSGS);
 	dump = debug_on(debug,
 			outgoing ? DEBUG_NL_DUMP_SND : DEBUG_NL_DUMP_RCV);
+	pretty = debug_on(debug, DEBUG_NL_PRETTY_MSG);
 	if (!summary && !dump)
 		return;
 	switch(nlsk->nl_fam) {
@@ -128,7 +151,7 @@ static void debug_msg(struct nl_socket *nlsk, const void *msg, unsigned int len,
 	while (nlhdr && left > 0 && mnl_nlmsg_ok(nlhdr, left)) {
 		if (summary)
 			debug_msg_summary(nlhdr, nlsk->nlctx->ethnl_fam,
-					  nlsk->nl_fam, outgoing);
+					  nlsk->nl_fam, outgoing, pretty);
 		if (dump)
 			mnl_nlmsg_fprintf(stdout, nlhdr, nlhdr->nlmsg_len,
 					  GENL_HDRLEN);
@@ -146,7 +169,7 @@ static void debug_msg(struct nl_socket *nlsk, const void *msg, unsigned int len,
  * Return: error code extracted from the message
  */
 static int nlsock_process_ack(struct nlmsghdr *nlhdr, ssize_t len,
-			      unsigned int suppress_nlerr)
+			      unsigned int suppress_nlerr, bool pretty)
 {
 	const struct nlattr *tb[NLMSGERR_ATTR_MAX + 1] = {};
 	DECLARE_ATTR_TB_INFO(tb);
@@ -174,12 +197,23 @@ static int nlsock_process_ack(struct nlmsghdr *nlhdr, ssize_t len,
 
 		fprintf(stderr, "netlink %s: %s",
 			nlerr->error ? "error" : "warning", msg);
-		if (tb[NLMSGERR_ATTR_OFFS])
+		if (!pretty && tb[NLMSGERR_ATTR_OFFS])
 			fprintf(stderr, " (offset %u)",
 				mnl_attr_get_u32(tb[NLMSGERR_ATTR_OFFS]));
 		fputc('\n', stderr);
 	}
 
+	if (nlerr->error && pretty) {
+		unsigned int err_offset = 0;
+
+		if (tb[NLMSGERR_ATTR_OFFS])
+			err_offset = mnl_attr_get_u32(tb[NLMSGERR_ATTR_OFFS]);
+		fprintf(stderr, "offending message%s:\n",
+			err_offset ? " and attribute" : "");
+		pretty_print_genlmsg(&nlerr->msg, ethnl_umsg_desc,
+				     ethnl_umsg_n_desc, err_offset);
+	}
+
 out:
 	if (nlerr->error) {
 		errno = -nlerr->error;
@@ -223,9 +257,14 @@ int nlsock_process_reply(struct nl_socket *nlsk, mnl_cb_t reply_cb, void *data)
 			return -EFAULT;
 
 		nlhdr = (struct nlmsghdr *)buff;
-		if (nlhdr->nlmsg_type == NLMSG_ERROR)
-			return nlsock_process_ack(nlhdr, len,
-						  nlsk->nlctx->suppress_nlerr);
+		if (nlhdr->nlmsg_type == NLMSG_ERROR) {
+			bool silent = nlsk->nlctx->suppress_nlerr;
+			bool pretty;
+
+			pretty = debug_on(nlsk->nlctx->ctx->debug,
+					  DEBUG_NL_PRETTY_MSG);
+			return nlsock_process_ack(nlhdr, len, silent, pretty);
+		}
 
 		msgbuff->nlhdr = nlhdr;
 		msgbuff->genlhdr = mnl_nlmsg_get_payload(nlhdr);
-- 
2.25.1


  parent reply	other threads:[~2020-03-04 20:26 UTC|newest]

Thread overview: 30+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-03-04 20:24 [PATCH ethtool v2 00/25] initial netlink interface implementation for 5.6 release Michal Kubecek
2020-03-04 20:24 ` [PATCH ethtool v2 01/25] move UAPI header copies to a separate directory Michal Kubecek
2020-03-04 20:24 ` [PATCH ethtool v2 02/25] update UAPI header copies Michal Kubecek
2020-03-04 20:24 ` [PATCH ethtool v2 03/25] add --debug option to control debugging messages Michal Kubecek
2020-03-04 20:24 ` [PATCH ethtool v2 04/25] use named initializers in command line option list Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 05/25] netlink: add netlink related UAPI header files Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 06/25] netlink: introduce the netlink interface Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 07/25] netlink: message buffer and composition helpers Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 08/25] netlink: netlink socket wrapper and helpers Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 09/25] netlink: initialize ethtool netlink socket Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 10/25] netlink: add support for string sets Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 11/25] netlink: add notification monitor Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 12/25] move shared code into a common file Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 13/25] netlink: add bitset helpers Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 14/25] netlink: partial netlink handler for gset (no option) Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 15/25] netlink: support getting wake-on-lan and debugging settings Michal Kubecek
2020-03-04 20:25 ` [PATCH ethtool v2 16/25] netlink: add basic command line parsing helpers Michal Kubecek
2020-03-04 20:26 ` [PATCH ethtool v2 17/25] netlink: add bitset command line parser handlers Michal Kubecek
2020-03-04 20:26 ` [PATCH ethtool v2 18/25] netlink: add netlink handler for sset (-s) Michal Kubecek
2020-03-04 20:26 ` [PATCH ethtool v2 19/25] netlink: support tests with netlink enabled Michal Kubecek
2020-03-04 20:26 ` [PATCH ethtool v2 20/25] netlink: add handler for permaddr (-P) Michal Kubecek
2020-03-04 20:26 ` [PATCH ethtool v2 21/25] netlink: support for pretty printing netlink messages Michal Kubecek
2020-03-04 20:26 ` [PATCH ethtool v2 22/25] netlink: message format description for ethtool netlink Michal Kubecek
2020-03-04 20:26 ` [PATCH ethtool v2 23/25] netlink: message format descriptions for genetlink control Michal Kubecek
2020-03-04 20:26 ` [PATCH ethtool v2 24/25] netlink: message format descriptions for rtnetlink Michal Kubecek
2020-03-04 20:26 ` Michal Kubecek [this message]
2020-03-04 20:34 ` [PATCH ethtool v2 00/25] initial netlink interface implementation for 5.6 release Michal Kubecek
2020-03-05 19:24 ` John W. Linville
2020-03-05 20:32   ` Michal Kubecek
2020-03-05 21:14     ` Michal Kubecek

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=5d787f17d58fb66c671a90d2cfc8f47eaaf730e8.1583347351.git.mkubecek@suse.cz \
    --to=mkubecek@suse.cz \
    --cc=andrew@lunn.ch \
    --cc=f.fainelli@gmail.com \
    --cc=linville@tuxdriver.com \
    --cc=netdev@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).