aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/net/ixgbe/ixgbe.h2
-rw-r--r--drivers/net/ixgbe/ixgbe_main.c1
-rw-r--r--drivers/net/ixgbe/ixgbe_sriov.c85
-rw-r--r--drivers/net/ixgbe/ixgbe_sriov.h1
-rw-r--r--drivers/net/ixgbe/ixgbe_type.h6
5 files changed, 93 insertions, 2 deletions
diff --git a/drivers/net/ixgbe/ixgbe.h b/drivers/net/ixgbe/ixgbe.h
index b7e62d568b85..8d468028bb55 100644
--- a/drivers/net/ixgbe/ixgbe.h
+++ b/drivers/net/ixgbe/ixgbe.h
@@ -118,6 +118,7 @@ struct vf_data_storage {
118 bool pf_set_mac; 118 bool pf_set_mac;
119 u16 pf_vlan; /* When set, guest VLAN config not allowed. */ 119 u16 pf_vlan; /* When set, guest VLAN config not allowed. */
120 u16 pf_qos; 120 u16 pf_qos;
121 u16 tx_rate;
121}; 122};
122 123
123/* wrapper around a pointer to a socket buffer, 124/* wrapper around a pointer to a socket buffer,
@@ -468,6 +469,7 @@ struct ixgbe_adapter {
468 DECLARE_BITMAP(active_vfs, IXGBE_MAX_VF_FUNCTIONS); 469 DECLARE_BITMAP(active_vfs, IXGBE_MAX_VF_FUNCTIONS);
469 unsigned int num_vfs; 470 unsigned int num_vfs;
470 struct vf_data_storage *vfinfo; 471 struct vf_data_storage *vfinfo;
472 int vf_rate_link_speed;
471}; 473};
472 474
473enum ixbge_state_t { 475enum ixbge_state_t {
diff --git a/drivers/net/ixgbe/ixgbe_main.c b/drivers/net/ixgbe/ixgbe_main.c
index 38f9758c4c44..f17e4a7ee731 100644
--- a/drivers/net/ixgbe/ixgbe_main.c
+++ b/drivers/net/ixgbe/ixgbe_main.c
@@ -6217,6 +6217,7 @@ static void ixgbe_watchdog_task(struct work_struct *work)
6217 (flow_tx ? "TX" : "None")))); 6217 (flow_tx ? "TX" : "None"))));
6218 6218
6219 netif_carrier_on(netdev); 6219 netif_carrier_on(netdev);
6220 ixgbe_check_vf_rate_limit(adapter);
6220 } else { 6221 } else {
6221 /* Force detection of hung controller */ 6222 /* Force detection of hung controller */
6222 for (i = 0; i < adapter->num_tx_queues; i++) { 6223 for (i = 0; i < adapter->num_tx_queues; i++) {
diff --git a/drivers/net/ixgbe/ixgbe_sriov.c b/drivers/net/ixgbe/ixgbe_sriov.c
index 58c9b45989ff..6e50d8328942 100644
--- a/drivers/net/ixgbe/ixgbe_sriov.c
+++ b/drivers/net/ixgbe/ixgbe_sriov.c
@@ -478,9 +478,90 @@ out:
478 return err; 478 return err;
479} 479}
480 480
481static int ixgbe_link_mbps(int internal_link_speed)
482{
483 switch (internal_link_speed) {
484 case IXGBE_LINK_SPEED_100_FULL:
485 return 100;
486 case IXGBE_LINK_SPEED_1GB_FULL:
487 return 1000;
488 case IXGBE_LINK_SPEED_10GB_FULL:
489 return 10000;
490 default:
491 return 0;
492 }
493}
494
495static void ixgbe_set_vf_rate_limit(struct ixgbe_hw *hw, int vf, int tx_rate,
496 int link_speed)
497{
498 int rf_dec, rf_int;
499 u32 bcnrc_val;
500
501 if (tx_rate != 0) {
502 /* Calculate the rate factor values to set */
503 rf_int = link_speed / tx_rate;
504 rf_dec = (link_speed - (rf_int * tx_rate));
505 rf_dec = (rf_dec * (1<<IXGBE_RTTBCNRC_RF_INT_SHIFT)) / tx_rate;
506
507 bcnrc_val = IXGBE_RTTBCNRC_RS_ENA;
508 bcnrc_val |= ((rf_int<<IXGBE_RTTBCNRC_RF_INT_SHIFT) &
509 IXGBE_RTTBCNRC_RF_INT_MASK);
510 bcnrc_val |= (rf_dec & IXGBE_RTTBCNRC_RF_DEC_MASK);
511 } else {
512 bcnrc_val = 0;
513 }
514
515 IXGBE_WRITE_REG(hw, IXGBE_RTTDQSEL, 2*vf); /* vf Y uses queue 2*Y */
516 IXGBE_WRITE_REG(hw, IXGBE_RTTBCNRC, bcnrc_val);
517}
518
519void ixgbe_check_vf_rate_limit(struct ixgbe_adapter *adapter)
520{
521 int actual_link_speed, i;
522 bool reset_rate = false;
523
524 /* VF Tx rate limit was not set */
525 if (adapter->vf_rate_link_speed == 0)
526 return;
527
528 actual_link_speed = ixgbe_link_mbps(adapter->link_speed);
529 if (actual_link_speed != adapter->vf_rate_link_speed) {
530 reset_rate = true;
531 adapter->vf_rate_link_speed = 0;
532 dev_info(&adapter->pdev->dev,
533 "Link speed has been changed. VF Transmit rate "
534 "is disabled\n");
535 }
536
537 for (i = 0; i < adapter->num_vfs; i++) {
538 if (reset_rate)
539 adapter->vfinfo[i].tx_rate = 0;
540
541 ixgbe_set_vf_rate_limit(&adapter->hw, i,
542 adapter->vfinfo[i].tx_rate,
543 actual_link_speed);
544 }
545}
546
481int ixgbe_ndo_set_vf_bw(struct net_device *netdev, int vf, int tx_rate) 547int ixgbe_ndo_set_vf_bw(struct net_device *netdev, int vf, int tx_rate)
482{ 548{
483 return -EOPNOTSUPP; 549 struct ixgbe_adapter *adapter = netdev_priv(netdev);
550 struct ixgbe_hw *hw = &adapter->hw;
551 int actual_link_speed;
552
553 actual_link_speed = ixgbe_link_mbps(adapter->link_speed);
554 if ((vf >= adapter->num_vfs) || (!adapter->link_up) ||
555 (tx_rate > actual_link_speed) || (actual_link_speed != 10000) ||
556 ((tx_rate != 0) && (tx_rate <= 10)))
557 /* rate limit cannot be set to 10Mb or less in 10Gb adapters */
558 return -EINVAL;
559
560 adapter->vf_rate_link_speed = actual_link_speed;
561 adapter->vfinfo[vf].tx_rate = (u16)tx_rate;
562 ixgbe_set_vf_rate_limit(hw, vf, tx_rate, actual_link_speed);
563
564 return 0;
484} 565}
485 566
486int ixgbe_ndo_get_vf_config(struct net_device *netdev, 567int ixgbe_ndo_get_vf_config(struct net_device *netdev,
@@ -491,7 +572,7 @@ int ixgbe_ndo_get_vf_config(struct net_device *netdev,
491 return -EINVAL; 572 return -EINVAL;
492 ivi->vf = vf; 573 ivi->vf = vf;
493 memcpy(&ivi->mac, adapter->vfinfo[vf].vf_mac_addresses, ETH_ALEN); 574 memcpy(&ivi->mac, adapter->vfinfo[vf].vf_mac_addresses, ETH_ALEN);
494 ivi->tx_rate = 0; 575 ivi->tx_rate = adapter->vfinfo[vf].tx_rate;
495 ivi->vlan = adapter->vfinfo[vf].pf_vlan; 576 ivi->vlan = adapter->vfinfo[vf].pf_vlan;
496 ivi->qos = adapter->vfinfo[vf].pf_qos; 577 ivi->qos = adapter->vfinfo[vf].pf_qos;
497 return 0; 578 return 0;
diff --git a/drivers/net/ixgbe/ixgbe_sriov.h b/drivers/net/ixgbe/ixgbe_sriov.h
index e7dd029d576a..34175564bb78 100644
--- a/drivers/net/ixgbe/ixgbe_sriov.h
+++ b/drivers/net/ixgbe/ixgbe_sriov.h
@@ -40,6 +40,7 @@ int ixgbe_ndo_set_vf_vlan(struct net_device *netdev, int queue, u16 vlan,
40int ixgbe_ndo_set_vf_bw(struct net_device *netdev, int vf, int tx_rate); 40int ixgbe_ndo_set_vf_bw(struct net_device *netdev, int vf, int tx_rate);
41int ixgbe_ndo_get_vf_config(struct net_device *netdev, 41int ixgbe_ndo_get_vf_config(struct net_device *netdev,
42 int vf, struct ifla_vf_info *ivi); 42 int vf, struct ifla_vf_info *ivi);
43void ixgbe_check_vf_rate_limit(struct ixgbe_adapter *adapter);
43 44
44#endif /* _IXGBE_SRIOV_H_ */ 45#endif /* _IXGBE_SRIOV_H_ */
45 46
diff --git a/drivers/net/ixgbe/ixgbe_type.h b/drivers/net/ixgbe/ixgbe_type.h
index 63d862d3fd90..25c1fb7eda06 100644
--- a/drivers/net/ixgbe/ixgbe_type.h
+++ b/drivers/net/ixgbe/ixgbe_type.h
@@ -533,6 +533,12 @@
533#define IXGBE_RTTDTECC 0x04990 533#define IXGBE_RTTDTECC 0x04990
534#define IXGBE_RTTDTECC_NO_BCN 0x00000100 534#define IXGBE_RTTDTECC_NO_BCN 0x00000100
535#define IXGBE_RTTBCNRC 0x04984 535#define IXGBE_RTTBCNRC 0x04984
536#define IXGBE_RTTBCNRC_RS_ENA 0x80000000
537#define IXGBE_RTTBCNRC_RF_DEC_MASK 0x00003FFF
538#define IXGBE_RTTBCNRC_RF_INT_SHIFT 14
539#define IXGBE_RTTBCNRC_RF_INT_MASK \
540 (IXGBE_RTTBCNRC_RF_DEC_MASK << IXGBE_RTTBCNRC_RF_INT_SHIFT)
541
536 542
537/* FCoE registers */ 543/* FCoE registers */
538#define IXGBE_FCPTRL 0x02410 /* FC User Desc. PTR Low */ 544#define IXGBE_FCPTRL 0x02410 /* FC User Desc. PTR Low */