xref: /dpdk/drivers/net/hns3/hns3_ethdev_dump.c (revision dfee5606)
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(C) 2022 HiSilicon Limited
3  */
4 
5 #include "hns3_common.h"
6 #include "hns3_logs.h"
7 #include "hns3_regs.h"
8 #include "hns3_rxtx.h"
9 #include "hns3_ethdev.h"
10 
11 static const char *
get_adapter_state_name(enum hns3_adapter_state state)12 get_adapter_state_name(enum hns3_adapter_state state)
13 {
14 	const struct {
15 		enum hns3_adapter_state state;
16 		const char *name;
17 	} adapter_state_name[] = {
18 		{HNS3_NIC_UNINITIALIZED, "UNINITIALIZED"},
19 		{HNS3_NIC_INITIALIZED, "INITIALIZED"},
20 		{HNS3_NIC_CONFIGURING, "CONFIGURING"},
21 		{HNS3_NIC_CONFIGURED, "CONFIGURED"},
22 		{HNS3_NIC_STARTING, "STARTING"},
23 		{HNS3_NIC_STARTED, "STARTED"},
24 		{HNS3_NIC_STOPPING, "STOPPING"},
25 		{HNS3_NIC_CLOSING, "CLOSING"},
26 		{HNS3_NIC_CLOSED, "CLOSED"},
27 		{HNS3_NIC_REMOVED, "REMOVED"},
28 		{HNS3_NIC_NSTATES, "NSTATES"},
29 	};
30 	uint32_t i;
31 
32 	for (i = 0; i < RTE_DIM(adapter_state_name); i++)
33 		if (state == adapter_state_name[i].state)
34 			return adapter_state_name[i].name;
35 
36 	return "Unknown";
37 }
38 
39 static const char *
get_io_func_hint_name(uint32_t hint)40 get_io_func_hint_name(uint32_t hint)
41 {
42 	switch (hint) {
43 	case HNS3_IO_FUNC_HINT_NONE:
44 		return "none";
45 	case HNS3_IO_FUNC_HINT_VEC:
46 		return "vec";
47 	case HNS3_IO_FUNC_HINT_SVE:
48 		return "sve";
49 	case HNS3_IO_FUNC_HINT_SIMPLE:
50 		return "simple";
51 	case HNS3_IO_FUNC_HINT_COMMON:
52 		return "common";
53 	default:
54 		return "unknown";
55 	}
56 }
57 
58 static void
get_dev_mac_info(FILE * file,struct hns3_adapter * hns)59 get_dev_mac_info(FILE *file, struct hns3_adapter *hns)
60 {
61 	struct hns3_hw *hw = &hns->hw;
62 	struct hns3_pf *pf = &hns->pf;
63 
64 	fprintf(file, "  - MAC Info:\n");
65 	fprintf(file,
66 		"\t  -- query_type=%u\n"
67 		"\t  -- supported_speed=0x%x\n"
68 		"\t  -- advertising=0x%x\n"
69 		"\t  -- lp_advertising=0x%x\n"
70 		"\t  -- support_autoneg=%s\n"
71 		"\t  -- support_fc_autoneg=%s\n",
72 		hw->mac.query_type,
73 		hw->mac.supported_speed,
74 		hw->mac.advertising,
75 		hw->mac.lp_advertising,
76 		hw->mac.support_autoneg != 0 ? "Yes" : "No",
77 		pf->support_fc_autoneg ? "Yes" : "No");
78 }
79 
80 static void
get_dev_feature_capability(FILE * file,struct hns3_hw * hw)81 get_dev_feature_capability(FILE *file, struct hns3_hw *hw)
82 {
83 	const struct {
84 		enum hns3_dev_cap cap;
85 		const char *name;
86 	} caps_name[] = {
87 		{HNS3_DEV_SUPPORT_DCB_B, "DCB"},
88 		{HNS3_DEV_SUPPORT_COPPER_B, "COPPER"},
89 		{HNS3_DEV_SUPPORT_FD_QUEUE_REGION_B, "FD QUEUE REGION"},
90 		{HNS3_DEV_SUPPORT_PTP_B, "PTP"},
91 		{HNS3_DEV_SUPPORT_TX_PUSH_B, "TX PUSH"},
92 		{HNS3_DEV_SUPPORT_INDEP_TXRX_B, "INDEP TXRX"},
93 		{HNS3_DEV_SUPPORT_STASH_B, "STASH"},
94 		{HNS3_DEV_SUPPORT_RXD_ADV_LAYOUT_B, "RXD Advanced Layout"},
95 		{HNS3_DEV_SUPPORT_OUTER_UDP_CKSUM_B, "OUTER UDP CKSUM"},
96 		{HNS3_DEV_SUPPORT_RAS_IMP_B, "RAS IMP"},
97 		{HNS3_DEV_SUPPORT_TM_B, "TM"},
98 	};
99 	uint32_t i;
100 
101 	fprintf(file, "  - Dev Capability:\n");
102 	for (i = 0; i < RTE_DIM(caps_name); i++)
103 		fprintf(file, "\t  -- support %s: %s\n", caps_name[i].name,
104 			hns3_get_bit(hw->capability, caps_name[i].cap) ? "Yes" :
105 									 "No");
106 }
107 
108 static const char *
get_fdir_tuple_name(uint32_t index)109 get_fdir_tuple_name(uint32_t index)
110 {
111 	static const char * const tuple_name[] = {
112 		"outer_dst_mac",
113 		"outer_src_mac",
114 		"outer_vlan_1st_tag",
115 		"outer_vlan_2nd_tag",
116 		"outer_eth_type",
117 		"outer_l2_rsv",
118 		"outer_ip_tos",
119 		"outer_ip_proto",
120 		"outer_src_ip",
121 		"outer_dst_ip",
122 		"outer_l3_rsv",
123 		"outer_src_port",
124 		"outer_dst_port",
125 		"outer_l4_rsv",
126 		"outer_tun_vni",
127 		"outer_tun_flow_id",
128 		"inner_dst_mac",
129 		"inner_src_mac",
130 		"inner_vlan_tag1",
131 		"inner_vlan_tag2",
132 		"inner_eth_type",
133 		"inner_l2_rsv",
134 		"inner_ip_tos",
135 		"inner_ip_proto",
136 		"inner_src_ip",
137 		"inner_dst_ip",
138 		"inner_l3_rsv",
139 		"inner_src_port",
140 		"inner_dst_port",
141 		"inner_sctp_tag",
142 	};
143 	if (index < RTE_DIM(tuple_name))
144 		return tuple_name[index];
145 	else
146 		return "unknown";
147 }
148 
149 static void
get_fdir_basic_info(FILE * file,struct hns3_pf * pf)150 get_fdir_basic_info(FILE *file, struct hns3_pf *pf)
151 {
152 #define TMPBUF_SIZE		2048
153 #define PERLINE_TUPLE_NAMES	4
154 	struct hns3_fd_cfg *fdcfg = &pf->fdir.fd_cfg;
155 	char tmpbuf[TMPBUF_SIZE] = {0};
156 	uint32_t i, count = 0;
157 
158 	fprintf(file, "  - Fdir Info:\n");
159 	fprintf(file,
160 		"\t  -- mode=%u max_key_len=%u rule_num:%u cnt_num:%u\n"
161 		"\t  -- key_sel=%u tuple_active=0x%x meta_data_active=0x%x\n"
162 		"\t  -- ipv6_word_en: in_s=%u in_d=%u out_s=%u out_d=%u\n"
163 		"\t  -- active_tuples:\n",
164 		fdcfg->fd_mode, fdcfg->max_key_length,
165 		fdcfg->rule_num[HNS3_FD_STAGE_1],
166 		fdcfg->cnt_num[HNS3_FD_STAGE_1],
167 		fdcfg->key_cfg[HNS3_FD_STAGE_1].key_sel,
168 		fdcfg->key_cfg[HNS3_FD_STAGE_1].tuple_active,
169 		fdcfg->key_cfg[HNS3_FD_STAGE_1].meta_data_active,
170 		fdcfg->key_cfg[HNS3_FD_STAGE_1].inner_sipv6_word_en,
171 		fdcfg->key_cfg[HNS3_FD_STAGE_1].inner_dipv6_word_en,
172 		fdcfg->key_cfg[HNS3_FD_STAGE_1].outer_sipv6_word_en,
173 		fdcfg->key_cfg[HNS3_FD_STAGE_1].outer_dipv6_word_en);
174 
175 	for (i = 0; i < MAX_TUPLE; i++) {
176 		if (!(fdcfg->key_cfg[HNS3_FD_STAGE_1].tuple_active & BIT(i)))
177 			continue;
178 		if (count % PERLINE_TUPLE_NAMES == 0)
179 			fprintf(file, "\t      ");
180 		fprintf(file, " %s", get_fdir_tuple_name(i));
181 		count++;
182 		if (count % PERLINE_TUPLE_NAMES == 0)
183 			fprintf(file, "\n");
184 	}
185 	if (count % PERLINE_TUPLE_NAMES)
186 		fprintf(file, "\n");
187 
188 	fprintf(file, "%s", tmpbuf);
189 }
190 
191 static void
get_device_basic_info(FILE * file,struct rte_eth_dev * dev)192 get_device_basic_info(FILE *file, struct rte_eth_dev *dev)
193 {
194 	struct hns3_adapter *hns = dev->data->dev_private;
195 	struct hns3_hw *hw = &hns->hw;
196 
197 	fprintf(file,
198 		"  - Device Base Info:\n"
199 		"\t  -- name: %s\n"
200 		"\t  -- adapter_state=%s\n"
201 		"\t  -- nb_rx_queues=%u nb_tx_queues=%u\n"
202 		"\t  -- total_tqps_num=%u tqps_num=%u intr_tqps_num=%u\n"
203 		"\t  -- rss_size_max=%u alloc_rss_size=%u tx_qnum_per_tc=%u\n"
204 		"\t  -- min_tx_pkt_len=%u intr_mapping_mode=%u vlan_mode=%u\n"
205 		"\t  -- tso_mode=%u max_non_tso_bd_num=%u\n"
206 		"\t  -- max_tm_rate=%u Mbps\n"
207 		"\t  -- set link down: %s\n"
208 		"\t  -- rx_func_hint=%s tx_func_hint=%s\n"
209 		"\t  -- dev_flags: lsc=%d\n"
210 		"\t  -- intr_conf: lsc=%u rxq=%u\n",
211 		dev->data->name,
212 		get_adapter_state_name(hw->adapter_state),
213 		dev->data->nb_rx_queues, dev->data->nb_tx_queues,
214 		hw->total_tqps_num, hw->tqps_num, hw->intr_tqps_num,
215 		hw->rss_size_max, hw->alloc_rss_size, hw->tx_qnum_per_tc,
216 		hw->min_tx_pkt_len, hw->intr.mapping_mode, hw->vlan_mode,
217 		hw->tso_mode, hw->max_non_tso_bd_num,
218 		hw->max_tm_rate,
219 		hw->set_link_down ? "Yes" : "No",
220 		get_io_func_hint_name(hns->rx_func_hint),
221 		get_io_func_hint_name(hns->tx_func_hint),
222 		!!(dev->data->dev_flags & RTE_ETH_DEV_INTR_LSC),
223 		dev->data->dev_conf.intr_conf.lsc,
224 		dev->data->dev_conf.intr_conf.rxq);
225 }
226 
227 static struct hns3_rx_queue *
get_rx_queue(struct rte_eth_dev * dev)228 get_rx_queue(struct rte_eth_dev *dev)
229 {
230 	struct hns3_hw *hw = HNS3_DEV_PRIVATE_TO_HW(dev->data->dev_private);
231 	struct hns3_rx_queue *rxq;
232 	uint32_t queue_id;
233 	void **rx_queues;
234 
235 	for (queue_id = 0; queue_id < dev->data->nb_rx_queues; queue_id++) {
236 		rx_queues = dev->data->rx_queues;
237 		if (rx_queues == NULL || rx_queues[queue_id] == NULL) {
238 			hns3_err(hw, "detect rx_queues is NULL!\n");
239 			return NULL;
240 		}
241 
242 		rxq = (struct hns3_rx_queue *)rx_queues[queue_id];
243 		if (rxq->rx_deferred_start)
244 			continue;
245 
246 		return rx_queues[queue_id];
247 	}
248 
249 	return NULL;
250 }
251 
252 static struct hns3_tx_queue *
get_tx_queue(struct rte_eth_dev * dev)253 get_tx_queue(struct rte_eth_dev *dev)
254 {
255 	struct hns3_hw *hw = HNS3_DEV_PRIVATE_TO_HW(dev->data->dev_private);
256 	struct hns3_tx_queue *txq;
257 	uint32_t queue_id;
258 	void **tx_queues;
259 
260 	for (queue_id = 0; queue_id < dev->data->nb_tx_queues; queue_id++) {
261 		tx_queues = dev->data->tx_queues;
262 		if (tx_queues == NULL || tx_queues[queue_id] == NULL) {
263 			hns3_err(hw, "detect tx_queues is NULL!\n");
264 			return NULL;
265 		}
266 
267 		txq = (struct hns3_tx_queue *)tx_queues[queue_id];
268 		if (txq->tx_deferred_start)
269 			continue;
270 
271 		return tx_queues[queue_id];
272 	}
273 
274 	return NULL;
275 }
276 
277 static void
get_rxtx_fake_queue_info(FILE * file,struct rte_eth_dev * dev)278 get_rxtx_fake_queue_info(FILE *file, struct rte_eth_dev *dev)
279 {
280 	struct hns3_hw *hw = HNS3_DEV_PRIVATE_TO_HW(dev->data->dev_private);
281 	struct hns3_rx_queue *rxq;
282 	struct hns3_tx_queue *txq;
283 	uint32_t queue_id = 0;
284 	void **rx_queues;
285 	void **tx_queues;
286 
287 	if (hns3_dev_get_support(hw, INDEP_TXRX))
288 		return;
289 
290 	if (dev->data->nb_rx_queues < dev->data->nb_tx_queues) {
291 		rx_queues = hw->fkq_data.rx_queues;
292 		if (rx_queues == NULL || rx_queues[queue_id] == NULL) {
293 			hns3_err(hw, "detect rx_queues is NULL!\n");
294 			return;
295 		}
296 		rxq = (struct hns3_rx_queue *)rx_queues[queue_id];
297 
298 		fprintf(file,
299 			"\t  -- first fake_queue info:\n"
300 			"\t       Rx: port=%u nb_desc=%u free_thresh=%u\n",
301 			rxq->port_id, rxq->nb_rx_desc, rxq->rx_free_thresh);
302 	} else if (dev->data->nb_rx_queues > dev->data->nb_tx_queues) {
303 		tx_queues = hw->fkq_data.tx_queues;
304 		queue_id = 0;
305 
306 		if (tx_queues == NULL || tx_queues[queue_id] == NULL) {
307 			hns3_err(hw, "detect tx_queues is NULL!\n");
308 			return;
309 		}
310 		txq = (struct hns3_tx_queue *)tx_queues[queue_id];
311 
312 		fprintf(file,
313 			"\t  -- first fake_queue info:\n"
314 			"\t	  Tx: port=%u nb_desc=%u\n",
315 			txq->port_id, txq->nb_tx_desc);
316 	}
317 }
318 
319 static void
get_queue_enable_state(struct hns3_hw * hw,uint32_t * queue_state,uint32_t nb_queues,bool is_rxq)320 get_queue_enable_state(struct hns3_hw *hw, uint32_t *queue_state,
321 			uint32_t nb_queues, bool is_rxq)
322 {
323 #define STATE_SIZE (sizeof(*queue_state) * CHAR_BIT)
324 	uint32_t queue_en_reg;
325 	uint32_t reg_offset;
326 	uint32_t state;
327 	uint32_t i;
328 
329 	queue_en_reg = is_rxq ? HNS3_RING_RX_EN_REG : HNS3_RING_TX_EN_REG;
330 	for (i = 0; i < nb_queues; i++) {
331 		reg_offset = hns3_get_tqp_reg_offset(i);
332 		state = hns3_read_dev(hw, reg_offset + HNS3_RING_EN_REG);
333 		if (hns3_dev_get_support(hw, INDEP_TXRX))
334 			state = state && hns3_read_dev(hw, reg_offset +
335 						       queue_en_reg);
336 		hns3_set_bit(queue_state[i / STATE_SIZE],
337 				i % STATE_SIZE, state);
338 	}
339 }
340 
341 static void
print_queue_state_perline(FILE * file,const uint32_t * queue_state,uint32_t nb_queues,uint32_t line_num)342 print_queue_state_perline(FILE *file, const uint32_t *queue_state,
343 			  uint32_t nb_queues, uint32_t line_num)
344 {
345 #define NUM_QUEUE_PER_LINE (sizeof(*queue_state) * CHAR_BIT)
346 	uint32_t qid = line_num * NUM_QUEUE_PER_LINE;
347 	uint32_t j;
348 
349 	for (j = 0; j < NUM_QUEUE_PER_LINE; j++) {
350 		fprintf(file, "%1lx", hns3_get_bit(queue_state[line_num], j));
351 
352 		if (qid % CHAR_BIT == CHAR_BIT - 1) {
353 			fprintf(file, "%s",
354 				j == NUM_QUEUE_PER_LINE - 1 ? "\n" : ":");
355 		}
356 		qid++;
357 		if (qid >= nb_queues) {
358 			fprintf(file, "\n");
359 			break;
360 		}
361 	}
362 }
363 
364 static void
display_queue_enable_state(FILE * file,const uint32_t * queue_state,uint32_t nb_queues,bool is_rxq)365 display_queue_enable_state(FILE *file, const uint32_t *queue_state,
366 			   uint32_t nb_queues, bool is_rxq)
367 {
368 #define NUM_QUEUE_PER_LINE (sizeof(*queue_state) * CHAR_BIT)
369 	uint32_t i;
370 
371 	if (nb_queues == 0) {
372 		fprintf(file, "\t       %s queue number is 0\n",
373 				is_rxq ? "Rx" : "Tx");
374 		return;
375 	}
376 
377 	fprintf(file, "\t       %s queue id | enable state bitMap\n",
378 			is_rxq ? "rx" : "tx");
379 
380 	for (i = 0; i < (nb_queues - 1) / NUM_QUEUE_PER_LINE + 1; i++) {
381 		uint32_t line_end = (i + 1) * NUM_QUEUE_PER_LINE - 1;
382 		uint32_t line_start = i * NUM_QUEUE_PER_LINE;
383 		fprintf(file, "\t       %04u - %04u | ", line_start,
384 			nb_queues - 1 > line_end ? line_end : nb_queues - 1);
385 
386 
387 		print_queue_state_perline(file, queue_state, nb_queues, i);
388 	}
389 }
390 
391 static void
get_rxtx_queue_enable_state(FILE * file,struct rte_eth_dev * dev)392 get_rxtx_queue_enable_state(FILE *file, struct rte_eth_dev *dev)
393 {
394 #define MAX_TQP_NUM 1280
395 #define QUEUE_BITMAP_SIZE (MAX_TQP_NUM / 32)
396 	struct hns3_hw *hw = HNS3_DEV_PRIVATE_TO_HW(dev->data->dev_private);
397 	uint32_t rx_queue_state[QUEUE_BITMAP_SIZE] = {0};
398 	uint32_t tx_queue_state[QUEUE_BITMAP_SIZE] = {0};
399 	uint32_t nb_rx_queues;
400 	uint32_t nb_tx_queues;
401 
402 	nb_rx_queues = dev->data->nb_rx_queues;
403 	nb_tx_queues = dev->data->nb_tx_queues;
404 
405 	fprintf(file, "\t  -- enable state:\n");
406 	get_queue_enable_state(hw, rx_queue_state, nb_rx_queues, true);
407 	display_queue_enable_state(file, rx_queue_state, nb_rx_queues,
408 					 true);
409 
410 	get_queue_enable_state(hw, tx_queue_state, nb_tx_queues, false);
411 	display_queue_enable_state(file, tx_queue_state, nb_tx_queues,
412 					 false);
413 }
414 
415 static void
get_rxtx_queue_info(FILE * file,struct rte_eth_dev * dev)416 get_rxtx_queue_info(FILE *file, struct rte_eth_dev *dev)
417 {
418 	struct hns3_rx_queue *rxq;
419 	struct hns3_tx_queue *txq;
420 
421 	rxq = get_rx_queue(dev);
422 	if (rxq == NULL)
423 		return;
424 	txq = get_tx_queue(dev);
425 	if (txq == NULL)
426 		return;
427 	fprintf(file, "  - Rx/Tx Queue Info:\n");
428 	fprintf(file,
429 		"\t  -- first queue rxtx info:\n"
430 		"\t       Rx: port=%u nb_desc=%u free_thresh=%u\n"
431 		"\t       Tx: port=%u nb_desc=%u\n"
432 		"\t  -- tx push: %s\n",
433 		rxq->port_id, rxq->nb_rx_desc, rxq->rx_free_thresh,
434 		txq->port_id, txq->nb_tx_desc,
435 		txq->tx_push_enable ? "enabled" : "disabled");
436 
437 	get_rxtx_fake_queue_info(file, dev);
438 	get_rxtx_queue_enable_state(file, dev);
439 }
440 
441 static int
get_vlan_filter_cfg(FILE * file,struct hns3_hw * hw)442 get_vlan_filter_cfg(FILE *file, struct hns3_hw *hw)
443 {
444 #define HNS3_FILTER_TYPE_VF		0
445 #define HNS3_FILTER_TYPE_PORT		1
446 #define HNS3_FILTER_FE_NIC_INGRESS_B	BIT(0)
447 #define HNS3_FILTER_FE_NIC_EGRESS_B	BIT(1)
448 	struct hns3_vlan_filter_ctrl_cmd *req;
449 	struct hns3_cmd_desc desc;
450 	uint8_t i;
451 	int ret;
452 
453 	static const uint32_t vlan_filter_type[] = {
454 		HNS3_FILTER_TYPE_PORT,
455 		HNS3_FILTER_TYPE_VF
456 	};
457 
458 	for (i = 0; i < RTE_DIM(vlan_filter_type); i++) {
459 		hns3_cmd_setup_basic_desc(&desc, HNS3_OPC_VLAN_FILTER_CTRL,
460 						true);
461 		req = (struct hns3_vlan_filter_ctrl_cmd *)desc.data;
462 		req->vlan_type = vlan_filter_type[i];
463 		req->vf_id = HNS3_PF_FUNC_ID;
464 		ret = hns3_cmd_send(hw, &desc, 1);
465 		if (ret != 0) {
466 			hns3_err(hw,
467 				"NIC IMP exec ret=%d desc_num=%d optcode=0x%x!",
468 				ret, 1, rte_le_to_cpu_16(desc.opcode));
469 			return ret;
470 		}
471 		fprintf(file,
472 			"\t  -- %s VLAN filter configuration\n"
473 			"\t       nic_ingress           :%s\n"
474 			"\t       nic_egress            :%s\n",
475 			req->vlan_type == HNS3_FILTER_TYPE_PORT ?
476 			"Port" : "VF",
477 			req->vlan_fe & HNS3_FILTER_FE_NIC_INGRESS_B ?
478 			"Enable" : "Disable",
479 			req->vlan_fe & HNS3_FILTER_FE_NIC_EGRESS_B ?
480 			"Enable" : "Disable");
481 	}
482 
483 	return 0;
484 }
485 
486 static int
get_vlan_rx_offload_cfg(FILE * file,struct hns3_hw * hw)487 get_vlan_rx_offload_cfg(FILE *file, struct hns3_hw *hw)
488 {
489 	struct hns3_vport_vtag_rx_cfg_cmd *req;
490 	struct hns3_cmd_desc desc;
491 	uint16_t vport_id;
492 	uint8_t bitmap;
493 	int ret;
494 
495 	hns3_cmd_setup_basic_desc(&desc, HNS3_OPC_VLAN_PORT_RX_CFG, true);
496 	req = (struct hns3_vport_vtag_rx_cfg_cmd *)desc.data;
497 	vport_id = HNS3_PF_FUNC_ID;
498 	req->vf_offset = vport_id / HNS3_VF_NUM_PER_CMD;
499 	bitmap = 1 << (vport_id % HNS3_VF_NUM_PER_BYTE);
500 	req->vf_bitmap[req->vf_offset] = bitmap;
501 
502 	/*
503 	 * current version VF is not supported when PF is driven by DPDK driver,
504 	 * just need to configure rx parameters for PF vport.
505 	 */
506 	ret = hns3_cmd_send(hw, &desc, 1);
507 	if (ret != 0) {
508 		hns3_err(hw,
509 			"NIC IMP exec ret=%d desc_num=%d optcode=0x%x!",
510 			ret, 1, rte_le_to_cpu_16(desc.opcode));
511 		return ret;
512 	}
513 
514 	fprintf(file,
515 		"\t  -- RX VLAN configuration\n"
516 		"\t       vlan1_strip_en        :%s\n"
517 		"\t       vlan2_strip_en        :%s\n"
518 		"\t       vlan1_vlan_prionly    :%s\n"
519 		"\t       vlan2_vlan_prionly    :%s\n"
520 		"\t       vlan1_strip_discard   :%s\n"
521 		"\t       vlan2_strip_discard   :%s\n",
522 		hns3_get_bit(req->vport_vlan_cfg,
523 			HNS3_REM_TAG1_EN_B) ? "Enable" : "Disable",
524 		hns3_get_bit(req->vport_vlan_cfg,
525 			HNS3_REM_TAG2_EN_B) ? "Enable" : "Disable",
526 		hns3_get_bit(req->vport_vlan_cfg,
527 			HNS3_SHOW_TAG1_EN_B) ? "Enable" : "Disable",
528 		hns3_get_bit(req->vport_vlan_cfg,
529 			HNS3_SHOW_TAG2_EN_B) ? "Enable" : "Disable",
530 		hns3_get_bit(req->vport_vlan_cfg,
531 			HNS3_DISCARD_TAG1_EN_B) ? "Enable" : "Disable",
532 		hns3_get_bit(req->vport_vlan_cfg,
533 			HNS3_DISCARD_TAG2_EN_B) ? "Enable" : "Disable");
534 
535 	return 0;
536 }
537 
538 static void
parse_tx_vlan_cfg(FILE * file,struct hns3_vport_vtag_tx_cfg_cmd * req)539 parse_tx_vlan_cfg(FILE *file, struct hns3_vport_vtag_tx_cfg_cmd *req)
540 {
541 #define VLAN_VID_MASK 0x0fff
542 #define VLAN_PRIO_SHIFT 13
543 
544 	fprintf(file,
545 		"\t  -- TX VLAN configuration\n"
546 		"\t       accept_tag1           :%s\n"
547 		"\t       accept_untag1         :%s\n"
548 		"\t       insert_tag1_en        :%s\n"
549 		"\t       default_vlan_tag1 = %d, qos = %d\n"
550 		"\t       accept_tag2           :%s\n"
551 		"\t       accept_untag2         :%s\n"
552 		"\t       insert_tag2_en        :%s\n"
553 		"\t       default_vlan_tag2 = %d, qos = %d\n"
554 		"\t       vlan_shift_mode       :%s\n",
555 		hns3_get_bit(req->vport_vlan_cfg,
556 			HNS3_ACCEPT_TAG1_B) ? "Enable" : "Disable",
557 		hns3_get_bit(req->vport_vlan_cfg,
558 			HNS3_ACCEPT_UNTAG1_B) ? "Enable" : "Disable",
559 		hns3_get_bit(req->vport_vlan_cfg,
560 			HNS3_PORT_INS_TAG1_EN_B) ? "Enable" : "Disable",
561 		req->def_vlan_tag1 & VLAN_VID_MASK,
562 		req->def_vlan_tag1 >> VLAN_PRIO_SHIFT,
563 		hns3_get_bit(req->vport_vlan_cfg,
564 			HNS3_ACCEPT_TAG2_B) ? "Enable" : "Disable",
565 		hns3_get_bit(req->vport_vlan_cfg,
566 			HNS3_ACCEPT_UNTAG2_B) ? "Enable" : "Disable",
567 		hns3_get_bit(req->vport_vlan_cfg,
568 			HNS3_PORT_INS_TAG2_EN_B) ? "Enable" : "Disable",
569 		req->def_vlan_tag2 & VLAN_VID_MASK,
570 		req->def_vlan_tag2 >> VLAN_PRIO_SHIFT,
571 		hns3_get_bit(req->vport_vlan_cfg,
572 			HNS3_TAG_SHIFT_MODE_EN_B) ? "Enable" :
573 			"Disable");
574 }
575 
576 static int
get_vlan_tx_offload_cfg(FILE * file,struct hns3_hw * hw)577 get_vlan_tx_offload_cfg(FILE *file, struct hns3_hw *hw)
578 {
579 	struct hns3_vport_vtag_tx_cfg_cmd *req;
580 	struct hns3_cmd_desc desc;
581 	uint16_t vport_id;
582 	uint8_t bitmap;
583 	int ret;
584 
585 	hns3_cmd_setup_basic_desc(&desc, HNS3_OPC_VLAN_PORT_TX_CFG, true);
586 	req = (struct hns3_vport_vtag_tx_cfg_cmd *)desc.data;
587 	vport_id = HNS3_PF_FUNC_ID;
588 	req->vf_offset = vport_id / HNS3_VF_NUM_PER_CMD;
589 	bitmap = 1 << (vport_id % HNS3_VF_NUM_PER_BYTE);
590 	req->vf_bitmap[req->vf_offset] = bitmap;
591 	/*
592 	 * current version VF is not supported when PF is driven by DPDK driver,
593 	 * just need to configure tx parameters for PF vport.
594 	 */
595 	ret = hns3_cmd_send(hw, &desc, 1);
596 	if (ret != 0) {
597 		hns3_err(hw,
598 			"NIC IMP exec ret=%d desc_num=%d optcode=0x%x!",
599 			ret, 1, rte_le_to_cpu_16(desc.opcode));
600 		return ret;
601 	}
602 
603 	parse_tx_vlan_cfg(file, req);
604 
605 	return 0;
606 }
607 
608 static void
get_port_pvid_info(FILE * file,struct hns3_hw * hw)609 get_port_pvid_info(FILE *file, struct hns3_hw *hw)
610 {
611 	fprintf(file, "\t  -- pvid status: %s\n",
612 		hw->port_base_vlan_cfg.state ? "on" : "off");
613 }
614 
615 static void
get_vlan_config_info(FILE * file,struct hns3_hw * hw)616 get_vlan_config_info(FILE *file, struct hns3_hw *hw)
617 {
618 	int ret;
619 
620 	fprintf(file, "  - VLAN Config Info:\n");
621 	ret = get_vlan_filter_cfg(file, hw);
622 	if (ret < 0)
623 		return;
624 
625 	ret = get_vlan_rx_offload_cfg(file, hw);
626 	if (ret < 0)
627 		return;
628 
629 	ret = get_vlan_tx_offload_cfg(file, hw);
630 	if (ret < 0)
631 		return;
632 }
633 
634 static void
get_tm_conf_shaper_info(FILE * file,struct hns3_tm_conf * conf)635 get_tm_conf_shaper_info(FILE *file, struct hns3_tm_conf *conf)
636 {
637 	struct hns3_shaper_profile_list *shaper_profile_list =
638 		&conf->shaper_profile_list;
639 	struct hns3_tm_shaper_profile *shaper_profile;
640 
641 	if (!conf->nb_shaper_profile)
642 		return;
643 
644 	fprintf(file, "  shaper_profile:\n");
645 	TAILQ_FOREACH(shaper_profile, shaper_profile_list, node) {
646 		fprintf(file,
647 			"    id=%u reference_count=%u peak_rate=%" PRIu64 "Bps\n",
648 			shaper_profile->shaper_profile_id,
649 			shaper_profile->reference_count,
650 			shaper_profile->profile.peak.rate);
651 	}
652 }
653 
654 static void
get_tm_conf_port_node_info(FILE * file,struct hns3_tm_conf * conf)655 get_tm_conf_port_node_info(FILE *file, struct hns3_tm_conf *conf)
656 {
657 	if (!conf->root)
658 		return;
659 
660 	fprintf(file,
661 		"  port_node:\n"
662 		"    node_id=%u reference_count=%u shaper_profile_id=%d\n",
663 		conf->root->id, conf->root->reference_count,
664 		conf->root->shaper_profile ?
665 		(int)conf->root->shaper_profile->shaper_profile_id : -1);
666 }
667 
668 static void
get_tm_conf_tc_node_info(FILE * file,struct hns3_tm_conf * conf)669 get_tm_conf_tc_node_info(FILE *file, struct hns3_tm_conf *conf)
670 {
671 	struct hns3_tm_node_list *tc_list = &conf->tc_list;
672 	struct hns3_tm_node *tc_node[HNS3_MAX_TC_NUM];
673 	struct hns3_tm_node *tm_node;
674 	uint32_t tidx;
675 
676 	if (!conf->nb_tc_node)
677 		return;
678 
679 	fprintf(file, "  tc_node:\n");
680 	memset(tc_node, 0, sizeof(tc_node));
681 	TAILQ_FOREACH(tm_node, tc_list, node) {
682 		tidx = hns3_tm_calc_node_tc_no(conf, tm_node->id);
683 		if (tidx < HNS3_MAX_TC_NUM)
684 			tc_node[tidx] = tm_node;
685 	}
686 
687 	for (tidx = 0; tidx < HNS3_MAX_TC_NUM; tidx++) {
688 		tm_node = tc_node[tidx];
689 		if (tm_node == NULL)
690 			continue;
691 		fprintf(file,
692 			"    id=%u TC%u reference_count=%u parent_id=%d "
693 			"shaper_profile_id=%d\n",
694 			tm_node->id, hns3_tm_calc_node_tc_no(conf, tm_node->id),
695 			tm_node->reference_count,
696 			tm_node->parent ? (int)tm_node->parent->id : -1,
697 			tm_node->shaper_profile ?
698 			(int)tm_node->shaper_profile->shaper_profile_id : -1);
699 	}
700 }
701 
702 static void
get_tm_conf_queue_format_info(FILE * file,struct hns3_tm_node ** queue_node,uint32_t * queue_node_tc,uint32_t nb_tx_queues)703 get_tm_conf_queue_format_info(FILE *file, struct hns3_tm_node **queue_node,
704 			      uint32_t *queue_node_tc,  uint32_t nb_tx_queues)
705 {
706 #define PERLINE_QUEUES	32
707 #define PERLINE_STRIDE	8
708 #define LINE_BUF_SIZE	1024
709 	uint32_t i, j, line_num, start_queue, end_queue;
710 
711 	line_num = (nb_tx_queues + PERLINE_QUEUES - 1) / PERLINE_QUEUES;
712 	for (i = 0; i < line_num; i++) {
713 		start_queue = i * PERLINE_QUEUES;
714 		end_queue = (i + 1) * PERLINE_QUEUES - 1;
715 		if (end_queue > nb_tx_queues - 1)
716 			end_queue = nb_tx_queues - 1;
717 		fprintf(file, "    %04u - %04u | ", start_queue, end_queue);
718 		for (j = start_queue; j < nb_tx_queues; j++) {
719 			if (j >= end_queue + 1)
720 				break;
721 			if (j > start_queue && j % PERLINE_STRIDE == 0)
722 				fprintf(file, ":");
723 			fprintf(file, "%u",
724 				queue_node[j] ? queue_node_tc[j] :
725 				HNS3_MAX_TC_NUM);
726 		}
727 		fprintf(file, "\n");
728 	}
729 }
730 
731 static void
get_tm_conf_queue_node_info(FILE * file,struct hns3_tm_conf * conf,uint32_t nb_tx_queues)732 get_tm_conf_queue_node_info(FILE *file, struct hns3_tm_conf *conf,
733 			    uint32_t nb_tx_queues)
734 {
735 	struct hns3_tm_node_list *queue_list = &conf->queue_list;
736 	uint32_t nb_queue_node = conf->nb_leaf_nodes_max + 1;
737 	struct hns3_tm_node *queue_node[nb_queue_node];
738 	uint32_t queue_node_tc[nb_queue_node];
739 	struct hns3_tm_node *tm_node;
740 
741 	if (!conf->nb_queue_node)
742 		return;
743 
744 	fprintf(file,
745 		"  queue_node:\n"
746 		"    tx queue id | mapped tc (8 mean node not exist)\n");
747 
748 	memset(queue_node, 0, sizeof(queue_node));
749 	memset(queue_node_tc, 0, sizeof(queue_node_tc));
750 	nb_tx_queues = RTE_MIN(nb_tx_queues, nb_queue_node);
751 	TAILQ_FOREACH(tm_node, queue_list, node) {
752 		if (tm_node->id >= nb_queue_node)
753 			continue;
754 		queue_node[tm_node->id] = tm_node;
755 		queue_node_tc[tm_node->id] = tm_node->parent ?
756 			hns3_tm_calc_node_tc_no(conf, tm_node->parent->id) : 0;
757 		nb_tx_queues = RTE_MAX(nb_tx_queues, tm_node->id + 1);
758 	}
759 
760 	get_tm_conf_queue_format_info(file, queue_node, queue_node_tc,
761 				      nb_tx_queues);
762 }
763 
764 static void
get_tm_conf_info(FILE * file,struct rte_eth_dev * dev)765 get_tm_conf_info(FILE *file, struct rte_eth_dev *dev)
766 {
767 	struct hns3_hw *hw = HNS3_DEV_PRIVATE_TO_HW(dev->data->dev_private);
768 	struct hns3_pf *pf = HNS3_DEV_PRIVATE_TO_PF(dev->data->dev_private);
769 	struct hns3_tm_conf *conf = &pf->tm_conf;
770 
771 	if (!hns3_dev_get_support(hw, TM))
772 		return;
773 
774 	fprintf(file, "  - TM config info:\n");
775 	fprintf(file,
776 		"\t  -- nb_leaf_nodes_max=%u nb_nodes_max=%u\n"
777 		"\t  -- nb_shaper_profile=%u nb_tc_node=%u nb_queue_node=%u\n"
778 		"\t  -- committed=%u\n",
779 		conf->nb_leaf_nodes_max, conf->nb_nodes_max,
780 		conf->nb_shaper_profile, conf->nb_tc_node, conf->nb_queue_node,
781 		conf->committed);
782 
783 	get_tm_conf_shaper_info(file, conf);
784 	get_tm_conf_port_node_info(file, conf);
785 	get_tm_conf_tc_node_info(file, conf);
786 	get_tm_conf_queue_node_info(file, conf, dev->data->nb_tx_queues);
787 }
788 
789 static void
hns3_fc_mode_to_rxtx_pause(enum hns3_fc_mode fc_mode,bool * rx_pause,bool * tx_pause)790 hns3_fc_mode_to_rxtx_pause(enum hns3_fc_mode fc_mode, bool *rx_pause,
791 			   bool *tx_pause)
792 {
793 	switch (fc_mode) {
794 	case HNS3_FC_NONE:
795 		*tx_pause = false;
796 		*rx_pause = false;
797 		break;
798 	case HNS3_FC_RX_PAUSE:
799 		*rx_pause = true;
800 		*tx_pause = false;
801 		break;
802 	case HNS3_FC_TX_PAUSE:
803 		*rx_pause = false;
804 		*tx_pause = true;
805 		break;
806 	case HNS3_FC_FULL:
807 		*rx_pause = true;
808 		*tx_pause = true;
809 		break;
810 	default:
811 		*rx_pause = false;
812 		*tx_pause = false;
813 		break;
814 	}
815 }
816 
817 static bool
is_link_fc_mode(struct hns3_adapter * hns)818 is_link_fc_mode(struct hns3_adapter *hns)
819 {
820 	struct hns3_hw *hw = &hns->hw;
821 	struct hns3_pf *pf = &hns->pf;
822 
823 	if (hw->current_fc_status == HNS3_FC_STATUS_PFC)
824 		return false;
825 
826 	if (hw->num_tc > 1 && !pf->support_multi_tc_pause)
827 		return false;
828 
829 	return true;
830 }
831 
832 static void
get_link_fc_info(FILE * file,struct rte_eth_dev * dev)833 get_link_fc_info(FILE *file, struct rte_eth_dev *dev)
834 {
835 	struct hns3_adapter *hns = dev->data->dev_private;
836 	struct hns3_hw *hw = &hns->hw;
837 	struct rte_eth_fc_conf fc_conf;
838 	bool rx_pause1;
839 	bool tx_pause1;
840 	bool rx_pause2;
841 	bool tx_pause2;
842 	int ret;
843 
844 	if (!is_link_fc_mode(hns))
845 		return;
846 
847 	ret = hns3_flow_ctrl_get(dev, &fc_conf);
848 	if (ret)  {
849 		fprintf(file, "get device flow control info fail!\n");
850 		return;
851 	}
852 
853 	hns3_fc_mode_to_rxtx_pause(hw->requested_fc_mode,
854 				   &rx_pause1, &tx_pause1);
855 	hns3_fc_mode_to_rxtx_pause((enum hns3_fc_mode)fc_conf.mode,
856 				   &rx_pause2, &tx_pause2);
857 
858 	fprintf(file,
859 		"\t  -- link_fc_info:\n"
860 		"\t       Requested fc:\n"
861 		"\t         Rx:	%s\n"
862 		"\t         Tx:	%s\n"
863 		"\t       Current fc:\n"
864 		"\t         Rx:	%s\n"
865 		"\t         Tx:	%s\n"
866 		"\t       Autonegotiate: %s\n"
867 		"\t       Pause time:	0x%x\n",
868 		rx_pause1 ? "On" : "Off", tx_pause1 ? "On" : "Off",
869 		rx_pause2 ? "On" : "Off", tx_pause2 ? "On" : "Off",
870 		fc_conf.autoneg == RTE_ETH_LINK_AUTONEG ? "On" : "Off",
871 		fc_conf.pause_time);
872 }
873 
874 static void
get_flow_ctrl_info(FILE * file,struct rte_eth_dev * dev)875 get_flow_ctrl_info(FILE *file, struct rte_eth_dev *dev)
876 {
877 	struct hns3_adapter *hns = dev->data->dev_private;
878 	struct hns3_hw *hw = &hns->hw;
879 
880 	fprintf(file, "  - Flow Ctrl Info:\n");
881 	fprintf(file,
882 		"\t  -- fc_common_info:\n"
883 		"\t       current_fc_status=%u\n"
884 		"\t       requested_fc_mode=%u\n",
885 		hw->current_fc_status,
886 		hw->requested_fc_mode);
887 
888 	get_link_fc_info(file, dev);
889 }
890 
891 int
hns3_eth_dev_priv_dump(struct rte_eth_dev * dev,FILE * file)892 hns3_eth_dev_priv_dump(struct rte_eth_dev *dev, FILE *file)
893 {
894 	struct hns3_adapter *hns = dev->data->dev_private;
895 	struct hns3_hw *hw = &hns->hw;
896 
897 	get_device_basic_info(file, dev);
898 	get_dev_feature_capability(file, hw);
899 	get_rxtx_queue_info(file, dev);
900 	get_port_pvid_info(file, hw);
901 
902 	/* VF only supports dumping basic info and feaure capability */
903 	if (hns->is_vf)
904 		return 0;
905 
906 	get_dev_mac_info(file, hns);
907 	get_vlan_config_info(file, hw);
908 	get_fdir_basic_info(file, &hns->pf);
909 	get_tm_conf_info(file, dev);
910 	get_flow_ctrl_info(file, dev);
911 
912 	return 0;
913 }
914