All of lore.kernel.org
 help / color / mirror / Atom feed
From: Leon Romanovsky <leon@kernel.org>
To: David Ahern <dsahern@gmail.com>
Cc: Maor Gottlieb <maorg@mellanox.com>,
	Doug Ledford <dledford@redhat.com>,
	Jason Gunthorpe <jgg@mellanox.com>,
	linux-netdev <netdev@vger.kernel.org>,
	RDMA mailing list <linux-rdma@vger.kernel.org>
Subject: [PATCH iproute2-next v1 2/4] rdma: Add support to get QP in raw format
Date: Wed, 24 Jun 2020 13:40:10 +0300	[thread overview]
Message-ID: <20200624104012.1450880-3-leon@kernel.org> (raw)
In-Reply-To: <20200624104012.1450880-1-leon@kernel.org>

From: Maor Gottlieb <maorg@mellanox.com>

Add 'raw' argument to get the resource in raw format.
When RDMA_NLDEV_ATTR_RES_RAW is set in the netlink message,
then the resource fields are in raw format, print it as byte array.

Example:
$rdma res show qp link rocep0s12f0/1 lqpn 1137 -j -r
[{"ifindex":7,"ifname":"mlx5_1","port":1,
"data":[0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,...]}]

Signed-off-by: Maor Gottlieb <maorg@mellanox.com>
Signed-off-by: Leon Romanovsky <leonro@mellanox.com>
---
 man/man8/rdma-resource.8 |  5 +++++
 man/man8/rdma.8          |  4 ++++
 rdma/rdma.c              | 10 ++++++++--
 rdma/rdma.h              |  7 +++++--
 rdma/res-qp.c            | 20 ++++++++++++++++++--
 rdma/res.h               | 26 +++++++++++++++++++++-----
 rdma/utils.c             | 20 ++++++++++++++++++++
 7 files changed, 81 insertions(+), 11 deletions(-)

diff --git a/man/man8/rdma-resource.8 b/man/man8/rdma-resource.8
index 05030d0a..8d0d14c6 100644
--- a/man/man8/rdma-resource.8
+++ b/man/man8/rdma-resource.8
@@ -83,6 +83,11 @@ rdma res show qp link mlx5_4/1 lqpn 0-6
 Limit to specific Local QPNs.
 .RE
 .PP
+rdma res show qp link mlx5_4/1 lqpn 6 -r
+.RS 4
+Driver specific details in raw format.
+.RE
+.PP
 rdma resource show cm_id dst-port 7174
 .RS 4
 Show CM_IDs with destination ip port of 7174.
diff --git a/man/man8/rdma.8 b/man/man8/rdma.8
index 221bf334..c9e5d50d 100644
--- a/man/man8/rdma.8
+++ b/man/man8/rdma.8
@@ -51,6 +51,10 @@ If there were any errors during execution of the commands, the application retur
 .BR "\-d" , " --details"
 Output detailed information.  Adding a second \-d includes driver-specific details.
 
+.TP
+.BR "\-r" , " --raw"
+Output includes driver-specific details in raw format.
+
 .TP
 .BR "\-p" , " --pretty"
 When combined with -j generate a pretty JSON output.
diff --git a/rdma/rdma.c b/rdma/rdma.c
index 22050555..c24894d6 100644
--- a/rdma/rdma.c
+++ b/rdma/rdma.c
@@ -13,7 +13,7 @@ static void help(char *name)
 	pr_out("Usage: %s [ OPTIONS ] OBJECT { COMMAND | help }\n"
 	       "       %s [ -f[orce] ] -b[atch] filename\n"
 	       "where  OBJECT := { dev | link | resource | system | statistic | help }\n"
-	       "       OPTIONS := { -V[ersion] | -d[etails] | -j[son] | -p[retty]}\n", name, name);
+	       "       OPTIONS := { -V[ersion] | -d[etails] | -j[son] | -p[retty] -r[aw]}\n", name, name);
 }
 
 static int cmd_help(struct rd *rd)
@@ -112,6 +112,7 @@ int main(int argc, char **argv)
 		{ "json",		no_argument,		NULL, 'j' },
 		{ "pretty",		no_argument,		NULL, 'p' },
 		{ "details",		no_argument,		NULL, 'd' },
+		{ "raw",		no_argument,		NULL, 'r' },
 		{ "force",		no_argument,		NULL, 'f' },
 		{ "batch",		required_argument,	NULL, 'b' },
 		{ NULL, 0, NULL, 0 }
@@ -120,6 +121,7 @@ int main(int argc, char **argv)
 	const char *batch_file = NULL;
 	bool show_details = false;
 	bool json_output = false;
+	bool show_raw = false;
 	bool force = false;
 	struct rd rd = {};
 	char *filename;
@@ -127,7 +129,7 @@ int main(int argc, char **argv)
 	int err;
 	filename = basename(argv[0]);
 
