aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/enic
diff options
context:
space:
mode:
authorVasanthy Kolluri <vkolluri@cisco.com>2010-10-20 06:16:59 -0400
committerDavid S. Miller <davem@davemloft.net>2010-10-21 04:26:47 -0400
commit717258ba4b3ecca9c7c0ef2b76d7aa5800242bad (patch)
treed82deb82352401aa9b3877c2b99fec348e3b583d /drivers/net/enic
parente0e8ab596012d8c2147beb3c8b70d2d6ab90acda (diff)
enic: Add support for multiple hardware receive queues
Add support for multiple hardware receive queues. The ingress traffic is hashed into one of the receive queues based on IP or TCP or both headers. The max no. of receive queues supported is 8. Signed-off-by: Vasanthy Kolluri <vkolluri@cisco.com> Signed-off-by: Roopa Prabhu <roprabhu@cisco.com> Signed-off-by: David Wang <dwang2@cisco.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/enic')
-rw-r--r--drivers/net/enic/enic.h28
-rw-r--r--drivers/net/enic/enic_main.c373
-rw-r--r--drivers/net/enic/enic_res.c49
-rw-r--r--drivers/net/enic/enic_res.h2
-rw-r--r--drivers/net/enic/vnic_rss.h40
5 files changed, 368 insertions, 124 deletions
diff --git a/drivers/net/enic/enic.h b/drivers/net/enic/enic.h
index ae623206f180..c91d364c5527 100644
--- a/drivers/net/enic/enic.h
+++ b/drivers/net/enic/enic.h
@@ -28,10 +28,11 @@
28#include "vnic_intr.h" 28#include "vnic_intr.h"
29#include "vnic_stats.h" 29#include "vnic_stats.h"
30#include "vnic_nic.h" 30#include "vnic_nic.h"
31#include "vnic_rss.h"
31 32
32#define DRV_NAME "enic" 33#define DRV_NAME "enic"
33#define DRV_DESCRIPTION "Cisco VIC Ethernet NIC Driver" 34#define DRV_DESCRIPTION "Cisco VIC Ethernet NIC Driver"
34#define DRV_VERSION "1.4.1.2a" 35#define DRV_VERSION "1.4.1.6"
35#define DRV_COPYRIGHT "Copyright 2008-2010 Cisco Systems, Inc" 36#define DRV_COPYRIGHT "Copyright 2008-2010 Cisco Systems, Inc"
36 37
37#define ENIC_BARS_MAX 6 38#define ENIC_BARS_MAX 6
@@ -41,25 +42,6 @@
41#define ENIC_CQ_MAX (ENIC_WQ_MAX + ENIC_RQ_MAX) 42#define ENIC_CQ_MAX (ENIC_WQ_MAX + ENIC_RQ_MAX)
42#define ENIC_INTR_MAX (ENIC_CQ_MAX + 2) 43#define ENIC_INTR_MAX (ENIC_CQ_MAX + 2)
43 44
44enum enic_cq_index {
45 ENIC_CQ_RQ,
46 ENIC_CQ_WQ,
47};
48
49enum enic_intx_intr_index {
50 ENIC_INTX_WQ_RQ,
51 ENIC_INTX_ERR,
52 ENIC_INTX_NOTIFY,
53};
54
55enum enic_msix_intr_index {
56 ENIC_MSIX_RQ,
57 ENIC_MSIX_WQ,
58 ENIC_MSIX_ERR,
59 ENIC_MSIX_NOTIFY,
60 ENIC_MSIX_MAX,
61};
62
63struct enic_msix_entry { 45struct enic_msix_entry {
64 int requested; 46 int requested;
65 char devname[IFNAMSIZ]; 47 char devname[IFNAMSIZ];
@@ -90,8 +72,8 @@ struct enic {
90 struct vnic_dev *vdev; 72 struct vnic_dev *vdev;
91 struct timer_list notify_timer; 73 struct timer_list notify_timer;
92 struct work_struct reset; 74 struct work_struct reset;
93 struct msix_entry msix_entry[ENIC_MSIX_MAX]; 75 struct msix_entry msix_entry[ENIC_INTR_MAX];
94 struct enic_msix_entry msix[ENIC_MSIX_MAX]; 76 struct enic_msix_entry msix[ENIC_INTR_MAX];
95 u32 msg_enable; 77 u32 msg_enable;
96 spinlock_t devcmd_lock; 78 spinlock_t devcmd_lock;
97 u8 mac_addr[ETH_ALEN]; 79 u8 mac_addr[ETH_ALEN];
@@ -118,7 +100,7 @@ struct enic {
118 int (*rq_alloc_buf)(struct vnic_rq *rq); 100 int (*rq_alloc_buf)(struct vnic_rq *rq);
119 u64 rq_truncated_pkts; 101 u64 rq_truncated_pkts;
120 u64 rq_bad_fcs; 102 u64 rq_bad_fcs;
121 struct napi_struct napi; 103 struct napi_struct napi[ENIC_RQ_MAX];
122 104
123 /* interrupt resource cache line section */ 105 /* interrupt resource cache line section */
124 ____cacheline_aligned struct vnic_intr intr[ENIC_INTR_MAX]; 106 ____cacheline_aligned struct vnic_intr intr[ENIC_INTR_MAX];
diff --git a/drivers/net/enic/enic_main.c b/drivers/net/enic/enic_main.c
index a1f92f193976..dcfc541291ef 100644
--- a/drivers/net/enic/enic_main.c
+++ b/drivers/net/enic/enic_main.c
@@ -122,6 +122,51 @@ static int enic_is_dynamic(struct enic *enic)
122 return enic->pdev->device == PCI_DEVICE_ID_CISCO_VIC_ENET_DYN; 122 return enic->pdev->device == PCI_DEVICE_ID_CISCO_VIC_ENET_DYN;
123} 123}
124 124
125static inline unsigned int enic_cq_rq(struct enic *enic, unsigned int rq)
126{
127 return rq;
128}
129
130static inline unsigned int enic_cq_wq(struct enic *enic, unsigned int wq)
131{
132 return enic->rq_count + wq;
133}
134
135static inline unsigned int enic_legacy_io_intr(void)
136{
137 return 0;
138}
139
140static inline unsigned int enic_legacy_err_intr(void)
141{
142 return 1;
143}
144
145static inline unsigned int enic_legacy_notify_intr(void)
146{
147 return 2;
148}
149
150static inline unsigned int enic_msix_rq_intr(struct enic *enic, unsigned int rq)
151{
152 return rq;
153}
154
155static inline unsigned int enic_msix_wq_intr(struct enic *enic, unsigned int wq)
156{
157 return enic->rq_count + wq;
158}
159
160static inline unsigned int enic_msix_err_intr(struct enic *enic)
161{
162 return enic->rq_count + enic->wq_count;
163}
164
165static inline unsigned int enic_msix_notify_intr(struct enic *enic)
166{
167 return enic->rq_count + enic->wq_count + 1;
168}
169
125static int enic_get_settings(struct net_device *netdev, 170static int enic_get_settings(struct net_device *netdev,
126 struct ethtool_cmd *ecmd) 171 struct ethtool_cmd *ecmd)
127{ 172{
@@ -306,6 +351,7 @@ static int enic_set_coalesce(struct net_device *netdev,
306 struct enic *enic = netdev_priv(netdev); 351 struct enic *enic = netdev_priv(netdev);
307 u32 tx_coalesce_usecs; 352 u32 tx_coalesce_usecs;
308 u32 rx_coalesce_usecs; 353 u32 rx_coalesce_usecs;
354 unsigned int i, intr;
309 355
310 tx_coalesce_usecs = min_t(u32, 356 tx_coalesce_usecs = min_t(u32,
311 INTR_COALESCE_HW_TO_USEC(VNIC_INTR_TIMER_MAX), 357 INTR_COALESCE_HW_TO_USEC(VNIC_INTR_TIMER_MAX),
@@ -319,7 +365,8 @@ static int enic_set_coalesce(struct net_device *netdev,
319 if (tx_coalesce_usecs != rx_coalesce_usecs) 365 if (tx_coalesce_usecs != rx_coalesce_usecs)
320 return -EINVAL; 366 return -EINVAL;
321 367
322 vnic_intr_coalescing_timer_set(&enic->intr[ENIC_INTX_WQ_RQ], 368 intr = enic_legacy_io_intr();
369 vnic_intr_coalescing_timer_set(&enic->intr[intr],
323 INTR_COALESCE_USEC_TO_HW(tx_coalesce_usecs)); 370 INTR_COALESCE_USEC_TO_HW(tx_coalesce_usecs));
324 break; 371 break;
325 case VNIC_DEV_INTR_MODE_MSI: 372 case VNIC_DEV_INTR_MODE_MSI:
@@ -330,10 +377,18 @@ static int enic_set_coalesce(struct net_device *netdev,
330 INTR_COALESCE_USEC_TO_HW(tx_coalesce_usecs)); 377 INTR_COALESCE_USEC_TO_HW(tx_coalesce_usecs));
331 break; 378 break;
332 case VNIC_DEV_INTR_MODE_MSIX: 379 case VNIC_DEV_INTR_MODE_MSIX:
333 vnic_intr_coalescing_timer_set(&enic->intr[ENIC_MSIX_WQ], 380 for (i = 0; i < enic->wq_count; i++) {
334 INTR_COALESCE_USEC_TO_HW(tx_coalesce_usecs)); 381 intr = enic_msix_wq_intr(enic, i);
335 vnic_intr_coalescing_timer_set(&enic->intr[ENIC_MSIX_RQ], 382 vnic_intr_coalescing_timer_set(&enic->intr[intr],
336 INTR_COALESCE_USEC_TO_HW(rx_coalesce_usecs)); 383 INTR_COALESCE_USEC_TO_HW(tx_coalesce_usecs));
384 }
385
386 for (i = 0; i < enic->rq_count; i++) {
387 intr = enic_msix_rq_intr(enic, i);
388 vnic_intr_coalescing_timer_set(&enic->intr[intr],
389 INTR_COALESCE_USEC_TO_HW(rx_coalesce_usecs));
390 }
391
337 break; 392 break;
338 default: 393 default:
339 break; 394 break;
@@ -482,34 +537,37 @@ static irqreturn_t enic_isr_legacy(int irq, void *data)
482{ 537{
483 struct net_device *netdev = data; 538 struct net_device *netdev = data;
484 struct enic *enic = netdev_priv(netdev); 539 struct enic *enic = netdev_priv(netdev);
540 unsigned int io_intr = enic_legacy_io_intr();
541 unsigned int err_intr = enic_legacy_err_intr();
542 unsigned int notify_intr = enic_legacy_notify_intr();
485 u32 pba; 543 u32 pba;
486 544
487 vnic_intr_mask(&enic->intr[ENIC_INTX_WQ_RQ]); 545 vnic_intr_mask(&enic->intr[io_intr]);
488 546
489 pba = vnic_intr_legacy_pba(enic->legacy_pba); 547 pba = vnic_intr_legacy_pba(enic->legacy_pba);
490 if (!pba) { 548 if (!pba) {
491 vnic_intr_unmask(&enic->intr[ENIC_INTX_WQ_RQ]); 549 vnic_intr_unmask(&enic->intr[io_intr]);
492 return IRQ_NONE; /* not our interrupt */ 550 return IRQ_NONE; /* not our interrupt */
493 } 551 }
494 552
495 if (ENIC_TEST_INTR(pba, ENIC_INTX_NOTIFY)) { 553 if (ENIC_TEST_INTR(pba, notify_intr)) {
496 vnic_intr_return_all_credits(&enic->intr[ENIC_INTX_NOTIFY]); 554 vnic_intr_return_all_credits(&enic->intr[notify_intr]);
497 enic_notify_check(enic); 555 enic_notify_check(enic);
498 } 556 }
499 557
500 if (ENIC_TEST_INTR(pba, ENIC_INTX_ERR)) { 558 if (ENIC_TEST_INTR(pba, err_intr)) {
501 vnic_intr_return_all_credits(&enic->intr[ENIC_INTX_ERR]); 559 vnic_intr_return_all_credits(&enic->intr[err_intr]);
502 enic_log_q_error(enic); 560 enic_log_q_error(enic);
503 /* schedule recovery from WQ/RQ error */ 561 /* schedule recovery from WQ/RQ error */
504 schedule_work(&enic->reset); 562 schedule_work(&enic->reset);
505 return IRQ_HANDLED; 563 return IRQ_HANDLED;
506 } 564 }
507 565
508 if (ENIC_TEST_INTR(pba, ENIC_INTX_WQ_RQ)) { 566 if (ENIC_TEST_INTR(pba, io_intr)) {
509 if (napi_schedule_prep(&enic->napi)) 567 if (napi_schedule_prep(&enic->napi[0]))
510 __napi_schedule(&enic->napi); 568 __napi_schedule(&enic->napi[0]);
511 } else { 569 } else {
512 vnic_intr_unmask(&enic->intr[ENIC_INTX_WQ_RQ]); 570 vnic_intr_unmask(&enic->intr[io_intr]);
513 } 571 }
514 572
515 return IRQ_HANDLED; 573 return IRQ_HANDLED;
@@ -535,17 +593,17 @@ static irqreturn_t enic_isr_msi(int irq, void *data)
535 * writes). 593 * writes).
536 */ 594 */
537 595
538 napi_schedule(&enic->napi); 596 napi_schedule(&enic->napi[0]);
539 597
540 return IRQ_HANDLED; 598 return IRQ_HANDLED;
541} 599}
542 600
543static irqreturn_t enic_isr_msix_rq(int irq, void *data) 601static irqreturn_t enic_isr_msix_rq(int irq, void *data)
544{ 602{
545 struct enic *enic = data; 603 struct napi_struct *napi = data;
546 604
547 /* schedule NAPI polling for RQ cleanup */ 605 /* schedule NAPI polling for RQ cleanup */
548 napi_schedule(&enic->napi); 606 napi_schedule(napi);
549 607
550 return IRQ_HANDLED; 608 return IRQ_HANDLED;
551} 609}
@@ -553,13 +611,15 @@ static irqreturn_t enic_isr_msix_rq(int irq, void *data)
553static irqreturn_t enic_isr_msix_wq(int irq, void *data) 611static irqreturn_t enic_isr_msix_wq(int irq, void *data)
554{ 612{
555 struct enic *enic = data; 613 struct enic *enic = data;
614 unsigned int cq = enic_cq_wq(enic, 0);
615 unsigned int intr = enic_msix_wq_intr(enic, 0);
556 unsigned int wq_work_to_do = -1; /* no limit */ 616 unsigned int wq_work_to_do = -1; /* no limit */
557 unsigned int wq_work_done; 617 unsigned int wq_work_done;
558 618
559 wq_work_done = vnic_cq_service(&enic->cq[ENIC_CQ_WQ], 619 wq_work_done = vnic_cq_service(&enic->cq[cq],
560 wq_work_to_do, enic_wq_service, NULL); 620 wq_work_to_do, enic_wq_service, NULL);
561 621
562 vnic_intr_return_credits(&enic->intr[ENIC_MSIX_WQ], 622 vnic_intr_return_credits(&enic->intr[intr],
563 wq_work_done, 623 wq_work_done,
564 1 /* unmask intr */, 624 1 /* unmask intr */,
565 1 /* reset intr timer */); 625 1 /* reset intr timer */);
@@ -570,8 +630,9 @@ static irqreturn_t enic_isr_msix_wq(int irq, void *data)
570static irqreturn_t enic_isr_msix_err(int irq, void *data) 630static irqreturn_t enic_isr_msix_err(int irq, void *data)
571{ 631{
572 struct enic *enic = data; 632 struct enic *enic = data;
633 unsigned int intr = enic_msix_err_intr(enic);
573 634
574 vnic_intr_return_all_credits(&enic->intr[ENIC_MSIX_ERR]); 635 vnic_intr_return_all_credits(&enic->intr[intr]);
575 636
576 enic_log_q_error(enic); 637 enic_log_q_error(enic);
577 638
@@ -584,8 +645,9 @@ static irqreturn_t enic_isr_msix_err(int irq, void *data)
584static irqreturn_t enic_isr_msix_notify(int irq, void *data) 645static irqreturn_t enic_isr_msix_notify(int irq, void *data)
585{ 646{
586 struct enic *enic = data; 647 struct enic *enic = data;
648 unsigned int intr = enic_msix_notify_intr(enic);
587 649
588 vnic_intr_return_all_credits(&enic->intr[ENIC_MSIX_NOTIFY]); 650 vnic_intr_return_all_credits(&enic->intr[intr]);
589 enic_notify_check(enic); 651 enic_notify_check(enic);
590 652
591 return IRQ_HANDLED; 653 return IRQ_HANDLED;
@@ -1409,8 +1471,8 @@ static void enic_rq_indicate_buf(struct vnic_rq *rq,
1409 (vlan_tci & CQ_ENET_RQ_DESC_VLAN_TCI_VLAN_MASK)) { 1471 (vlan_tci & CQ_ENET_RQ_DESC_VLAN_TCI_VLAN_MASK)) {
1410 1472
1411 if (netdev->features & NETIF_F_GRO) 1473 if (netdev->features & NETIF_F_GRO)
1412 vlan_gro_receive(&enic->napi, enic->vlan_group, 1474 vlan_gro_receive(&enic->napi[q_number],
1413 vlan_tci, skb); 1475 enic->vlan_group, vlan_tci, skb);
1414 else 1476 else
1415 vlan_hwaccel_receive_skb(skb, 1477 vlan_hwaccel_receive_skb(skb,
1416 enic->vlan_group, vlan_tci); 1478 enic->vlan_group, vlan_tci);
@@ -1418,12 +1480,11 @@ static void enic_rq_indicate_buf(struct vnic_rq *rq,
1418 } else { 1480 } else {
1419 1481
1420 if (netdev->features & NETIF_F_GRO) 1482 if (netdev->features & NETIF_F_GRO)
1421 napi_gro_receive(&enic->napi, skb); 1483 napi_gro_receive(&enic->napi[q_number], skb);
1422 else 1484 else
1423 netif_receive_skb(skb); 1485 netif_receive_skb(skb);
1424 1486
1425 } 1487 }
1426
1427 } else { 1488 } else {
1428 1489
1429 /* Buffer overflow 1490 /* Buffer overflow
@@ -1447,7 +1508,11 @@ static int enic_rq_service(struct vnic_dev *vdev, struct cq_desc *cq_desc,
1447 1508
1448static int enic_poll(struct napi_struct *napi, int budget) 1509static int enic_poll(struct napi_struct *napi, int budget)
1449{ 1510{
1450 struct enic *enic = container_of(napi, struct enic, napi); 1511 struct net_device *netdev = napi->dev;
1512 struct enic *enic = netdev_priv(netdev);
1513 unsigned int cq_rq = enic_cq_rq(enic, 0);
1514 unsigned int cq_wq = enic_cq_wq(enic, 0);
1515 unsigned int intr = enic_legacy_io_intr();
1451 unsigned int rq_work_to_do = budget; 1516 unsigned int rq_work_to_do = budget;
1452 unsigned int wq_work_to_do = -1; /* no limit */ 1517 unsigned int wq_work_to_do = -1; /* no limit */
1453 unsigned int work_done, rq_work_done, wq_work_done; 1518 unsigned int work_done, rq_work_done, wq_work_done;
@@ -1456,10 +1521,10 @@ static int enic_poll(struct napi_struct *napi, int budget)
1456 /* Service RQ (first) and WQ 1521 /* Service RQ (first) and WQ
1457 */ 1522 */
1458 1523
1459 rq_work_done = vnic_cq_service(&enic->cq[ENIC_CQ_RQ], 1524 rq_work_done = vnic_cq_service(&enic->cq[cq_rq],
1460 rq_work_to_do, enic_rq_service, NULL); 1525 rq_work_to_do, enic_rq_service, NULL);
1461 1526
1462 wq_work_done = vnic_cq_service(&enic->cq[ENIC_CQ_WQ], 1527 wq_work_done = vnic_cq_service(&enic->cq[cq_wq],
1463 wq_work_to_do, enic_wq_service, NULL); 1528 wq_work_to_do, enic_wq_service, NULL);
1464 1529
1465 /* Accumulate intr event credits for this polling 1530 /* Accumulate intr event credits for this polling
@@ -1470,7 +1535,7 @@ static int enic_poll(struct napi_struct *napi, int budget)
1470 work_done = rq_work_done + wq_work_done; 1535 work_done = rq_work_done + wq_work_done;
1471 1536
1472 if (work_done > 0) 1537 if (work_done > 0)
1473 vnic_intr_return_credits(&enic->intr[ENIC_INTX_WQ_RQ], 1538 vnic_intr_return_credits(&enic->intr[intr],
1474 work_done, 1539 work_done,
1475 0 /* don't unmask intr */, 1540 0 /* don't unmask intr */,
1476 0 /* don't reset intr timer */); 1541 0 /* don't reset intr timer */);
@@ -1491,7 +1556,7 @@ static int enic_poll(struct napi_struct *napi, int budget)
1491 */ 1556 */
1492 1557
1493 napi_complete(napi); 1558 napi_complete(napi);
1494 vnic_intr_unmask(&enic->intr[ENIC_INTX_WQ_RQ]); 1559 vnic_intr_unmask(&enic->intr[intr]);
1495 } 1560 }
1496 1561
1497 return rq_work_done; 1562 return rq_work_done;
@@ -1499,7 +1564,11 @@ static int enic_poll(struct napi_struct *napi, int budget)
1499 1564
1500static int enic_poll_msix(struct napi_struct *napi, int budget) 1565static int enic_poll_msix(struct napi_struct *napi, int budget)
1501{ 1566{
1502 struct enic *enic = container_of(napi, struct enic, napi); 1567 struct net_device *netdev = napi->dev;
1568 struct enic *enic = netdev_priv(netdev);
1569 unsigned int rq = (napi - &enic->napi[0]);
1570 unsigned int cq = enic_cq_rq(enic, rq);
1571 unsigned int intr = enic_msix_rq_intr(enic, rq);
1503 unsigned int work_to_do = budget; 1572 unsigned int work_to_do = budget;
1504 unsigned int work_done; 1573 unsigned int work_done;
1505 int err; 1574 int err;
@@ -1507,7 +1576,7 @@ static int enic_poll_msix(struct napi_struct *napi, int budget)
1507 /* Service RQ 1576 /* Service RQ
1508 */ 1577 */
1509 1578
1510 work_done = vnic_cq_service(&enic->cq[ENIC_CQ_RQ], 1579 work_done = vnic_cq_service(&enic->cq[cq],
1511 work_to_do, enic_rq_service, NULL); 1580 work_to_do, enic_rq_service, NULL);
1512 1581
1513 /* Return intr event credits for this polling 1582 /* Return intr event credits for this polling
@@ -1516,12 +1585,12 @@ static int enic_poll_msix(struct napi_struct *napi, int budget)
1516 */ 1585 */
1517 1586
1518 if (work_done > 0) 1587 if (work_done > 0)
1519 vnic_intr_return_credits(&enic->intr[ENIC_MSIX_RQ], 1588 vnic_intr_return_credits(&enic->intr[intr],
1520 work_done, 1589 work_done,
1521 0 /* don't unmask intr */, 1590 0 /* don't unmask intr */,
1522 0 /* don't reset intr timer */); 1591 0 /* don't reset intr timer */);
1523 1592
1524 err = vnic_rq_fill(&enic->rq[0], enic->rq_alloc_buf); 1593 err = vnic_rq_fill(&enic->rq[rq], enic->rq_alloc_buf);
1525 1594
1526 /* Buffer allocation failed. Stay in polling mode 1595 /* Buffer allocation failed. Stay in polling mode
1527 * so we can try to fill the ring again. 1596 * so we can try to fill the ring again.
@@ -1537,7 +1606,7 @@ static int enic_poll_msix(struct napi_struct *napi, int budget)
1537 */ 1606 */
1538 1607
1539 napi_complete(napi); 1608 napi_complete(napi);
1540 vnic_intr_unmask(&enic->intr[ENIC_MSIX_RQ]); 1609 vnic_intr_unmask(&enic->intr[intr]);
1541 } 1610 }
1542 1611
1543 return work_done; 1612 return work_done;
@@ -1579,7 +1648,7 @@ static void enic_free_intr(struct enic *enic)
1579static int enic_request_intr(struct enic *enic) 1648static int enic_request_intr(struct enic *enic)
1580{ 1649{
1581 struct net_device *netdev = enic->netdev; 1650 struct net_device *netdev = enic->netdev;
1582 unsigned int i; 1651 unsigned int i, intr;
1583 int err = 0; 1652 int err = 0;
1584 1653
1585 switch (vnic_dev_get_intr_mode(enic->vdev)) { 1654 switch (vnic_dev_get_intr_mode(enic->vdev)) {
@@ -1598,27 +1667,38 @@ static int enic_request_intr(struct enic *enic)
1598 1667
1599 case VNIC_DEV_INTR_MODE_MSIX: 1668 case VNIC_DEV_INTR_MODE_MSIX:
1600 1669
1601 sprintf(enic->msix[ENIC_MSIX_RQ].devname, 1670 for (i = 0; i < enic->rq_count; i++) {
1602 "%.11s-rx-0", netdev->name); 1671 intr = enic_msix_rq_intr(enic, i);
1603 enic->msix[ENIC_MSIX_RQ].isr = enic_isr_msix_rq; 1672 sprintf(enic->msix[intr].devname,
1604 enic->msix[ENIC_MSIX_RQ].devid = enic; 1673 "%.11s-rx-%d", netdev->name, i);
1674 enic->msix[intr].isr = enic_isr_msix_rq;
1675 enic->msix[intr].devid = &enic->napi[i];
1676 }
1605 1677
1606 sprintf(enic->msix[ENIC_MSIX_WQ].devname, 1678 for (i = 0; i < enic->wq_count; i++) {
1607 "%.11s-tx-0", netdev->name); 1679 intr = enic_msix_wq_intr(enic, i);
1608 enic->msix[ENIC_MSIX_WQ].isr = enic_isr_msix_wq; 1680 sprintf(enic->msix[intr].devname,
1609 enic->msix[ENIC_MSIX_WQ].devid = enic; 1681 "%.11s-tx-%d", netdev->name, i);
1682 enic->msix[intr].isr = enic_isr_msix_wq;
1683 enic->msix[intr].devid = enic;
1684 }
1610 1685
1611 sprintf(enic->msix[ENIC_MSIX_ERR].devname, 1686 intr = enic_msix_err_intr(enic);
1687 sprintf(enic->msix[intr].devname,
1612 "%.11s-err", netdev->name); 1688 "%.11s-err", netdev->name);
1613 enic->msix[ENIC_MSIX_ERR].isr = enic_isr_msix_err; 1689 enic->msix[intr].isr = enic_isr_msix_err;
1614 enic->msix[ENIC_MSIX_ERR].devid = enic; 1690 enic->msix[intr].devid = enic;
1615 1691
1616 sprintf(enic->msix[ENIC_MSIX_NOTIFY].devname, 1692 intr = enic_msix_notify_intr(enic);
1693 sprintf(enic->msix[intr].devname,
1617 "%.11s-notify", netdev->name); 1694 "%.11s-notify", netdev->name);
1618 enic->msix[ENIC_MSIX_NOTIFY].isr = enic_isr_msix_notify; 1695 enic->msix[intr].isr = enic_isr_msix_notify;
1619 enic->msix[ENIC_MSIX_NOTIFY].devid = enic; 1696 enic->msix[intr].devid = enic;
1697
1698 for (i = 0; i < ARRAY_SIZE(enic->msix); i++)
1699 enic->msix[i].requested = 0;
1620 1700
1621 for (i = 0; i < ARRAY_SIZE(enic->msix); i++) { 1701 for (i = 0; i < enic->intr_count; i++) {
1622 err = request_irq(enic->msix_entry[i].vector, 1702 err = request_irq(enic->msix_entry[i].vector,
1623 enic->msix[i].isr, 0, 1703 enic->msix[i].isr, 0,
1624 enic->msix[i].devname, 1704 enic->msix[i].devname,
@@ -1664,10 +1744,12 @@ static int enic_dev_notify_set(struct enic *enic)
1664 spin_lock(&enic->devcmd_lock); 1744 spin_lock(&enic->devcmd_lock);
1665 switch (vnic_dev_get_intr_mode(enic->vdev)) { 1745 switch (vnic_dev_get_intr_mode(enic->vdev)) {
1666 case VNIC_DEV_INTR_MODE_INTX: 1746 case VNIC_DEV_INTR_MODE_INTX:
1667 err = vnic_dev_notify_set(enic->vdev, ENIC_INTX_NOTIFY); 1747 err = vnic_dev_notify_set(enic->vdev,
1748 enic_legacy_notify_intr());
1668 break; 1749 break;
1669 case VNIC_DEV_INTR_MODE_MSIX: 1750 case VNIC_DEV_INTR_MODE_MSIX:
1670 err = vnic_dev_notify_set(enic->vdev, ENIC_MSIX_NOTIFY); 1751 err = vnic_dev_notify_set(enic->vdev,
1752 enic_msix_notify_intr(enic));
1671 break; 1753 break;
1672 default: 1754 default:
1673 err = vnic_dev_notify_set(enic->vdev, -1 /* no intr */); 1755 err = vnic_dev_notify_set(enic->vdev, -1 /* no intr */);
@@ -1762,7 +1844,10 @@ static int enic_open(struct net_device *netdev)
1762 enic_set_multicast_list(netdev); 1844 enic_set_multicast_list(netdev);
1763 1845
1764 netif_wake_queue(netdev); 1846 netif_wake_queue(netdev);
1765 napi_enable(&enic->napi); 1847
1848 for (i = 0; i < enic->rq_count; i++)
1849 napi_enable(&enic->napi[i]);
1850
1766 enic_dev_enable(enic); 1851 enic_dev_enable(enic);
1767 1852
1768 for (i = 0; i < enic->intr_count; i++) 1853 for (i = 0; i < enic->intr_count; i++)
@@ -1797,7 +1882,10 @@ static int enic_stop(struct net_device *netdev)
1797 del_timer_sync(&enic->notify_timer); 1882 del_timer_sync(&enic->notify_timer);
1798 1883
1799 enic_dev_disable(enic); 1884 enic_dev_disable(enic);
1800 napi_disable(&enic->napi); 1885
1886 for (i = 0; i < enic->rq_count; i++)
1887 napi_disable(&enic->napi[i]);
1888
1801 netif_carrier_off(netdev); 1889 netif_carrier_off(netdev);
1802 netif_tx_disable(netdev); 1890 netif_tx_disable(netdev);
1803 enic_dev_del_station_addr(enic); 1891 enic_dev_del_station_addr(enic);
@@ -1857,11 +1945,16 @@ static void enic_poll_controller(struct net_device *netdev)
1857{ 1945{
1858 struct enic *enic = netdev_priv(netdev); 1946 struct enic *enic = netdev_priv(netdev);
1859 struct vnic_dev *vdev = enic->vdev; 1947 struct vnic_dev *vdev = enic->vdev;
1948 unsigned int i, intr;
1860 1949
1861 switch (vnic_dev_get_intr_mode(vdev)) { 1950 switch (vnic_dev_get_intr_mode(vdev)) {
1862 case VNIC_DEV_INTR_MODE_MSIX: 1951 case VNIC_DEV_INTR_MODE_MSIX:
1863 enic_isr_msix_rq(enic->pdev->irq, enic); 1952 for (i = 0; i < enic->rq_count; i++) {
1864 enic_isr_msix_wq(enic->pdev->irq, enic); 1953 intr = enic_msix_rq_intr(enic, i);
1954 enic_isr_msix_rq(enic->msix_entry[intr].vector, enic);
1955 }
1956 intr = enic_msix_wq_intr(enic, i);
1957 enic_isr_msix_wq(enic->msix_entry[intr].vector, enic);
1865 break; 1958 break;
1866 case VNIC_DEV_INTR_MODE_MSI: 1959 case VNIC_DEV_INTR_MODE_MSI:
1867 enic_isr_msi(enic->pdev->irq, enic); 1960 enic_isr_msi(enic->pdev->irq, enic);
@@ -1936,19 +2029,73 @@ static int enic_dev_hang_reset(struct enic *enic)
1936 return err; 2029 return err;
1937} 2030}
1938 2031
1939static int enic_set_niccfg(struct enic *enic) 2032static int enic_set_rsskey(struct enic *enic)
2033{
2034 u64 rss_key_buf_pa;
2035 union vnic_rss_key *rss_key_buf_va = NULL;
2036 union vnic_rss_key rss_key = {
2037 .key[0].b = {85, 67, 83, 97, 119, 101, 115, 111, 109, 101},
2038 .key[1].b = {80, 65, 76, 79, 117, 110, 105, 113, 117, 101},
2039 .key[2].b = {76, 73, 78, 85, 88, 114, 111, 99, 107, 115},
2040 .key[3].b = {69, 78, 73, 67, 105, 115, 99, 111, 111, 108},
2041 };
2042 int err;
2043
2044 rss_key_buf_va = pci_alloc_consistent(enic->pdev,
2045 sizeof(union vnic_rss_key), &rss_key_buf_pa);
2046 if (!rss_key_buf_va)
2047 return -ENOMEM;
2048
2049 memcpy(rss_key_buf_va, &rss_key, sizeof(union vnic_rss_key));
2050
2051 spin_lock(&enic->devcmd_lock);
2052 err = enic_set_rss_key(enic,
2053 rss_key_buf_pa,
2054 sizeof(union vnic_rss_key));
2055 spin_unlock(&enic->devcmd_lock);
2056
2057 pci_free_consistent(enic->pdev, sizeof(union vnic_rss_key),
2058 rss_key_buf_va, rss_key_buf_pa);
2059
2060 return err;
2061}
2062
2063static int enic_set_rsscpu(struct enic *enic, u8 rss_hash_bits)
2064{
2065 u64 rss_cpu_buf_pa;
2066 union vnic_rss_cpu *rss_cpu_buf_va = NULL;
2067 unsigned int i;
2068 int err;
2069
2070 rss_cpu_buf_va = pci_alloc_consistent(enic->pdev,
2071 sizeof(union vnic_rss_cpu), &rss_cpu_buf_pa);
2072 if (!rss_cpu_buf_va)
2073 return -ENOMEM;
2074
2075 for (i = 0; i < (1 << rss_hash_bits); i++)
2076 (*rss_cpu_buf_va).cpu[i/4].b[i%4] = i % enic->rq_count;
2077
2078 spin_lock(&enic->devcmd_lock);
2079 err = enic_set_rss_cpu(enic,
2080 rss_cpu_buf_pa,
2081 sizeof(union vnic_rss_cpu));
2082 spin_unlock(&enic->devcmd_lock);
2083
2084 pci_free_consistent(enic->pdev, sizeof(union vnic_rss_cpu),
2085 rss_cpu_buf_va, rss_cpu_buf_pa);
2086
2087 return err;
2088}
2089
2090static int enic_set_niccfg(struct enic *enic, u8 rss_default_cpu,
2091 u8 rss_hash_type, u8 rss_hash_bits, u8 rss_base_cpu, u8 rss_enable)
1940{ 2092{
1941 const u8 rss_default_cpu = 0;
1942 const u8 rss_hash_type = 0;
1943 const u8 rss_hash_bits = 0;
1944 const u8 rss_base_cpu = 0;
1945 const u8 rss_enable = 0;
1946 const u8 tso_ipid_split_en = 0; 2093 const u8 tso_ipid_split_en = 0;
1947 const u8 ig_vlan_strip_en = 1; 2094 const u8 ig_vlan_strip_en = 1;
1948 int err; 2095 int err;
1949 2096
1950 /* Enable VLAN tag stripping. RSS not enabled (yet). 2097 /* Enable VLAN tag stripping.
1951 */ 2098 */
1952 2099
1953 spin_lock(&enic->devcmd_lock); 2100 spin_lock(&enic->devcmd_lock);
1954 err = enic_set_nic_cfg(enic, 2101 err = enic_set_nic_cfg(enic,
@@ -1961,6 +2108,35 @@ static int enic_set_niccfg(struct enic *enic)
1961 return err; 2108 return err;
1962} 2109}
1963 2110
2111static int enic_set_rss_nic_cfg(struct enic *enic)
2112{
2113 struct device *dev = enic_get_dev(enic);
2114 const u8 rss_default_cpu = 0;
2115 const u8 rss_hash_type = NIC_CFG_RSS_HASH_TYPE_IPV4 |
2116 NIC_CFG_RSS_HASH_TYPE_TCP_IPV4 |
2117 NIC_CFG_RSS_HASH_TYPE_IPV6 |
2118 NIC_CFG_RSS_HASH_TYPE_TCP_IPV6;
2119 const u8 rss_hash_bits = 7;
2120 const u8 rss_base_cpu = 0;
2121 u8 rss_enable = ENIC_SETTING(enic, RSS) && (enic->rq_count > 1);
2122
2123 if (rss_enable) {
2124 if (!enic_set_rsskey(enic)) {
2125 if (enic_set_rsscpu(enic, rss_hash_bits)) {
2126 rss_enable = 0;
2127 dev_warn(dev, "RSS disabled, "
2128 "Failed to set RSS cpu indirection table.");
2129 }
2130 } else {
2131 rss_enable = 0;
2132 dev_warn(dev, "RSS disabled, Failed to set RSS key.\n");
2133 }
2134 }
2135
2136 return enic_set_niccfg(enic, rss_default_cpu, rss_hash_type,
2137 rss_hash_bits, rss_base_cpu, rss_enable);
2138}
2139
1964static int enic_dev_hang_notify(struct enic *enic) 2140static int enic_dev_hang_notify(struct enic *enic)
1965{ 2141{
1966 int err; 2142 int err;
@@ -1998,7 +2174,7 @@ static void enic_reset(struct work_struct *work)
1998 enic_dev_hang_reset(enic); 2174 enic_dev_hang_reset(enic);
1999 enic_reset_multicast_list(enic); 2175 enic_reset_multicast_list(enic);
2000 enic_init_vnic_resources(enic); 2176 enic_init_vnic_resources(enic);
2001 enic_set_niccfg(enic); 2177 enic_set_rss_nic_cfg(enic);
2002 enic_dev_set_ig_vlan_rewrite_mode(enic); 2178 enic_dev_set_ig_vlan_rewrite_mode(enic);
2003 enic_open(enic->netdev); 2179 enic_open(enic->netdev);
2004 2180
@@ -2007,12 +2183,12 @@ static void enic_reset(struct work_struct *work)
2007 2183
2008static int enic_set_intr_mode(struct enic *enic) 2184static int enic_set_intr_mode(struct enic *enic)
2009{ 2185{
2010 unsigned int n = 1; 2186 unsigned int n = min_t(unsigned int, enic->rq_count, ENIC_RQ_MAX);
2011 unsigned int m = 1; 2187 unsigned int m = 1;
2012 unsigned int i; 2188 unsigned int i;
2013 2189
2014 /* Set interrupt mode (INTx, MSI, MSI-X) depending 2190 /* Set interrupt mode (INTx, MSI, MSI-X) depending
2015 * system capabilities. 2191 * on system capabilities.
2016 * 2192 *
2017 * Try MSI-X first 2193 * Try MSI-X first
2018 * 2194 *
@@ -2025,21 +2201,47 @@ static int enic_set_intr_mode(struct enic *enic)
2025 for (i = 0; i < n + m + 2; i++) 2201 for (i = 0; i < n + m + 2; i++)
2026 enic->msix_entry[i].entry = i; 2202 enic->msix_entry[i].entry = i;
2027 2203
2028 if (enic->config.intr_mode < 1 && 2204 /* Use multiple RQs if RSS is enabled
2205 */
2206
2207 if (ENIC_SETTING(enic, RSS) &&
2208 enic->config.intr_mode < 1 &&
2029 enic->rq_count >= n && 2209 enic->rq_count >= n &&
2030 enic->wq_count >= m && 2210 enic->wq_count >= m &&
2031 enic->cq_count >= n + m && 2211 enic->cq_count >= n + m &&
2032 enic->intr_count >= n + m + 2 && 2212 enic->intr_count >= n + m + 2) {
2033 !pci_enable_msix(enic->pdev, enic->msix_entry, n + m + 2)) {
2034 2213
2035 enic->rq_count = n; 2214 if (!pci_enable_msix(enic->pdev, enic->msix_entry, n + m + 2)) {
2036 enic->wq_count = m;
2037 enic->cq_count = n + m;
2038 enic->intr_count = n + m + 2;
2039 2215
2040 vnic_dev_set_intr_mode(enic->vdev, VNIC_DEV_INTR_MODE_MSIX); 2216 enic->rq_count = n;
2217 enic->wq_count = m;
2218 enic->cq_count = n + m;
2219 enic->intr_count = n + m + 2;
2041 2220
2042 return 0; 2221 vnic_dev_set_intr_mode(enic->vdev,
2222 VNIC_DEV_INTR_MODE_MSIX);
2223
2224 return 0;
2225 }
2226 }
2227
2228 if (enic->config.intr_mode < 1 &&
2229 enic->rq_count >= 1 &&
2230 enic->wq_count >= m &&
2231 enic->cq_count >= 1 + m &&
2232 enic->intr_count >= 1 + m + 2) {
2233 if (!pci_enable_msix(enic->pdev, enic->msix_entry, 1 + m + 2)) {
2234
2235 enic->rq_count = 1;
2236 enic->wq_count = m;
2237 enic->cq_count = 1 + m;
2238 enic->intr_count = 1 + m + 2;
2239
2240 vnic_dev_set_intr_mode(enic->vdev,
2241 VNIC_DEV_INTR_MODE_MSIX);
2242
2243 return 0;
2244 }
2043 } 2245 }
2044 2246
2045 /* Next try MSI 2247 /* Next try MSI
@@ -2149,7 +2351,11 @@ static const struct net_device_ops enic_netdev_ops = {
2149 2351
2150static void enic_dev_deinit(struct enic *enic) 2352static void enic_dev_deinit(struct enic *enic)
2151{ 2353{
2152 netif_napi_del(&enic->napi); 2354 unsigned int i;
2355
2356 for (i = 0; i < enic->rq_count; i++)
2357 netif_napi_del(&enic->napi[i]);
2358
2153 enic_free_vnic_resources(enic); 2359 enic_free_vnic_resources(enic);
2154 enic_clear_intr_mode(enic); 2360 enic_clear_intr_mode(enic);
2155} 2361}
@@ -2158,6 +2364,7 @@ static int enic_dev_init(struct enic *enic)
2158{ 2364{
2159 struct device *dev = enic_get_dev(enic); 2365 struct device *dev = enic_get_dev(enic);
2160 struct net_device *netdev = enic->netdev; 2366 struct net_device *netdev = enic->netdev;
2367 unsigned int i;
2161 int err; 2368 int err;
2162 2369
2163 /* Get vNIC configuration 2370 /* Get vNIC configuration
@@ -2202,7 +2409,7 @@ static int enic_dev_init(struct enic *enic)
2202 goto err_out_free_vnic_resources; 2409 goto err_out_free_vnic_resources;
2203 } 2410 }
2204 2411
2205 err = enic_set_niccfg(enic); 2412 err = enic_set_rss_nic_cfg(enic);
2206 if (err) { 2413 if (err) {
2207 dev_err(dev, "Failed to config nic, aborting\n"); 2414 dev_err(dev, "Failed to config nic, aborting\n");
2208 goto err_out_free_vnic_resources; 2415 goto err_out_free_vnic_resources;
@@ -2217,10 +2424,12 @@ static int enic_dev_init(struct enic *enic)
2217 2424
2218 switch (vnic_dev_get_intr_mode(enic->vdev)) { 2425 switch (vnic_dev_get_intr_mode(enic->vdev)) {
2219 default: 2426 default:
2220 netif_napi_add(netdev, &enic->napi, enic_poll, 64); 2427 netif_napi_add(netdev, &enic->napi[0], enic_poll, 64);
2221 break; 2428 break;
2222 case VNIC_DEV_INTR_MODE_MSIX: 2429 case VNIC_DEV_INTR_MODE_MSIX:
2223 netif_napi_add(netdev, &enic->napi, enic_poll_msix, 64); 2430 for (i = 0; i < enic->rq_count; i++)
2431 netif_napi_add(netdev, &enic->napi[i],
2432 enic_poll_msix, 64);
2224 break; 2433 break;
2225 } 2434 }
2226 2435
diff --git a/drivers/net/enic/enic_res.c b/drivers/net/enic/enic_res.c
index 19a276cf7681..f111a37419ce 100644
--- a/drivers/net/enic/enic_res.c
+++ b/drivers/net/enic/enic_res.c
@@ -35,6 +35,7 @@
35#include "vnic_intr.h" 35#include "vnic_intr.h"
36#include "vnic_stats.h" 36#include "vnic_stats.h"
37#include "vnic_nic.h" 37#include "vnic_nic.h"
38#include "vnic_rss.h"
38#include "enic_res.h" 39#include "enic_res.h"
39#include "enic.h" 40#include "enic.h"
40 41
@@ -93,13 +94,14 @@ int enic_get_vnic_config(struct enic *enic)
93 INTR_COALESCE_HW_TO_USEC(VNIC_INTR_TIMER_MAX), 94 INTR_COALESCE_HW_TO_USEC(VNIC_INTR_TIMER_MAX),
94 c->intr_timer_usec); 95 c->intr_timer_usec);
95 96
96 dev_info(enic_get_dev(enic), "vNIC MAC addr %pM wq/rq %d/%d\n", 97 dev_info(enic_get_dev(enic),
97 enic->mac_addr, c->wq_desc_count, c->rq_desc_count); 98 "vNIC MAC addr %pM wq/rq %d/%d mtu %d\n",
98 dev_info(enic_get_dev(enic), "vNIC mtu %d csum tx/rx %d/%d " 99 enic->mac_addr, c->wq_desc_count, c->rq_desc_count, c->mtu);
99 "tso/lro %d/%d intr timer %d usec\n", 100 dev_info(enic_get_dev(enic), "vNIC csum tx/rx %d/%d "
100 c->mtu, ENIC_SETTING(enic, TXCSUM), 101 "tso/lro %d/%d intr timer %d usec rss %d\n",
101 ENIC_SETTING(enic, RXCSUM), ENIC_SETTING(enic, TSO), 102 ENIC_SETTING(enic, TXCSUM), ENIC_SETTING(enic, RXCSUM),
102 ENIC_SETTING(enic, LRO), c->intr_timer_usec); 103 ENIC_SETTING(enic, TSO), ENIC_SETTING(enic, LRO),
104 c->intr_timer_usec, ENIC_SETTING(enic, RSS));
103 105
104 return 0; 106 return 0;
105} 107}
@@ -148,6 +150,22 @@ int enic_set_nic_cfg(struct enic *enic, u8 rss_default_cpu, u8 rss_hash_type,
148 return vnic_dev_cmd(enic->vdev, CMD_NIC_CFG, &a0, &a1, wait); 150 return vnic_dev_cmd(enic->vdev, CMD_NIC_CFG, &a0, &a1, wait);
149} 151}
150 152
153int enic_set_rss_key(struct enic *enic, dma_addr_t key_pa, u64 len)
154{
155 u64 a0 = (u64)key_pa, a1 = len;
156 int wait = 1000;
157
158 return vnic_dev_cmd(enic->vdev, CMD_RSS_KEY, &a0, &a1, wait);
159}
160
161int enic_set_rss_cpu(struct enic *enic, dma_addr_t cpu_pa, u64 len)
162{
163 u64 a0 = (u64)cpu_pa, a1 = len;
164 int wait = 1000;
165
166 return vnic_dev_cmd(enic->vdev, CMD_RSS_CPU, &a0, &a1, wait);
167}
168
151void enic_free_vnic_resources(struct enic *enic) 169void enic_free_vnic_resources(struct enic *enic)
152{ 170{
153 unsigned int i; 171 unsigned int i;
@@ -164,18 +182,11 @@ void enic_free_vnic_resources(struct enic *enic)
164 182
165void enic_get_res_counts(struct enic *enic) 183void enic_get_res_counts(struct enic *enic)
166{ 184{
167 enic->wq_count = min_t(int, 185 enic->wq_count = vnic_dev_get_res_count(enic->vdev, RES_TYPE_WQ);
168 vnic_dev_get_res_count(enic->vdev, RES_TYPE_WQ), 186 enic->rq_count = vnic_dev_get_res_count(enic->vdev, RES_TYPE_RQ);
169 ENIC_WQ_MAX); 187 enic->cq_count = vnic_dev_get_res_count(enic->vdev, RES_TYPE_CQ);
170 enic->rq_count = min_t(int, 188 enic->intr_count = vnic_dev_get_res_count(enic->vdev,
171 vnic_dev_get_res_count(enic->vdev, RES_TYPE_RQ), 189 RES_TYPE_INTR_CTRL);
172 ENIC_RQ_MAX);
173 enic->cq_count = min_t(int,
174 vnic_dev_get_res_count(enic->vdev, RES_TYPE_CQ),
175 ENIC_CQ_MAX);
176 enic->intr_count = min_t(int,
177 vnic_dev_get_res_count(enic->vdev, RES_TYPE_INTR_CTRL),
178 ENIC_INTR_MAX);
179 190
180 dev_info(enic_get_dev(enic), 191 dev_info(enic_get_dev(enic),
181 "vNIC resources avail: wq %d rq %d cq %d intr %d\n", 192 "vNIC resources avail: wq %d rq %d cq %d intr %d\n",
diff --git a/drivers/net/enic/enic_res.h b/drivers/net/enic/enic_res.h
index 3c59f541cb5d..83bd172c356c 100644
--- a/drivers/net/enic/enic_res.h
+++ b/drivers/net/enic/enic_res.h
@@ -137,6 +137,8 @@ int enic_del_vlan(struct enic *enic, u16 vlanid);
137int enic_set_nic_cfg(struct enic *enic, u8 rss_default_cpu, u8 rss_hash_type, 137int enic_set_nic_cfg(struct enic *enic, u8 rss_default_cpu, u8 rss_hash_type,
138 u8 rss_hash_bits, u8 rss_base_cpu, u8 rss_enable, u8 tso_ipid_split_en, 138 u8 rss_hash_bits, u8 rss_base_cpu, u8 rss_enable, u8 tso_ipid_split_en,
139 u8 ig_vlan_strip_en); 139 u8 ig_vlan_strip_en);
140int enic_set_rss_key(struct enic *enic, dma_addr_t key_pa, u64 len);
141int enic_set_rss_cpu(struct enic *enic, dma_addr_t cpu_pa, u64 len);
140void enic_get_res_counts(struct enic *enic); 142void enic_get_res_counts(struct enic *enic);
141void enic_init_vnic_resources(struct enic *enic); 143void enic_init_vnic_resources(struct enic *enic);
142int enic_alloc_vnic_resources(struct enic *); 144int enic_alloc_vnic_resources(struct enic *);
diff --git a/drivers/net/enic/vnic_rss.h b/drivers/net/enic/vnic_rss.h
new file mode 100644
index 000000000000..fa421baf45b8
--- /dev/null
+++ b/drivers/net/enic/vnic_rss.h
@@ -0,0 +1,40 @@
1/*
2 * Copyright 2008-2010 Cisco Systems, Inc. All rights reserved.
3 * Copyright 2007 Nuova Systems, Inc. All rights reserved.
4 *
5 * This program is free software; you may redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; version 2 of the License.
8 *
9 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
10 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
11 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
12 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
13 * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
14 * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
15 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
16 * SOFTWARE.
17 */
18
19#ifndef _VNIC_RSS_H_
20#define _VNIC_RSS_H_
21
22/* RSS key array */
23union vnic_rss_key {
24 struct {
25 u8 b[10];
26 u8 b_pad[6];
27 } key[4];
28 u64 raw[8];
29};
30
31/* RSS cpu array */
32union vnic_rss_cpu {
33 struct {
34 u8 b[4] ;
35 u8 b_pad[4];
36 } cpu[32];
37 u64 raw[32];
38};
39
40#endif /* _VNIC_RSS_H_ */