net: Add extack argument to ndo_fdb_add()
[linux-2.6-block.git] / drivers / net / ethernet / intel / ice / ice_main.c
index 333312a1d59572dfe8cef5bc02d745ab7c2920cf..48f033928aa207d715ce7f56fd10a8bca24201b1 100644 (file)
@@ -349,6 +349,9 @@ ice_prepare_for_reset(struct ice_pf *pf)
        /* disable the VSIs and their queues that are not already DOWN */
        ice_pf_dis_all_vsi(pf);
 
+       if (hw->port_info)
+               ice_sched_clear_port(hw->port_info);
+
        ice_shutdown_all_ctrlq(hw);
 
        set_bit(__ICE_PREPARED_FOR_RESET, pf->state);
@@ -405,7 +408,7 @@ static void ice_reset_subtask(struct ice_pf *pf)
        /* When a CORER/GLOBR/EMPR is about to happen, the hardware triggers an
         * OICR interrupt. The OICR handler (ice_misc_intr) determines what type
         * of reset is pending and sets bits in pf->state indicating the reset
-        * type and __ICE_RESET_OICR_RECV.  So, if the latter bit is set
+        * type and __ICE_RESET_OICR_RECV. So, if the latter bit is set
         * prepare for pending reset if not already (for PF software-initiated
         * global resets the software should already be prepared for it as
         * indicated by __ICE_PREPARED_FOR_RESET; for global resets initiated
@@ -1379,14 +1382,13 @@ static void ice_free_irq_msix_misc(struct ice_pf *pf)
  * @pf: board private structure
  *
  * This sets up the handler for MSIX 0, which is used to manage the
- * non-queue interrupts, e.g. AdminQ and errors.  This is not used
+ * non-queue interrupts, e.g. AdminQ and errors. This is not used
  * when in MSI or Legacy interrupt mode.
  */
 static int ice_req_irq_msix_misc(struct ice_pf *pf)
 {
        struct ice_hw *hw = &pf->hw;
        int oicr_idx, err = 0;
-       u8 itr_gran;
        u32 val;
 
        if (!pf->int_name[0])
@@ -1450,10 +1452,8 @@ skip_req_irq:
               PFINT_MBX_CTL_CAUSE_ENA_M);
        wr32(hw, PFINT_MBX_CTL, val);
 
-       itr_gran = hw->itr_gran;
-
        wr32(hw, GLINT_ITR(ICE_RX_ITR, pf->hw_oicr_idx),
-            ITR_TO_REG(ICE_ITR_8K, itr_gran));
+            ITR_REG_ALIGN(ICE_ITR_8K) >> ICE_ITR_GRAN_S);
 
        ice_flush(hw);
        ice_irq_dynamic_ena(hw, NULL, NULL);
@@ -1528,6 +1528,7 @@ static int ice_cfg_netdev(struct ice_vsi *vsi)
 
        csumo_features = NETIF_F_RXCSUM   |
                         NETIF_F_IP_CSUM  |
+                        NETIF_F_SCTP_CRC |
                         NETIF_F_IPV6_CSUM;
 
        vlano_features = NETIF_F_HW_VLAN_CTAG_FILTER |
@@ -1783,7 +1784,7 @@ static void ice_determine_q_usage(struct ice_pf *pf)
 
        pf->num_lan_tx = min_t(int, q_left_tx, num_online_cpus());
 
-       /* only 1 rx queue unless RSS is enabled */
+       /* only 1 Rx queue unless RSS is enabled */
        if (!test_bit(ICE_FLAG_RSS_ENA, pf->flags))
                pf->num_lan_rx = 1;
        else
@@ -1994,6 +1995,23 @@ static int ice_init_interrupt_scheme(struct ice_pf *pf)
        return 0;
 }
 