-	while ((opt = getopt_long(argc, argv, ":Vhdpjfb:",
+	while ((opt = getopt_long(argc, argv, ":Vhdrpjfb:",
 				  long_options, NULL)) >= 0) {
 		switch (opt) {
 		case 'V':
@@ -143,6 +145,9 @@ int main(int argc, char **argv)
 			else
 				show_details = true;
 			break;
+		case 'r':
+			show_raw = true;
+			break;
 		case 'j':
 			json_output = 1;
 			break;
@@ -172,6 +177,7 @@ int main(int argc, char **argv)
 	rd.show_driver_details = show_driver_details;
 	rd.json_output = json_output;
 	rd.pretty_output = pretty;
+	rd.show_raw = show_raw;
 
 	err = rd_init(&rd, filename);
 	if (err)
diff --git a/rdma/rdma.h b/rdma/rdma.h
index 735b1bf7..a6c6bdea 100644
--- a/rdma/rdma.h
+++ b/rdma/rdma.h
@@ -57,8 +57,9 @@ struct rd {
 	int argc;
 	char **argv;
 	char *filename;
-	bool show_details;
-	bool show_driver_details;
+	uint8_t show_details:1;
+	uint8_t show_driver_details:1;
+	uint8_t show_raw:1;
 	struct list_head dev_map_list;
 	uint32_t dev_idx;
 	uint32_t port_idx;
@@ -134,9 +135,11 @@ int rd_attr_check(const struct nlattr *attr, int *typep);
  * Print helpers
  */
 void print_driver_table(struct rd *rd, struct nlattr *tb);
+void print_raw_data(struct rd *rd, struct nlattr **nla_line);
 void newline(struct rd *rd);
 void newline_indent(struct rd *rd);
 void print_on_off(struct rd *rd, const char *key_str, bool on);
+void print_raw_data(struct rd *rd, struct nlattr **nla_line);
 #define MAX_LINE_LENGTH 80
 
 #endif /* _RDMA_TOOL_H_ */
diff --git a/rdma/res-qp.c b/rdma/res-qp.c
index 801cfca9..a38be399 100644
--- a/rdma/res-qp.c
+++ b/rdma/res-qp.c
@@ -64,6 +64,20 @@ static void print_pathmig(struct rd *rd, uint32_t val, struct nlattr **nla_line)
 			   "path-mig-state %s ", path_mig_to_str(val));
 }
 
+static int res_qp_line_raw(struct rd *rd, const char *name, int idx,
+			   struct nlattr **nla_line)
+{
+	if (!nla_line[RDMA_NLDEV_ATTR_RES_RAW])
+		return MNL_CB_ERROR;
+
+	open_json_object(NULL);
+	print_link(rd, idx, name, rd->port_idx, nla_line);
+	print_raw_data(rd, nla_line);
+	newline(rd);
+
+	return MNL_CB_OK;
+}
+
 static int res_qp_line(struct rd *rd, const char *name, int idx,
 		       struct nlattr **nla_line)
 {
@@ -184,7 +198,8 @@ int res_qp_idx_parse_cb(const struct nlmsghdr *nlh, void *data)
 	name = mnl_attr_get_str(tb[RDMA_NLDEV_ATTR_DEV_NAME]);
 	idx = mnl_attr_get_u32(tb[RDMA_NLDEV_ATTR_DEV_INDEX]);
 
-	return res_qp_line(rd, name, idx, tb);
+	return (rd->show_raw) ? res_qp_line_raw(rd, name, idx, tb) :
+		res_qp_line(rd, name, idx, tb);
 }
 
 int res_qp_parse_cb(const struct nlmsghdr *nlh, void *data)
@@ -212,7 +227,8 @@ int res_qp_parse_cb(const struct nlmsghdr *nlh, void *data)
 		if (ret != MNL_CB_OK)
 			break;
 
-		ret = res_qp_line(rd, name, idx, nla_line);
+		ret = (rd->show_raw) ? res_qp_line_raw(rd, name, idx, nla_line) :
+			res_qp_line(rd, name, idx, nla_line);
 		if (ret != MNL_CB_OK)
 			break;
 	}
diff --git a/rdma/res.h b/rdma/res.h
index 525171fc..24eee2a1 100644
--- a/rdma/res.h
+++ b/rdma/res.h
@@ -23,24 +23,40 @@ int res_cm_id_idx_parse_cb(const struct nlmsghdr *nlh, void *data);
 int res_qp_parse_cb(const struct nlmsghdr *nlh, void *data);
 int res_qp_idx_parse_cb(const struct nlmsghdr *nlh, void *data);
 
+static inline uint32_t res_get_command(uint32_t command, struct rd *rd)
+{
+	if (!rd->show_raw)
+		return command;
+
+	switch (command) {
+	case RDMA_NLDEV_CMD_RES_QP_GET:
+		return RDMA_NLDEV_CMD_RES_QP_GET_RAW;
+	default:
+		return command;
+	}
+}
+
 #define RES_FUNC(name, command, valid_filters, strict_port, id)                        \
 	static inline int _##name(struct rd *rd)                                       \
 	{                                                                              \
-		uint32_t idx;                                                          \
+		uint32_t idx, _command;                                                \
 		int ret;                                                               \
+		_command = res_get_command(command, rd);			       \
 		if (id) {                                                              \
 			ret = rd_doit_index(rd, &idx);                                 \
 			if (ret) {                                                     \
 				rd->suppress_errors = true;                            \
-				ret = _res_send_idx_msg(rd, command,                   \
+				ret = _res_send_idx_msg(rd, _command,                  \
 							name##_idx_parse_cb,           \
 							idx, id);                      \
-				if (!ret)                                              \
+				if (!ret || rd->show_raw)                              \
 					return ret;                                    \
-				/* Fallback for old systems without .doit callbacks */ \
+				/* Fallback for old systems without .doit callbacks.   \
+				 * Kernel that supports raw, for sure supports doit.   \
+				 */						       \
 			}                                                              \
 		}                                                                      \
-		return _res_send_msg(rd, command, name##_parse_cb);                    \
+		return _res_send_msg(rd, _command, name##_parse_cb);                   \
 	}                                                                              \
 	static inline int name(struct rd *rd)                                          \
 	{                                                                              \
diff --git a/rdma/utils.c b/rdma/utils.c
index e25c3adf..4d3de4fa 100644
--- a/rdma/utils.c
+++ b/rdma/utils.c
@@ -450,6 +450,7 @@ static const enum mnl_attr_data_type nldev_policy[RDMA_NLDEV_ATTR_MAX] = {
 	[RDMA_NLDEV_ATTR_STAT_RES] = MNL_TYPE_U32,
 	[RDMA_NLDEV_ATTR_STAT_AUTO_MODE_MASK] = MNL_TYPE_U32,
 	[RDMA_NLDEV_ATTR_DEV_DIM] = MNL_TYPE_U8,
+	[RDMA_NLDEV_ATTR_RES_RAW] = MNL_TYPE_BINARY,
 };
 
 int rd_attr_check(const struct nlattr *attr, int *typep)
@@ -890,6 +891,25 @@ static int print_driver_entry(struct rd *rd, struct nlattr *key_attr,
 	return ret;
 }
 
+void print_raw_data(struct rd *rd, struct nlattr **nla_line)
+{
+	uint8_t *data;
+	uint32_t len;
+	int i = 0;
+
+	if (!rd->show_raw)
+		return;
+
+	len = mnl_attr_get_payload_len(nla_line[RDMA_NLDEV_ATTR_RES_RAW]);
+	data = mnl_attr_get_payload(nla_line[RDMA_NLDEV_ATTR_RES_RAW]);
+	open_json_array(PRINT_JSON, "data");
+	while (i < len) {
+		print_color_uint(PRINT_ANY, COLOR_NONE, NULL, "%d", data[i]);
+		i++;
+	}
+	close_json_array(PRINT_ANY, ">");
+}
+
 void print_driver_table(struct rd *rd, struct nlattr *tb)
 {
 	int print_type = RDMA_NLDEV_PRINT_TYPE_UNSPEC;
-- 
2.26.2


  parent reply	other threads:[~2020-06-24 10:40 UTC|newest]

Thread overview: 13+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-06-24 10:40 [PATCH iproute2-next v1 0/4] RAW format dumps through RDMAtool Leon Romanovsky
2020-06-24 10:40 ` [PATCH iproute2-next v1 1/4] rdma: update uapi headers Leon Romanovsky
2020-06-25  8:15   ` Leon Romanovsky
2020-06-26  5:00     ` David Ahern
2020-07-05 15:02   ` David Ahern
2020-07-05 18:04     ` Leon Romanovsky
2020-07-05 18:07       ` David Ahern
2020-07-06  5:33         ` Leon Romanovsky
2020-06-24 10:40 ` Leon Romanovsky [this message]
2020-06-24 10:40 ` [PATCH iproute2-next v1 3/4] rdma: Add support to get CQ in raw format Leon Romanovsky
2020-06-24 10:40 ` [PATCH iproute2-next v1 4/4] rdma: Add support to get MR " Leon Romanovsky
2020-07-05 18:14 ` [PATCH iproute2-next v1 0/4] RAW format dumps through RDMAtool David Ahern
2020-07-06  5:34   ` Leon Romanovsky

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=20200624104012.1450880-3-leon@kernel.org \
    --to=leon@kernel.org \
    --cc=dledford@redhat.com \
    --cc=dsahern@gmail.com \
    --cc=jgg@mellanox.com \
    --cc=linux-rdma@vger.kernel.org \
    --cc=maorg@mellanox.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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.