i40e: Fix not setting default xps_cpus after reset
authorMichal Jaron <michalx.jaron@intel.com>
Mon, 24 Oct 2022 08:19:42 +0000 (10:19 +0200)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Wed, 14 Dec 2022 10:37:26 +0000 (11:37 +0100)
[ Upstream commit 82e0572b23029b380464fa9fdc125db9c1506d0a ]

During tx rings configuration default XPS queue config is set and
__I40E_TX_XPS_INIT_DONE is locked. __I40E_TX_XPS_INIT_DONE state is
cleared and set again with default mapping only during queues build,
it means after first setup or reset with queues rebuild. (i.e.
ethtool -L <interface> combined <number>) After other resets (i.e.
ethtool -t <interface>) XPS_INIT_DONE is not cleared and those default
maps cannot be set again. It results in cleared xps_cpus mapping
until queues are not rebuild or mapping is not set by user.

Add clearing __I40E_TX_XPS_INIT_DONE state during reset to let
the driver set xps_cpus to defaults again after it was cleared.

Fixes: 6f853d4f8e93 ("i40e: allow XPS with QoS enabled")
Signed-off-by: Michal Jaron <michalx.jaron@intel.com>
Signed-off-by: Kamil Maziarz <kamil.maziarz@intel.com>
Tested-by: Gurucharan <gurucharanx.g@intel.com> (A Contingent worker at Intel)
Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
Signed-off-by: Sasha Levin <sashal@kernel.org>
drivers/net/ethernet/intel/i40e/i40e_main.c

index 19b5c56..ed2c961 100644 (file)
@@ -10520,6 +10520,21 @@ static int i40e_rebuild_channels(struct i40e_vsi *vsi)
 }
 
 /**
+ * i40e_clean_xps_state - clean xps state for every tx_ring
+ * @vsi: ptr to the VSI
+ **/
+static void i40e_clean_xps_state(struct i40e_vsi *vsi)
+{
+       int i;
+
+       if (vsi->tx_rings)
+               for (i = 0; i < vsi->num_queue_pairs; i++)
+                       if (vsi->tx_rings[i])
+                               clear_bit(__I40E_TX_XPS_INIT_DONE,
+                                         vsi->tx_rings[i]->state);
+}
+
+/**
  * i40e_prep_for_reset - prep for the core to reset
  * @pf: board private structure
  *
@@ -10543,8 +10558,10 @@ static void i40e_prep_for_reset(struct i40e_pf *pf)
        i40e_pf_quiesce_all_vsi(pf);
 
        for (v = 0; v < pf->num_alloc_vsi; v++) {
-               if (pf->vsi[v])
+               if (pf->vsi[v]) {
+                       i40e_clean_xps_state(pf->vsi[v]);
                        pf->vsi[v]->seid = 0;
+               }
        }
 
        i40e_shutdown_adminq(&pf->hw);