+/**
+ * ice_verify_itr_gran - verify driver's assumption of ITR granularity
+ * @pf: pointer to the PF structure
+ *
+ * There is no error returned here because the driver will be able to handle a
+ * different ITR granularity, but interrupt moderation will not be accurate if
+ * the driver's assumptions are not verified. This assumption is made so we can
+ * use constants in the hot path instead of accessing structure members.
+ */
+static void ice_verify_itr_gran(struct ice_pf *pf)
+{
+       if (pf->hw.itr_gran != (ICE_ITR_GRAN_S << 1))
+               dev_warn(&pf->pdev->dev,
+                        "%d ITR granularity assumption is invalid, actual ITR granularity is %d. Interrupt moderation will be inaccurate!\n",
+                        (ICE_ITR_GRAN_S << 1), pf->hw.itr_gran);
+}
+
 /**
  * ice_verify_cacheline_size - verify driver's assumption of 64 Byte cache lines
  * @pf: pointer to the PF structure
@@ -2091,8 +2109,7 @@ static int ice_probe(struct pci_dev *pdev,
 
        ice_determine_q_usage(pf);
 
-       pf->num_alloc_vsi = min_t(u16, ICE_MAX_VSI_ALLOC,
-                                 hw->func_caps.guaranteed_num_vsi);
+       pf->num_alloc_vsi = hw->func_caps.guar_num_vsi;
        if (!pf->num_alloc_vsi) {
                err = -EIO;
                goto err_init_pf_unroll;
@@ -2161,6 +2178,7 @@ static int ice_probe(struct pci_dev *pdev,
        mod_timer(&pf->serv_tmr, round_jiffies(jiffies + pf->serv_tmr_period));
 
        ice_verify_cacheline_size(pf);
+       ice_verify_itr_gran(pf);
 
        return 0;
 
@@ -2420,7 +2438,8 @@ static void ice_set_rx_mode(struct net_device *netdev)
  */
 static int ice_fdb_add(struct ndmsg *ndm, struct nlattr __always_unused *tb[],
                       struct net_device *dev, const unsigned char *addr,
-                      u16 vid, u16 flags)
+                      u16 vid, u16 flags,
+                      struct netlink_ext_ack *extack)
 {
        int err;
 
@@ -2545,7 +2564,7 @@ static int ice_vsi_cfg(struct ice_vsi *vsi)
                        return err;
        }
 
-       err = ice_vsi_cfg_txqs(vsi);
+       err = ice_vsi_cfg_lan_txqs(vsi);
        if (!err)
                err = ice_vsi_cfg_rxqs(vsi);
 
@@ -2563,8 +2582,12 @@ static void ice_napi_enable_all(struct ice_vsi *vsi)
        if (!vsi->netdev)
                return;
 
