]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
5.4-stable patches
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Sun, 30 Jan 2022 14:44:38 +0000 (15:44 +0100)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Sun, 30 Jan 2022 14:44:38 +0000 (15:44 +0100)
added patches:
i40e-fix-issue-when-maximum-queues-is-exceeded.patch
i40e-fix-queues-reservation-for-xdp.patch
i40e-fix-unsigned-stat-widths.patch
i40e-increase-delay-to-1-s-after-global-emp-reset.patch

queue-5.4/i40e-fix-issue-when-maximum-queues-is-exceeded.patch [new file with mode: 0644]
queue-5.4/i40e-fix-queues-reservation-for-xdp.patch [new file with mode: 0644]
queue-5.4/i40e-fix-unsigned-stat-widths.patch [new file with mode: 0644]
queue-5.4/i40e-increase-delay-to-1-s-after-global-emp-reset.patch [new file with mode: 0644]
queue-5.4/series

diff --git a/queue-5.4/i40e-fix-issue-when-maximum-queues-is-exceeded.patch b/queue-5.4/i40e-fix-issue-when-maximum-queues-is-exceeded.patch
new file mode 100644 (file)
index 0000000..ba6c6bd
--- /dev/null
@@ -0,0 +1,195 @@
+From d701658a50a471591094b3eb3961b4926cc8f104 Mon Sep 17 00:00:00 2001
+From: Jedrzej Jagielski <jedrzej.jagielski@intel.com>
+Date: Fri, 5 Nov 2021 11:17:00 +0000
+Subject: i40e: Fix issue when maximum queues is exceeded
+
+From: Jedrzej Jagielski <jedrzej.jagielski@intel.com>
+
+commit d701658a50a471591094b3eb3961b4926cc8f104 upstream.
+
+Before this patch VF interface vanished when
+maximum queue number was exceeded. Driver tried
+to add next queues even if there was not enough
+space. PF sent incorrect number of queues to
+the VF when there were not enough of them.
+
+Add an additional condition introduced to check
+available space in 'qp_pile' before proceeding.
+This condition makes it impossible to add queues
+if they number is greater than the number resulting
+from available space.
+Also add the search for free space in PF queue
+pair piles.
+
+Without this patch VF interfaces are not seen
+when available space for queues has been
+exceeded and following logs appears permanently
+in dmesg:
+"Unable to get VF config (-32)".
+"VF 62 failed opcode 3, retval: -5"
+"Unable to get VF config due to PF error condition, not retrying"
+
+Fixes: 7daa6bf3294e ("i40e: driver core headers")
+Fixes: 41c445ff0f48 ("i40e: main driver core")
+Signed-off-by: Jaroslaw Gawin <jaroslawx.gawin@intel.com>
+Signed-off-by: Slawomir Laba <slawomirx.laba@intel.com>
+Signed-off-by: Jedrzej Jagielski <jedrzej.jagielski@intel.com>
+Tested-by: Konrad Jankowski <konrad0.jankowski@intel.com>
+Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/net/ethernet/intel/i40e/i40e.h             |    1 
+ drivers/net/ethernet/intel/i40e/i40e_main.c        |   14 ----
+ drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c |   59 +++++++++++++++++++++
+ 3 files changed, 61 insertions(+), 13 deletions(-)
+
+--- a/drivers/net/ethernet/intel/i40e/i40e.h
++++ b/drivers/net/ethernet/intel/i40e/i40e.h
+@@ -182,7 +182,6 @@ enum i40e_interrupt_policy {
+ struct i40e_lump_tracking {
+       u16 num_entries;
+-      u16 search_hint;
+       u16 list[0];
+ #define I40E_PILE_VALID_BIT  0x8000
+ #define I40E_IWARP_IRQ_PILE_ID  (I40E_PILE_VALID_BIT - 2)
+--- a/drivers/net/ethernet/intel/i40e/i40e_main.c
++++ b/drivers/net/ethernet/intel/i40e/i40e_main.c
+@@ -204,10 +204,6 @@ int i40e_free_virt_mem_d(struct i40e_hw
+  * @id: an owner id to stick on the items assigned
+  *
+  * Returns the base item index of the lump, or negative for error
+- *
+- * The search_hint trick and lack of advanced fit-finding only work
+- * because we're highly likely to have all the same size lump requests.
+- * Linear search time and any fragmentation should be minimal.
+  **/
+ static int i40e_get_lump(struct i40e_pf *pf, struct i40e_lump_tracking *pile,
+                        u16 needed, u16 id)
+@@ -222,8 +218,7 @@ static int i40e_get_lump(struct i40e_pf
+               return -EINVAL;
+       }
+-      /* start the linear search with an imperfect hint */
+-      i = pile->search_hint;
++      i = 0;
+       while (i < pile->num_entries) {
+               /* skip already allocated entries */
+               if (pile->list[i] & I40E_PILE_VALID_BIT) {
+@@ -242,7 +237,6 @@ static int i40e_get_lump(struct i40e_pf
+                       for (j = 0; j < needed; j++)
+                               pile->list[i+j] = id | I40E_PILE_VALID_BIT;
+                       ret = i;
+-                      pile->search_hint = i + j;
+                       break;
+               }
+@@ -265,7 +259,7 @@ static int i40e_put_lump(struct i40e_lum
+ {
+       int valid_id = (id | I40E_PILE_VALID_BIT);
+       int count = 0;
+-      int i;
++      u16 i;
+       if (!pile || index >= pile->num_entries)
+               return -EINVAL;
+@@ -277,8 +271,6 @@ static int i40e_put_lump(struct i40e_lum
+               count++;
+       }
+-      if (count && index < pile->search_hint)
+-              pile->search_hint = index;
+       return count;
+ }
+@@ -11382,7 +11374,6 @@ static int i40e_init_interrupt_scheme(st
+               return -ENOMEM;
+       pf->irq_pile->num_entries = vectors;
+-      pf->irq_pile->search_hint = 0;
+       /* track first vector for misc interrupts, ignore return */
+       (void)i40e_get_lump(pf, pf->irq_pile, 1, I40E_PILE_VALID_BIT - 1);
+@@ -12133,7 +12124,6 @@ static int i40e_sw_init(struct i40e_pf *
+               goto sw_init_done;
+       }
+       pf->qp_pile->num_entries = pf->hw.func_caps.num_tx_qp;
+-      pf->qp_pile->search_hint = 0;
+       pf->tx_timeout_recovery_level = 1;
+--- a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
++++ b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
+@@ -2486,6 +2486,59 @@ error_param:
+ }
+ /**
++ * i40e_check_enough_queue - find big enough queue number
++ * @vf: pointer to the VF info
++ * @needed: the number of items needed
++ *
++ * Returns the base item index of the queue, or negative for error
++ **/
++static int i40e_check_enough_queue(struct i40e_vf *vf, u16 needed)
++{
++      unsigned int  i, cur_queues, more, pool_size;
++      struct i40e_lump_tracking *pile;
++      struct i40e_pf *pf = vf->pf;
++      struct i40e_vsi *vsi;
++
++      vsi = pf->vsi[vf->lan_vsi_idx];
++      cur_queues = vsi->alloc_queue_pairs;
++
++      /* if current allocated queues are enough for need */
++      if (cur_queues >= needed)
++              return vsi->base_queue;
++
++      pile = pf->qp_pile;
++      if (cur_queues > 0) {
++              /* if the allocated queues are not zero
++               * just check if there are enough queues for more
++               * behind the allocated queues.
++               */
++              more = needed - cur_queues;
++              for (i = vsi->base_queue + cur_queues;
++                      i < pile->num_entries; i++) {
++                      if (pile->list[i] & I40E_PILE_VALID_BIT)
++                              break;
++
++                      if (more-- == 1)
++                              /* there is enough */
++                              return vsi->base_queue;
++              }
++      }
++
++      pool_size = 0;
++      for (i = 0; i < pile->num_entries; i++) {
++              if (pile->list[i] & I40E_PILE_VALID_BIT) {
++                      pool_size = 0;
++                      continue;
++              }
++              if (needed <= ++pool_size)
++                      /* there is enough */
++                      return i;
++      }
++
++      return -ENOMEM;
++}
++
++/**
+  * i40e_vc_request_queues_msg
+  * @vf: pointer to the VF info
+  * @msg: pointer to the msg buffer
+@@ -2519,6 +2572,12 @@ static int i40e_vc_request_queues_msg(st
+                        req_pairs - cur_pairs,
+                        pf->queues_left);
+               vfres->num_queue_pairs = pf->queues_left + cur_pairs;
++      } else if (i40e_check_enough_queue(vf, req_pairs) < 0) {
++              dev_warn(&pf->pdev->dev,
++                       "VF %d requested %d more queues, but there is not enough for it.\n",
++                       vf->vf_id,
++                       req_pairs - cur_pairs);
++              vfres->num_queue_pairs = cur_pairs;
+       } else {
+               /* successful request */
+               vf->num_req_queues = req_pairs;
diff --git a/queue-5.4/i40e-fix-queues-reservation-for-xdp.patch b/queue-5.4/i40e-fix-queues-reservation-for-xdp.patch
new file mode 100644 (file)
index 0000000..684d192
--- /dev/null
@@ -0,0 +1,89 @@
+From 92947844b8beee988c0ce17082b705c2f75f0742 Mon Sep 17 00:00:00 2001
+From: Sylwester Dziedziuch <sylwesterx.dziedziuch@intel.com>
+Date: Fri, 26 Nov 2021 11:11:22 +0100
+Subject: i40e: Fix queues reservation for XDP
+
+From: Sylwester Dziedziuch <sylwesterx.dziedziuch@intel.com>
+
+commit 92947844b8beee988c0ce17082b705c2f75f0742 upstream.
+
+When XDP was configured on a system with large number of CPUs
+and X722 NIC there was a call trace with NULL pointer dereference.
+
+i40e 0000:87:00.0: failed to get tracking for 256 queues for VSI 0 err -12
+i40e 0000:87:00.0: setup of MAIN VSI failed
+
+BUG: kernel NULL pointer dereference, address: 0000000000000000
+RIP: 0010:i40e_xdp+0xea/0x1b0 [i40e]
+Call Trace:
+? i40e_reconfig_rss_queues+0x130/0x130 [i40e]
+dev_xdp_install+0x61/0xe0
+dev_xdp_attach+0x18a/0x4c0
+dev_change_xdp_fd+0x1e6/0x220
+do_setlink+0x616/0x1030
+? ahci_port_stop+0x80/0x80
+? ata_qc_issue+0x107/0x1e0
+? lock_timer_base+0x61/0x80
+? __mod_timer+0x202/0x380
+rtnl_setlink+0xe5/0x170
+? bpf_lsm_binder_transaction+0x10/0x10
+? security_capable+0x36/0x50
+rtnetlink_rcv_msg+0x121/0x350
+? rtnl_calcit.isra.0+0x100/0x100
+netlink_rcv_skb+0x50/0xf0
+netlink_unicast+0x1d3/0x2a0
+netlink_sendmsg+0x22a/0x440
+sock_sendmsg+0x5e/0x60
+__sys_sendto+0xf0/0x160
+? __sys_getsockname+0x7e/0xc0
+? _copy_from_user+0x3c/0x80
+? __sys_setsockopt+0xc8/0x1a0
+__x64_sys_sendto+0x20/0x30
+do_syscall_64+0x33/0x40
+entry_SYSCALL_64_after_hwframe+0x44/0xae
+RIP: 0033:0x7f83fa7a39e0
+
+This was caused by PF queue pile fragmentation due to
+flow director VSI queue being placed right after main VSI.
+Because of this main VSI was not able to resize its
+queue allocation for XDP resulting in no queues allocated
+for main VSI when XDP was turned on.
+
+Fix this by always allocating last queue in PF queue pile
+for a flow director VSI.
+
+Fixes: 41c445ff0f48 ("i40e: main driver core")
+Fixes: 74608d17fe29 ("i40e: add support for XDP_TX action")
+Signed-off-by: Sylwester Dziedziuch <sylwesterx.dziedziuch@intel.com>
+Signed-off-by: Mateusz Palczewski <mateusz.palczewski@intel.com>
+Reviewed-by: Maciej Fijalkowski <maciej.fijalkowski@intel.com>
+Tested-by: Kiran Bhandare <kiranx.bhandare@intel.com>
+Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/net/ethernet/intel/i40e/i40e_main.c |   14 ++++++++++++++
+ 1 file changed, 14 insertions(+)
+
+--- a/drivers/net/ethernet/intel/i40e/i40e_main.c
++++ b/drivers/net/ethernet/intel/i40e/i40e_main.c
+@@ -218,6 +218,20 @@ static int i40e_get_lump(struct i40e_pf
+               return -EINVAL;
+       }
++      /* Allocate last queue in the pile for FDIR VSI queue
++       * so it doesn't fragment the qp_pile
++       */
++      if (pile == pf->qp_pile && pf->vsi[id]->type == I40E_VSI_FDIR) {
++              if (pile->list[pile->num_entries - 1] & I40E_PILE_VALID_BIT) {
++                      dev_err(&pf->pdev->dev,
++                              "Cannot allocate queue %d for I40E_VSI_FDIR\n",
++                              pile->num_entries - 1);
++                      return -ENOMEM;
++              }
++              pile->list[pile->num_entries - 1] = id | I40E_PILE_VALID_BIT;
++              return pile->num_entries - 1;
++      }
++
+       i = 0;
+       while (i < pile->num_entries) {
+               /* skip already allocated entries */
diff --git a/queue-5.4/i40e-fix-unsigned-stat-widths.patch b/queue-5.4/i40e-fix-unsigned-stat-widths.patch
new file mode 100644 (file)
index 0000000..4874725
--- /dev/null
@@ -0,0 +1,70 @@
+From 3b8428b84539c78fdc8006c17ebd25afd4722d51 Mon Sep 17 00:00:00 2001
+From: Joe Damato <jdamato@fastly.com>
+Date: Wed, 8 Dec 2021 17:56:33 -0800
+Subject: i40e: fix unsigned stat widths
+
+From: Joe Damato <jdamato@fastly.com>
+
+commit 3b8428b84539c78fdc8006c17ebd25afd4722d51 upstream.
+
+Change i40e_update_vsi_stats and struct i40e_vsi to use u64 fields to match
+the width of the stats counters in struct i40e_rx_queue_stats.
+
+Update debugfs code to use the correct format specifier for u64.
+
+Fixes: 41c445ff0f48 ("i40e: main driver core")
+Signed-off-by: Joe Damato <jdamato@fastly.com>
+Reported-by: kernel test robot <lkp@intel.com>
+Tested-by: Gurucharan G <gurucharanx.g@intel.com>
+Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/net/ethernet/intel/i40e/i40e.h         |    8 ++++----
+ drivers/net/ethernet/intel/i40e/i40e_debugfs.c |    2 +-
+ drivers/net/ethernet/intel/i40e/i40e_main.c    |    4 ++--
+ 3 files changed, 7 insertions(+), 7 deletions(-)
+
+--- a/drivers/net/ethernet/intel/i40e/i40e.h
++++ b/drivers/net/ethernet/intel/i40e/i40e.h
+@@ -756,12 +756,12 @@ struct i40e_vsi {
+       struct rtnl_link_stats64 net_stats_offsets;
+       struct i40e_eth_stats eth_stats;
+       struct i40e_eth_stats eth_stats_offsets;
+-      u32 tx_restart;
+-      u32 tx_busy;
++      u64 tx_restart;
++      u64 tx_busy;
+       u64 tx_linearize;
+       u64 tx_force_wb;
+-      u32 rx_buf_failed;
+-      u32 rx_page_failed;
++      u64 rx_buf_failed;
++      u64 rx_page_failed;
+       /* These are containers of ring pointers, allocated at run-time */
+       struct i40e_ring **rx_rings;
+--- a/drivers/net/ethernet/intel/i40e/i40e_debugfs.c
++++ b/drivers/net/ethernet/intel/i40e/i40e_debugfs.c
+@@ -234,7 +234,7 @@ static void i40e_dbg_dump_vsi_seid(struc
+                (unsigned long int)vsi->net_stats_offsets.rx_compressed,
+                (unsigned long int)vsi->net_stats_offsets.tx_compressed);
+       dev_info(&pf->pdev->dev,
+-               "    tx_restart = %d, tx_busy = %d, rx_buf_failed = %d, rx_page_failed = %d\n",
++               "    tx_restart = %llu, tx_busy = %llu, rx_buf_failed = %llu, rx_page_failed = %llu\n",
+                vsi->tx_restart, vsi->tx_busy,
+                vsi->rx_buf_failed, vsi->rx_page_failed);
+       rcu_read_lock();
+--- a/drivers/net/ethernet/intel/i40e/i40e_main.c
++++ b/drivers/net/ethernet/intel/i40e/i40e_main.c
+@@ -804,9 +804,9 @@ static void i40e_update_vsi_stats(struct
+       struct rtnl_link_stats64 *ns;   /* netdev stats */
+       struct i40e_eth_stats *oes;
+       struct i40e_eth_stats *es;     /* device's eth stats */
+-      u32 tx_restart, tx_busy;
++      u64 tx_restart, tx_busy;
+       struct i40e_ring *p;
+-      u32 rx_page, rx_buf;
++      u64 rx_page, rx_buf;
+       u64 bytes, packets;
+       unsigned int start;
+       u64 tx_linearize;
diff --git a/queue-5.4/i40e-increase-delay-to-1-s-after-global-emp-reset.patch b/queue-5.4/i40e-increase-delay-to-1-s-after-global-emp-reset.patch
new file mode 100644 (file)
index 0000000..95b1000
--- /dev/null
@@ -0,0 +1,47 @@
+From 9b13bd53134c9ddd544a790125199fdbdb505e67 Mon Sep 17 00:00:00 2001
+From: Jedrzej Jagielski <jedrzej.jagielski@intel.com>
+Date: Thu, 28 Oct 2021 13:51:14 +0000
+Subject: i40e: Increase delay to 1 s after global EMP reset
+
+From: Jedrzej Jagielski <jedrzej.jagielski@intel.com>
+
+commit 9b13bd53134c9ddd544a790125199fdbdb505e67 upstream.
+
+Recently simplified i40e_rebuild causes that FW sometimes
+is not ready after NVM update, the ping does not return.
+
+Increase the delay in case of EMP reset.
+Old delay of 300 ms was introduced for specific cards for 710 series.
+Now it works for all the cards and delay was increased.
+
+Fixes: 1fa51a650e1d ("i40e: Add delay after EMP reset for firmware to recover")
+Signed-off-by: Arkadiusz Kubalewski <arkadiusz.kubalewski@intel.com>
+Signed-off-by: Jedrzej Jagielski <jedrzej.jagielski@intel.com>
+Tested-by: Gurucharan G <gurucharanx.g@intel.com>
+Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/net/ethernet/intel/i40e/i40e_main.c |   12 +++---------
+ 1 file changed, 3 insertions(+), 9 deletions(-)
+
+--- a/drivers/net/ethernet/intel/i40e/i40e_main.c
++++ b/drivers/net/ethernet/intel/i40e/i40e_main.c
+@@ -10084,15 +10084,9 @@ static void i40e_rebuild(struct i40e_pf
+       }
+       i40e_get_oem_version(&pf->hw);
+-      if (test_bit(__I40E_EMP_RESET_INTR_RECEIVED, pf->state) &&
+-          ((hw->aq.fw_maj_ver == 4 && hw->aq.fw_min_ver <= 33) ||
+-           hw->aq.fw_maj_ver < 4) && hw->mac.type == I40E_MAC_XL710) {
+-              /* The following delay is necessary for 4.33 firmware and older
+-               * to recover after EMP reset. 200 ms should suffice but we
+-               * put here 300 ms to be sure that FW is ready to operate
+-               * after reset.
+-               */
+-              mdelay(300);
++      if (test_and_clear_bit(__I40E_EMP_RESET_INTR_RECEIVED, pf->state)) {
++              /* The following delay is necessary for firmware update. */
++              mdelay(1000);
+       }
+       /* re-verify the eeprom if we just had an EMP reset */
index 9103bbbbb810e22c54b4c3abe3a39a2b68f65355..1c9c3bd1f494706f77d332b0c6d05f6992270a85 100644 (file)
@@ -22,3 +22,7 @@ usb-typec-tcpm-do-not-disconnect-while-receiving-vbus-off.patch
 ucsi_ccg-check-dev_int-bit-only-when-starting-ccg4.patch
 net-sfp-ignore-disabled-sfp-node.patch
 powerpc-32-fix-boot-failure-with-gcc-latent-entropy-plugin.patch
+i40e-increase-delay-to-1-s-after-global-emp-reset.patch
+i40e-fix-issue-when-maximum-queues-is-exceeded.patch
+i40e-fix-queues-reservation-for-xdp.patch
+i40e-fix-unsigned-stat-widths.patch