]> git.karo-electronics.de Git - linux-beck.git/blobdiff - drivers/net/ethernet/intel/i40e/i40e_main.c
Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/jkirsher/net...
[linux-beck.git] / drivers / net / ethernet / intel / i40e / i40e_main.c
index aadc604329808f7c503130472251a60800788cf9..c3858e7f0e66f032de3899082e29cfbfdea056b9 100644 (file)
@@ -39,7 +39,7 @@ static const char i40e_driver_string[] =
 
 #define DRV_VERSION_MAJOR 1
 #define DRV_VERSION_MINOR 2
-#define DRV_VERSION_BUILD 9
+#define DRV_VERSION_BUILD 10
 #define DRV_VERSION __stringify(DRV_VERSION_MAJOR) "." \
             __stringify(DRV_VERSION_MINOR) "." \
             __stringify(DRV_VERSION_BUILD)    DRV_KERN
@@ -1566,6 +1566,12 @@ static void i40e_vsi_setup_queue_map(struct i40e_vsi *vsi,
 
        /* Set actual Tx/Rx queue pairs */
        vsi->num_queue_pairs = offset;
+       if ((vsi->type == I40E_VSI_MAIN) && (numtc == 1)) {
+               if (vsi->req_queue_pairs > 0)
+                       vsi->num_queue_pairs = vsi->req_queue_pairs;
+               else
+                       vsi->num_queue_pairs = pf->num_lan_msix;
+       }
 
        /* Scheduler section valid can only be set for ADD VSI */
        if (is_add) {
@@ -4101,7 +4107,7 @@ static u8 i40e_pf_get_num_tc(struct i40e_pf *pf)
        if (pf->hw.func_caps.iscsi)
                enabled_tc =  i40e_get_iscsi_tc_map(pf);
        else
-               enabled_tc = pf->hw.func_caps.enabled_tcmap;
+               return 1; /* Only TC0 */
 
        /* At least have TC0 */
        enabled_tc = (enabled_tc ? enabled_tc : 0x1);
@@ -4151,11 +4157,11 @@ static u8 i40e_pf_get_tc_map(struct i40e_pf *pf)
        if (!(pf->flags & I40E_FLAG_MFP_ENABLED))
                return i40e_dcb_get_enabled_tc(&pf->hw.local_dcbx_config);
 
-       /* MPF enabled and iSCSI PF type */
+       /* MFP enabled and iSCSI PF type */
        if (pf->hw.func_caps.iscsi)
                return i40e_get_iscsi_tc_map(pf);
        else
-               return pf->hw.func_caps.enabled_tcmap;
+               return i40e_pf_get_default_tc(pf);
 }
 
 /**
@@ -4545,6 +4551,11 @@ static int i40e_init_pf_dcb(struct i40e_pf *pf)
        struct i40e_hw *hw = &pf->hw;
        int err = 0;
 
+       /* Do not enable DCB for SW1 and SW2 images even if the FW is capable */
+       if (((pf->hw.aq.fw_maj_ver == 4) && (pf->hw.aq.fw_min_ver < 33)) ||
+           (pf->hw.aq.fw_maj_ver < 4))
+               goto out;
+
        /* Get the initial DCB configuration */
        err = i40e_init_dcb(hw);
        if (!err) {
@@ -5155,7 +5166,6 @@ static int i40e_handle_lldp_event(struct i40e_pf *pf,
        struct i40e_aqc_lldp_get_mib *mib =
                (struct i40e_aqc_lldp_get_mib *)&e->desc.params.raw;
        struct i40e_hw *hw = &pf->hw;
-       struct i40e_dcbx_config *dcbx_cfg = &hw->local_dcbx_config;
        struct i40e_dcbx_config tmp_dcbx_cfg;
        bool need_reconfig = false;
        int ret = 0;
@@ -5188,8 +5198,10 @@ static int i40e_handle_lldp_event(struct i40e_pf *pf,
 
        memset(&tmp_dcbx_cfg, 0, sizeof(tmp_dcbx_cfg));
        /* Store the old configuration */
-       tmp_dcbx_cfg = *dcbx_cfg;
+       memcpy(&tmp_dcbx_cfg, &hw->local_dcbx_config, sizeof(tmp_dcbx_cfg));
 
+       /* Reset the old DCBx configuration data */
+       memset(&hw->local_dcbx_config, 0, sizeof(hw->local_dcbx_config));
        /* Get updated DCBX data from firmware */
        ret = i40e_get_dcb_config(&pf->hw);
        if (ret) {
@@ -5198,20 +5210,22 @@ static int i40e_handle_lldp_event(struct i40e_pf *pf,
        }
 
        /* No change detected in DCBX configs */
-       if (!memcmp(&tmp_dcbx_cfg, dcbx_cfg, sizeof(tmp_dcbx_cfg))) {
+       if (!memcmp(&tmp_dcbx_cfg, &hw->local_dcbx_config,
+                   sizeof(tmp_dcbx_cfg))) {
                dev_dbg(&pf->pdev->dev, "No change detected in DCBX configuration.\n");
                goto exit;
        }
 
-       need_reconfig = i40e_dcb_need_reconfig(pf, &tmp_dcbx_cfg, dcbx_cfg);
+       need_reconfig = i40e_dcb_need_reconfig(pf, &tmp_dcbx_cfg,
+                                              &hw->local_dcbx_config);
 
-       i40e_dcbnl_flush_apps(pf, dcbx_cfg);
+       i40e_dcbnl_flush_apps(pf, &tmp_dcbx_cfg, &hw->local_dcbx_config);
 
        if (!need_reconfig)
                goto exit;
 
        /* Enable DCB tagging only when more than one TC */
-       if (i40e_dcb_get_num_tc(dcbx_cfg) > 1)
+       if (i40e_dcb_get_num_tc(&hw->local_dcbx_config) > 1)
                pf->flags |= I40E_FLAG_DCB_ENABLED;
        else
                pf->flags &= ~I40E_FLAG_DCB_ENABLED;
@@ -6305,13 +6319,14 @@ static void i40e_reset_and_rebuild(struct i40e_pf *pf, bool reinit)
                }
        }
 
-       msleep(75);
-       ret = i40e_aq_set_link_restart_an(&pf->hw, true, NULL);
-       if (ret) {
-               dev_info(&pf->pdev->dev, "link restart failed, aq_err=%d\n",
-                        pf->hw.aq.asq_last_status);
+       if (((pf->hw.aq.fw_maj_ver == 4) && (pf->hw.aq.fw_min_ver < 33)) ||
+           (pf->hw.aq.fw_maj_ver < 4)) {
+               msleep(75);
+               ret = i40e_aq_set_link_restart_an(&pf->hw, true, NULL);
+               if (ret)
+                       dev_info(&pf->pdev->dev, "link restart failed, aq_err=%d\n",
+                                pf->hw.aq.asq_last_status);
        }
-
        /* reinit the misc interrupt */
        if (pf->flags & I40E_FLAG_MSIX_ENABLED)
                ret = i40e_setup_misc_vector(pf);
@@ -6698,6 +6713,8 @@ static int i40e_vsi_mem_alloc(struct i40e_pf *pf, enum i40e_vsi_type type)
        vsi->idx = vsi_idx;
        vsi->rx_itr_setting = pf->rx_itr_default;
        vsi->tx_itr_setting = pf->tx_itr_default;
+       vsi->rss_table_size = (vsi->type == I40E_VSI_MAIN) ?
+                               pf->rss_table_size : 64;
        vsi->netdev_registered = false;
        vsi->work_limit = I40E_DEFAULT_IRQ_WORK;
        INIT_LIST_HEAD(&vsi->mac_filter_list);
@@ -6921,7 +6938,8 @@ static int i40e_init_msix(struct i40e_pf *pf)
         * If we can't get what we want, we'll simplify to nearly nothing
         * and try again.  If that still fails, we punt.
         */
-       pf->num_lan_msix = pf->num_lan_qps - (pf->rss_size_max - pf->rss_size);
+       pf->num_lan_msix = min_t(int, num_online_cpus(),
+                                hw->func_caps.num_msix_vectors);
        pf->num_vmdq_msix = pf->num_vmdq_qps;
        other_vecs = 1;
        other_vecs += (pf->num_vmdq_vsis * pf->num_vmdq_msix);
@@ -7189,6 +7207,7 @@ static int i40e_setup_misc_vector(struct i40e_pf *pf)
 static int i40e_config_rss(struct i40e_pf *pf)
 {
        u32 rss_key[I40E_PFQF_HKEY_MAX_INDEX + 1];
+       struct i40e_vsi *vsi = pf->vsi[pf->lan_vsi];
        struct i40e_hw *hw = &pf->hw;
        u32 lut = 0;
        int i, j;
@@ -7206,6 +7225,8 @@ static int i40e_config_rss(struct i40e_pf *pf)
        wr32(hw, I40E_PFQF_HENA(0), (u32)hena);
        wr32(hw, I40E_PFQF_HENA(1), (u32)(hena >> 32));
 
+       vsi->rss_size = min_t(int, pf->rss_size, vsi->num_queue_pairs);
+
        /* Check capability and Set table size and register per hw expectation*/
        reg_val = rd32(hw, I40E_PFQF_CTL_0);
        if (hw->func_caps.rss_table_size == 512) {
@@ -7227,7 +7248,7 @@ static int i40e_config_rss(struct i40e_pf *pf)
                 * If LAN VSI is the only consumer for RSS then this requirement
                 * is not necessary.
                 */
-               if (j == pf->rss_size)
+               if (j == vsi->rss_size)
                        j = 0;
                /* lut = 4-byte sliding window of 4 lut entries */
                lut = (lut << 8) | (j &
@@ -7251,15 +7272,19 @@ static int i40e_config_rss(struct i40e_pf *pf)
  **/
 int i40e_reconfig_rss_queues(struct i40e_pf *pf, int queue_count)
 {
+       struct i40e_vsi *vsi = pf->vsi[pf->lan_vsi];
+       int new_rss_size;
+
        if (!(pf->flags & I40E_FLAG_RSS_ENABLED))
                return 0;
 
-       queue_count = min_t(int, queue_count, pf->rss_size_max);
+       new_rss_size = min_t(int, queue_count, pf->rss_size_max);
 
-       if (queue_count != pf->rss_size) {
+       if (queue_count != vsi->num_queue_pairs) {
+               vsi->req_queue_pairs = queue_count;
                i40e_prep_for_reset(pf);
 
-               pf->rss_size = queue_count;
+               pf->rss_size = new_rss_size;
 
                i40e_reset_and_rebuild(pf, true);
                i40e_config_rss(pf);
@@ -7432,6 +7457,7 @@ static int i40e_sw_init(struct i40e_pf *pf)
         */
        pf->rss_size_max = 0x1 << pf->hw.func_caps.rss_table_entry_width;
        pf->rss_size = 1;
+       pf->rss_table_size = pf->hw.func_caps.rss_table_size;
        pf->rss_size_max = min_t(int, pf->rss_size_max,
                                 pf->hw.func_caps.num_tx_qp);
        if (pf->hw.func_caps.rss) {
@@ -9258,7 +9284,11 @@ static void i40e_determine_queue_usage(struct i40e_pf *pf)
                        pf->flags &= ~I40E_FLAG_DCB_CAPABLE;
                        dev_info(&pf->pdev->dev, "not enough queues for DCB. DCB is disabled.\n");
                }
-               pf->num_lan_qps = pf->rss_size_max;
+               pf->num_lan_qps = max_t(int, pf->rss_size_max,
+                                       num_online_cpus());
+               pf->num_lan_qps = min_t(int, pf->num_lan_qps,
+                                       pf->hw.func_caps.num_tx_qp);
+
                queues_left -= pf->num_lan_qps;
        }
 
@@ -9662,13 +9692,14 @@ static int i40e_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
        if (err)
                dev_info(&pf->pdev->dev, "set phy mask fail, aq_err %d\n", err);
 
-       msleep(75);
-       err = i40e_aq_set_link_restart_an(&pf->hw, true, NULL);
-       if (err) {
-               dev_info(&pf->pdev->dev, "link restart failed, aq_err=%d\n",
-                        pf->hw.aq.asq_last_status);
+       if (((pf->hw.aq.fw_maj_ver == 4) && (pf->hw.aq.fw_min_ver < 33)) ||
+           (pf->hw.aq.fw_maj_ver < 4)) {
+               msleep(75);
+               err = i40e_aq_set_link_restart_an(&pf->hw, true, NULL);
+               if (err)
+                       dev_info(&pf->pdev->dev, "link restart failed, aq_err=%d\n",
+                                pf->hw.aq.asq_last_status);
        }
-
        /* The main driver is (mostly) up and happy. We need to set this state
         * before setting up the misc vector or we get a race and the vector
         * ends up disabled forever.