-       for (q_idx = 0; q_idx < vsi->num_q_vectors; q_idx++)
-               napi_enable(&vsi->q_vectors[q_idx]->napi);
+       for (q_idx = 0; q_idx < vsi->num_q_vectors; q_idx++) {
+               struct ice_q_vector *q_vector = vsi->q_vectors[q_idx];
+
+               if (q_vector->rx.ring || q_vector->tx.ring)
+                       napi_enable(&q_vector->napi);
+       }
 }
 
 /**
@@ -2931,8 +2954,91 @@ static void ice_napi_disable_all(struct ice_vsi *vsi)
        if (!vsi->netdev)
                return;
 
-       for (q_idx = 0; q_idx < vsi->num_q_vectors; q_idx++)
-               napi_disable(&vsi->q_vectors[q_idx]->napi);
+       for (q_idx = 0; q_idx < vsi->num_q_vectors; q_idx++) {
+               struct ice_q_vector *q_vector = vsi->q_vectors[q_idx];
+
+               if (q_vector->rx.ring || q_vector->tx.ring)
+                       napi_disable(&q_vector->napi);
+       }
+}
+
+/**
+ * ice_force_phys_link_state - Force the physical link state
+ * @vsi: VSI to force the physical link state to up/down
+ * @link_up: true/false indicates to set the physical link to up/down
+ *
+ * Force the physical link state by getting the current PHY capabilities from
+ * hardware and setting the PHY config based on the determined capabilities. If
+ * link changes a link event will be triggered because both the Enable Automatic
+ * Link Update and LESM Enable bits are set when setting the PHY capabilities.
+ *
+ * Returns 0 on success, negative on failure
+ */
+static int ice_force_phys_link_state(struct ice_vsi *vsi, bool link_up)
+{
+       struct ice_aqc_get_phy_caps_data *pcaps;
+       struct ice_aqc_set_phy_cfg_data *cfg;
+       struct ice_port_info *pi;
+       struct device *dev;
+       int retcode;
+
+       if (!vsi || !vsi->port_info || !vsi->back)
+               return -EINVAL;
+       if (vsi->type != ICE_VSI_PF)
+               return 0;
+
+       dev = &vsi->back->pdev->dev;
+
+       pi = vsi->port_info;
+
+       pcaps = devm_kzalloc(dev, sizeof(*pcaps), GFP_KERNEL);
+       if (!pcaps)
+               return -ENOMEM;
+
+       retcode = ice_aq_get_phy_caps(pi, false, ICE_AQC_REPORT_SW_CFG, pcaps,
+                                     NULL);
+       if (retcode) {
+               dev_err(dev,
+                       "Failed to get phy capabilities, VSI %d error %d\n",
+                       vsi->vsi_num, retcode);
+               retcode = -EIO;
+               goto out;
+       }
+
+       /* No change in link */
+       if (link_up == !!(pcaps->caps & ICE_AQC_PHY_EN_LINK) &&
+           link_up == !!(pi->phy.link_info.link_info & ICE_AQ_LINK_UP))
+               goto out;
+
+       cfg = devm_kzalloc(dev, sizeof(*cfg), GFP_KERNEL);
+       if (!cfg) {
+               retcode = -ENOMEM;
+               goto out;
+       }
+
+       cfg->phy_type_low = pcaps->phy_type_low;
+       cfg->phy_type_high = pcaps->phy_type_high;
+       cfg->caps = pcaps->caps | ICE_AQ_PHY_ENA_AUTO_LINK_UPDT;
+       cfg->low_power_ctrl = pcaps->low_power_ctrl;
+       cfg->eee_cap = pcaps->eee_cap;
+       cfg->eeer_value = pcaps->eeer_value;
+       cfg->link_fec_opt = pcaps->link_fec_options;
+       if (link_up)
+               cfg->caps |= ICE_AQ_PHY_ENA_LINK;
+       else
+               cfg->caps &= ~ICE_AQ_PHY_ENA_LINK;
+
+       retcode = ice_aq_set_phy_cfg(&vsi->back->hw, pi->lport, cfg, NULL);
+       if (retcode) {
+               dev_err(dev, "Failed to set phy config, VSI %d error %d\n",
+                       vsi->vsi_num, retcode);
+               retcode = -EIO;
+       }
+
+       devm_kfree(dev, cfg);
+out:
+       devm_kfree(dev, pcaps);
+       return retcode;
 }
 
 /**
@@ -2941,7 +3047,7 @@ static void ice_napi_disable_all(struct ice_vsi *vsi)
  */
 int ice_down(struct ice_vsi *vsi)
 {
-       int i, tx_err, rx_err;
+       int i, tx_err, rx_err, link_err = 0;
 
        /* Caller of this function is expected to set the
         * vsi->state __ICE_DOWN bit
@@ -2952,7 +3058,8 @@ int ice_down(struct ice_vsi *vsi)
        }
 
        ice_vsi_dis_irq(vsi);
-       tx_err = ice_vsi_stop_tx_rings(vsi, ICE_NO_RESET, 0);
+
+       tx_err = ice_vsi_stop_lan_tx_rings(vsi, ICE_NO_RESET, 0);
        if (tx_err)
                netdev_err(vsi->netdev,
                           "Failed stop Tx rings, VSI %d error %d\n",
@@ -2966,13 +3073,21 @@ int ice_down(struct ice_vsi *vsi)
 
        ice_napi_disable_all(vsi);
 
+       if (test_bit(ICE_FLAG_LINK_DOWN_ON_CLOSE_ENA, vsi->back->flags)) {
+               link_err = ice_force_phys_link_state(vsi, false);
+               if (link_err)
+                       netdev_err(vsi->netdev,
+                                  "Failed to set physical link down, VSI %d error %d\n",
+                                  vsi->vsi_num, link_err);
+       }
+
        ice_for_each_txq(vsi, i)
                ice_clean_tx_ring(vsi->tx_rings[i]);
 
        ice_for_each_rxq(vsi, i)
                ice_clean_rx_ring(vsi->rx_rings[i]);
 
-       if (tx_err || rx_err) {
+       if (tx_err || rx_err || link_err) {
                netdev_err(vsi->netdev,
                           "Failed to close VSI 0x%04X on switch 0x%04X\n",
                           vsi->vsi_num, vsi->vsw->sw_id);
@@ -3138,8 +3253,9 @@ static void ice_vsi_release_all(struct ice_pf *pf)
 /**
  * ice_dis_vsi - pause a VSI
  * @vsi: the VSI being paused
+ * @locked: is the rtnl_lock already held
  */
-static void ice_dis_vsi(struct ice_vsi *vsi)
+static void ice_dis_vsi(struct ice_vsi *vsi, bool locked)
 {
        if (test_bit(__ICE_DOWN, vsi->state))
                return;
@@ -3148,9 +3264,13 @@ static void ice_dis_vsi(struct ice_vsi *vsi)
 
        if (vsi->type == ICE_VSI_PF && vsi->netdev) {
                if (netif_running(vsi->netdev)) {
-                       rtnl_lock();
-                       vsi->netdev->netdev_ops->ndo_stop(vsi->netdev);
-                       rtnl_unlock();
+                       if (!locked) {
+                               rtnl_lock();
+                               vsi->netdev->netdev_ops->ndo_stop(vsi->netdev);
+                               rtnl_unlock();
+                       } else {
+                               vsi->netdev->netdev_ops->ndo_stop(vsi->netdev);
+                       }
                } else {
                        ice_vsi_close(vsi);
                }
@@ -3189,7 +3309,7 @@ static void ice_pf_dis_all_vsi(struct ice_pf *pf)
 
        ice_for_each_vsi(pf, v)
                if (pf->vsi[v])
-                       ice_dis_vsi(pf->vsi[v]);
+                       ice_dis_vsi(pf->vsi[v], false);
 }
 
 /**
@@ -3618,6 +3738,7 @@ static int ice_vsi_update_bridge_mode(struct ice_vsi *vsi, u16 bmode)
  * @dev: the netdev being configured
  * @nlh: RTNL message
  * @flags: bridge setlink flags
+ * @extack: netlink extended ack
  *
  * Sets the bridge mode (VEB/VEPA) of the switch to which the netdev (VSI) is
  * hooked up to. Iterates through the PF VSI list and sets the loopback mode (if
@@ -3626,7 +3747,8 @@ static int ice_vsi_update_bridge_mode(struct ice_vsi *vsi, u16 bmode)
  */
 static int
 ice_bridge_setlink(struct net_device *dev, struct nlmsghdr *nlh,
-                  u16 __always_unused flags)
+                  u16 __always_unused flags,
+                  struct netlink_ext_ack __always_unused *extack)
 {
        struct ice_netdev_priv *np = netdev_priv(dev);
        struct ice_pf *pf = np->vsi->back;
@@ -3668,7 +3790,7 @@ ice_bridge_setlink(struct net_device *dev, struct nlmsghdr *nlh,
                 */
                status = ice_update_sw_rule_bridge_mode(hw);
                if (status) {
-                       netdev_err(dev, "update SW_RULE for bridge mode failed,  = %d err %d aq_err %d\n",
+                       netdev_err(dev, "switch rule update failed, mode = %d err %d aq_err %d\n",
                                   mode, status, hw->adminq.sq_last_status);
                        /* revert hw->evb_veb */
                        hw->evb_veb = (pf_sw->bridge_mode == BRIDGE_MODE_VEB);
@@ -3691,40 +3813,36 @@ static void ice_tx_timeout(struct net_device *netdev)
        struct ice_ring *tx_ring = NULL;
        struct ice_vsi *vsi = np->vsi;
        struct ice_pf *pf = vsi->back;
-       u32 head, val = 0, i;
        int hung_queue = -1;
+       u32 i;
 
        pf->tx_timeout_count++;
 
-       /* find the stopped queue the same way the stack does */
+       /* find the stopped queue the same way dev_watchdog() does */
        for (i = 0; i < netdev->num_tx_queues; i++) {
-               struct netdev_queue *q;
                unsigned long trans_start;
+               struct netdev_queue *q;
 
                q = netdev_get_tx_queue(netdev, i);
                trans_start = q->trans_start;
                if (netif_xmit_stopped(q) &&
                    time_after(jiffies,
-                              (trans_start + netdev->watchdog_timeo))) {
+                              trans_start + netdev->watchdog_timeo)) {
                        hung_queue = i;
                        break;
                }
        }
 
-       if (i == netdev->num_tx_queues) {
+       if (i == netdev->num_tx_queues)
                netdev_info(netdev, "tx_timeout: no netdev hung queue found\n");
-       } else {
+       else
                /* now that we have an index, find the tx_ring struct */
-               for (i = 0; i < vsi->num_txq; i++) {
-                       if (vsi->tx_rings[i] && vsi->tx_rings[i]->desc) {
-                               if (hung_queue ==
-                                   vsi->tx_rings[i]->q_index) {
+               for (i = 0; i < vsi->num_txq; i++)
+                       if (vsi->tx_rings[i] && vsi->tx_rings[i]->desc)
+                               if (hung_queue == vsi->tx_rings[i]->q_index) {
                                        tx_ring = vsi->tx_rings[i];
                                        break;
                                }
-                       }
-               }
-       }
 
        /* Reset recovery level if enough time has elapsed after last timeout.
         * Also ensure no new reset action happens before next timeout period.
@@ -3736,17 +3854,20 @@ static void ice_tx_timeout(struct net_device *netdev)
                return;
 
        if (tx_ring) {
-               head = tx_ring->next_to_clean;
+               struct ice_hw *hw = &pf->hw;
+               u32 head, val = 0;
+
+               head = (rd32(hw, QTX_COMM_HEAD(vsi->txq_map[hung_queue])) &
+                       QTX_COMM_HEAD_HEAD_M) >> QTX_COMM_HEAD_HEAD_S;
                /* Read interrupt register */
                if (test_bit(ICE_FLAG_MSIX_ENA, pf->flags))
-                       val = rd32(&pf->hw,
+                       val = rd32(hw,
                                   GLINT_DYN_CTL(tx_ring->q_vector->v_idx +
-                                       tx_ring->vsi->hw_base_vector));
+                                                tx_ring->vsi->hw_base_vector));
 
-               netdev_info(netdev, "tx_timeout: VSI_num: %d, Q %d, NTC: 0x%x, HWB: 0x%x, NTU: 0x%x, TAIL: 0x%x, INT: 0x%x\n",
+               netdev_info(netdev, "tx_timeout: VSI_num: %d, Q %d, NTC: 0x%x, HW_HEAD: 0x%x, NTU: 0x%x, INT: 0x%x\n",
                            vsi->vsi_num, hung_queue, tx_ring->next_to_clean,
-                           head, tx_ring->next_to_use,
-                           readl(tx_ring->tail), val);
+                           head, tx_ring->next_to_use, val);
        }
 
        pf->tx_timeout_last_recovery = jiffies;
@@ -3780,7 +3901,7 @@ static void ice_tx_timeout(struct net_device *netdev)
  * @netdev: network interface device structure
  *
  * The open entry point is called when a network interface is made
- * active by the system (IFF_UP).  At this point all resources needed
+ * active by the system (IFF_UP). At this point all resources needed
  * for transmit and receive operations are allocated, the interrupt
  * handler is registered with the OS, the netdev watchdog is enabled,
  * and the stack is notified that the interface is ready.
@@ -3800,8 +3921,14 @@ static int ice_open(struct net_device *netdev)
 
        netif_carrier_off(netdev);
 
-       err = ice_vsi_open(vsi);
+       err = ice_force_phys_link_state(vsi, true);
+       if (err) {
+               netdev_err(netdev,
+                          "Failed to set physical link up, error %d\n", err);
+               return err;
+       }
 
+       err = ice_vsi_open(vsi);
        if (err)
                netdev_err(netdev, "Failed to open VSI 0x%04X on switch 0x%04X\n",
                           vsi->vsi_num, vsi->vsw->sw_id);
@@ -3813,7 +3940,7 @@ static int ice_open(struct net_device *netdev)
  * @netdev: network interface device structure
  *
  * The stop entry point is called when an interface is de-activated by the OS,
- * and the netdevice enters the DOWN state.  The hardware is still under the
+ * and the netdevice enters the DOWN state. The hardware is still under the
  * driver's control, but the netdev interface is disabled.
  *
  * Returns success only - not allowed to fail
@@ -3842,14 +3969,14 @@ ice_features_check(struct sk_buff *skb,
        size_t len;
 
        /* No point in doing any of this if neither checksum nor GSO are
-        * being requested for this frame.  We can rule out both by just
+        * being requested for this frame. We can rule out both by just
         * checking for CHECKSUM_PARTIAL
         */
        if (skb->ip_summed != CHECKSUM_PARTIAL)
                return features;
 
        /* We cannot support GSO if the MSS is going to be less than
-        * 64 bytes.  If it is then we need to drop support for GSO.
+        * 64 bytes. If it is then we need to drop support for GSO.
         */
        if (skb_is_gso(skb) && (skb_shinfo(skb)->gso_size < 64))
                features &= ~NETIF_F_GSO_MASK;