cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

hns3_debugfs.c (38570B)


      1// SPDX-License-Identifier: GPL-2.0+
      2/* Copyright (c) 2018-2019 Hisilicon Limited. */
      3
      4#include <linux/debugfs.h>
      5#include <linux/device.h>
      6
      7#include "hnae3.h"
      8#include "hns3_debugfs.h"
      9#include "hns3_enet.h"
     10
     11static struct dentry *hns3_dbgfs_root;
     12
     13static struct hns3_dbg_dentry_info hns3_dbg_dentry[] = {
     14	{
     15		.name = "tm"
     16	},
     17	{
     18		.name = "tx_bd_info"
     19	},
     20	{
     21		.name = "rx_bd_info"
     22	},
     23	{
     24		.name = "mac_list"
     25	},
     26	{
     27		.name = "reg"
     28	},
     29	{
     30		.name = "queue"
     31	},
     32	{
     33		.name = "fd"
     34	},
     35	/* keep common at the bottom and add new directory above */
     36	{
     37		.name = "common"
     38	},
     39};
     40
     41static int hns3_dbg_bd_file_init(struct hnae3_handle *handle, u32 cmd);
     42static int hns3_dbg_common_file_init(struct hnae3_handle *handle, u32 cmd);
     43
     44static struct hns3_dbg_cmd_info hns3_dbg_cmd[] = {
     45	{
     46		.name = "tm_nodes",
     47		.cmd = HNAE3_DBG_CMD_TM_NODES,
     48		.dentry = HNS3_DBG_DENTRY_TM,
     49		.buf_len = HNS3_DBG_READ_LEN,
     50		.init = hns3_dbg_common_file_init,
     51	},
     52	{
     53		.name = "tm_priority",
     54		.cmd = HNAE3_DBG_CMD_TM_PRI,
     55		.dentry = HNS3_DBG_DENTRY_TM,
     56		.buf_len = HNS3_DBG_READ_LEN,
     57		.init = hns3_dbg_common_file_init,
     58	},
     59	{
     60		.name = "tm_qset",
     61		.cmd = HNAE3_DBG_CMD_TM_QSET,
     62		.dentry = HNS3_DBG_DENTRY_TM,
     63		.buf_len = HNS3_DBG_READ_LEN,
     64		.init = hns3_dbg_common_file_init,
     65	},
     66	{
     67		.name = "tm_map",
     68		.cmd = HNAE3_DBG_CMD_TM_MAP,
     69		.dentry = HNS3_DBG_DENTRY_TM,
     70		.buf_len = HNS3_DBG_READ_LEN_1MB,
     71		.init = hns3_dbg_common_file_init,
     72	},
     73	{
     74		.name = "tm_pg",
     75		.cmd = HNAE3_DBG_CMD_TM_PG,
     76		.dentry = HNS3_DBG_DENTRY_TM,
     77		.buf_len = HNS3_DBG_READ_LEN,
     78		.init = hns3_dbg_common_file_init,
     79	},
     80	{
     81		.name = "tm_port",
     82		.cmd = HNAE3_DBG_CMD_TM_PORT,
     83		.dentry = HNS3_DBG_DENTRY_TM,
     84		.buf_len = HNS3_DBG_READ_LEN,
     85		.init = hns3_dbg_common_file_init,
     86	},
     87	{
     88		.name = "tc_sch_info",
     89		.cmd = HNAE3_DBG_CMD_TC_SCH_INFO,
     90		.dentry = HNS3_DBG_DENTRY_TM,
     91		.buf_len = HNS3_DBG_READ_LEN,
     92		.init = hns3_dbg_common_file_init,
     93	},
     94	{
     95		.name = "qos_pause_cfg",
     96		.cmd = HNAE3_DBG_CMD_QOS_PAUSE_CFG,
     97		.dentry = HNS3_DBG_DENTRY_TM,
     98		.buf_len = HNS3_DBG_READ_LEN,
     99		.init = hns3_dbg_common_file_init,
    100	},
    101	{
    102		.name = "qos_pri_map",
    103		.cmd = HNAE3_DBG_CMD_QOS_PRI_MAP,
    104		.dentry = HNS3_DBG_DENTRY_TM,
    105		.buf_len = HNS3_DBG_READ_LEN,
    106		.init = hns3_dbg_common_file_init,
    107	},
    108	{
    109		.name = "qos_buf_cfg",
    110		.cmd = HNAE3_DBG_CMD_QOS_BUF_CFG,
    111		.dentry = HNS3_DBG_DENTRY_TM,
    112		.buf_len = HNS3_DBG_READ_LEN,
    113		.init = hns3_dbg_common_file_init,
    114	},
    115	{
    116		.name = "dev_info",
    117		.cmd = HNAE3_DBG_CMD_DEV_INFO,
    118		.dentry = HNS3_DBG_DENTRY_COMMON,
    119		.buf_len = HNS3_DBG_READ_LEN,
    120		.init = hns3_dbg_common_file_init,
    121	},
    122	{
    123		.name = "tx_bd_queue",
    124		.cmd = HNAE3_DBG_CMD_TX_BD,
    125		.dentry = HNS3_DBG_DENTRY_TX_BD,
    126		.buf_len = HNS3_DBG_READ_LEN_4MB,
    127		.init = hns3_dbg_bd_file_init,
    128	},
    129	{
    130		.name = "rx_bd_queue",
    131		.cmd = HNAE3_DBG_CMD_RX_BD,
    132		.dentry = HNS3_DBG_DENTRY_RX_BD,
    133		.buf_len = HNS3_DBG_READ_LEN_4MB,
    134		.init = hns3_dbg_bd_file_init,
    135	},
    136	{
    137		.name = "uc",
    138		.cmd = HNAE3_DBG_CMD_MAC_UC,
    139		.dentry = HNS3_DBG_DENTRY_MAC,
    140		.buf_len = HNS3_DBG_READ_LEN_128KB,
    141		.init = hns3_dbg_common_file_init,
    142	},
    143	{
    144		.name = "mc",
    145		.cmd = HNAE3_DBG_CMD_MAC_MC,
    146		.dentry = HNS3_DBG_DENTRY_MAC,
    147		.buf_len = HNS3_DBG_READ_LEN,
    148		.init = hns3_dbg_common_file_init,
    149	},
    150	{
    151		.name = "mng_tbl",
    152		.cmd = HNAE3_DBG_CMD_MNG_TBL,
    153		.dentry = HNS3_DBG_DENTRY_COMMON,
    154		.buf_len = HNS3_DBG_READ_LEN,
    155		.init = hns3_dbg_common_file_init,
    156	},
    157	{
    158		.name = "loopback",
    159		.cmd = HNAE3_DBG_CMD_LOOPBACK,
    160		.dentry = HNS3_DBG_DENTRY_COMMON,
    161		.buf_len = HNS3_DBG_READ_LEN,
    162		.init = hns3_dbg_common_file_init,
    163	},
    164	{
    165		.name = "interrupt_info",
    166		.cmd = HNAE3_DBG_CMD_INTERRUPT_INFO,
    167		.dentry = HNS3_DBG_DENTRY_COMMON,
    168		.buf_len = HNS3_DBG_READ_LEN,
    169		.init = hns3_dbg_common_file_init,
    170	},
    171	{
    172		.name = "reset_info",
    173		.cmd = HNAE3_DBG_CMD_RESET_INFO,
    174		.dentry = HNS3_DBG_DENTRY_COMMON,
    175		.buf_len = HNS3_DBG_READ_LEN,
    176		.init = hns3_dbg_common_file_init,
    177	},
    178	{
    179		.name = "imp_info",
    180		.cmd = HNAE3_DBG_CMD_IMP_INFO,
    181		.dentry = HNS3_DBG_DENTRY_COMMON,
    182		.buf_len = HNS3_DBG_READ_LEN,
    183		.init = hns3_dbg_common_file_init,
    184	},
    185	{
    186		.name = "ncl_config",
    187		.cmd = HNAE3_DBG_CMD_NCL_CONFIG,
    188		.dentry = HNS3_DBG_DENTRY_COMMON,
    189		.buf_len = HNS3_DBG_READ_LEN_128KB,
    190		.init = hns3_dbg_common_file_init,
    191	},
    192	{
    193		.name = "mac_tnl_status",
    194		.cmd = HNAE3_DBG_CMD_MAC_TNL_STATUS,
    195		.dentry = HNS3_DBG_DENTRY_COMMON,
    196		.buf_len = HNS3_DBG_READ_LEN,
    197		.init = hns3_dbg_common_file_init,
    198	},
    199	{
    200		.name = "bios_common",
    201		.cmd = HNAE3_DBG_CMD_REG_BIOS_COMMON,
    202		.dentry = HNS3_DBG_DENTRY_REG,
    203		.buf_len = HNS3_DBG_READ_LEN,
    204		.init = hns3_dbg_common_file_init,
    205	},
    206	{
    207		.name = "ssu",
    208		.cmd = HNAE3_DBG_CMD_REG_SSU,
    209		.dentry = HNS3_DBG_DENTRY_REG,
    210		.buf_len = HNS3_DBG_READ_LEN,
    211		.init = hns3_dbg_common_file_init,
    212	},
    213	{
    214		.name = "igu_egu",
    215		.cmd = HNAE3_DBG_CMD_REG_IGU_EGU,
    216		.dentry = HNS3_DBG_DENTRY_REG,
    217		.buf_len = HNS3_DBG_READ_LEN,
    218		.init = hns3_dbg_common_file_init,
    219	},
    220	{
    221		.name = "rpu",
    222		.cmd = HNAE3_DBG_CMD_REG_RPU,
    223		.dentry = HNS3_DBG_DENTRY_REG,
    224		.buf_len = HNS3_DBG_READ_LEN,
    225		.init = hns3_dbg_common_file_init,
    226	},
    227	{
    228		.name = "ncsi",
    229		.cmd = HNAE3_DBG_CMD_REG_NCSI,
    230		.dentry = HNS3_DBG_DENTRY_REG,
    231		.buf_len = HNS3_DBG_READ_LEN,
    232		.init = hns3_dbg_common_file_init,
    233	},
    234	{
    235		.name = "rtc",
    236		.cmd = HNAE3_DBG_CMD_REG_RTC,
    237		.dentry = HNS3_DBG_DENTRY_REG,
    238		.buf_len = HNS3_DBG_READ_LEN,
    239		.init = hns3_dbg_common_file_init,
    240	},
    241	{
    242		.name = "ppp",
    243		.cmd = HNAE3_DBG_CMD_REG_PPP,
    244		.dentry = HNS3_DBG_DENTRY_REG,
    245		.buf_len = HNS3_DBG_READ_LEN,
    246		.init = hns3_dbg_common_file_init,
    247	},
    248	{
    249		.name = "rcb",
    250		.cmd = HNAE3_DBG_CMD_REG_RCB,
    251		.dentry = HNS3_DBG_DENTRY_REG,
    252		.buf_len = HNS3_DBG_READ_LEN,
    253		.init = hns3_dbg_common_file_init,
    254	},
    255	{
    256		.name = "tqp",
    257		.cmd = HNAE3_DBG_CMD_REG_TQP,
    258		.dentry = HNS3_DBG_DENTRY_REG,
    259		.buf_len = HNS3_DBG_READ_LEN_128KB,
    260		.init = hns3_dbg_common_file_init,
    261	},
    262	{
    263		.name = "mac",
    264		.cmd = HNAE3_DBG_CMD_REG_MAC,
    265		.dentry = HNS3_DBG_DENTRY_REG,
    266		.buf_len = HNS3_DBG_READ_LEN,
    267		.init = hns3_dbg_common_file_init,
    268	},
    269	{
    270		.name = "dcb",
    271		.cmd = HNAE3_DBG_CMD_REG_DCB,
    272		.dentry = HNS3_DBG_DENTRY_REG,
    273		.buf_len = HNS3_DBG_READ_LEN,
    274		.init = hns3_dbg_common_file_init,
    275	},
    276	{
    277		.name = "queue_map",
    278		.cmd = HNAE3_DBG_CMD_QUEUE_MAP,
    279		.dentry = HNS3_DBG_DENTRY_QUEUE,
    280		.buf_len = HNS3_DBG_READ_LEN,
    281		.init = hns3_dbg_common_file_init,
    282	},
    283	{
    284		.name = "rx_queue_info",
    285		.cmd = HNAE3_DBG_CMD_RX_QUEUE_INFO,
    286		.dentry = HNS3_DBG_DENTRY_QUEUE,
    287		.buf_len = HNS3_DBG_READ_LEN_1MB,
    288		.init = hns3_dbg_common_file_init,
    289	},
    290	{
    291		.name = "tx_queue_info",
    292		.cmd = HNAE3_DBG_CMD_TX_QUEUE_INFO,
    293		.dentry = HNS3_DBG_DENTRY_QUEUE,
    294		.buf_len = HNS3_DBG_READ_LEN_1MB,
    295		.init = hns3_dbg_common_file_init,
    296	},
    297	{
    298		.name = "fd_tcam",
    299		.cmd = HNAE3_DBG_CMD_FD_TCAM,
    300		.dentry = HNS3_DBG_DENTRY_FD,
    301		.buf_len = HNS3_DBG_READ_LEN_1MB,
    302		.init = hns3_dbg_common_file_init,
    303	},
    304	{
    305		.name = "service_task_info",
    306		.cmd = HNAE3_DBG_CMD_SERV_INFO,
    307		.dentry = HNS3_DBG_DENTRY_COMMON,
    308		.buf_len = HNS3_DBG_READ_LEN,
    309		.init = hns3_dbg_common_file_init,
    310	},
    311	{
    312		.name = "vlan_config",
    313		.cmd = HNAE3_DBG_CMD_VLAN_CONFIG,
    314		.dentry = HNS3_DBG_DENTRY_COMMON,
    315		.buf_len = HNS3_DBG_READ_LEN,
    316		.init = hns3_dbg_common_file_init,
    317	},
    318	{
    319		.name = "ptp_info",
    320		.cmd = HNAE3_DBG_CMD_PTP_INFO,
    321		.dentry = HNS3_DBG_DENTRY_COMMON,
    322		.buf_len = HNS3_DBG_READ_LEN,
    323		.init = hns3_dbg_common_file_init,
    324	},
    325	{
    326		.name = "fd_counter",
    327		.cmd = HNAE3_DBG_CMD_FD_COUNTER,
    328		.dentry = HNS3_DBG_DENTRY_FD,
    329		.buf_len = HNS3_DBG_READ_LEN,
    330		.init = hns3_dbg_common_file_init,
    331	},
    332	{
    333		.name = "umv_info",
    334		.cmd = HNAE3_DBG_CMD_UMV_INFO,
    335		.dentry = HNS3_DBG_DENTRY_COMMON,
    336		.buf_len = HNS3_DBG_READ_LEN,
    337		.init = hns3_dbg_common_file_init,
    338	},
    339	{
    340		.name = "page_pool_info",
    341		.cmd = HNAE3_DBG_CMD_PAGE_POOL_INFO,
    342		.dentry = HNS3_DBG_DENTRY_COMMON,
    343		.buf_len = HNS3_DBG_READ_LEN,
    344		.init = hns3_dbg_common_file_init,
    345	},
    346	{
    347		.name = "coalesce_info",
    348		.cmd = HNAE3_DBG_CMD_COAL_INFO,
    349		.dentry = HNS3_DBG_DENTRY_COMMON,
    350		.buf_len = HNS3_DBG_READ_LEN_1MB,
    351		.init = hns3_dbg_common_file_init,
    352	},
    353};
    354
    355static struct hns3_dbg_cap_info hns3_dbg_cap[] = {
    356	{
    357		.name = "support FD",
    358		.cap_bit = HNAE3_DEV_SUPPORT_FD_B,
    359	}, {
    360		.name = "support GRO",
    361		.cap_bit = HNAE3_DEV_SUPPORT_GRO_B,
    362	}, {
    363		.name = "support FEC",
    364		.cap_bit = HNAE3_DEV_SUPPORT_FEC_B,
    365	}, {
    366		.name = "support UDP GSO",
    367		.cap_bit = HNAE3_DEV_SUPPORT_UDP_GSO_B,
    368	}, {
    369		.name = "support PTP",
    370		.cap_bit = HNAE3_DEV_SUPPORT_PTP_B,
    371	}, {
    372		.name = "support INT QL",
    373		.cap_bit = HNAE3_DEV_SUPPORT_INT_QL_B,
    374	}, {
    375		.name = "support HW TX csum",
    376		.cap_bit = HNAE3_DEV_SUPPORT_HW_TX_CSUM_B,
    377	}, {
    378		.name = "support UDP tunnel csum",
    379		.cap_bit = HNAE3_DEV_SUPPORT_UDP_TUNNEL_CSUM_B,
    380	}, {
    381		.name = "support TX push",
    382		.cap_bit = HNAE3_DEV_SUPPORT_TX_PUSH_B,
    383	}, {
    384		.name = "support imp-controlled PHY",
    385		.cap_bit = HNAE3_DEV_SUPPORT_PHY_IMP_B,
    386	}, {
    387		.name = "support imp-controlled RAS",
    388		.cap_bit = HNAE3_DEV_SUPPORT_RAS_IMP_B,
    389	}, {
    390		.name = "support rxd advanced layout",
    391		.cap_bit = HNAE3_DEV_SUPPORT_RXD_ADV_LAYOUT_B,
    392	}, {
    393		.name = "support port vlan bypass",
    394		.cap_bit = HNAE3_DEV_SUPPORT_PORT_VLAN_BYPASS_B,
    395	}, {
    396		.name = "support modify vlan filter state",
    397		.cap_bit = HNAE3_DEV_SUPPORT_VLAN_FLTR_MDF_B,
    398	}
    399};
    400
    401static const struct hns3_dbg_item coal_info_items[] = {
    402	{ "VEC_ID", 2 },
    403	{ "ALGO_STATE", 2 },
    404	{ "PROFILE_ID", 2 },
    405	{ "CQE_MODE", 2 },
    406	{ "TUNE_STATE", 2 },
    407	{ "STEPS_LEFT", 2 },
    408	{ "STEPS_RIGHT", 2 },
    409	{ "TIRED", 2 },
    410	{ "SW_GL", 2 },
    411	{ "SW_QL", 2 },
    412	{ "HW_GL", 2 },
    413	{ "HW_QL", 2 },
    414};
    415
    416static const char * const dim_cqe_mode_str[] = { "EQE", "CQE" };
    417static const char * const dim_state_str[] = { "START", "IN_PROG", "APPLY" };
    418static const char * const
    419dim_tune_stat_str[] = { "ON_TOP", "TIRED", "RIGHT", "LEFT" };
    420
    421static void hns3_dbg_fill_content(char *content, u16 len,
    422				  const struct hns3_dbg_item *items,
    423				  const char **result, u16 size)
    424{
    425	char *pos = content;
    426	u16 i;
    427
    428	memset(content, ' ', len);
    429	for (i = 0; i < size; i++) {
    430		if (result)
    431			strncpy(pos, result[i], strlen(result[i]));
    432		else
    433			strncpy(pos, items[i].name, strlen(items[i].name));
    434
    435		pos += strlen(items[i].name) + items[i].interval;
    436	}
    437
    438	*pos++ = '\n';
    439	*pos++ = '\0';
    440}
    441
    442static void hns3_get_coal_info(struct hns3_enet_tqp_vector *tqp_vector,
    443			       char **result, int i, bool is_tx)
    444{
    445	unsigned int gl_offset, ql_offset;
    446	struct hns3_enet_coalesce *coal;
    447	unsigned int reg_val;
    448	unsigned int j = 0;
    449	struct dim *dim;
    450	bool ql_enable;
    451
    452	if (is_tx) {
    453		coal = &tqp_vector->tx_group.coal;
    454		dim = &tqp_vector->tx_group.dim;
    455		gl_offset = HNS3_VECTOR_GL1_OFFSET;
    456		ql_offset = HNS3_VECTOR_TX_QL_OFFSET;
    457		ql_enable = tqp_vector->tx_group.coal.ql_enable;
    458	} else {
    459		coal = &tqp_vector->rx_group.coal;
    460		dim = &tqp_vector->rx_group.dim;
    461		gl_offset = HNS3_VECTOR_GL0_OFFSET;
    462		ql_offset = HNS3_VECTOR_RX_QL_OFFSET;
    463		ql_enable = tqp_vector->rx_group.coal.ql_enable;
    464	}
    465
    466	sprintf(result[j++], "%d", i);
    467	sprintf(result[j++], "%s", dim_state_str[dim->state]);
    468	sprintf(result[j++], "%u", dim->profile_ix);
    469	sprintf(result[j++], "%s", dim_cqe_mode_str[dim->mode]);
    470	sprintf(result[j++], "%s",
    471		dim_tune_stat_str[dim->tune_state]);
    472	sprintf(result[j++], "%u", dim->steps_left);
    473	sprintf(result[j++], "%u", dim->steps_right);
    474	sprintf(result[j++], "%u", dim->tired);
    475	sprintf(result[j++], "%u", coal->int_gl);
    476	sprintf(result[j++], "%u", coal->int_ql);
    477	reg_val = readl(tqp_vector->mask_addr + gl_offset) &
    478		  HNS3_VECTOR_GL_MASK;
    479	sprintf(result[j++], "%u", reg_val);
    480	if (ql_enable) {
    481		reg_val = readl(tqp_vector->mask_addr + ql_offset) &
    482			  HNS3_VECTOR_QL_MASK;
    483		sprintf(result[j++], "%u", reg_val);
    484	} else {
    485		sprintf(result[j++], "NA");
    486	}
    487}
    488
    489static void hns3_dump_coal_info(struct hnae3_handle *h, char *buf, int len,
    490				int *pos, bool is_tx)
    491{
    492	char data_str[ARRAY_SIZE(coal_info_items)][HNS3_DBG_DATA_STR_LEN];
    493	char *result[ARRAY_SIZE(coal_info_items)];
    494	struct hns3_enet_tqp_vector *tqp_vector;
    495	struct hns3_nic_priv *priv = h->priv;
    496	char content[HNS3_DBG_INFO_LEN];
    497	unsigned int i;
    498
    499	for (i = 0; i < ARRAY_SIZE(coal_info_items); i++)
    500		result[i] = &data_str[i][0];
    501
    502	*pos += scnprintf(buf + *pos, len - *pos,
    503			  "%s interrupt coalesce info:\n",
    504			  is_tx ? "tx" : "rx");
    505	hns3_dbg_fill_content(content, sizeof(content), coal_info_items,
    506			      NULL, ARRAY_SIZE(coal_info_items));
    507	*pos += scnprintf(buf + *pos, len - *pos, "%s", content);
    508
    509	for (i = 0; i < priv->vector_num; i++) {
    510		tqp_vector = &priv->tqp_vector[i];
    511		hns3_get_coal_info(tqp_vector, result, i, is_tx);
    512		hns3_dbg_fill_content(content, sizeof(content), coal_info_items,
    513				      (const char **)result,
    514				      ARRAY_SIZE(coal_info_items));
    515		*pos += scnprintf(buf + *pos, len - *pos, "%s", content);
    516	}
    517}
    518
    519static int hns3_dbg_coal_info(struct hnae3_handle *h, char *buf, int len)
    520{
    521	int pos = 0;
    522
    523	hns3_dump_coal_info(h, buf, len, &pos, true);
    524	pos += scnprintf(buf + pos, len - pos, "\n");
    525	hns3_dump_coal_info(h, buf, len, &pos, false);
    526
    527	return 0;
    528}
    529
    530static const struct hns3_dbg_item tx_spare_info_items[] = {
    531	{ "QUEUE_ID", 2 },
    532	{ "COPYBREAK", 2 },
    533	{ "LEN", 7 },
    534	{ "NTU", 4 },
    535	{ "NTC", 4 },
    536	{ "LTC", 4 },
    537	{ "DMA", 17 },
    538};
    539
    540static void hns3_dbg_tx_spare_info(struct hns3_enet_ring *ring, char *buf,
    541				   int len, u32 ring_num, int *pos)
    542{
    543	char data_str[ARRAY_SIZE(tx_spare_info_items)][HNS3_DBG_DATA_STR_LEN];
    544	struct hns3_tx_spare *tx_spare = ring->tx_spare;
    545	char *result[ARRAY_SIZE(tx_spare_info_items)];
    546	char content[HNS3_DBG_INFO_LEN];
    547	u32 i, j;
    548
    549	if (!tx_spare) {
    550		*pos += scnprintf(buf + *pos, len - *pos,
    551				  "tx spare buffer is not enabled\n");
    552		return;
    553	}
    554
    555	for (i = 0; i < ARRAY_SIZE(tx_spare_info_items); i++)
    556		result[i] = &data_str[i][0];
    557
    558	*pos += scnprintf(buf + *pos, len - *pos, "tx spare buffer info\n");
    559	hns3_dbg_fill_content(content, sizeof(content), tx_spare_info_items,
    560			      NULL, ARRAY_SIZE(tx_spare_info_items));
    561	*pos += scnprintf(buf + *pos, len - *pos, "%s", content);
    562
    563	for (i = 0; i < ring_num; i++) {
    564		j = 0;
    565		sprintf(result[j++], "%u", i);
    566		sprintf(result[j++], "%u", ring->tx_copybreak);
    567		sprintf(result[j++], "%u", tx_spare->len);
    568		sprintf(result[j++], "%u", tx_spare->next_to_use);
    569		sprintf(result[j++], "%u", tx_spare->next_to_clean);
    570		sprintf(result[j++], "%u", tx_spare->last_to_clean);
    571		sprintf(result[j++], "%pad", &tx_spare->dma);
    572		hns3_dbg_fill_content(content, sizeof(content),
    573				      tx_spare_info_items,
    574				      (const char **)result,
    575				      ARRAY_SIZE(tx_spare_info_items));
    576		*pos += scnprintf(buf + *pos, len - *pos, "%s", content);
    577	}
    578}
    579
    580static const struct hns3_dbg_item rx_queue_info_items[] = {
    581	{ "QUEUE_ID", 2 },
    582	{ "BD_NUM", 2 },
    583	{ "BD_LEN", 2 },
    584	{ "TAIL", 2 },
    585	{ "HEAD", 2 },
    586	{ "FBDNUM", 2 },
    587	{ "PKTNUM", 5 },
    588	{ "COPYBREAK", 2 },
    589	{ "RING_EN", 2 },
    590	{ "RX_RING_EN", 2 },
    591	{ "BASE_ADDR", 10 },
    592};
    593
    594static void hns3_dump_rx_queue_info(struct hns3_enet_ring *ring,
    595				    struct hnae3_ae_dev *ae_dev, char **result,
    596				    u32 index)
    597{
    598	u32 base_add_l, base_add_h;
    599	u32 j = 0;
    600
    601	sprintf(result[j++], "%u", index);
    602
    603	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    604		HNS3_RING_RX_RING_BD_NUM_REG));
    605
    606	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    607		HNS3_RING_RX_RING_BD_LEN_REG));
    608
    609	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    610		HNS3_RING_RX_RING_TAIL_REG));
    611
    612	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    613		HNS3_RING_RX_RING_HEAD_REG));
    614
    615	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    616		HNS3_RING_RX_RING_FBDNUM_REG));
    617
    618	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    619		HNS3_RING_RX_RING_PKTNUM_RECORD_REG));
    620	sprintf(result[j++], "%u", ring->rx_copybreak);
    621
    622	sprintf(result[j++], "%s", readl_relaxed(ring->tqp->io_base +
    623		HNS3_RING_EN_REG) ? "on" : "off");
    624
    625	if (hnae3_ae_dev_tqp_txrx_indep_supported(ae_dev))
    626		sprintf(result[j++], "%s", readl_relaxed(ring->tqp->io_base +
    627			HNS3_RING_RX_EN_REG) ? "on" : "off");
    628	else
    629		sprintf(result[j++], "%s", "NA");
    630
    631	base_add_h = readl_relaxed(ring->tqp->io_base +
    632					HNS3_RING_RX_RING_BASEADDR_H_REG);
    633	base_add_l = readl_relaxed(ring->tqp->io_base +
    634					HNS3_RING_RX_RING_BASEADDR_L_REG);
    635	sprintf(result[j++], "0x%08x%08x", base_add_h, base_add_l);
    636}
    637
    638static int hns3_dbg_rx_queue_info(struct hnae3_handle *h,
    639				  char *buf, int len)
    640{
    641	char data_str[ARRAY_SIZE(rx_queue_info_items)][HNS3_DBG_DATA_STR_LEN];
    642	struct hnae3_ae_dev *ae_dev = pci_get_drvdata(h->pdev);
    643	char *result[ARRAY_SIZE(rx_queue_info_items)];
    644	struct hns3_nic_priv *priv = h->priv;
    645	char content[HNS3_DBG_INFO_LEN];
    646	struct hns3_enet_ring *ring;
    647	int pos = 0;
    648	u32 i;
    649
    650	if (!priv->ring) {
    651		dev_err(&h->pdev->dev, "priv->ring is NULL\n");
    652		return -EFAULT;
    653	}
    654
    655	for (i = 0; i < ARRAY_SIZE(rx_queue_info_items); i++)
    656		result[i] = &data_str[i][0];
    657
    658	hns3_dbg_fill_content(content, sizeof(content), rx_queue_info_items,
    659			      NULL, ARRAY_SIZE(rx_queue_info_items));
    660	pos += scnprintf(buf + pos, len - pos, "%s", content);
    661	for (i = 0; i < h->kinfo.num_tqps; i++) {
    662		/* Each cycle needs to determine whether the instance is reset,
    663		 * to prevent reference to invalid memory. And need to ensure
    664		 * that the following code is executed within 100ms.
    665		 */
    666		if (!test_bit(HNS3_NIC_STATE_INITED, &priv->state) ||
    667		    test_bit(HNS3_NIC_STATE_RESETTING, &priv->state))
    668			return -EPERM;
    669
    670		ring = &priv->ring[(u32)(i + h->kinfo.num_tqps)];
    671		hns3_dump_rx_queue_info(ring, ae_dev, result, i);
    672		hns3_dbg_fill_content(content, sizeof(content),
    673				      rx_queue_info_items,
    674				      (const char **)result,
    675				      ARRAY_SIZE(rx_queue_info_items));
    676		pos += scnprintf(buf + pos, len - pos, "%s", content);
    677	}
    678
    679	return 0;
    680}
    681
    682static const struct hns3_dbg_item tx_queue_info_items[] = {
    683	{ "QUEUE_ID", 2 },
    684	{ "BD_NUM", 2 },
    685	{ "TC", 2 },
    686	{ "TAIL", 2 },
    687	{ "HEAD", 2 },
    688	{ "FBDNUM", 2 },
    689	{ "OFFSET", 2 },
    690	{ "PKTNUM", 5 },
    691	{ "RING_EN", 2 },
    692	{ "TX_RING_EN", 2 },
    693	{ "BASE_ADDR", 10 },
    694};
    695
    696static void hns3_dump_tx_queue_info(struct hns3_enet_ring *ring,
    697				    struct hnae3_ae_dev *ae_dev, char **result,
    698				    u32 index)
    699{
    700	u32 base_add_l, base_add_h;
    701	u32 j = 0;
    702
    703	sprintf(result[j++], "%u", index);
    704	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    705		HNS3_RING_TX_RING_BD_NUM_REG));
    706
    707	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    708		HNS3_RING_TX_RING_TC_REG));
    709
    710	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    711		HNS3_RING_TX_RING_TAIL_REG));
    712
    713	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    714		HNS3_RING_TX_RING_HEAD_REG));
    715
    716	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    717		HNS3_RING_TX_RING_FBDNUM_REG));
    718
    719	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    720		HNS3_RING_TX_RING_OFFSET_REG));
    721
    722	sprintf(result[j++], "%u", readl_relaxed(ring->tqp->io_base +
    723		HNS3_RING_TX_RING_PKTNUM_RECORD_REG));
    724
    725	sprintf(result[j++], "%s", readl_relaxed(ring->tqp->io_base +
    726		HNS3_RING_EN_REG) ? "on" : "off");
    727
    728	if (hnae3_ae_dev_tqp_txrx_indep_supported(ae_dev))
    729		sprintf(result[j++], "%s", readl_relaxed(ring->tqp->io_base +
    730			HNS3_RING_TX_EN_REG) ? "on" : "off");
    731	else
    732		sprintf(result[j++], "%s", "NA");
    733
    734	base_add_h = readl_relaxed(ring->tqp->io_base +
    735					HNS3_RING_TX_RING_BASEADDR_H_REG);
    736	base_add_l = readl_relaxed(ring->tqp->io_base +
    737					HNS3_RING_TX_RING_BASEADDR_L_REG);
    738	sprintf(result[j++], "0x%08x%08x", base_add_h, base_add_l);
    739}
    740
    741static int hns3_dbg_tx_queue_info(struct hnae3_handle *h,
    742				  char *buf, int len)
    743{
    744	char data_str[ARRAY_SIZE(tx_queue_info_items)][HNS3_DBG_DATA_STR_LEN];
    745	struct hnae3_ae_dev *ae_dev = pci_get_drvdata(h->pdev);
    746	char *result[ARRAY_SIZE(tx_queue_info_items)];
    747	struct hns3_nic_priv *priv = h->priv;
    748	char content[HNS3_DBG_INFO_LEN];
    749	struct hns3_enet_ring *ring;
    750	int pos = 0;
    751	u32 i;
    752
    753	if (!priv->ring) {
    754		dev_err(&h->pdev->dev, "priv->ring is NULL\n");
    755		return -EFAULT;
    756	}
    757
    758	for (i = 0; i < ARRAY_SIZE(tx_queue_info_items); i++)
    759		result[i] = &data_str[i][0];
    760
    761	hns3_dbg_fill_content(content, sizeof(content), tx_queue_info_items,
    762			      NULL, ARRAY_SIZE(tx_queue_info_items));
    763	pos += scnprintf(buf + pos, len - pos, "%s", content);
    764
    765	for (i = 0; i < h->kinfo.num_tqps; i++) {
    766		/* Each cycle needs to determine whether the instance is reset,
    767		 * to prevent reference to invalid memory. And need to ensure
    768		 * that the following code is executed within 100ms.
    769		 */
    770		if (!test_bit(HNS3_NIC_STATE_INITED, &priv->state) ||
    771		    test_bit(HNS3_NIC_STATE_RESETTING, &priv->state))
    772			return -EPERM;
    773
    774		ring = &priv->ring[i];
    775		hns3_dump_tx_queue_info(ring, ae_dev, result, i);
    776		hns3_dbg_fill_content(content, sizeof(content),
    777				      tx_queue_info_items,
    778				      (const char **)result,
    779				      ARRAY_SIZE(tx_queue_info_items));
    780		pos += scnprintf(buf + pos, len - pos, "%s", content);
    781	}
    782
    783	hns3_dbg_tx_spare_info(ring, buf, len, h->kinfo.num_tqps, &pos);
    784
    785	return 0;
    786}
    787
    788static const struct hns3_dbg_item queue_map_items[] = {
    789	{ "local_queue_id", 2 },
    790	{ "global_queue_id", 2 },
    791	{ "vector_id", 2 },
    792};
    793
    794static int hns3_dbg_queue_map(struct hnae3_handle *h, char *buf, int len)
    795{
    796	char data_str[ARRAY_SIZE(queue_map_items)][HNS3_DBG_DATA_STR_LEN];
    797	char *result[ARRAY_SIZE(queue_map_items)];
    798	struct hns3_nic_priv *priv = h->priv;
    799	char content[HNS3_DBG_INFO_LEN];
    800	int pos = 0;
    801	int j;
    802	u32 i;
    803
    804	if (!h->ae_algo->ops->get_global_queue_id)
    805		return -EOPNOTSUPP;
    806
    807	for (i = 0; i < ARRAY_SIZE(queue_map_items); i++)
    808		result[i] = &data_str[i][0];
    809
    810	hns3_dbg_fill_content(content, sizeof(content), queue_map_items,
    811			      NULL, ARRAY_SIZE(queue_map_items));
    812	pos += scnprintf(buf + pos, len - pos, "%s", content);
    813	for (i = 0; i < h->kinfo.num_tqps; i++) {
    814		if (!priv->ring || !priv->ring[i].tqp_vector)
    815			continue;
    816		j = 0;
    817		sprintf(result[j++], "%u", i);
    818		sprintf(result[j++], "%u",
    819			h->ae_algo->ops->get_global_queue_id(h, i));
    820		sprintf(result[j++], "%d",
    821			priv->ring[i].tqp_vector->vector_irq);
    822		hns3_dbg_fill_content(content, sizeof(content), queue_map_items,
    823				      (const char **)result,
    824				      ARRAY_SIZE(queue_map_items));
    825		pos += scnprintf(buf + pos, len - pos, "%s", content);
    826	}
    827
    828	return 0;
    829}
    830
    831static const struct hns3_dbg_item rx_bd_info_items[] = {
    832	{ "BD_IDX", 3 },
    833	{ "L234_INFO", 2 },
    834	{ "PKT_LEN", 3 },
    835	{ "SIZE", 4 },
    836	{ "RSS_HASH", 4 },
    837	{ "FD_ID", 2 },
    838	{ "VLAN_TAG", 2 },
    839	{ "O_DM_VLAN_ID_FB", 2 },
    840	{ "OT_VLAN_TAG", 2 },
    841	{ "BD_BASE_INFO", 2 },
    842	{ "PTYPE", 2 },
    843	{ "HW_CSUM", 2 },
    844};
    845
    846static void hns3_dump_rx_bd_info(struct hns3_nic_priv *priv,
    847				 struct hns3_desc *desc, char **result, int idx)
    848{
    849	unsigned int j = 0;
    850
    851	sprintf(result[j++], "%d", idx);
    852	sprintf(result[j++], "%#x", le32_to_cpu(desc->rx.l234_info));
    853	sprintf(result[j++], "%u", le16_to_cpu(desc->rx.pkt_len));
    854	sprintf(result[j++], "%u", le16_to_cpu(desc->rx.size));
    855	sprintf(result[j++], "%#x", le32_to_cpu(desc->rx.rss_hash));
    856	sprintf(result[j++], "%u", le16_to_cpu(desc->rx.fd_id));
    857	sprintf(result[j++], "%u", le16_to_cpu(desc->rx.vlan_tag));
    858	sprintf(result[j++], "%u", le16_to_cpu(desc->rx.o_dm_vlan_id_fb));
    859	sprintf(result[j++], "%u", le16_to_cpu(desc->rx.ot_vlan_tag));
    860	sprintf(result[j++], "%#x", le32_to_cpu(desc->rx.bd_base_info));
    861	if (test_bit(HNS3_NIC_STATE_RXD_ADV_LAYOUT_ENABLE, &priv->state)) {
    862		u32 ol_info = le32_to_cpu(desc->rx.ol_info);
    863
    864		sprintf(result[j++], "%5lu", hnae3_get_field(ol_info,
    865							     HNS3_RXD_PTYPE_M,
    866							     HNS3_RXD_PTYPE_S));
    867		sprintf(result[j++], "%7u", le16_to_cpu(desc->csum));
    868	} else {
    869		sprintf(result[j++], "NA");
    870		sprintf(result[j++], "NA");
    871	}
    872}
    873
    874static int hns3_dbg_rx_bd_info(struct hns3_dbg_data *d, char *buf, int len)
    875{
    876	char data_str[ARRAY_SIZE(rx_bd_info_items)][HNS3_DBG_DATA_STR_LEN];
    877	struct hns3_nic_priv *priv = d->handle->priv;
    878	char *result[ARRAY_SIZE(rx_bd_info_items)];
    879	char content[HNS3_DBG_INFO_LEN];
    880	struct hns3_enet_ring *ring;
    881	struct hns3_desc *desc;
    882	unsigned int i;
    883	int pos = 0;
    884
    885	if (d->qid >= d->handle->kinfo.num_tqps) {
    886		dev_err(&d->handle->pdev->dev,
    887			"queue%u is not in use\n", d->qid);
    888		return -EINVAL;
    889	}
    890
    891	for (i = 0; i < ARRAY_SIZE(rx_bd_info_items); i++)
    892		result[i] = &data_str[i][0];
    893
    894	pos += scnprintf(buf + pos, len - pos,
    895			  "Queue %u rx bd info:\n", d->qid);
    896	hns3_dbg_fill_content(content, sizeof(content), rx_bd_info_items,
    897			      NULL, ARRAY_SIZE(rx_bd_info_items));
    898	pos += scnprintf(buf + pos, len - pos, "%s", content);
    899
    900	ring = &priv->ring[d->qid + d->handle->kinfo.num_tqps];
    901	for (i = 0; i < ring->desc_num; i++) {
    902		desc = &ring->desc[i];
    903
    904		hns3_dump_rx_bd_info(priv, desc, result, i);
    905		hns3_dbg_fill_content(content, sizeof(content),
    906				      rx_bd_info_items, (const char **)result,
    907				      ARRAY_SIZE(rx_bd_info_items));
    908		pos += scnprintf(buf + pos, len - pos, "%s", content);
    909	}
    910
    911	return 0;
    912}
    913
    914static const struct hns3_dbg_item tx_bd_info_items[] = {
    915	{ "BD_IDX", 2 },
    916	{ "ADDRESS", 13 },
    917	{ "VLAN_TAG", 2 },
    918	{ "SIZE", 2 },
    919	{ "T_CS_VLAN_TSO", 2 },
    920	{ "OT_VLAN_TAG", 3 },
    921	{ "TV", 5 },
    922	{ "OLT_VLAN_LEN", 2 },
    923	{ "PAYLEN_OL4CS", 2 },
    924	{ "BD_FE_SC_VLD", 2 },
    925	{ "MSS_HW_CSUM", 0 },
    926};
    927
    928static void hns3_dump_tx_bd_info(struct hns3_nic_priv *priv,
    929				 struct hns3_desc *desc, char **result, int idx)
    930{
    931	unsigned int j = 0;
    932
    933	sprintf(result[j++], "%d", idx);
    934	sprintf(result[j++], "%#llx", le64_to_cpu(desc->addr));
    935	sprintf(result[j++], "%u", le16_to_cpu(desc->tx.vlan_tag));
    936	sprintf(result[j++], "%u", le16_to_cpu(desc->tx.send_size));
    937	sprintf(result[j++], "%#x",
    938		le32_to_cpu(desc->tx.type_cs_vlan_tso_len));
    939	sprintf(result[j++], "%u", le16_to_cpu(desc->tx.outer_vlan_tag));
    940	sprintf(result[j++], "%u", le16_to_cpu(desc->tx.tv));
    941	sprintf(result[j++], "%u",
    942		le32_to_cpu(desc->tx.ol_type_vlan_len_msec));
    943	sprintf(result[j++], "%#x", le32_to_cpu(desc->tx.paylen_ol4cs));
    944	sprintf(result[j++], "%#x", le16_to_cpu(desc->tx.bdtp_fe_sc_vld_ra_ri));
    945	sprintf(result[j++], "%u", le16_to_cpu(desc->tx.mss_hw_csum));
    946}
    947
    948static int hns3_dbg_tx_bd_info(struct hns3_dbg_data *d, char *buf, int len)
    949{
    950	char data_str[ARRAY_SIZE(tx_bd_info_items)][HNS3_DBG_DATA_STR_LEN];
    951	struct hns3_nic_priv *priv = d->handle->priv;
    952	char *result[ARRAY_SIZE(tx_bd_info_items)];
    953	char content[HNS3_DBG_INFO_LEN];
    954	struct hns3_enet_ring *ring;
    955	struct hns3_desc *desc;
    956	unsigned int i;
    957	int pos = 0;
    958
    959	if (d->qid >= d->handle->kinfo.num_tqps) {
    960		dev_err(&d->handle->pdev->dev,
    961			"queue%u is not in use\n", d->qid);
    962		return -EINVAL;
    963	}
    964
    965	for (i = 0; i < ARRAY_SIZE(tx_bd_info_items); i++)
    966		result[i] = &data_str[i][0];
    967
    968	pos += scnprintf(buf + pos, len - pos,
    969			  "Queue %u tx bd info:\n", d->qid);
    970	hns3_dbg_fill_content(content, sizeof(content), tx_bd_info_items,
    971			      NULL, ARRAY_SIZE(tx_bd_info_items));
    972	pos += scnprintf(buf + pos, len - pos, "%s", content);
    973
    974	ring = &priv->ring[d->qid];
    975	for (i = 0; i < ring->desc_num; i++) {
    976		desc = &ring->desc[i];
    977
    978		hns3_dump_tx_bd_info(priv, desc, result, i);
    979		hns3_dbg_fill_content(content, sizeof(content),
    980				      tx_bd_info_items, (const char **)result,
    981				      ARRAY_SIZE(tx_bd_info_items));
    982		pos += scnprintf(buf + pos, len - pos, "%s", content);
    983	}
    984
    985	return 0;
    986}
    987
    988static void
    989hns3_dbg_dev_caps(struct hnae3_handle *h, char *buf, int len, int *pos)
    990{
    991	struct hnae3_ae_dev *ae_dev = pci_get_drvdata(h->pdev);
    992	const char * const str[] = {"no", "yes"};
    993	unsigned long *caps = ae_dev->caps;
    994	u32 i, state;
    995
    996	*pos += scnprintf(buf + *pos, len - *pos, "dev capability:\n");
    997
    998	for (i = 0; i < ARRAY_SIZE(hns3_dbg_cap); i++) {
    999		state = test_bit(hns3_dbg_cap[i].cap_bit, caps);
   1000		*pos += scnprintf(buf + *pos, len - *pos, "%s: %s\n",
   1001				  hns3_dbg_cap[i].name, str[state]);
   1002	}
   1003
   1004	*pos += scnprintf(buf + *pos, len - *pos, "\n");
   1005}
   1006
   1007static void
   1008hns3_dbg_dev_specs(struct hnae3_handle *h, char *buf, int len, int *pos)
   1009{
   1010	struct hnae3_ae_dev *ae_dev = pci_get_drvdata(h->pdev);
   1011	struct hnae3_dev_specs *dev_specs = &ae_dev->dev_specs;
   1012	struct hnae3_knic_private_info *kinfo = &h->kinfo;
   1013
   1014	*pos += scnprintf(buf + *pos, len - *pos, "dev_spec:\n");
   1015	*pos += scnprintf(buf + *pos, len - *pos, "MAC entry num: %u\n",
   1016			  dev_specs->mac_entry_num);
   1017	*pos += scnprintf(buf + *pos, len - *pos, "MNG entry num: %u\n",
   1018			  dev_specs->mng_entry_num);
   1019	*pos += scnprintf(buf + *pos, len - *pos, "MAX non tso bd num: %u\n",
   1020			  dev_specs->max_non_tso_bd_num);
   1021	*pos += scnprintf(buf + *pos, len - *pos, "RSS ind tbl size: %u\n",
   1022			  dev_specs->rss_ind_tbl_size);
   1023	*pos += scnprintf(buf + *pos, len - *pos, "RSS key size: %u\n",
   1024			  dev_specs->rss_key_size);
   1025	*pos += scnprintf(buf + *pos, len - *pos, "RSS size: %u\n",
   1026			  kinfo->rss_size);
   1027	*pos += scnprintf(buf + *pos, len - *pos, "Allocated RSS size: %u\n",
   1028			  kinfo->req_rss_size);
   1029	*pos += scnprintf(buf + *pos, len - *pos,
   1030			  "Task queue pairs numbers: %u\n",
   1031			  kinfo->num_tqps);
   1032	*pos += scnprintf(buf + *pos, len - *pos, "RX buffer length: %u\n",
   1033			  kinfo->rx_buf_len);
   1034	*pos += scnprintf(buf + *pos, len - *pos, "Desc num per TX queue: %u\n",
   1035			  kinfo->num_tx_desc);
   1036	*pos += scnprintf(buf + *pos, len - *pos, "Desc num per RX queue: %u\n",
   1037			  kinfo->num_rx_desc);
   1038	*pos += scnprintf(buf + *pos, len - *pos,
   1039			  "Total number of enabled TCs: %u\n",
   1040			  kinfo->tc_info.num_tc);
   1041	*pos += scnprintf(buf + *pos, len - *pos, "MAX INT QL: %u\n",
   1042			  dev_specs->int_ql_max);
   1043	*pos += scnprintf(buf + *pos, len - *pos, "MAX INT GL: %u\n",
   1044			  dev_specs->max_int_gl);
   1045	*pos += scnprintf(buf + *pos, len - *pos, "MAX TM RATE: %u\n",
   1046			  dev_specs->max_tm_rate);
   1047	*pos += scnprintf(buf + *pos, len - *pos, "MAX QSET number: %u\n",
   1048			  dev_specs->max_qset_num);
   1049	*pos += scnprintf(buf + *pos, len - *pos, "umv size: %u\n",
   1050			  dev_specs->umv_size);
   1051	*pos += scnprintf(buf + *pos, len - *pos, "mc mac size: %u\n",
   1052			  dev_specs->mc_mac_size);
   1053	*pos += scnprintf(buf + *pos, len - *pos, "MAC statistics number: %u\n",
   1054			  dev_specs->mac_stats_num);
   1055}
   1056
   1057static int hns3_dbg_dev_info(struct hnae3_handle *h, char *buf, int len)
   1058{
   1059	int pos = 0;
   1060
   1061	hns3_dbg_dev_caps(h, buf, len, &pos);
   1062
   1063	hns3_dbg_dev_specs(h, buf, len, &pos);
   1064
   1065	return 0;
   1066}
   1067
   1068static const struct hns3_dbg_item page_pool_info_items[] = {
   1069	{ "QUEUE_ID", 2 },
   1070	{ "ALLOCATE_CNT", 2 },
   1071	{ "FREE_CNT", 6 },
   1072	{ "POOL_SIZE(PAGE_NUM)", 2 },
   1073	{ "ORDER", 2 },
   1074	{ "NUMA_ID", 2 },
   1075	{ "MAX_LEN", 2 },
   1076};
   1077
   1078static void hns3_dump_page_pool_info(struct hns3_enet_ring *ring,
   1079				     char **result, u32 index)
   1080{
   1081	u32 j = 0;
   1082
   1083	sprintf(result[j++], "%u", index);
   1084	sprintf(result[j++], "%u",
   1085		READ_ONCE(ring->page_pool->pages_state_hold_cnt));
   1086	sprintf(result[j++], "%d",
   1087		atomic_read(&ring->page_pool->pages_state_release_cnt));
   1088	sprintf(result[j++], "%u", ring->page_pool->p.pool_size);
   1089	sprintf(result[j++], "%u", ring->page_pool->p.order);
   1090	sprintf(result[j++], "%d", ring->page_pool->p.nid);
   1091	sprintf(result[j++], "%uK", ring->page_pool->p.max_len / 1024);
   1092}
   1093
   1094static int
   1095hns3_dbg_page_pool_info(struct hnae3_handle *h, char *buf, int len)
   1096{
   1097	char data_str[ARRAY_SIZE(page_pool_info_items)][HNS3_DBG_DATA_STR_LEN];
   1098	char *result[ARRAY_SIZE(page_pool_info_items)];
   1099	struct hns3_nic_priv *priv = h->priv;
   1100	char content[HNS3_DBG_INFO_LEN];
   1101	struct hns3_enet_ring *ring;
   1102	int pos = 0;
   1103	u32 i;
   1104
   1105	if (!priv->ring) {
   1106		dev_err(&h->pdev->dev, "priv->ring is NULL\n");
   1107		return -EFAULT;
   1108	}
   1109
   1110	if (!priv->ring[h->kinfo.num_tqps].page_pool) {
   1111		dev_err(&h->pdev->dev, "page pool is not initialized\n");
   1112		return -EFAULT;
   1113	}
   1114
   1115	for (i = 0; i < ARRAY_SIZE(page_pool_info_items); i++)
   1116		result[i] = &data_str[i][0];
   1117
   1118	hns3_dbg_fill_content(content, sizeof(content), page_pool_info_items,
   1119			      NULL, ARRAY_SIZE(page_pool_info_items));
   1120	pos += scnprintf(buf + pos, len - pos, "%s", content);
   1121	for (i = 0; i < h->kinfo.num_tqps; i++) {
   1122		if (!test_bit(HNS3_NIC_STATE_INITED, &priv->state) ||
   1123		    test_bit(HNS3_NIC_STATE_RESETTING, &priv->state))
   1124			return -EPERM;
   1125		ring = &priv->ring[(u32)(i + h->kinfo.num_tqps)];
   1126		hns3_dump_page_pool_info(ring, result, i);
   1127		hns3_dbg_fill_content(content, sizeof(content),
   1128				      page_pool_info_items,
   1129				      (const char **)result,
   1130				      ARRAY_SIZE(page_pool_info_items));
   1131		pos += scnprintf(buf + pos, len - pos, "%s", content);
   1132	}
   1133
   1134	return 0;
   1135}
   1136
   1137static int hns3_dbg_get_cmd_index(struct hns3_dbg_data *dbg_data, u32 *index)
   1138{
   1139	u32 i;
   1140
   1141	for (i = 0; i < ARRAY_SIZE(hns3_dbg_cmd); i++) {
   1142		if (hns3_dbg_cmd[i].cmd == dbg_data->cmd) {
   1143			*index = i;
   1144			return 0;
   1145		}
   1146	}
   1147
   1148	dev_err(&dbg_data->handle->pdev->dev, "unknown command(%d)\n",
   1149		dbg_data->cmd);
   1150	return -EINVAL;
   1151}
   1152
   1153static const struct hns3_dbg_func hns3_dbg_cmd_func[] = {
   1154	{
   1155		.cmd = HNAE3_DBG_CMD_QUEUE_MAP,
   1156		.dbg_dump = hns3_dbg_queue_map,
   1157	},
   1158	{
   1159		.cmd = HNAE3_DBG_CMD_DEV_INFO,
   1160		.dbg_dump = hns3_dbg_dev_info,
   1161	},
   1162	{
   1163		.cmd = HNAE3_DBG_CMD_TX_BD,
   1164		.dbg_dump_bd = hns3_dbg_tx_bd_info,
   1165	},
   1166	{
   1167		.cmd = HNAE3_DBG_CMD_RX_BD,
   1168		.dbg_dump_bd = hns3_dbg_rx_bd_info,
   1169	},
   1170	{
   1171		.cmd = HNAE3_DBG_CMD_RX_QUEUE_INFO,
   1172		.dbg_dump = hns3_dbg_rx_queue_info,
   1173	},
   1174	{
   1175		.cmd = HNAE3_DBG_CMD_TX_QUEUE_INFO,
   1176		.dbg_dump = hns3_dbg_tx_queue_info,
   1177	},
   1178	{
   1179		.cmd = HNAE3_DBG_CMD_PAGE_POOL_INFO,
   1180		.dbg_dump = hns3_dbg_page_pool_info,
   1181	},
   1182	{
   1183		.cmd = HNAE3_DBG_CMD_COAL_INFO,
   1184		.dbg_dump = hns3_dbg_coal_info,
   1185	},
   1186};
   1187
   1188static int hns3_dbg_read_cmd(struct hns3_dbg_data *dbg_data,
   1189			     enum hnae3_dbg_cmd cmd, char *buf, int len)
   1190{
   1191	const struct hnae3_ae_ops *ops = dbg_data->handle->ae_algo->ops;
   1192	const struct hns3_dbg_func *cmd_func;
   1193	u32 i;
   1194
   1195	for (i = 0; i < ARRAY_SIZE(hns3_dbg_cmd_func); i++) {
   1196		if (cmd == hns3_dbg_cmd_func[i].cmd) {
   1197			cmd_func = &hns3_dbg_cmd_func[i];
   1198			if (cmd_func->dbg_dump)
   1199				return cmd_func->dbg_dump(dbg_data->handle, buf,
   1200							  len);
   1201			else
   1202				return cmd_func->dbg_dump_bd(dbg_data, buf,
   1203							     len);
   1204		}
   1205	}
   1206
   1207	if (!ops->dbg_read_cmd)
   1208		return -EOPNOTSUPP;
   1209
   1210	return ops->dbg_read_cmd(dbg_data->handle, cmd, buf, len);
   1211}
   1212
   1213static ssize_t hns3_dbg_read(struct file *filp, char __user *buffer,
   1214			     size_t count, loff_t *ppos)
   1215{
   1216	struct hns3_dbg_data *dbg_data = filp->private_data;
   1217	struct hnae3_handle *handle = dbg_data->handle;
   1218	struct hns3_nic_priv *priv = handle->priv;
   1219	ssize_t size = 0;
   1220	char **save_buf;
   1221	char *read_buf;
   1222	u32 index;
   1223	int ret;
   1224
   1225	ret = hns3_dbg_get_cmd_index(dbg_data, &index);
   1226	if (ret)
   1227		return ret;
   1228
   1229	mutex_lock(&handle->dbgfs_lock);
   1230	save_buf = &handle->dbgfs_buf[index];
   1231
   1232	if (!test_bit(HNS3_NIC_STATE_INITED, &priv->state) ||
   1233	    test_bit(HNS3_NIC_STATE_RESETTING, &priv->state)) {
   1234		ret = -EBUSY;
   1235		goto out;
   1236	}
   1237
   1238	if (*save_buf) {
   1239		read_buf = *save_buf;
   1240	} else {
   1241		read_buf = kvzalloc(hns3_dbg_cmd[index].buf_len, GFP_KERNEL);
   1242		if (!read_buf) {
   1243			ret = -ENOMEM;
   1244			goto out;
   1245		}
   1246
   1247		/* save the buffer addr until the last read operation */
   1248		*save_buf = read_buf;
   1249
   1250		/* get data ready for the first time to read */
   1251		ret = hns3_dbg_read_cmd(dbg_data, hns3_dbg_cmd[index].cmd,
   1252					read_buf, hns3_dbg_cmd[index].buf_len);
   1253		if (ret)
   1254			goto out;
   1255	}
   1256
   1257	size = simple_read_from_buffer(buffer, count, ppos, read_buf,
   1258				       strlen(read_buf));
   1259	if (size > 0) {
   1260		mutex_unlock(&handle->dbgfs_lock);
   1261		return size;
   1262	}
   1263
   1264out:
   1265	/* free the buffer for the last read operation */
   1266	if (*save_buf) {
   1267		kvfree(*save_buf);
   1268		*save_buf = NULL;
   1269	}
   1270
   1271	mutex_unlock(&handle->dbgfs_lock);
   1272	return ret;
   1273}
   1274
   1275static const struct file_operations hns3_dbg_fops = {
   1276	.owner = THIS_MODULE,
   1277	.open  = simple_open,
   1278	.read  = hns3_dbg_read,
   1279};
   1280
   1281static int hns3_dbg_bd_file_init(struct hnae3_handle *handle, u32 cmd)
   1282{
   1283	struct dentry *entry_dir;
   1284	struct hns3_dbg_data *data;
   1285	u16 max_queue_num;
   1286	unsigned int i;
   1287
   1288	entry_dir = hns3_dbg_dentry[hns3_dbg_cmd[cmd].dentry].dentry;
   1289	max_queue_num = hns3_get_max_available_channels(handle);
   1290	data = devm_kzalloc(&handle->pdev->dev, max_queue_num * sizeof(*data),
   1291			    GFP_KERNEL);
   1292	if (!data)
   1293		return -ENOMEM;
   1294
   1295	for (i = 0; i < max_queue_num; i++) {
   1296		char name[HNS3_DBG_FILE_NAME_LEN];
   1297
   1298		data[i].handle = handle;
   1299		data[i].cmd = hns3_dbg_cmd[cmd].cmd;
   1300		data[i].qid = i;
   1301		sprintf(name, "%s%u", hns3_dbg_cmd[cmd].name, i);
   1302		debugfs_create_file(name, 0400, entry_dir, &data[i],
   1303				    &hns3_dbg_fops);
   1304	}
   1305
   1306	return 0;
   1307}
   1308
   1309static int
   1310hns3_dbg_common_file_init(struct hnae3_handle *handle, u32 cmd)
   1311{
   1312	struct hns3_dbg_data *data;
   1313	struct dentry *entry_dir;
   1314
   1315	data = devm_kzalloc(&handle->pdev->dev, sizeof(*data), GFP_KERNEL);
   1316	if (!data)
   1317		return -ENOMEM;
   1318
   1319	data->handle = handle;
   1320	data->cmd = hns3_dbg_cmd[cmd].cmd;
   1321	entry_dir = hns3_dbg_dentry[hns3_dbg_cmd[cmd].dentry].dentry;
   1322	debugfs_create_file(hns3_dbg_cmd[cmd].name, 0400, entry_dir,
   1323			    data, &hns3_dbg_fops);
   1324
   1325	return 0;
   1326}
   1327
   1328int hns3_dbg_init(struct hnae3_handle *handle)
   1329{
   1330	struct hnae3_ae_dev *ae_dev = pci_get_drvdata(handle->pdev);
   1331	const char *name = pci_name(handle->pdev);
   1332	int ret;
   1333	u32 i;
   1334
   1335	handle->dbgfs_buf = devm_kcalloc(&handle->pdev->dev,
   1336					 ARRAY_SIZE(hns3_dbg_cmd),
   1337					 sizeof(*handle->dbgfs_buf),
   1338					 GFP_KERNEL);
   1339	if (!handle->dbgfs_buf)
   1340		return -ENOMEM;
   1341
   1342	hns3_dbg_dentry[HNS3_DBG_DENTRY_COMMON].dentry =
   1343				debugfs_create_dir(name, hns3_dbgfs_root);
   1344	handle->hnae3_dbgfs = hns3_dbg_dentry[HNS3_DBG_DENTRY_COMMON].dentry;
   1345
   1346	for (i = 0; i < HNS3_DBG_DENTRY_COMMON; i++)
   1347		hns3_dbg_dentry[i].dentry =
   1348			debugfs_create_dir(hns3_dbg_dentry[i].name,
   1349					   handle->hnae3_dbgfs);
   1350
   1351	mutex_init(&handle->dbgfs_lock);
   1352
   1353	for (i = 0; i < ARRAY_SIZE(hns3_dbg_cmd); i++) {
   1354		if ((hns3_dbg_cmd[i].cmd == HNAE3_DBG_CMD_TM_NODES &&
   1355		     ae_dev->dev_version <= HNAE3_DEVICE_VERSION_V2) ||
   1356		    (hns3_dbg_cmd[i].cmd == HNAE3_DBG_CMD_PTP_INFO &&
   1357		     !test_bit(HNAE3_DEV_SUPPORT_PTP_B, ae_dev->caps)))
   1358			continue;
   1359
   1360		if (!hns3_dbg_cmd[i].init) {
   1361			dev_err(&handle->pdev->dev,
   1362				"cmd %s lack of init func\n",
   1363				hns3_dbg_cmd[i].name);
   1364			ret = -EINVAL;
   1365			goto out;
   1366		}
   1367
   1368		ret = hns3_dbg_cmd[i].init(handle, i);
   1369		if (ret) {
   1370			dev_err(&handle->pdev->dev, "failed to init cmd %s\n",
   1371				hns3_dbg_cmd[i].name);
   1372			goto out;
   1373		}
   1374	}
   1375
   1376	return 0;
   1377
   1378out:
   1379	mutex_destroy(&handle->dbgfs_lock);
   1380	debugfs_remove_recursive(handle->hnae3_dbgfs);
   1381	handle->hnae3_dbgfs = NULL;
   1382	return ret;
   1383}
   1384
   1385void hns3_dbg_uninit(struct hnae3_handle *handle)
   1386{
   1387	u32 i;
   1388
   1389	for (i = 0; i < ARRAY_SIZE(hns3_dbg_cmd); i++)
   1390		if (handle->dbgfs_buf[i]) {
   1391			kvfree(handle->dbgfs_buf[i]);
   1392			handle->dbgfs_buf[i] = NULL;
   1393		}
   1394
   1395	mutex_destroy(&handle->dbgfs_lock);
   1396	debugfs_remove_recursive(handle->hnae3_dbgfs);
   1397	handle->hnae3_dbgfs = NULL;
   1398}
   1399
   1400void hns3_dbg_register_debugfs(const char *debugfs_dir_name)
   1401{
   1402	hns3_dbgfs_root = debugfs_create_dir(debugfs_dir_name, NULL);
   1403}
   1404
   1405void hns3_dbg_unregister_debugfs(void)
   1406{
   1407	debugfs_remove_recursive(hns3_dbgfs_root);
   1408	hns3_dbgfs_root = NULL;
   1409}