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