1/*
2 * QLogic qlcnic NIC Driver
3 * Copyright (c) 2009-2013 QLogic Corporation
4 *
5 * See LICENSE.qlcnic for copyright and licensing details.
6 */
7
8#include <linux/types.h>
9#include <linux/delay.h>
10#include <linux/pci.h>
11#include <linux/io.h>
12#include <linux/netdevice.h>
13#include <linux/ethtool.h>
14
15#include "qlcnic.h"
16
17struct qlcnic_stats {
18	char stat_string[ETH_GSTRING_LEN];
19	int sizeof_stat;
20	int stat_offset;
21};
22
23#define QLC_SIZEOF(m) FIELD_SIZEOF(struct qlcnic_adapter, m)
24#define QLC_OFF(m) offsetof(struct qlcnic_adapter, m)
25static const u32 qlcnic_fw_dump_level[] = {
26	0x3, 0x7, 0xf, 0x1f, 0x3f, 0x7f, 0xff
27};
28
29static const struct qlcnic_stats qlcnic_gstrings_stats[] = {
30	{"xmit_on", QLC_SIZEOF(stats.xmit_on), QLC_OFF(stats.xmit_on)},
31	{"xmit_off", QLC_SIZEOF(stats.xmit_off), QLC_OFF(stats.xmit_off)},
32	{"xmit_called", QLC_SIZEOF(stats.xmitcalled),
33	 QLC_OFF(stats.xmitcalled)},
34	{"xmit_finished", QLC_SIZEOF(stats.xmitfinished),
35	 QLC_OFF(stats.xmitfinished)},
36	{"tx dma map error", QLC_SIZEOF(stats.tx_dma_map_error),
37	 QLC_OFF(stats.tx_dma_map_error)},
38	{"tx_bytes", QLC_SIZEOF(stats.txbytes), QLC_OFF(stats.txbytes)},
39	{"tx_dropped", QLC_SIZEOF(stats.txdropped), QLC_OFF(stats.txdropped)},
40	{"rx dma map error", QLC_SIZEOF(stats.rx_dma_map_error),
41	 QLC_OFF(stats.rx_dma_map_error)},
42	{"rx_pkts", QLC_SIZEOF(stats.rx_pkts), QLC_OFF(stats.rx_pkts)},
43	{"rx_bytes", QLC_SIZEOF(stats.rxbytes), QLC_OFF(stats.rxbytes)},
44	{"rx_dropped", QLC_SIZEOF(stats.rxdropped), QLC_OFF(stats.rxdropped)},
45	{"null rxbuf", QLC_SIZEOF(stats.null_rxbuf), QLC_OFF(stats.null_rxbuf)},
46	{"csummed", QLC_SIZEOF(stats.csummed), QLC_OFF(stats.csummed)},
47	{"lro_pkts", QLC_SIZEOF(stats.lro_pkts), QLC_OFF(stats.lro_pkts)},
48	{"lrobytes", QLC_SIZEOF(stats.lrobytes), QLC_OFF(stats.lrobytes)},
49	{"lso_frames", QLC_SIZEOF(stats.lso_frames), QLC_OFF(stats.lso_frames)},
50	{"encap_lso_frames", QLC_SIZEOF(stats.encap_lso_frames),
51	 QLC_OFF(stats.encap_lso_frames)},
52	{"encap_tx_csummed", QLC_SIZEOF(stats.encap_tx_csummed),
53	 QLC_OFF(stats.encap_tx_csummed)},
54	{"encap_rx_csummed", QLC_SIZEOF(stats.encap_rx_csummed),
55	 QLC_OFF(stats.encap_rx_csummed)},
56	{"skb_alloc_failure", QLC_SIZEOF(stats.skb_alloc_failure),
57	 QLC_OFF(stats.skb_alloc_failure)},
58	{"mac_filter_limit_overrun", QLC_SIZEOF(stats.mac_filter_limit_overrun),
59	 QLC_OFF(stats.mac_filter_limit_overrun)},
60	{"spurious intr", QLC_SIZEOF(stats.spurious_intr),
61	 QLC_OFF(stats.spurious_intr)},
62
63};
64
65static const char qlcnic_device_gstrings_stats[][ETH_GSTRING_LEN] = {
66	"tx unicast frames",
67	"tx multicast frames",
68	"tx broadcast frames",
69	"tx dropped frames",
70	"tx errors",
71	"tx local frames",
72	"tx numbytes",
73	"rx unicast frames",
74	"rx multicast frames",
75	"rx broadcast frames",
76	"rx dropped frames",
77	"rx errors",
78	"rx local frames",
79	"rx numbytes",
80};
81
82static const char qlcnic_83xx_tx_stats_strings[][ETH_GSTRING_LEN] = {
83	"ctx_tx_bytes",
84	"ctx_tx_pkts",
85	"ctx_tx_errors",
86	"ctx_tx_dropped_pkts",
87	"ctx_tx_num_buffers",
88};
89
90static const char qlcnic_83xx_mac_stats_strings[][ETH_GSTRING_LEN] = {
91	"mac_tx_frames",
92	"mac_tx_bytes",
93	"mac_tx_mcast_pkts",
94	"mac_tx_bcast_pkts",
95	"mac_tx_pause_cnt",
96	"mac_tx_ctrl_pkt",
97	"mac_tx_lt_64b_pkts",
98	"mac_tx_lt_127b_pkts",
99	"mac_tx_lt_255b_pkts",
100	"mac_tx_lt_511b_pkts",
101	"mac_tx_lt_1023b_pkts",
102	"mac_tx_lt_1518b_pkts",
103	"mac_tx_gt_1518b_pkts",
104	"mac_rx_frames",
105	"mac_rx_bytes",
106	"mac_rx_mcast_pkts",
107	"mac_rx_bcast_pkts",
108	"mac_rx_pause_cnt",
109	"mac_rx_ctrl_pkt",
110	"mac_rx_lt_64b_pkts",
111	"mac_rx_lt_127b_pkts",
112	"mac_rx_lt_255b_pkts",
113	"mac_rx_lt_511b_pkts",
114	"mac_rx_lt_1023b_pkts",
115	"mac_rx_lt_1518b_pkts",
116	"mac_rx_gt_1518b_pkts",
117	"mac_rx_length_error",
118	"mac_rx_length_small",
119	"mac_rx_length_large",
120	"mac_rx_jabber",
121	"mac_rx_dropped",
122	"mac_crc_error",
123	"mac_align_error",
124	"eswitch_frames",
125	"eswitch_bytes",
126	"eswitch_multicast_frames",
127	"eswitch_broadcast_frames",
128	"eswitch_unicast_frames",
129	"eswitch_error_free_frames",
130	"eswitch_error_free_bytes",
131};
132
133#define QLCNIC_STATS_LEN	ARRAY_SIZE(qlcnic_gstrings_stats)
134
135static const char qlcnic_tx_queue_stats_strings[][ETH_GSTRING_LEN] = {
136	"xmit_on",
137	"xmit_off",
138	"xmit_called",
139	"xmit_finished",
140	"tx_bytes",
141};
142
143#define QLCNIC_TX_STATS_LEN	ARRAY_SIZE(qlcnic_tx_queue_stats_strings)
144
145static const char qlcnic_83xx_rx_stats_strings[][ETH_GSTRING_LEN] = {
146	"ctx_rx_bytes",
147	"ctx_rx_pkts",
148	"ctx_lro_pkt_cnt",
149	"ctx_ip_csum_error",
150	"ctx_rx_pkts_wo_ctx",
151	"ctx_rx_pkts_drop_wo_sds_on_card",
152	"ctx_rx_pkts_drop_wo_sds_on_host",
153	"ctx_rx_osized_pkts",
154	"ctx_rx_pkts_dropped_wo_rds",
155	"ctx_rx_unexpected_mcast_pkts",
156	"ctx_invalid_mac_address",
157	"ctx_rx_rds_ring_prim_attempted",
158	"ctx_rx_rds_ring_prim_success",
159	"ctx_num_lro_flows_added",
160	"ctx_num_lro_flows_removed",
161	"ctx_num_lro_flows_active",
162	"ctx_pkts_dropped_unknown",
163};
164
165static const char qlcnic_gstrings_test[][ETH_GSTRING_LEN] = {
166	"Register_Test_on_offline",
167	"Link_Test_on_offline",
168	"Interrupt_Test_offline",
169	"Internal_Loopback_offline",
170	"External_Loopback_offline",
171	"EEPROM_Test_offline"
172};
173
174#define QLCNIC_TEST_LEN	ARRAY_SIZE(qlcnic_gstrings_test)
175
176static inline int qlcnic_82xx_statistics(struct qlcnic_adapter *adapter)
177{
178	return ARRAY_SIZE(qlcnic_gstrings_stats) +
179	       ARRAY_SIZE(qlcnic_83xx_mac_stats_strings) +
180	       QLCNIC_TX_STATS_LEN * adapter->drv_tx_rings;
181}
182
183static inline int qlcnic_83xx_statistics(struct qlcnic_adapter *adapter)
184{
185	return ARRAY_SIZE(qlcnic_gstrings_stats) +
186	       ARRAY_SIZE(qlcnic_83xx_tx_stats_strings) +
187	       ARRAY_SIZE(qlcnic_83xx_mac_stats_strings) +
188	       ARRAY_SIZE(qlcnic_83xx_rx_stats_strings) +
189	       QLCNIC_TX_STATS_LEN * adapter->drv_tx_rings;
190}
191
192static int qlcnic_dev_statistics_len(struct qlcnic_adapter *adapter)
193{
194	int len = -1;
195
196	if (qlcnic_82xx_check(adapter)) {
197		len = qlcnic_82xx_statistics(adapter);
198		if (adapter->flags & QLCNIC_ESWITCH_ENABLED)
199			len += ARRAY_SIZE(qlcnic_device_gstrings_stats);
200	} else if (qlcnic_83xx_check(adapter)) {
201		len = qlcnic_83xx_statistics(adapter);
202	}
203
204	return len;
205}
206
207#define	QLCNIC_TX_INTR_NOT_CONFIGURED	0X78563412
208
209#define QLCNIC_MAX_EEPROM_LEN   1024
210
211static const u32 diag_registers[] = {
212	QLCNIC_CMDPEG_STATE,
213	QLCNIC_RCVPEG_STATE,
214	QLCNIC_FW_CAPABILITIES,
215	QLCNIC_CRB_DRV_ACTIVE,
216	QLCNIC_CRB_DEV_STATE,
217	QLCNIC_CRB_DRV_STATE,
218	QLCNIC_CRB_DRV_SCRATCH,
219	QLCNIC_CRB_DEV_PARTITION_INFO,
220	QLCNIC_CRB_DRV_IDC_VER,
221	QLCNIC_PEG_ALIVE_COUNTER,
222	QLCNIC_PEG_HALT_STATUS1,
223	QLCNIC_PEG_HALT_STATUS2,
224	-1
225};
226
227
228static const u32 ext_diag_registers[] = {
229	CRB_XG_STATE_P3P,
230	ISR_INT_STATE_REG,
231	QLCNIC_CRB_PEG_NET_0+0x3c,
232	QLCNIC_CRB_PEG_NET_1+0x3c,
233	QLCNIC_CRB_PEG_NET_2+0x3c,
234	QLCNIC_CRB_PEG_NET_4+0x3c,
235	-1
236};
237
238#define QLCNIC_MGMT_API_VERSION	3
239#define QLCNIC_ETHTOOL_REGS_VER	4
240
241static inline int qlcnic_get_ring_regs_len(struct qlcnic_adapter *adapter)
242{
243	int ring_regs_cnt = (adapter->drv_tx_rings * 5) +
244			    (adapter->max_rds_rings * 2) +
245			    (adapter->drv_sds_rings * 3) + 5;
246	return ring_regs_cnt * sizeof(u32);
247}
248
249static int qlcnic_get_regs_len(struct net_device *dev)
250{
251	struct qlcnic_adapter *adapter = netdev_priv(dev);
252	u32 len;
253
254	if (qlcnic_83xx_check(adapter))
255		len = qlcnic_83xx_get_regs_len(adapter);
256	else
257		len = sizeof(ext_diag_registers) + sizeof(diag_registers);
258
259	len += ((QLCNIC_DEV_INFO_SIZE + 2) * sizeof(u32));
260	len += qlcnic_get_ring_regs_len(adapter);
261	return len;
262}
263
264static int qlcnic_get_eeprom_len(struct net_device *dev)
265{
266	return QLCNIC_FLASH_TOTAL_SIZE;
267}
268
269static void
270qlcnic_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo *drvinfo)
271{
272	struct qlcnic_adapter *adapter = netdev_priv(dev);
273	u32 fw_major, fw_minor, fw_build;
274	fw_major = QLC_SHARED_REG_RD32(adapter, QLCNIC_FW_VERSION_MAJOR);
275	fw_minor = QLC_SHARED_REG_RD32(adapter, QLCNIC_FW_VERSION_MINOR);
276	fw_build = QLC_SHARED_REG_RD32(adapter, QLCNIC_FW_VERSION_SUB);
277	snprintf(drvinfo->fw_version, sizeof(drvinfo->fw_version),
278		"%d.%d.%d", fw_major, fw_minor, fw_build);
279
280	strlcpy(drvinfo->bus_info, pci_name(adapter->pdev),
281		sizeof(drvinfo->bus_info));
282	strlcpy(drvinfo->driver, qlcnic_driver_name, sizeof(drvinfo->driver));
283	strlcpy(drvinfo->version, QLCNIC_LINUX_VERSIONID,
284		sizeof(drvinfo->version));
285}
286
287static int qlcnic_82xx_get_settings(struct qlcnic_adapter *adapter,
288				    struct ethtool_cmd *ecmd)
289{
290	struct qlcnic_hardware_context *ahw = adapter->ahw;
291	u32 speed, reg;
292	int check_sfp_module = 0, err = 0;
293	u16 pcifn = ahw->pci_func;
294
295	/* read which mode */
296	if (adapter->ahw->port_type == QLCNIC_GBE) {
297		ecmd->supported = (SUPPORTED_10baseT_Half |
298				   SUPPORTED_10baseT_Full |
299				   SUPPORTED_100baseT_Half |
300				   SUPPORTED_100baseT_Full |
301				   SUPPORTED_1000baseT_Half |
302				   SUPPORTED_1000baseT_Full);
303
304		ecmd->advertising = (ADVERTISED_100baseT_Half |
305				     ADVERTISED_100baseT_Full |
306				     ADVERTISED_1000baseT_Half |
307				     ADVERTISED_1000baseT_Full);
308
309		ethtool_cmd_speed_set(ecmd, adapter->ahw->link_speed);
310		ecmd->duplex = adapter->ahw->link_duplex;
311		ecmd->autoneg = adapter->ahw->link_autoneg;
312
313	} else if (adapter->ahw->port_type == QLCNIC_XGBE) {
314		u32 val = 0;
315		val = QLCRD32(adapter, QLCNIC_PORT_MODE_ADDR, &err);
316
317		if (val == QLCNIC_PORT_MODE_802_3_AP) {
318			ecmd->supported = SUPPORTED_1000baseT_Full;
319			ecmd->advertising = ADVERTISED_1000baseT_Full;
320		} else {
321			ecmd->supported = SUPPORTED_10000baseT_Full;
322			ecmd->advertising = ADVERTISED_10000baseT_Full;
323		}
324
325		if (netif_running(adapter->netdev) && ahw->has_link_events) {
326			if (ahw->linkup) {
327				reg = QLCRD32(adapter,
328					      P3P_LINK_SPEED_REG(pcifn), &err);
329				speed = P3P_LINK_SPEED_VAL(pcifn, reg);
330				ahw->link_speed = speed * P3P_LINK_SPEED_MHZ;
331			}
332
333			ethtool_cmd_speed_set(ecmd, ahw->link_speed);
334			ecmd->autoneg = ahw->link_autoneg;
335			ecmd->duplex = ahw->link_duplex;
336			goto skip;
337		}
338
339		ethtool_cmd_speed_set(ecmd, SPEED_UNKNOWN);
340		ecmd->duplex = DUPLEX_UNKNOWN;
341		ecmd->autoneg = AUTONEG_DISABLE;
342	} else
343		return -EIO;
344
345skip:
346	ecmd->phy_address = adapter->ahw->physical_port;
347	ecmd->transceiver = XCVR_EXTERNAL;
348
349	switch (adapter->ahw->board_type) {
350	case QLCNIC_BRDTYPE_P3P_REF_QG:
351	case QLCNIC_BRDTYPE_P3P_4_GB:
352	case QLCNIC_BRDTYPE_P3P_4_GB_MM:
353
354		ecmd->supported |= SUPPORTED_Autoneg;
355		ecmd->advertising |= ADVERTISED_Autoneg;
356	case QLCNIC_BRDTYPE_P3P_10G_CX4:
357	case QLCNIC_BRDTYPE_P3P_10G_CX4_LP:
358	case QLCNIC_BRDTYPE_P3P_10000_BASE_T:
359		ecmd->supported |= SUPPORTED_TP;
360		ecmd->advertising |= ADVERTISED_TP;
361		ecmd->port = PORT_TP;
362		ecmd->autoneg =  adapter->ahw->link_autoneg;
363		break;
364	case QLCNIC_BRDTYPE_P3P_IMEZ:
365	case QLCNIC_BRDTYPE_P3P_XG_LOM:
366	case QLCNIC_BRDTYPE_P3P_HMEZ:
367		ecmd->supported |= SUPPORTED_MII;
368		ecmd->advertising |= ADVERTISED_MII;
369		ecmd->port = PORT_MII;
370		ecmd->autoneg = AUTONEG_DISABLE;
371		break;
372	case QLCNIC_BRDTYPE_P3P_10G_SFP_PLUS:
373	case QLCNIC_BRDTYPE_P3P_10G_SFP_CT:
374	case QLCNIC_BRDTYPE_P3P_10G_SFP_QT:
375		ecmd->advertising |= ADVERTISED_TP;
376		ecmd->supported |= SUPPORTED_TP;
377		check_sfp_module = netif_running(adapter->netdev) &&
378				   ahw->has_link_events;
379	case QLCNIC_BRDTYPE_P3P_10G_XFP:
380		ecmd->supported |= SUPPORTED_FIBRE;
381		ecmd->advertising |= ADVERTISED_FIBRE;
382		ecmd->port = PORT_FIBRE;
383		ecmd->autoneg = AUTONEG_DISABLE;
384		break;
385	case QLCNIC_BRDTYPE_P3P_10G_TP:
386		if (adapter->ahw->port_type == QLCNIC_XGBE) {
387			ecmd->autoneg = AUTONEG_DISABLE;
388			ecmd->supported |= (SUPPORTED_FIBRE | SUPPORTED_TP);
389			ecmd->advertising |=
390				(ADVERTISED_FIBRE | ADVERTISED_TP);
391			ecmd->port = PORT_FIBRE;
392			check_sfp_module = netif_running(adapter->netdev) &&
393					   ahw->has_link_events;
394		} else {
395			ecmd->autoneg = AUTONEG_ENABLE;
396			ecmd->supported |= (SUPPORTED_TP | SUPPORTED_Autoneg);
397			ecmd->advertising |=
398				(ADVERTISED_TP | ADVERTISED_Autoneg);
399			ecmd->port = PORT_TP;
400		}
401		break;
402	default:
403		dev_err(&adapter->pdev->dev, "Unsupported board model %d\n",
404			adapter->ahw->board_type);
405		return -EIO;
406	}
407
408	if (check_sfp_module) {
409		switch (adapter->ahw->module_type) {
410		case LINKEVENT_MODULE_OPTICAL_UNKNOWN:
411		case LINKEVENT_MODULE_OPTICAL_SRLR:
412		case LINKEVENT_MODULE_OPTICAL_LRM:
413		case LINKEVENT_MODULE_OPTICAL_SFP_1G:
414			ecmd->port = PORT_FIBRE;
415			break;
416		case LINKEVENT_MODULE_TWINAX_UNSUPPORTED_CABLE:
417		case LINKEVENT_MODULE_TWINAX_UNSUPPORTED_CABLELEN:
418		case LINKEVENT_MODULE_TWINAX:
419			ecmd->port = PORT_TP;
420			break;
421		default:
422			ecmd->port = PORT_OTHER;
423		}
424	}
425
426	return 0;
427}
428
429static int qlcnic_get_settings(struct net_device *dev,
430			       struct ethtool_cmd *ecmd)
431{
432	struct qlcnic_adapter *adapter = netdev_priv(dev);
433
434	if (qlcnic_82xx_check(adapter))
435		return qlcnic_82xx_get_settings(adapter, ecmd);
436	else if (qlcnic_83xx_check(adapter))
437		return qlcnic_83xx_get_settings(adapter, ecmd);
438
439	return -EIO;
440}
441
442
443static int qlcnic_set_port_config(struct qlcnic_adapter *adapter,
444				  struct ethtool_cmd *ecmd)
445{
446	u32 ret = 0, config = 0;
447	/* read which mode */
448	if (ecmd->duplex)
449		config |= 0x1;
450
451	if (ecmd->autoneg)
452		config |= 0x2;
453
454	switch (ethtool_cmd_speed(ecmd)) {
455	case SPEED_10:
456		config |= (0 << 8);
457		break;
458	case SPEED_100:
459		config |= (1 << 8);
460		break;
461	case SPEED_1000:
462		config |= (10 << 8);
463		break;
464	default:
465		return -EIO;
466	}
467
468	ret = qlcnic_fw_cmd_set_port(adapter, config);
469
470	if (ret == QLCNIC_RCODE_NOT_SUPPORTED)
471		return -EOPNOTSUPP;
472	else if (ret)
473		return -EIO;
474	return ret;
475}
476
477static int qlcnic_set_settings(struct net_device *dev, struct ethtool_cmd *ecmd)
478{
479	u32 ret = 0;
480	struct qlcnic_adapter *adapter = netdev_priv(dev);
481
482	if (adapter->ahw->port_type != QLCNIC_GBE)
483		return -EOPNOTSUPP;
484
485	if (qlcnic_83xx_check(adapter))
486		ret = qlcnic_83xx_set_settings(adapter, ecmd);
487	else
488		ret = qlcnic_set_port_config(adapter, ecmd);
489
490	if (!ret)
491		return ret;
492
493	adapter->ahw->link_speed = ethtool_cmd_speed(ecmd);
494	adapter->ahw->link_duplex = ecmd->duplex;
495	adapter->ahw->link_autoneg = ecmd->autoneg;
496
497	if (!netif_running(dev))
498		return 0;
499
500	dev->netdev_ops->ndo_stop(dev);
501	return dev->netdev_ops->ndo_open(dev);
502}
503
504static int qlcnic_82xx_get_registers(struct qlcnic_adapter *adapter,
505				     u32 *regs_buff)
506{
507	int i, j = 0, err = 0;
508
509	for (i = QLCNIC_DEV_INFO_SIZE + 1; diag_registers[j] != -1; j++, i++)
510		regs_buff[i] = QLC_SHARED_REG_RD32(adapter, diag_registers[j]);
511	j = 0;
512	while (ext_diag_registers[j] != -1)
513		regs_buff[i++] = QLCRD32(adapter, ext_diag_registers[j++],
514					 &err);
515	return i;
516}
517
518static void
519qlcnic_get_regs(struct net_device *dev, struct ethtool_regs *regs, void *p)
520{
521	struct qlcnic_adapter *adapter = netdev_priv(dev);
522	struct qlcnic_recv_context *recv_ctx = adapter->recv_ctx;
523	struct qlcnic_host_sds_ring *sds_ring;
524	struct qlcnic_host_rds_ring *rds_rings;
525	struct qlcnic_host_tx_ring *tx_ring;
526	u32 *regs_buff = p;
527	int ring, i = 0;
528
529	memset(p, 0, qlcnic_get_regs_len(dev));
530
531	regs->version = (QLCNIC_ETHTOOL_REGS_VER << 24) |
532		(adapter->ahw->revision_id << 16) | (adapter->pdev)->device;
533
534	regs_buff[0] = (0xcafe0000 | (QLCNIC_DEV_INFO_SIZE & 0xffff));
535	regs_buff[1] = QLCNIC_MGMT_API_VERSION;
536
537	if (adapter->ahw->capabilities & QLC_83XX_ESWITCH_CAPABILITY)
538		regs_buff[2] = adapter->ahw->max_vnic_func;
539
540	if (qlcnic_82xx_check(adapter))
541		i = qlcnic_82xx_get_registers(adapter, regs_buff);
542	else
543		i = qlcnic_83xx_get_registers(adapter, regs_buff);
544
545	if (!test_bit(__QLCNIC_DEV_UP, &adapter->state))
546		return;
547
548	/* Marker btw regs and TX ring count */
549	regs_buff[i++] = 0xFFEFCDAB;
550
551	regs_buff[i++] = adapter->drv_tx_rings; /* No. of TX ring */
552	for (ring = 0; ring < adapter->drv_tx_rings; ring++) {
553		tx_ring = &adapter->tx_ring[ring];
554		regs_buff[i++] = le32_to_cpu(*(tx_ring->hw_consumer));
555		regs_buff[i++] = tx_ring->sw_consumer;
556		regs_buff[i++] = readl(tx_ring->crb_cmd_producer);
557		regs_buff[i++] = tx_ring->producer;
558		if (tx_ring->crb_intr_mask)
559			regs_buff[i++] = readl(tx_ring->crb_intr_mask);
560		else
561			regs_buff[i++] = QLCNIC_TX_INTR_NOT_CONFIGURED;
562	}
563
564	regs_buff[i++] = adapter->max_rds_rings; /* No. of RX ring */
565	for (ring = 0; ring < adapter->max_rds_rings; ring++) {
566		rds_rings = &recv_ctx->rds_rings[ring];
567		regs_buff[i++] = readl(rds_rings->crb_rcv_producer);
568		regs_buff[i++] = rds_rings->producer;
569	}
570
571	regs_buff[i++] = adapter->drv_sds_rings; /* No. of SDS ring */
572	for (ring = 0; ring < adapter->drv_sds_rings; ring++) {
573		sds_ring = &(recv_ctx->sds_rings[ring]);
574		regs_buff[i++] = readl(sds_ring->crb_sts_consumer);
575		regs_buff[i++] = sds_ring->consumer;
576		regs_buff[i++] = readl(sds_ring->crb_intr_mask);
577	}
578}
579
580static u32 qlcnic_test_link(struct net_device *dev)
581{
582	struct qlcnic_adapter *adapter = netdev_priv(dev);
583	int err = 0;
584	u32 val;
585
586	if (qlcnic_83xx_check(adapter)) {
587		val = qlcnic_83xx_test_link(adapter);
588		return (val & 1) ? 0 : 1;
589	}
590	val = QLCRD32(adapter, CRB_XG_STATE_P3P, &err);
591	if (err == -EIO)
592		return err;
593	val = XG_LINK_STATE_P3P(adapter->ahw->pci_func, val);
594	return (val == XG_LINK_UP_P3P) ? 0 : 1;
595}
596
597static int
598qlcnic_get_eeprom(struct net_device *dev, struct ethtool_eeprom *eeprom,
599		      u8 *bytes)
600{
601	struct qlcnic_adapter *adapter = netdev_priv(dev);
602	int offset;
603	int ret = -1;
604
605	if (qlcnic_83xx_check(adapter))
606		return 0;
607	if (eeprom->len == 0)
608		return -EINVAL;
609
610	eeprom->magic = (adapter->pdev)->vendor |
611			((adapter->pdev)->device << 16);
612	offset = eeprom->offset;
613
614	if (qlcnic_82xx_check(adapter))
615		ret = qlcnic_rom_fast_read_words(adapter, offset, bytes,
616						 eeprom->len);
617	if (ret < 0)
618		return ret;
619
620	return 0;
621}
622
623static void
624qlcnic_get_ringparam(struct net_device *dev,
625		struct ethtool_ringparam *ring)
626{
627	struct qlcnic_adapter *adapter = netdev_priv(dev);
628
629	ring->rx_pending = adapter->num_rxd;
630	ring->rx_jumbo_pending = adapter->num_jumbo_rxd;
631	ring->tx_pending = adapter->num_txd;
632
633	ring->rx_max_pending = adapter->max_rxd;
634	ring->rx_jumbo_max_pending = adapter->max_jumbo_rxd;
635	ring->tx_max_pending = MAX_CMD_DESCRIPTORS;
636}
637
638static u32
639qlcnic_validate_ringparam(u32 val, u32 min, u32 max, char *r_name)
640{
641	u32 num_desc;
642	num_desc = max(val, min);
643	num_desc = min(num_desc, max);
644	num_desc = roundup_pow_of_two(num_desc);
645
646	if (val != num_desc) {
647		printk(KERN_INFO "%s: setting %s ring size %d instead of %d\n",
648		       qlcnic_driver_name, r_name, num_desc, val);
649	}
650
651	return num_desc;
652}
653
654static int
655qlcnic_set_ringparam(struct net_device *dev,
656		struct ethtool_ringparam *ring)
657{
658	struct qlcnic_adapter *adapter = netdev_priv(dev);
659	u16 num_rxd, num_jumbo_rxd, num_txd;
660
661	if (ring->rx_mini_pending)
662		return -EOPNOTSUPP;
663
664	num_rxd = qlcnic_validate_ringparam(ring->rx_pending,
665			MIN_RCV_DESCRIPTORS, adapter->max_rxd, "rx");
666
667	num_jumbo_rxd = qlcnic_validate_ringparam(ring->rx_jumbo_pending,
668			MIN_JUMBO_DESCRIPTORS, adapter->max_jumbo_rxd,
669						"rx jumbo");
670
671	num_txd = qlcnic_validate_ringparam(ring->tx_pending,
672			MIN_CMD_DESCRIPTORS, MAX_CMD_DESCRIPTORS, "tx");
673
674	if (num_rxd == adapter->num_rxd && num_txd == adapter->num_txd &&
675			num_jumbo_rxd == adapter->num_jumbo_rxd)
676		return 0;
677
678	adapter->num_rxd = num_rxd;
679	adapter->num_jumbo_rxd = num_jumbo_rxd;
680	adapter->num_txd = num_txd;
681
682	return qlcnic_reset_context(adapter);
683}
684
685static int qlcnic_validate_ring_count(struct qlcnic_adapter *adapter,
686				      u8 rx_ring, u8 tx_ring)
687{
688	if (rx_ring == 0 || tx_ring == 0)
689		return -EINVAL;
690
691	if (rx_ring != 0) {
692		if (rx_ring > adapter->max_sds_rings) {
693			netdev_err(adapter->netdev,
694				   "Invalid ring count, SDS ring count %d should not be greater than max %d driver sds rings.\n",
695				   rx_ring, adapter->max_sds_rings);
696			return -EINVAL;
697		}
698	}
699
700	 if (tx_ring != 0) {
701		if (tx_ring > adapter->max_tx_rings) {
702			netdev_err(adapter->netdev,
703				   "Invalid ring count, Tx ring count %d should not be greater than max %d driver Tx rings.\n",
704				   tx_ring, adapter->max_tx_rings);
705			return -EINVAL;
706		}
707	}
708
709	return 0;
710}
711
712static void qlcnic_get_channels(struct net_device *dev,
713		struct ethtool_channels *channel)
714{
715	struct qlcnic_adapter *adapter = netdev_priv(dev);
716
717	channel->max_rx = adapter->max_sds_rings;
718	channel->max_tx = adapter->max_tx_rings;
719	channel->rx_count = adapter->drv_sds_rings;
720	channel->tx_count = adapter->drv_tx_rings;
721}
722
723static int qlcnic_set_channels(struct net_device *dev,
724			       struct ethtool_channels *channel)
725{
726	struct qlcnic_adapter *adapter = netdev_priv(dev);
727	int err;
728
729	if (!(adapter->flags & QLCNIC_MSIX_ENABLED)) {
730		netdev_err(dev, "No RSS/TSS support in non MSI-X mode\n");
731		return -EINVAL;
732	}
733
734	if (channel->other_count || channel->combined_count)
735		return -EINVAL;
736
737	err = qlcnic_validate_ring_count(adapter, channel->rx_count,
738					 channel->tx_count);
739	if (err)
740		return err;
741
742	if (adapter->drv_sds_rings != channel->rx_count) {
743		err = qlcnic_validate_rings(adapter, channel->rx_count,
744					    QLCNIC_RX_QUEUE);
745		if (err) {
746			netdev_err(dev, "Unable to configure %u SDS rings\n",
747				   channel->rx_count);
748			return err;
749		}
750		adapter->drv_rss_rings = channel->rx_count;
751	}
752
753	if (adapter->drv_tx_rings != channel->tx_count) {
754		err = qlcnic_validate_rings(adapter, channel->tx_count,
755					    QLCNIC_TX_QUEUE);
756		if (err) {
757			netdev_err(dev, "Unable to configure %u Tx rings\n",
758				   channel->tx_count);
759			return err;
760		}
761		adapter->drv_tss_rings = channel->tx_count;
762	}
763
764	adapter->flags |= QLCNIC_TSS_RSS;
765
766	err = qlcnic_setup_rings(adapter);
767	netdev_info(dev, "Allocated %d SDS rings and %d Tx rings\n",
768		    adapter->drv_sds_rings, adapter->drv_tx_rings);
769
770	return err;
771}
772
773static void
774qlcnic_get_pauseparam(struct net_device *netdev,
775			  struct ethtool_pauseparam *pause)
776{
777	struct qlcnic_adapter *adapter = netdev_priv(netdev);
778	int port = adapter->ahw->physical_port;
779	int err = 0;
780	__u32 val;
781
782	if (qlcnic_83xx_check(adapter)) {
783		qlcnic_83xx_get_pauseparam(adapter, pause);
784		return;
785	}
786	if (adapter->ahw->port_type == QLCNIC_GBE) {
787		if ((port < 0) || (port > QLCNIC_NIU_MAX_GBE_PORTS))
788			return;
789		/* get flow control settings */
790		val = QLCRD32(adapter, QLCNIC_NIU_GB_MAC_CONFIG_0(port), &err);
791		if (err == -EIO)
792			return;
793		pause->rx_pause = qlcnic_gb_get_rx_flowctl(val);
794		val = QLCRD32(adapter, QLCNIC_NIU_GB_PAUSE_CTL, &err);
795		if (err == -EIO)
796			return;
797		switch (port) {
798		case 0:
799			pause->tx_pause = !(qlcnic_gb_get_gb0_mask(val));
800			break;
801		case 1:
802			pause->tx_pause = !(qlcnic_gb_get_gb1_mask(val));
803			break;
804		case 2:
805			pause->tx_pause = !(qlcnic_gb_get_gb2_mask(val));
806			break;
807		case 3:
808		default:
809			pause->tx_pause = !(qlcnic_gb_get_gb3_mask(val));
810			break;
811		}
812	} else if (adapter->ahw->port_type == QLCNIC_XGBE) {
813		if ((port < 0) || (port > QLCNIC_NIU_MAX_XG_PORTS))
814			return;
815		pause->rx_pause = 1;
816		val = QLCRD32(adapter, QLCNIC_NIU_XG_PAUSE_CTL, &err);
817		if (err == -EIO)
818			return;
819		if (port == 0)
820			pause->tx_pause = !(qlcnic_xg_get_xg0_mask(val));
821		else
822			pause->tx_pause = !(qlcnic_xg_get_xg1_mask(val));
823	} else {
824		dev_err(&netdev->dev, "Unknown board type: %x\n",
825					adapter->ahw->port_type);
826	}
827}
828
829static int
830qlcnic_set_pauseparam(struct net_device *netdev,
831			  struct ethtool_pauseparam *pause)
832{
833	struct qlcnic_adapter *adapter = netdev_priv(netdev);
834	int port = adapter->ahw->physical_port;
835	int err = 0;
836	__u32 val;
837
838	if (qlcnic_83xx_check(adapter))
839		return qlcnic_83xx_set_pauseparam(adapter, pause);
840
841	/* read mode */
842	if (adapter->ahw->port_type == QLCNIC_GBE) {
843		if ((port < 0) || (port > QLCNIC_NIU_MAX_GBE_PORTS))
844			return -EIO;
845		/* set flow control */
846		val = QLCRD32(adapter, QLCNIC_NIU_GB_MAC_CONFIG_0(port), &err);
847		if (err == -EIO)
848			return err;
849
850		if (pause->rx_pause)
851			qlcnic_gb_rx_flowctl(val);
852		else
853			qlcnic_gb_unset_rx_flowctl(val);
854
855		QLCWR32(adapter, QLCNIC_NIU_GB_MAC_CONFIG_0(port),
856				val);
857		QLCWR32(adapter, QLCNIC_NIU_GB_MAC_CONFIG_0(port), val);
858		/* set autoneg */
859		val = QLCRD32(adapter, QLCNIC_NIU_GB_PAUSE_CTL, &err);
860		if (err == -EIO)
861			return err;
862		switch (port) {
863		case 0:
864			if (pause->tx_pause)
865				qlcnic_gb_unset_gb0_mask(val);
866			else
867				qlcnic_gb_set_gb0_mask(val);
868			break;
869		case 1:
870			if (pause->tx_pause)
871				qlcnic_gb_unset_gb1_mask(val);
872			else
873				qlcnic_gb_set_gb1_mask(val);
874			break;
875		case 2:
876			if (pause->tx_pause)
877				qlcnic_gb_unset_gb2_mask(val);
878			else
879				qlcnic_gb_set_gb2_mask(val);
880			break;
881		case 3:
882		default:
883			if (pause->tx_pause)
884				qlcnic_gb_unset_gb3_mask(val);
885			else
886				qlcnic_gb_set_gb3_mask(val);
887			break;
888		}
889		QLCWR32(adapter, QLCNIC_NIU_GB_PAUSE_CTL, val);
890	} else if (adapter->ahw->port_type == QLCNIC_XGBE) {
891		if (!pause->rx_pause || pause->autoneg)
892			return -EOPNOTSUPP;
893
894		if ((port < 0) || (port > QLCNIC_NIU_MAX_XG_PORTS))
895			return -EIO;
896
897		val = QLCRD32(adapter, QLCNIC_NIU_XG_PAUSE_CTL, &err);
898		if (err == -EIO)
899			return err;
900		if (port == 0) {
901			if (pause->tx_pause)
902				qlcnic_xg_unset_xg0_mask(val);
903			else
904				qlcnic_xg_set_xg0_mask(val);
905		} else {
906			if (pause->tx_pause)
907				qlcnic_xg_unset_xg1_mask(val);
908			else
909				qlcnic_xg_set_xg1_mask(val);
910		}
911		QLCWR32(adapter, QLCNIC_NIU_XG_PAUSE_CTL, val);
912	} else {
913		dev_err(&netdev->dev, "Unknown board type: %x\n",
914				adapter->ahw->port_type);
915	}
916	return 0;
917}
918
919static int qlcnic_reg_test(struct net_device *dev)
920{
921	struct qlcnic_adapter *adapter = netdev_priv(dev);
922	u32 data_read;
923	int err = 0;
924
925	if (qlcnic_83xx_check(adapter))
926		return qlcnic_83xx_reg_test(adapter);
927
928	data_read = QLCRD32(adapter, QLCNIC_PCIX_PH_REG(0), &err);
929	if (err == -EIO)
930		return err;
931	if ((data_read & 0xffff) != adapter->pdev->vendor)
932		return 1;
933
934	return 0;
935}
936
937static int qlcnic_eeprom_test(struct net_device *dev)
938{
939	struct qlcnic_adapter *adapter = netdev_priv(dev);
940
941	if (qlcnic_82xx_check(adapter))
942		return 0;
943
944	return qlcnic_83xx_flash_test(adapter);
945}
946
947static int qlcnic_get_sset_count(struct net_device *dev, int sset)
948{
949
950	struct qlcnic_adapter *adapter = netdev_priv(dev);
951	switch (sset) {
952	case ETH_SS_TEST:
953		return QLCNIC_TEST_LEN;
954	case ETH_SS_STATS:
955		return qlcnic_dev_statistics_len(adapter);
956	default:
957		return -EOPNOTSUPP;
958	}
959}
960
961static int qlcnic_irq_test(struct net_device *netdev)
962{
963	struct qlcnic_adapter *adapter = netdev_priv(netdev);
964	struct qlcnic_hardware_context *ahw = adapter->ahw;
965	struct qlcnic_cmd_args cmd;
966	int ret, drv_sds_rings = adapter->drv_sds_rings;
967	int drv_tx_rings = adapter->drv_tx_rings;
968
969	if (qlcnic_83xx_check(adapter))
970		return qlcnic_83xx_interrupt_test(netdev);
971
972	if (test_and_set_bit(__QLCNIC_RESETTING, &adapter->state))
973		return -EIO;
974
975	ret = qlcnic_diag_alloc_res(netdev, QLCNIC_INTERRUPT_TEST);
976	if (ret)
977		goto clear_diag_irq;
978
979	ahw->diag_cnt = 0;
980	ret = qlcnic_alloc_mbx_args(&cmd, adapter, QLCNIC_CMD_INTRPT_TEST);
981	if (ret)
982		goto free_diag_res;
983
984	cmd.req.arg[1] = ahw->pci_func;
985	ret = qlcnic_issue_cmd(adapter, &cmd);
986	if (ret)
987		goto done;
988
989	usleep_range(1000, 12000);
990	ret = !ahw->diag_cnt;
991
992done:
993	qlcnic_free_mbx_args(&cmd);
994
995free_diag_res:
996	qlcnic_diag_free_res(netdev, drv_sds_rings);
997
998clear_diag_irq:
999	adapter->drv_sds_rings = drv_sds_rings;
1000	adapter->drv_tx_rings = drv_tx_rings;
1001	clear_bit(__QLCNIC_RESETTING, &adapter->state);
1002
1003	return ret;
1004}
1005
1006#define QLCNIC_ILB_PKT_SIZE		64
1007#define QLCNIC_NUM_ILB_PKT		16
1008#define QLCNIC_ILB_MAX_RCV_LOOP		10
1009#define QLCNIC_LB_PKT_POLL_DELAY_MSEC	1
1010#define QLCNIC_LB_PKT_POLL_COUNT	20
1011
1012static void qlcnic_create_loopback_buff(unsigned char *data, u8 mac[])
1013{
1014	unsigned char random_data[] = {0xa8, 0x06, 0x45, 0x00};
1015
1016	memset(data, 0x4e, QLCNIC_ILB_PKT_SIZE);
1017
1018	memcpy(data, mac, ETH_ALEN);
1019	memcpy(data + ETH_ALEN, mac, ETH_ALEN);
1020
1021	memcpy(data + 2 * ETH_ALEN, random_data, sizeof(random_data));
1022}
1023
1024int qlcnic_check_loopback_buff(unsigned char *data, u8 mac[])
1025{
1026	unsigned char buff[QLCNIC_ILB_PKT_SIZE];
1027	qlcnic_create_loopback_buff(buff, mac);
1028	return memcmp(data, buff, QLCNIC_ILB_PKT_SIZE);
1029}
1030
1031int qlcnic_do_lb_test(struct qlcnic_adapter *adapter, u8 mode)
1032{
1033	struct qlcnic_recv_context *recv_ctx = adapter->recv_ctx;
1034	struct qlcnic_host_sds_ring *sds_ring = &recv_ctx->sds_rings[0];
1035	struct sk_buff *skb;
1036	int i, loop, cnt = 0;
1037
1038	for (i = 0; i < QLCNIC_NUM_ILB_PKT; i++) {
1039		skb = netdev_alloc_skb(adapter->netdev, QLCNIC_ILB_PKT_SIZE);
1040		qlcnic_create_loopback_buff(skb->data, adapter->mac_addr);
1041		skb_put(skb, QLCNIC_ILB_PKT_SIZE);
1042		adapter->ahw->diag_cnt = 0;
1043		qlcnic_xmit_frame(skb, adapter->netdev);
1044		loop = 0;
1045
1046		do {
1047			msleep(QLCNIC_LB_PKT_POLL_DELAY_MSEC);
1048			qlcnic_process_rcv_ring_diag(sds_ring);
1049			if (loop++ > QLCNIC_LB_PKT_POLL_COUNT)
1050				break;
1051		} while (!adapter->ahw->diag_cnt);
1052
1053		dev_kfree_skb_any(skb);
1054
1055		if (!adapter->ahw->diag_cnt)
1056			dev_warn(&adapter->pdev->dev,
1057				 "LB Test: packet #%d was not received\n",
1058				 i + 1);
1059		else
1060			cnt++;
1061	}
1062	if (cnt != i) {
1063		dev_err(&adapter->pdev->dev,
1064			"LB Test: failed, TX[%d], RX[%d]\n", i, cnt);
1065		if (mode != QLCNIC_ILB_MODE)
1066			dev_warn(&adapter->pdev->dev,
1067				 "WARNING: Please check loopback cable\n");
1068		return -1;
1069	}
1070	return 0;
1071}
1072
1073static int qlcnic_loopback_test(struct net_device *netdev, u8 mode)
1074{
1075	struct qlcnic_adapter *adapter = netdev_priv(netdev);
1076	int drv_tx_rings = adapter->drv_tx_rings;
1077	int drv_sds_rings = adapter->drv_sds_rings;
1078	struct qlcnic_host_sds_ring *sds_ring;
1079	struct qlcnic_hardware_context *ahw = adapter->ahw;
1080	int loop = 0;
1081	int ret;
1082
1083	if (qlcnic_83xx_check(adapter))
1084		return qlcnic_83xx_loopback_test(netdev, mode);
1085
1086	if (!(ahw->capabilities & QLCNIC_FW_CAPABILITY_MULTI_LOOPBACK)) {
1087		dev_info(&adapter->pdev->dev,
1088			 "Firmware do not support loopback test\n");
1089		return -EOPNOTSUPP;
1090	}
1091
1092	dev_warn(&adapter->pdev->dev, "%s loopback test in progress\n",
1093		 mode == QLCNIC_ILB_MODE ? "internal" : "external");
1094	if (ahw->op_mode == QLCNIC_NON_PRIV_FUNC) {
1095		dev_warn(&adapter->pdev->dev,
1096			 "Loopback test not supported in nonprivileged mode\n");
1097		return 0;
1098	}
1099
1100	if (test_and_set_bit(__QLCNIC_RESETTING, &adapter->state))
1101		return -EBUSY;
1102
1103	ret = qlcnic_diag_alloc_res(netdev, QLCNIC_LOOPBACK_TEST);
1104	if (ret)
1105		goto clear_it;
1106
1107	sds_ring = &adapter->recv_ctx->sds_rings[0];
1108	ret = qlcnic_set_lb_mode(adapter, mode);
1109	if (ret)
1110		goto free_res;
1111
1112	ahw->diag_cnt = 0;
1113	do {
1114		msleep(500);
1115		qlcnic_process_rcv_ring_diag(sds_ring);
1116		if (loop++ > QLCNIC_ILB_MAX_RCV_LOOP) {
1117			netdev_info(netdev,
1118				    "Firmware didn't sent link up event to loopback request\n");
1119			ret = -ETIMEDOUT;
1120			goto free_res;
1121		} else if (adapter->ahw->diag_cnt) {
1122			ret = adapter->ahw->diag_cnt;
1123			goto free_res;
1124		}
1125	} while (!QLCNIC_IS_LB_CONFIGURED(ahw->loopback_state));
1126
1127	ret = qlcnic_do_lb_test(adapter, mode);
1128
1129	qlcnic_clear_lb_mode(adapter, mode);
1130
1131 free_res:
1132	qlcnic_diag_free_res(netdev, drv_sds_rings);
1133
1134 clear_it:
1135	adapter->drv_sds_rings = drv_sds_rings;
1136	adapter->drv_tx_rings = drv_tx_rings;
1137	clear_bit(__QLCNIC_RESETTING, &adapter->state);
1138	return ret;
1139}
1140
1141static void
1142qlcnic_diag_test(struct net_device *dev, struct ethtool_test *eth_test,
1143		     u64 *data)
1144{
1145	memset(data, 0, sizeof(u64) * QLCNIC_TEST_LEN);
1146
1147	data[0] = qlcnic_reg_test(dev);
1148	if (data[0])
1149		eth_test->flags |= ETH_TEST_FL_FAILED;
1150
1151	data[1] = (u64) qlcnic_test_link(dev);
1152	if (data[1])
1153		eth_test->flags |= ETH_TEST_FL_FAILED;
1154
1155	if (eth_test->flags & ETH_TEST_FL_OFFLINE) {
1156		data[2] = qlcnic_irq_test(dev);
1157		if (data[2])
1158			eth_test->flags |= ETH_TEST_FL_FAILED;
1159
1160		data[3] = qlcnic_loopback_test(dev, QLCNIC_ILB_MODE);
1161		if (data[3])
1162			eth_test->flags |= ETH_TEST_FL_FAILED;
1163
1164		if (eth_test->flags & ETH_TEST_FL_EXTERNAL_LB) {
1165			data[4] = qlcnic_loopback_test(dev, QLCNIC_ELB_MODE);
1166			if (data[4])
1167				eth_test->flags |= ETH_TEST_FL_FAILED;
1168			eth_test->flags |= ETH_TEST_FL_EXTERNAL_LB_DONE;
1169		}
1170
1171		data[5] = qlcnic_eeprom_test(dev);
1172		if (data[5])
1173			eth_test->flags |= ETH_TEST_FL_FAILED;
1174	}
1175}
1176
1177static void
1178qlcnic_get_strings(struct net_device *dev, u32 stringset, u8 *data)
1179{
1180	struct qlcnic_adapter *adapter = netdev_priv(dev);
1181	int index, i, num_stats;
1182
1183	switch (stringset) {
1184	case ETH_SS_TEST:
1185		memcpy(data, *qlcnic_gstrings_test,
1186		       QLCNIC_TEST_LEN * ETH_GSTRING_LEN);
1187		break;
1188	case ETH_SS_STATS:
1189		num_stats = ARRAY_SIZE(qlcnic_tx_queue_stats_strings);
1190		for (i = 0; i < adapter->drv_tx_rings; i++) {
1191			for (index = 0; index < num_stats; index++) {
1192				sprintf(data, "tx_queue_%d %s", i,
1193					qlcnic_tx_queue_stats_strings[index]);
1194				data += ETH_GSTRING_LEN;
1195			}
1196		}
1197
1198		for (index = 0; index < QLCNIC_STATS_LEN; index++) {
1199			memcpy(data + index * ETH_GSTRING_LEN,
1200			       qlcnic_gstrings_stats[index].stat_string,
1201			       ETH_GSTRING_LEN);
1202		}
1203
1204		if (qlcnic_83xx_check(adapter)) {
1205			num_stats = ARRAY_SIZE(qlcnic_83xx_tx_stats_strings);
1206			for (i = 0; i < num_stats; i++, index++)
1207				memcpy(data + index * ETH_GSTRING_LEN,
1208				       qlcnic_83xx_tx_stats_strings[i],
1209				       ETH_GSTRING_LEN);
1210			num_stats = ARRAY_SIZE(qlcnic_83xx_mac_stats_strings);
1211			for (i = 0; i < num_stats; i++, index++)
1212				memcpy(data + index * ETH_GSTRING_LEN,
1213				       qlcnic_83xx_mac_stats_strings[i],
1214				       ETH_GSTRING_LEN);
1215			num_stats = ARRAY_SIZE(qlcnic_83xx_rx_stats_strings);
1216			for (i = 0; i < num_stats; i++, index++)
1217				memcpy(data + index * ETH_GSTRING_LEN,
1218				       qlcnic_83xx_rx_stats_strings[i],
1219				       ETH_GSTRING_LEN);
1220			return;
1221		} else {
1222			num_stats = ARRAY_SIZE(qlcnic_83xx_mac_stats_strings);
1223			for (i = 0; i < num_stats; i++, index++)
1224				memcpy(data + index * ETH_GSTRING_LEN,
1225				       qlcnic_83xx_mac_stats_strings[i],
1226				       ETH_GSTRING_LEN);
1227		}
1228		if (!(adapter->flags & QLCNIC_ESWITCH_ENABLED))
1229			return;
1230		num_stats = ARRAY_SIZE(qlcnic_device_gstrings_stats);
1231		for (i = 0; i < num_stats; index++, i++) {
1232			memcpy(data + index * ETH_GSTRING_LEN,
1233			       qlcnic_device_gstrings_stats[i],
1234			       ETH_GSTRING_LEN);
1235		}
1236	}
1237}
1238
1239static u64 *qlcnic_fill_stats(u64 *data, void *stats, int type)
1240{
1241	if (type == QLCNIC_MAC_STATS) {
1242		struct qlcnic_mac_statistics *mac_stats =
1243					(struct qlcnic_mac_statistics *)stats;
1244		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_frames);
1245		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_bytes);
1246		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_mcast_pkts);
1247		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_bcast_pkts);
1248		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_pause_cnt);
1249		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_ctrl_pkt);
1250		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_lt_64b_pkts);
1251		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_lt_127b_pkts);
1252		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_lt_255b_pkts);
1253		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_lt_511b_pkts);
1254		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_lt_1023b_pkts);
1255		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_lt_1518b_pkts);
1256		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_tx_gt_1518b_pkts);
1257		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_frames);
1258		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_bytes);
1259		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_mcast_pkts);
1260		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_bcast_pkts);
1261		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_pause_cnt);
1262		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_ctrl_pkt);
1263		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_lt_64b_pkts);
1264		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_lt_127b_pkts);
1265		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_lt_255b_pkts);
1266		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_lt_511b_pkts);
1267		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_lt_1023b_pkts);
1268		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_lt_1518b_pkts);
1269		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_gt_1518b_pkts);
1270		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_length_error);
1271		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_length_small);
1272		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_length_large);
1273		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_jabber);
1274		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_dropped);
1275		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_rx_crc_error);
1276		*data++ = QLCNIC_FILL_STATS(mac_stats->mac_align_error);
1277	} else if (type == QLCNIC_ESW_STATS) {
1278		struct __qlcnic_esw_statistics *esw_stats =
1279				(struct __qlcnic_esw_statistics *)stats;
1280		*data++ = QLCNIC_FILL_STATS(esw_stats->unicast_frames);
1281		*data++ = QLCNIC_FILL_STATS(esw_stats->multicast_frames);
1282		*data++ = QLCNIC_FILL_STATS(esw_stats->broadcast_frames);
1283		*data++ = QLCNIC_FILL_STATS(esw_stats->dropped_frames);
1284		*data++ = QLCNIC_FILL_STATS(esw_stats->errors);
1285		*data++ = QLCNIC_FILL_STATS(esw_stats->local_frames);
1286		*data++ = QLCNIC_FILL_STATS(esw_stats->numbytes);
1287	}
1288	return data;
1289}
1290
1291void qlcnic_update_stats(struct qlcnic_adapter *adapter)
1292{
1293	struct qlcnic_tx_queue_stats tx_stats;
1294	struct qlcnic_host_tx_ring *tx_ring;
1295	int ring;
1296
1297	memset(&tx_stats, 0, sizeof(tx_stats));
1298	for (ring = 0; ring < adapter->drv_tx_rings; ring++) {
1299		tx_ring = &adapter->tx_ring[ring];
1300		tx_stats.xmit_on += tx_ring->tx_stats.xmit_on;
1301		tx_stats.xmit_off += tx_ring->tx_stats.xmit_off;
1302		tx_stats.xmit_called += tx_ring->tx_stats.xmit_called;
1303		tx_stats.xmit_finished += tx_ring->tx_stats.xmit_finished;
1304		tx_stats.tx_bytes += tx_ring->tx_stats.tx_bytes;
1305	}
1306
1307	adapter->stats.xmit_on = tx_stats.xmit_on;
1308	adapter->stats.xmit_off = tx_stats.xmit_off;
1309	adapter->stats.xmitcalled = tx_stats.xmit_called;
1310	adapter->stats.xmitfinished = tx_stats.xmit_finished;
1311	adapter->stats.txbytes = tx_stats.tx_bytes;
1312}
1313
1314static u64 *qlcnic_fill_tx_queue_stats(u64 *data, void *stats)
1315{
1316	struct qlcnic_host_tx_ring *tx_ring;
1317
1318	tx_ring = (struct qlcnic_host_tx_ring *)stats;
1319
1320	*data++ = QLCNIC_FILL_STATS(tx_ring->tx_stats.xmit_on);
1321	*data++ = QLCNIC_FILL_STATS(tx_ring->tx_stats.xmit_off);
1322	*data++ = QLCNIC_FILL_STATS(tx_ring->tx_stats.xmit_called);
1323	*data++ = QLCNIC_FILL_STATS(tx_ring->tx_stats.xmit_finished);
1324	*data++ = QLCNIC_FILL_STATS(tx_ring->tx_stats.tx_bytes);
1325
1326	return data;
1327}
1328
1329static void qlcnic_get_ethtool_stats(struct net_device *dev,
1330				     struct ethtool_stats *stats, u64 *data)
1331{
1332	struct qlcnic_adapter *adapter = netdev_priv(dev);
1333	struct qlcnic_host_tx_ring *tx_ring;
1334	struct qlcnic_esw_statistics port_stats;
1335	struct qlcnic_mac_statistics mac_stats;
1336	int index, ret, length, size, ring;
1337	char *p;
1338
1339	memset(data, 0, stats->n_stats * sizeof(u64));
1340
1341	for (ring = 0, index = 0; ring < adapter->drv_tx_rings; ring++) {
1342		if (adapter->is_up == QLCNIC_ADAPTER_UP_MAGIC) {
1343			tx_ring = &adapter->tx_ring[ring];
1344			data = qlcnic_fill_tx_queue_stats(data, tx_ring);
1345			qlcnic_update_stats(adapter);
1346		} else {
1347			data += QLCNIC_TX_STATS_LEN;
1348		}
1349	}
1350
1351	length = QLCNIC_STATS_LEN;
1352	for (index = 0; index < length; index++) {
1353		p = (char *)adapter + qlcnic_gstrings_stats[index].stat_offset;
1354		size = qlcnic_gstrings_stats[index].sizeof_stat;
1355		*data++ = (size == sizeof(u64)) ? (*(u64 *)p) : ((*(u32 *)p));
1356	}
1357
1358	if (qlcnic_83xx_check(adapter)) {
1359		if (adapter->ahw->linkup)
1360			qlcnic_83xx_get_stats(adapter, data);
1361		return;
1362	} else {
1363		/* Retrieve MAC statistics from firmware */
1364		memset(&mac_stats, 0, sizeof(struct qlcnic_mac_statistics));
1365		qlcnic_get_mac_stats(adapter, &mac_stats);
1366		data = qlcnic_fill_stats(data, &mac_stats, QLCNIC_MAC_STATS);
1367	}
1368
1369	if (!(adapter->flags & QLCNIC_ESWITCH_ENABLED))
1370		return;
1371
1372	memset(&port_stats, 0, sizeof(struct qlcnic_esw_statistics));
1373	ret = qlcnic_get_port_stats(adapter, adapter->ahw->pci_func,
1374			QLCNIC_QUERY_RX_COUNTER, &port_stats.rx);
1375	if (ret)
1376		return;
1377
1378	data = qlcnic_fill_stats(data, &port_stats.rx, QLCNIC_ESW_STATS);
1379	ret = qlcnic_get_port_stats(adapter, adapter->ahw->pci_func,
1380			QLCNIC_QUERY_TX_COUNTER, &port_stats.tx);
1381	if (ret)
1382		return;
1383
1384	qlcnic_fill_stats(data, &port_stats.tx, QLCNIC_ESW_STATS);
1385}
1386
1387static int qlcnic_set_led(struct net_device *dev,
1388			  enum ethtool_phys_id_state state)
1389{
1390	struct qlcnic_adapter *adapter = netdev_priv(dev);
1391	int drv_sds_rings = adapter->drv_sds_rings;
1392	int err = -EIO, active = 1;
1393
1394	if (qlcnic_83xx_check(adapter))
1395		return qlcnic_83xx_set_led(dev, state);
1396
1397	if (adapter->ahw->op_mode == QLCNIC_NON_PRIV_FUNC) {
1398		netdev_warn(dev, "LED test not supported for non "
1399				"privilege function\n");
1400		return -EOPNOTSUPP;
1401	}
1402
1403	switch (state) {
1404	case ETHTOOL_ID_ACTIVE:
1405		if (test_and_set_bit(__QLCNIC_LED_ENABLE, &adapter->state))
1406			return -EBUSY;
1407
1408		if (test_bit(__QLCNIC_RESETTING, &adapter->state))
1409			break;
1410
1411		if (!test_bit(__QLCNIC_DEV_UP, &adapter->state)) {
1412			if (qlcnic_diag_alloc_res(dev, QLCNIC_LED_TEST))
1413				break;
1414			set_bit(__QLCNIC_DIAG_RES_ALLOC, &adapter->state);
1415		}
1416
1417		if (adapter->nic_ops->config_led(adapter, 1, 0xf) == 0) {
1418			err = 0;
1419			break;
1420		}
1421
1422		dev_err(&adapter->pdev->dev,
1423			"Failed to set LED blink state.\n");
1424		break;
1425
1426	case ETHTOOL_ID_INACTIVE:
1427		active = 0;
1428
1429		if (test_bit(__QLCNIC_RESETTING, &adapter->state))
1430			break;
1431
1432		if (!test_bit(__QLCNIC_DEV_UP, &adapter->state)) {
1433			if (qlcnic_diag_alloc_res(dev, QLCNIC_LED_TEST))
1434				break;
1435			set_bit(__QLCNIC_DIAG_RES_ALLOC, &adapter->state);
1436		}
1437
1438		if (adapter->nic_ops->config_led(adapter, 0, 0xf))
1439			dev_err(&adapter->pdev->dev,
1440				"Failed to reset LED blink state.\n");
1441
1442		break;
1443
1444	default:
1445		return -EINVAL;
1446	}
1447
1448	if (test_and_clear_bit(__QLCNIC_DIAG_RES_ALLOC, &adapter->state))
1449		qlcnic_diag_free_res(dev, drv_sds_rings);
1450
1451	if (!active || err)
1452		clear_bit(__QLCNIC_LED_ENABLE, &adapter->state);
1453
1454	return err;
1455}
1456
1457static void
1458qlcnic_get_wol(struct net_device *dev, struct ethtool_wolinfo *wol)
1459{
1460	struct qlcnic_adapter *adapter = netdev_priv(dev);
1461	u32 wol_cfg;
1462	int err = 0;
1463
1464	if (qlcnic_83xx_check(adapter))
1465		return;
1466	wol->supported = 0;
1467	wol->wolopts = 0;
1468
1469	wol_cfg = QLCRD32(adapter, QLCNIC_WOL_CONFIG_NV, &err);
1470	if (err == -EIO)
1471		return;
1472	if (wol_cfg & (1UL << adapter->portnum))
1473		wol->supported |= WAKE_MAGIC;
1474
1475	wol_cfg = QLCRD32(adapter, QLCNIC_WOL_CONFIG, &err);
1476	if (wol_cfg & (1UL << adapter->portnum))
1477		wol->wolopts |= WAKE_MAGIC;
1478}
1479
1480static int
1481qlcnic_set_wol(struct net_device *dev, struct ethtool_wolinfo *wol)
1482{
1483	struct qlcnic_adapter *adapter = netdev_priv(dev);
1484	u32 wol_cfg;
1485	int err = 0;
1486
1487	if (qlcnic_83xx_check(adapter))
1488		return -EOPNOTSUPP;
1489	if (wol->wolopts & ~WAKE_MAGIC)
1490		return -EINVAL;
1491
1492	wol_cfg = QLCRD32(adapter, QLCNIC_WOL_CONFIG_NV, &err);
1493	if (err == -EIO)
1494		return err;
1495	if (!(wol_cfg & (1 << adapter->portnum)))
1496		return -EOPNOTSUPP;
1497
1498	wol_cfg = QLCRD32(adapter, QLCNIC_WOL_CONFIG, &err);
1499	if (err == -EIO)
1500		return err;
1501	if (wol->wolopts & WAKE_MAGIC)
1502		wol_cfg |= 1UL << adapter->portnum;
1503	else
1504		wol_cfg &= ~(1UL << adapter->portnum);
1505
1506	QLCWR32(adapter, QLCNIC_WOL_CONFIG, wol_cfg);
1507
1508	return 0;
1509}
1510
1511/*
1512 * Set the coalescing parameters. Currently only normal is supported.
1513 * If rx_coalesce_usecs == 0 or rx_max_coalesced_frames == 0 then set the
1514 * firmware coalescing to default.
1515 */
1516static int qlcnic_set_intr_coalesce(struct net_device *netdev,
1517			struct ethtool_coalesce *ethcoal)
1518{
1519	struct qlcnic_adapter *adapter = netdev_priv(netdev);
1520	int err;
1521
1522	if (!test_bit(__QLCNIC_DEV_UP, &adapter->state))
1523		return -EINVAL;
1524
1525	/*
1526	* Return Error if unsupported values or
1527	* unsupported parameters are set.
1528	*/
1529	if (ethcoal->rx_coalesce_usecs > 0xffff ||
1530	    ethcoal->rx_max_coalesced_frames > 0xffff ||
1531	    ethcoal->tx_coalesce_usecs > 0xffff ||
1532	    ethcoal->tx_max_coalesced_frames > 0xffff ||
1533	    ethcoal->rx_coalesce_usecs_irq ||
1534	    ethcoal->rx_max_coalesced_frames_irq ||
1535	    ethcoal->tx_coalesce_usecs_irq ||
1536	    ethcoal->tx_max_coalesced_frames_irq ||
1537	    ethcoal->stats_block_coalesce_usecs ||
1538	    ethcoal->use_adaptive_rx_coalesce ||
1539	    ethcoal->use_adaptive_tx_coalesce ||
1540	    ethcoal->pkt_rate_low ||
1541	    ethcoal->rx_coalesce_usecs_low ||
1542	    ethcoal->rx_max_coalesced_frames_low ||
1543	    ethcoal->tx_coalesce_usecs_low ||
1544	    ethcoal->tx_max_coalesced_frames_low ||
1545	    ethcoal->pkt_rate_high ||
1546	    ethcoal->rx_coalesce_usecs_high ||
1547	    ethcoal->rx_max_coalesced_frames_high ||
1548	    ethcoal->tx_coalesce_usecs_high ||
1549	    ethcoal->tx_max_coalesced_frames_high)
1550		return -EINVAL;
1551
1552	err = qlcnic_config_intr_coalesce(adapter, ethcoal);
1553
1554	return err;
1555}
1556
1557static int qlcnic_get_intr_coalesce(struct net_device *netdev,
1558			struct ethtool_coalesce *ethcoal)
1559{
1560	struct qlcnic_adapter *adapter = netdev_priv(netdev);
1561
1562	if (adapter->is_up != QLCNIC_ADAPTER_UP_MAGIC)
1563		return -EINVAL;
1564
1565	ethcoal->rx_coalesce_usecs = adapter->ahw->coal.rx_time_us;
1566	ethcoal->rx_max_coalesced_frames = adapter->ahw->coal.rx_packets;
1567	ethcoal->tx_coalesce_usecs = adapter->ahw->coal.tx_time_us;
1568	ethcoal->tx_max_coalesced_frames = adapter->ahw->coal.tx_packets;
1569
1570	return 0;
1571}
1572
1573static u32 qlcnic_get_msglevel(struct net_device *netdev)
1574{
1575	struct qlcnic_adapter *adapter = netdev_priv(netdev);
1576
1577	return adapter->ahw->msg_enable;
1578}
1579
1580static void qlcnic_set_msglevel(struct net_device *netdev, u32 msglvl)
1581{
1582	struct qlcnic_adapter *adapter = netdev_priv(netdev);
1583
1584	adapter->ahw->msg_enable = msglvl;
1585}
1586
1587int qlcnic_enable_fw_dump_state(struct qlcnic_adapter *adapter)
1588{
1589	struct qlcnic_fw_dump *fw_dump = &adapter->ahw->fw_dump;
1590	u32 val;
1591
1592	if (qlcnic_84xx_check(adapter)) {
1593		if (qlcnic_83xx_lock_driver(adapter))
1594			return -EBUSY;
1595
1596		val = QLCRDX(adapter->ahw, QLC_83XX_IDC_CTRL);
1597		val &= ~QLC_83XX_IDC_DISABLE_FW_DUMP;
1598		QLCWRX(adapter->ahw, QLC_83XX_IDC_CTRL, val);
1599
1600		qlcnic_83xx_unlock_driver(adapter);
1601	} else {
1602		fw_dump->enable = true;
1603	}
1604
1605	dev_info(&adapter->pdev->dev, "FW dump enabled\n");
1606
1607	return 0;
1608}
1609
1610static int qlcnic_disable_fw_dump_state(struct qlcnic_adapter *adapter)
1611{
1612	struct qlcnic_fw_dump *fw_dump = &adapter->ahw->fw_dump;
1613	u32 val;
1614
1615	if (qlcnic_84xx_check(adapter)) {
1616		if (qlcnic_83xx_lock_driver(adapter))
1617			return -EBUSY;
1618
1619		val = QLCRDX(adapter->ahw, QLC_83XX_IDC_CTRL);
1620		val |= QLC_83XX_IDC_DISABLE_FW_DUMP;
1621		QLCWRX(adapter->ahw, QLC_83XX_IDC_CTRL, val);
1622
1623		qlcnic_83xx_unlock_driver(adapter);
1624	} else {
1625		fw_dump->enable = false;
1626	}
1627
1628	dev_info(&adapter->pdev->dev, "FW dump disabled\n");
1629
1630	return 0;
1631}
1632
1633bool qlcnic_check_fw_dump_state(struct qlcnic_adapter *adapter)
1634{
1635	struct qlcnic_fw_dump *fw_dump = &adapter->ahw->fw_dump;
1636	bool state;
1637	u32 val;
1638
1639	if (qlcnic_84xx_check(adapter)) {
1640		val = QLCRDX(adapter->ahw, QLC_83XX_IDC_CTRL);
1641		state = (val & QLC_83XX_IDC_DISABLE_FW_DUMP) ? false : true;
1642	} else {
1643		state = fw_dump->enable;
1644	}
1645
1646	return state;
1647}
1648
1649static int
1650qlcnic_get_dump_flag(struct net_device *netdev, struct ethtool_dump *dump)
1651{
1652	struct qlcnic_adapter *adapter = netdev_priv(netdev);
1653	struct qlcnic_fw_dump *fw_dump = &adapter->ahw->fw_dump;
1654
1655	if (!fw_dump->tmpl_hdr) {
1656		netdev_err(adapter->netdev, "FW Dump not supported\n");
1657		return -ENOTSUPP;
1658	}
1659
1660	if (fw_dump->clr)
1661		dump->len = fw_dump->tmpl_hdr_size + fw_dump->size;
1662	else
1663		dump->len = 0;
1664
1665	if (!qlcnic_check_fw_dump_state(adapter))
1666		dump->flag = ETH_FW_DUMP_DISABLE;
1667	else
1668		dump->flag = fw_dump->cap_mask;
1669
1670	dump->version = adapter->fw_version;
1671	return 0;
1672}
1673
1674static int
1675qlcnic_get_dump_data(struct net_device *netdev, struct ethtool_dump *dump,
1676			void *buffer)
1677{
1678	int i, copy_sz;
1679	u32 *hdr_ptr;
1680	__le32 *data;
1681	struct qlcnic_adapter *adapter = netdev_priv(netdev);
1682	struct qlcnic_fw_dump *fw_dump = &adapter->ahw->fw_dump;
1683
1684	if (!fw_dump->tmpl_hdr) {
1685		netdev_err(netdev, "FW Dump not supported\n");
1686		return -ENOTSUPP;
1687	}
1688
1689	if (!fw_dump->clr) {
1690		netdev_info(netdev, "Dump not available\n");
1691		return -EINVAL;
1692	}
1693
1694	/* Copy template header first */
1695	copy_sz = fw_dump->tmpl_hdr_size;
1696	hdr_ptr = (u32 *)fw_dump->tmpl_hdr;
1697	data = buffer;
1698	for (i = 0; i < copy_sz/sizeof(u32); i++)
1699		*data++ = cpu_to_le32(*hdr_ptr++);
1700
1701	/* Copy captured dump data */
1702	memcpy(buffer + copy_sz, fw_dump->data, fw_dump->size);
1703	dump->len = copy_sz + fw_dump->size;
1704	dump->flag = fw_dump->cap_mask;
1705
1706	/* Free dump area once data has been captured */
1707	vfree(fw_dump->data);
1708	fw_dump->data = NULL;
1709	fw_dump->clr = 0;
1710	netdev_info(netdev, "extracted the FW dump Successfully\n");
1711	return 0;
1712}
1713
1714static int qlcnic_set_dump_mask(struct qlcnic_adapter *adapter, u32 mask)
1715{
1716	struct qlcnic_fw_dump *fw_dump = &adapter->ahw->fw_dump;
1717	struct net_device *netdev = adapter->netdev;
1718
1719	if (!qlcnic_check_fw_dump_state(adapter)) {
1720		netdev_info(netdev,
1721			    "Can not change driver mask to 0x%x. FW dump not enabled\n",
1722			    mask);
1723		return -EOPNOTSUPP;
1724	}
1725
1726	fw_dump->cap_mask = mask;
1727
1728	/* Store new capture mask in template header as well*/
1729	qlcnic_store_cap_mask(adapter, fw_dump->tmpl_hdr, mask);
1730
1731	netdev_info(netdev, "Driver mask changed to: 0x%x\n", mask);
1732	return 0;
1733}
1734
1735static int
1736qlcnic_set_dump(struct net_device *netdev, struct ethtool_dump *val)
1737{
1738	struct qlcnic_adapter *adapter = netdev_priv(netdev);
1739	struct qlcnic_fw_dump *fw_dump = &adapter->ahw->fw_dump;
1740	bool valid_mask = false;
1741	int i, ret = 0;
1742
1743	switch (val->flag) {
1744	case QLCNIC_FORCE_FW_DUMP_KEY:
1745		if (!fw_dump->tmpl_hdr) {
1746			netdev_err(netdev, "FW dump not supported\n");
1747			ret = -EOPNOTSUPP;
1748			break;
1749		}
1750
1751		if (!qlcnic_check_fw_dump_state(adapter)) {
1752			netdev_info(netdev, "FW dump not enabled\n");
1753			ret = -EOPNOTSUPP;
1754			break;
1755		}
1756
1757		if (fw_dump->clr) {
1758			netdev_info(netdev,
1759				    "Previous dump not cleared, not forcing dump\n");
1760			break;
1761		}
1762
1763		netdev_info(netdev, "Forcing a FW dump\n");
1764		qlcnic_dev_request_reset(adapter, val->flag);
1765		break;
1766	case QLCNIC_DISABLE_FW_DUMP:
1767		if (!fw_dump->tmpl_hdr) {
1768			netdev_err(netdev, "FW dump not supported\n");
1769			ret = -EOPNOTSUPP;
1770			break;
1771		}
1772
1773		ret = qlcnic_disable_fw_dump_state(adapter);
1774		break;
1775
1776	case QLCNIC_ENABLE_FW_DUMP:
1777		if (!fw_dump->tmpl_hdr) {
1778			netdev_err(netdev, "FW dump not supported\n");
1779			ret = -EOPNOTSUPP;
1780			break;
1781		}
1782
1783		ret = qlcnic_enable_fw_dump_state(adapter);
1784		break;
1785
1786	case QLCNIC_FORCE_FW_RESET:
1787		netdev_info(netdev, "Forcing a FW reset\n");
1788		qlcnic_dev_request_reset(adapter, val->flag);
1789		adapter->flags &= ~QLCNIC_FW_RESET_OWNER;
1790		break;
1791
1792	case QLCNIC_SET_QUIESCENT:
1793	case QLCNIC_RESET_QUIESCENT:
1794		if (test_bit(__QLCNIC_MAINTENANCE_MODE, &adapter->state))
1795			netdev_info(netdev, "Device is in non-operational state\n");
1796		break;
1797
1798	default:
1799		if (!fw_dump->tmpl_hdr) {
1800			netdev_err(netdev, "FW dump not supported\n");
1801			ret = -EOPNOTSUPP;
1802			break;
1803		}
1804
1805		for (i = 0; i < ARRAY_SIZE(qlcnic_fw_dump_level); i++) {
1806			if (val->flag == qlcnic_fw_dump_level[i]) {
1807				valid_mask = true;
1808				break;
1809			}
1810		}
1811
1812		if (valid_mask) {
1813			ret = qlcnic_set_dump_mask(adapter, val->flag);
1814		} else {
1815			netdev_info(netdev, "Invalid dump level: 0x%x\n",
1816				    val->flag);
1817			ret = -EINVAL;
1818		}
1819	}
1820	return ret;
1821}
1822
1823const struct ethtool_ops qlcnic_ethtool_ops = {
1824	.get_settings = qlcnic_get_settings,
1825	.set_settings = qlcnic_set_settings,
1826	.get_drvinfo = qlcnic_get_drvinfo,
1827	.get_regs_len = qlcnic_get_regs_len,
1828	.get_regs = qlcnic_get_regs,
1829	.get_link = ethtool_op_get_link,
1830	.get_eeprom_len = qlcnic_get_eeprom_len,
1831	.get_eeprom = qlcnic_get_eeprom,
1832	.get_ringparam = qlcnic_get_ringparam,
1833	.set_ringparam = qlcnic_set_ringparam,
1834	.get_channels = qlcnic_get_channels,
1835	.set_channels = qlcnic_set_channels,
1836	.get_pauseparam = qlcnic_get_pauseparam,
1837	.set_pauseparam = qlcnic_set_pauseparam,
1838	.get_wol = qlcnic_get_wol,
1839	.set_wol = qlcnic_set_wol,
1840	.self_test = qlcnic_diag_test,
1841	.get_strings = qlcnic_get_strings,
1842	.get_ethtool_stats = qlcnic_get_ethtool_stats,
1843	.get_sset_count = qlcnic_get_sset_count,
1844	.get_coalesce = qlcnic_get_intr_coalesce,
1845	.set_coalesce = qlcnic_set_intr_coalesce,
1846	.set_phys_id = qlcnic_set_led,
1847	.set_msglevel = qlcnic_set_msglevel,
1848	.get_msglevel = qlcnic_get_msglevel,
1849	.get_dump_flag = qlcnic_get_dump_flag,
1850	.get_dump_data = qlcnic_get_dump_data,
1851	.set_dump = qlcnic_set_dump,
1852};
1853
1854const struct ethtool_ops qlcnic_sriov_vf_ethtool_ops = {
1855	.get_settings		= qlcnic_get_settings,
1856	.get_drvinfo		= qlcnic_get_drvinfo,
1857	.get_regs_len		= qlcnic_get_regs_len,
1858	.get_regs		= qlcnic_get_regs,
1859	.get_link		= ethtool_op_get_link,
1860	.get_eeprom_len		= qlcnic_get_eeprom_len,
1861	.get_eeprom		= qlcnic_get_eeprom,
1862	.get_ringparam		= qlcnic_get_ringparam,
1863	.set_ringparam		= qlcnic_set_ringparam,
1864	.get_channels		= qlcnic_get_channels,
1865	.get_pauseparam		= qlcnic_get_pauseparam,
1866	.get_wol		= qlcnic_get_wol,
1867	.get_strings		= qlcnic_get_strings,
1868	.get_ethtool_stats	= qlcnic_get_ethtool_stats,
1869	.get_sset_count		= qlcnic_get_sset_count,
1870	.get_coalesce		= qlcnic_get_intr_coalesce,
1871	.set_coalesce		= qlcnic_set_intr_coalesce,
1872	.set_msglevel		= qlcnic_set_msglevel,
1873	.get_msglevel		= qlcnic_get_msglevel,
1874};
1875
1876const struct ethtool_ops qlcnic_ethtool_failed_ops = {
1877	.get_settings		= qlcnic_get_settings,
1878	.get_drvinfo		= qlcnic_get_drvinfo,
1879	.set_msglevel		= qlcnic_set_msglevel,
1880	.get_msglevel		= qlcnic_get_msglevel,
1881	.set_dump		= qlcnic_set_dump,
1882};
1883