]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
Fixes for 5.4
authorSasha Levin <sashal@kernel.org>
Sat, 31 Aug 2024 23:13:52 +0000 (19:13 -0400)
committerSasha Levin <sashal@kernel.org>
Sat, 31 Aug 2024 23:13:52 +0000 (19:13 -0400)
Signed-off-by: Sasha Levin <sashal@kernel.org>
queue-5.4/ethtool-check-device-is-present-when-getting-link-se.patch [new file with mode: 0644]
queue-5.4/gtp-fix-a-potential-null-pointer-dereference.patch [new file with mode: 0644]
queue-5.4/net-busy-poll-use-ktime_get_ns-instead-of-local_cloc.patch [new file with mode: 0644]
queue-5.4/nfc-pn533-add-autopoll-capability.patch [new file with mode: 0644]
queue-5.4/nfc-pn533-add-dev_up-dev_down-hooks-to-phy_ops.patch [new file with mode: 0644]
queue-5.4/nfc-pn533-add-poll-mod-list-filling-check.patch [new file with mode: 0644]
queue-5.4/r8152-factor-out-oob-link-list-waits.patch [new file with mode: 0644]
queue-5.4/series

diff --git a/queue-5.4/ethtool-check-device-is-present-when-getting-link-se.patch b/queue-5.4/ethtool-check-device-is-present-when-getting-link-se.patch
new file mode 100644 (file)
index 0000000..bddf011
--- /dev/null
@@ -0,0 +1,79 @@
+From 4b78f349d42027928b2ac21fb04eb40a6d85f149 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Fri, 23 Aug 2024 16:26:58 +1000
+Subject: ethtool: check device is present when getting link settings
+
+From: Jamie Bainbridge <jamie.bainbridge@gmail.com>
+
+[ Upstream commit a699781c79ecf6cfe67fb00a0331b4088c7c8466 ]
+
+A sysfs reader can race with a device reset or removal, attempting to
+read device state when the device is not actually present. eg:
+
+     [exception RIP: qed_get_current_link+17]
+  #8 [ffffb9e4f2907c48] qede_get_link_ksettings at ffffffffc07a994a [qede]
+  #9 [ffffb9e4f2907cd8] __rh_call_get_link_ksettings at ffffffff992b01a3
+ #10 [ffffb9e4f2907d38] __ethtool_get_link_ksettings at ffffffff992b04e4
+ #11 [ffffb9e4f2907d90] duplex_show at ffffffff99260300
+ #12 [ffffb9e4f2907e38] dev_attr_show at ffffffff9905a01c
+ #13 [ffffb9e4f2907e50] sysfs_kf_seq_show at ffffffff98e0145b
+ #14 [ffffb9e4f2907e68] seq_read at ffffffff98d902e3
+ #15 [ffffb9e4f2907ec8] vfs_read at ffffffff98d657d1
+ #16 [ffffb9e4f2907f00] ksys_read at ffffffff98d65c3f
+ #17 [ffffb9e4f2907f38] do_syscall_64 at ffffffff98a052fb
+
+ crash> struct net_device.state ffff9a9d21336000
+    state = 5,
+
+state 5 is __LINK_STATE_START (0b1) and __LINK_STATE_NOCARRIER (0b100).
+The device is not present, note lack of __LINK_STATE_PRESENT (0b10).
+
+This is the same sort of panic as observed in commit 4224cfd7fb65
+("net-sysfs: add check for netdevice being present to speed_show").
+
+There are many other callers of __ethtool_get_link_ksettings() which
+don't have a device presence check.
+
+Move this check into ethtool to protect all callers.
+
+Fixes: d519e17e2d01 ("net: export device speed and duplex via sysfs")
+Fixes: 4224cfd7fb65 ("net-sysfs: add check for netdevice being present to speed_show")
+Signed-off-by: Jamie Bainbridge <jamie.bainbridge@gmail.com>
+Link: https://patch.msgid.link/8bae218864beaa44ed01628140475b9bf641c5b0.1724393671.git.jamie.bainbridge@gmail.com
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ net/core/ethtool.c   | 3 +++
+ net/core/net-sysfs.c | 2 +-
+ 2 files changed, 4 insertions(+), 1 deletion(-)
+
+diff --git a/net/core/ethtool.c b/net/core/ethtool.c
+index 9ae38c3e2bf0a..f0346cf4462e0 100644
+--- a/net/core/ethtool.c
++++ b/net/core/ethtool.c
+@@ -549,6 +549,9 @@ int __ethtool_get_link_ksettings(struct net_device *dev,
+       if (!dev->ethtool_ops->get_link_ksettings)
+               return -EOPNOTSUPP;
++      if (!netif_device_present(dev))
++              return -ENODEV;
++
+       memset(link_ksettings, 0, sizeof(*link_ksettings));
+       return dev->ethtool_ops->get_link_ksettings(dev, link_ksettings);
+ }
+diff --git a/net/core/net-sysfs.c b/net/core/net-sysfs.c
+index ad45f13a0370b..bcad7028bbf45 100644
+--- a/net/core/net-sysfs.c
++++ b/net/core/net-sysfs.c
+@@ -212,7 +212,7 @@ static ssize_t speed_show(struct device *dev,
+       if (!rtnl_trylock())
+               return restart_syscall();
+-      if (netif_running(netdev) && netif_device_present(netdev)) {
++      if (netif_running(netdev)) {
+               struct ethtool_link_ksettings cmd;
+               if (!__ethtool_get_link_ksettings(netdev, &cmd))
+-- 
+2.43.0
+
diff --git a/queue-5.4/gtp-fix-a-potential-null-pointer-dereference.patch b/queue-5.4/gtp-fix-a-potential-null-pointer-dereference.patch
new file mode 100644 (file)
index 0000000..11d28e2
--- /dev/null
@@ -0,0 +1,47 @@
+From b1ef8cc97b40a57c4710032a6e39dcea5f97faf7 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Sun, 25 Aug 2024 12:16:38 -0700
+Subject: gtp: fix a potential NULL pointer dereference
+
+From: Cong Wang <cong.wang@bytedance.com>
+
+[ Upstream commit defd8b3c37b0f9cb3e0f60f47d3d78d459d57fda ]
+
+When sockfd_lookup() fails, gtp_encap_enable_socket() returns a
+NULL pointer, but its callers only check for error pointers thus miss
+the NULL pointer case.
+
+Fix it by returning an error pointer with the error code carried from
+sockfd_lookup().
+
+(I found this bug during code inspection.)
+
+Fixes: 1e3a3abd8b28 ("gtp: make GTP sockets in gtp_newlink optional")
+Cc: Andreas Schultz <aschultz@tpip.net>
+Cc: Harald Welte <laforge@gnumonks.org>
+Signed-off-by: Cong Wang <cong.wang@bytedance.com>
+Reviewed-by: Simon Horman <horms@kernel.org>
+Reviewed-by: Pablo Neira Ayuso <pablo@netfilter.org>
+Link: https://patch.msgid.link/20240825191638.146748-1-xiyou.wangcong@gmail.com
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ drivers/net/gtp.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/drivers/net/gtp.c b/drivers/net/gtp.c
+index ce61c2b9ada8d..c868f4ffa240f 100644
+--- a/drivers/net/gtp.c
++++ b/drivers/net/gtp.c
+@@ -807,7 +807,7 @@ static struct sock *gtp_encap_enable_socket(int fd, int type,
+       sock = sockfd_lookup(fd, &err);
+       if (!sock) {
+               pr_debug("gtp socket fd=%d not found\n", fd);
+-              return NULL;
++              return ERR_PTR(err);
+       }
+       sk = sock->sk;
+-- 
+2.43.0
+
diff --git a/queue-5.4/net-busy-poll-use-ktime_get_ns-instead-of-local_cloc.patch b/queue-5.4/net-busy-poll-use-ktime_get_ns-instead-of-local_cloc.patch
new file mode 100644 (file)
index 0000000..3fd3ae3
--- /dev/null
@@ -0,0 +1,48 @@
+From e6738104c2a645bd3d434a99a8e20dc27e95da08 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 27 Aug 2024 11:49:16 +0000
+Subject: net: busy-poll: use ktime_get_ns() instead of local_clock()
+
+From: Eric Dumazet <edumazet@google.com>
+
+[ Upstream commit 0870b0d8b393dde53106678a1e2cec9dfa52f9b7 ]
+
+Typically, busy-polling durations are below 100 usec.
+
+When/if the busy-poller thread migrates to another cpu,
+local_clock() can be off by +/-2msec or more for small
+values of HZ, depending on the platform.
+
+Use ktimer_get_ns() to ensure deterministic behavior,
+which is the whole point of busy-polling.
+
+Fixes: 060212928670 ("net: add low latency socket poll")
+Fixes: 9a3c71aa8024 ("net: convert low latency sockets to sched_clock()")
+Fixes: 37089834528b ("sched, net: Fixup busy_loop_us_clock()")
+Signed-off-by: Eric Dumazet <edumazet@google.com>
+Cc: Mina Almasry <almasrymina@google.com>
+Cc: Willem de Bruijn <willemb@google.com>
+Reviewed-by: Joe Damato <jdamato@fastly.com>
+Link: https://patch.msgid.link/20240827114916.223377-1-edumazet@google.com
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ include/net/busy_poll.h | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/include/net/busy_poll.h b/include/net/busy_poll.h
+index 16258c0c7319e..36259516ec0d2 100644
+--- a/include/net/busy_poll.h
++++ b/include/net/busy_poll.h
+@@ -61,7 +61,7 @@ static inline bool sk_can_busy_loop(struct sock *sk)
+ static inline unsigned long busy_loop_current_time(void)
+ {
+ #ifdef CONFIG_NET_RX_BUSY_POLL
+-      return (unsigned long)(local_clock() >> 10);
++      return (unsigned long)(ktime_get_ns() >> 10);
+ #else
+       return 0;
+ #endif
+-- 
+2.43.0
+
diff --git a/queue-5.4/nfc-pn533-add-autopoll-capability.patch b/queue-5.4/nfc-pn533-add-autopoll-capability.patch
new file mode 100644 (file)
index 0000000..8090081
--- /dev/null
@@ -0,0 +1,305 @@
+From 34e477c7d236ead3a46f2e43e65fa8517419a688 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 29 Oct 2019 15:47:43 +0100
+Subject: nfc: pn533: Add autopoll capability
+
+From: Lars Poeschel <poeschel@lemonage.de>
+
+[ Upstream commit c64b875fe1e1f6b30e3a15cb74d623349c571001 ]
+
+pn532 devices support an autopoll command, that lets the chip
+automatically poll for selected nfc technologies instead of manually
+looping through every single nfc technology the user is interested in.
+This is faster and less cpu and bus intensive than manually polling.
+This adds this autopoll capability to the pn533 driver.
+
+Cc: Johan Hovold <johan@kernel.org>
+Cc: David Miller <davem@davemloft.net>
+Signed-off-by: Lars Poeschel <poeschel@lemonage.de>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Stable-dep-of: febccb39255f ("nfc: pn533: Add poll mod list filling check")
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ drivers/nfc/pn533/pn533.c | 193 +++++++++++++++++++++++++++++++++++++-
+ drivers/nfc/pn533/pn533.h |  10 +-
+ 2 files changed, 197 insertions(+), 6 deletions(-)
+
+diff --git a/drivers/nfc/pn533/pn533.c b/drivers/nfc/pn533/pn533.c
+index c36cd68b47eb5..1c3da3675d7df 100644
+--- a/drivers/nfc/pn533/pn533.c
++++ b/drivers/nfc/pn533/pn533.c
+@@ -185,6 +185,32 @@ struct pn533_cmd_jump_dep_response {
+       u8 gt[];
+ } __packed;
++struct pn532_autopoll_resp {
++      u8 type;
++      u8 ln;
++      u8 tg;
++      u8 tgdata[];
++};
++
++/* PN532_CMD_IN_AUTOPOLL */
++#define PN532_AUTOPOLL_POLLNR_INFINITE        0xff
++#define PN532_AUTOPOLL_PERIOD         0x03 /* in units of 150 ms */
++
++#define PN532_AUTOPOLL_TYPE_GENERIC_106               0x00
++#define PN532_AUTOPOLL_TYPE_GENERIC_212               0x01
++#define PN532_AUTOPOLL_TYPE_GENERIC_424               0x02
++#define PN532_AUTOPOLL_TYPE_JEWEL             0x04
++#define PN532_AUTOPOLL_TYPE_MIFARE            0x10
++#define PN532_AUTOPOLL_TYPE_FELICA212         0x11
++#define PN532_AUTOPOLL_TYPE_FELICA424         0x12
++#define PN532_AUTOPOLL_TYPE_ISOA              0x20
++#define PN532_AUTOPOLL_TYPE_ISOB              0x23
++#define PN532_AUTOPOLL_TYPE_DEP_PASSIVE_106   0x40
++#define PN532_AUTOPOLL_TYPE_DEP_PASSIVE_212   0x41
++#define PN532_AUTOPOLL_TYPE_DEP_PASSIVE_424   0x42
++#define PN532_AUTOPOLL_TYPE_DEP_ACTIVE_106    0x80
++#define PN532_AUTOPOLL_TYPE_DEP_ACTIVE_212    0x81
++#define PN532_AUTOPOLL_TYPE_DEP_ACTIVE_424    0x82
+ /* PN533_TG_INIT_AS_TARGET */
+ #define PN533_INIT_TARGET_PASSIVE 0x1
+@@ -1394,6 +1420,101 @@ static int pn533_poll_dep(struct nfc_dev *nfc_dev)
+       return rc;
+ }
++static int pn533_autopoll_complete(struct pn533 *dev, void *arg,
++                             struct sk_buff *resp)
++{
++      struct pn532_autopoll_resp *apr;
++      struct nfc_target nfc_tgt;
++      u8 nbtg;
++      int rc;
++
++      if (IS_ERR(resp)) {
++              rc = PTR_ERR(resp);
++
++              nfc_err(dev->dev, "%s  autopoll complete error %d\n",
++                      __func__, rc);
++
++              if (rc == -ENOENT) {
++                      if (dev->poll_mod_count != 0)
++                              return rc;
++                      goto stop_poll;
++              } else if (rc < 0) {
++                      nfc_err(dev->dev,
++                              "Error %d when running autopoll\n", rc);
++                      goto stop_poll;
++              }
++      }
++
++      nbtg = resp->data[0];
++      if ((nbtg > 2) || (nbtg <= 0))
++              return -EAGAIN;
++
++      apr = (struct pn532_autopoll_resp *)&resp->data[1];
++      while (nbtg--) {
++              memset(&nfc_tgt, 0, sizeof(struct nfc_target));
++              switch (apr->type) {
++              case PN532_AUTOPOLL_TYPE_ISOA:
++                      dev_dbg(dev->dev, "ISOA\n");
++                      rc = pn533_target_found_type_a(&nfc_tgt, apr->tgdata,
++                                                     apr->ln - 1);
++                      break;
++              case PN532_AUTOPOLL_TYPE_FELICA212:
++              case PN532_AUTOPOLL_TYPE_FELICA424:
++                      dev_dbg(dev->dev, "FELICA\n");
++                      rc = pn533_target_found_felica(&nfc_tgt, apr->tgdata,
++                                                     apr->ln - 1);
++                      break;
++              case PN532_AUTOPOLL_TYPE_JEWEL:
++                      dev_dbg(dev->dev, "JEWEL\n");
++                      rc = pn533_target_found_jewel(&nfc_tgt, apr->tgdata,
++                                                    apr->ln - 1);
++                      break;
++              case PN532_AUTOPOLL_TYPE_ISOB:
++                      dev_dbg(dev->dev, "ISOB\n");
++                      rc = pn533_target_found_type_b(&nfc_tgt, apr->tgdata,
++                                                     apr->ln - 1);
++                      break;
++              case PN532_AUTOPOLL_TYPE_MIFARE:
++                      dev_dbg(dev->dev, "Mifare\n");
++                      rc = pn533_target_found_type_a(&nfc_tgt, apr->tgdata,
++                                                     apr->ln - 1);
++                      break;
++              default:
++                      nfc_err(dev->dev,
++                                  "Unknown current poll modulation\n");
++                      rc = -EPROTO;
++              }
++
++              if (rc)
++                      goto done;
++
++              if (!(nfc_tgt.supported_protocols & dev->poll_protocols)) {
++                      nfc_err(dev->dev,
++                                  "The Tg found doesn't have the desired protocol\n");
++                      rc = -EAGAIN;
++                      goto done;
++              }
++
++              dev->tgt_available_prots = nfc_tgt.supported_protocols;
++              apr = (struct pn532_autopoll_resp *)
++                      (apr->tgdata + (apr->ln - 1));
++      }
++
++      pn533_poll_reset_mod_list(dev);
++      nfc_targets_found(dev->nfc_dev, &nfc_tgt, 1);
++
++done:
++      dev_kfree_skb(resp);
++      return rc;
++
++stop_poll:
++      nfc_err(dev->dev, "autopoll operation has been stopped\n");
++
++      pn533_poll_reset_mod_list(dev);
++      dev->poll_protocols = 0;
++      return rc;
++}
++
+ static int pn533_poll_complete(struct pn533 *dev, void *arg,
+                              struct sk_buff *resp)
+ {
+@@ -1537,6 +1658,7 @@ static int pn533_start_poll(struct nfc_dev *nfc_dev,
+ {
+       struct pn533 *dev = nfc_get_drvdata(nfc_dev);
+       struct pn533_poll_modulations *cur_mod;
++      struct sk_buff *skb;
+       u8 rand_mod;
+       int rc;
+@@ -1562,9 +1684,73 @@ static int pn533_start_poll(struct nfc_dev *nfc_dev,
+                       tm_protocols = 0;
+       }
+-      pn533_poll_create_mod_list(dev, im_protocols, tm_protocols);
+       dev->poll_protocols = im_protocols;
+       dev->listen_protocols = tm_protocols;
++      if (dev->device_type == PN533_DEVICE_PN532_AUTOPOLL) {
++              skb = pn533_alloc_skb(dev, 4 + 6);
++              if (!skb)
++                      return -ENOMEM;
++
++              *((u8 *)skb_put(skb, sizeof(u8))) =
++                      PN532_AUTOPOLL_POLLNR_INFINITE;
++              *((u8 *)skb_put(skb, sizeof(u8))) = PN532_AUTOPOLL_PERIOD;
++
++              if ((im_protocols & NFC_PROTO_MIFARE_MASK) &&
++                              (im_protocols & NFC_PROTO_ISO14443_MASK) &&
++                              (im_protocols & NFC_PROTO_NFC_DEP_MASK))
++                      *((u8 *)skb_put(skb, sizeof(u8))) =
++                              PN532_AUTOPOLL_TYPE_GENERIC_106;
++              else {
++                      if (im_protocols & NFC_PROTO_MIFARE_MASK)
++                              *((u8 *)skb_put(skb, sizeof(u8))) =
++                                      PN532_AUTOPOLL_TYPE_MIFARE;
++
++                      if (im_protocols & NFC_PROTO_ISO14443_MASK)
++                              *((u8 *)skb_put(skb, sizeof(u8))) =
++                                      PN532_AUTOPOLL_TYPE_ISOA;
++
++                      if (im_protocols & NFC_PROTO_NFC_DEP_MASK) {
++                              *((u8 *)skb_put(skb, sizeof(u8))) =
++                                      PN532_AUTOPOLL_TYPE_DEP_PASSIVE_106;
++                              *((u8 *)skb_put(skb, sizeof(u8))) =
++                                      PN532_AUTOPOLL_TYPE_DEP_PASSIVE_212;
++                              *((u8 *)skb_put(skb, sizeof(u8))) =
++                                      PN532_AUTOPOLL_TYPE_DEP_PASSIVE_424;
++                      }
++              }
++
++              if (im_protocols & NFC_PROTO_FELICA_MASK ||
++                              im_protocols & NFC_PROTO_NFC_DEP_MASK) {
++                      *((u8 *)skb_put(skb, sizeof(u8))) =
++                              PN532_AUTOPOLL_TYPE_FELICA212;
++                      *((u8 *)skb_put(skb, sizeof(u8))) =
++                              PN532_AUTOPOLL_TYPE_FELICA424;
++              }
++
++              if (im_protocols & NFC_PROTO_JEWEL_MASK)
++                      *((u8 *)skb_put(skb, sizeof(u8))) =
++                              PN532_AUTOPOLL_TYPE_JEWEL;
++
++              if (im_protocols & NFC_PROTO_ISO14443_B_MASK)
++                      *((u8 *)skb_put(skb, sizeof(u8))) =
++                              PN532_AUTOPOLL_TYPE_ISOB;
++
++              if (tm_protocols)
++                      *((u8 *)skb_put(skb, sizeof(u8))) =
++                              PN532_AUTOPOLL_TYPE_DEP_ACTIVE_106;
++
++              rc = pn533_send_cmd_async(dev, PN533_CMD_IN_AUTOPOLL, skb,
++                              pn533_autopoll_complete, NULL);
++
++              if (rc < 0)
++                      dev_kfree_skb(skb);
++              else
++                      dev->poll_mod_count++;
++
++              return rc;
++      }
++
++      pn533_poll_create_mod_list(dev, im_protocols, tm_protocols);
+       /* Do not always start polling from the same modulation */
+       get_random_bytes(&rand_mod, sizeof(rand_mod));
+@@ -2468,7 +2654,8 @@ static int pn533_dev_up(struct nfc_dev *nfc_dev)
+       if (dev->phy_ops->dev_up)
+               dev->phy_ops->dev_up(dev);
+-      if (dev->device_type == PN533_DEVICE_PN532) {
++      if ((dev->device_type == PN533_DEVICE_PN532) ||
++              (dev->device_type == PN533_DEVICE_PN532_AUTOPOLL)) {
+               int rc = pn532_sam_configuration(nfc_dev);
+               if (rc)
+@@ -2515,6 +2702,7 @@ static int pn533_setup(struct pn533 *dev)
+       case PN533_DEVICE_PASORI:
+       case PN533_DEVICE_ACR122U:
+       case PN533_DEVICE_PN532:
++      case PN533_DEVICE_PN532_AUTOPOLL:
+               max_retries.mx_rty_atr = 0x2;
+               max_retries.mx_rty_psl = 0x1;
+               max_retries.mx_rty_passive_act =
+@@ -2551,6 +2739,7 @@ static int pn533_setup(struct pn533 *dev)
+       switch (dev->device_type) {
+       case PN533_DEVICE_STD:
+       case PN533_DEVICE_PN532:
++      case PN533_DEVICE_PN532_AUTOPOLL:
+               break;
+       case PN533_DEVICE_PASORI:
+diff --git a/drivers/nfc/pn533/pn533.h b/drivers/nfc/pn533/pn533.h
+index 570ee0a3e832b..f9256e5485acc 100644
+--- a/drivers/nfc/pn533/pn533.h
++++ b/drivers/nfc/pn533/pn533.h
+@@ -6,10 +6,11 @@
+  * Copyright (C) 2012-2013 Tieto Poland
+  */
+-#define PN533_DEVICE_STD     0x1
+-#define PN533_DEVICE_PASORI  0x2
+-#define PN533_DEVICE_ACR122U 0x3
+-#define PN533_DEVICE_PN532   0x4
++#define PN533_DEVICE_STD              0x1
++#define PN533_DEVICE_PASORI           0x2
++#define PN533_DEVICE_ACR122U          0x3
++#define PN533_DEVICE_PN532            0x4
++#define PN533_DEVICE_PN532_AUTOPOLL   0x5
+ #define PN533_ALL_PROTOCOLS (NFC_PROTO_JEWEL_MASK | NFC_PROTO_MIFARE_MASK |\
+                            NFC_PROTO_FELICA_MASK | NFC_PROTO_ISO14443_MASK |\
+@@ -70,6 +71,7 @@
+ #define PN533_CMD_IN_ATR 0x50
+ #define PN533_CMD_IN_RELEASE 0x52
+ #define PN533_CMD_IN_JUMP_FOR_DEP 0x56
++#define PN533_CMD_IN_AUTOPOLL 0x60
+ #define PN533_CMD_TG_INIT_AS_TARGET 0x8c
+ #define PN533_CMD_TG_GET_DATA 0x86
+-- 
+2.43.0
+
diff --git a/queue-5.4/nfc-pn533-add-dev_up-dev_down-hooks-to-phy_ops.patch b/queue-5.4/nfc-pn533-add-dev_up-dev_down-hooks-to-phy_ops.patch
new file mode 100644 (file)
index 0000000..9db3b32
--- /dev/null
@@ -0,0 +1,79 @@
+From 283c4e13f6a91ec6334d82ad36371891365ee4c9 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 29 Oct 2019 15:46:29 +0100
+Subject: nfc: pn533: Add dev_up/dev_down hooks to phy_ops
+
+From: Lars Poeschel <poeschel@lemonage.de>
+
+[ Upstream commit 0bf2840ccc6efcba82d83b224dcde19dea9f1ee3 ]
+
+This adds hooks for dev_up and dev_down to the phy_ops. They are
+optional.
+The idea is to inform the phy driver when the nfc chip is really going
+to be used. When it is not used, the phy driver can suspend it's
+interface to the nfc chip to save some power. The nfc chip is considered
+not in use before dev_up and after dev_down.
+
+Cc: Johan Hovold <johan@kernel.org>
+Signed-off-by: Lars Poeschel <poeschel@lemonage.de>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Stable-dep-of: febccb39255f ("nfc: pn533: Add poll mod list filling check")
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ drivers/nfc/pn533/pn533.c | 12 +++++++++++-
+ drivers/nfc/pn533/pn533.h |  9 +++++++++
+ 2 files changed, 20 insertions(+), 1 deletion(-)
+
+diff --git a/drivers/nfc/pn533/pn533.c b/drivers/nfc/pn533/pn533.c
+index 1e90ff17f87db..c36cd68b47eb5 100644
+--- a/drivers/nfc/pn533/pn533.c
++++ b/drivers/nfc/pn533/pn533.c
+@@ -2465,6 +2465,9 @@ static int pn533_dev_up(struct nfc_dev *nfc_dev)
+ {
+       struct pn533 *dev = nfc_get_drvdata(nfc_dev);
++      if (dev->phy_ops->dev_up)
++              dev->phy_ops->dev_up(dev);
++
+       if (dev->device_type == PN533_DEVICE_PN532) {
+               int rc = pn532_sam_configuration(nfc_dev);
+@@ -2477,7 +2480,14 @@ static int pn533_dev_up(struct nfc_dev *nfc_dev)
+ static int pn533_dev_down(struct nfc_dev *nfc_dev)
+ {
+-      return pn533_rf_field(nfc_dev, 0);
++      struct pn533 *dev = nfc_get_drvdata(nfc_dev);
++      int ret;
++
++      ret = pn533_rf_field(nfc_dev, 0);
++      if (dev->phy_ops->dev_down && !ret)
++              dev->phy_ops->dev_down(dev);
++
++      return ret;
+ }
+ static struct nfc_ops pn533_nfc_ops = {
+diff --git a/drivers/nfc/pn533/pn533.h b/drivers/nfc/pn533/pn533.h
+index 8bf9d6ece0f50..570ee0a3e832b 100644
+--- a/drivers/nfc/pn533/pn533.h
++++ b/drivers/nfc/pn533/pn533.h
+@@ -207,6 +207,15 @@ struct pn533_phy_ops {
+                         struct sk_buff *out);
+       int (*send_ack)(struct pn533 *dev, gfp_t flags);
+       void (*abort_cmd)(struct pn533 *priv, gfp_t flags);
++      /*
++       * dev_up and dev_down are optional.
++       * They are used to inform the phy layer that the nfc chip
++       * is going to be really used very soon. The phy layer can then
++       * bring up it's interface to the chip and have it suspended for power
++       * saving reasons otherwise.
++       */
++      void (*dev_up)(struct pn533 *priv);
++      void (*dev_down)(struct pn533 *priv);
+ };
+-- 
+2.43.0
+
diff --git a/queue-5.4/nfc-pn533-add-poll-mod-list-filling-check.patch b/queue-5.4/nfc-pn533-add-poll-mod-list-filling-check.patch
new file mode 100644 (file)
index 0000000..f1da043
--- /dev/null
@@ -0,0 +1,62 @@
+From 3d259fbc024b50f5694ae2c5f9c7a66bfe5cdd50 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 27 Aug 2024 11:48:22 +0300
+Subject: nfc: pn533: Add poll mod list filling check
+
+From: Aleksandr Mishin <amishin@t-argos.ru>
+
+[ Upstream commit febccb39255f9df35527b88c953b2e0deae50e53 ]
+
+In case of im_protocols value is 1 and tm_protocols value is 0 this
+combination successfully passes the check
+'if (!im_protocols && !tm_protocols)' in the nfc_start_poll().
+But then after pn533_poll_create_mod_list() call in pn533_start_poll()
+poll mod list will remain empty and dev->poll_mod_count will remain 0
+which lead to division by zero.
+
+Normally no im protocol has value 1 in the mask, so this combination is
+not expected by driver. But these protocol values actually come from
+userspace via Netlink interface (NFC_CMD_START_POLL operation). So a
+broken or malicious program may pass a message containing a "bad"
+combination of protocol parameter values so that dev->poll_mod_count
+is not incremented inside pn533_poll_create_mod_list(), thus leading
+to division by zero.
+Call trace looks like:
+nfc_genl_start_poll()
+  nfc_start_poll()
+    ->start_poll()
+    pn533_start_poll()
+
+Add poll mod list filling check.
+
+Found by Linux Verification Center (linuxtesting.org) with SVACE.
+
+Fixes: dfccd0f58044 ("NFC: pn533: Add some polling entropy")
+Signed-off-by: Aleksandr Mishin <amishin@t-argos.ru>
+Acked-by: Krzysztof Kozlowski <krzysztof.kozlowski@linaro.org>
+Link: https://patch.msgid.link/20240827084822.18785-1-amishin@t-argos.ru
+Signed-off-by: Paolo Abeni <pabeni@redhat.com>
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ drivers/nfc/pn533/pn533.c | 5 +++++
+ 1 file changed, 5 insertions(+)
+
+diff --git a/drivers/nfc/pn533/pn533.c b/drivers/nfc/pn533/pn533.c
+index 1c3da3675d7df..9610a9b1929f1 100644
+--- a/drivers/nfc/pn533/pn533.c
++++ b/drivers/nfc/pn533/pn533.c
+@@ -1751,6 +1751,11 @@ static int pn533_start_poll(struct nfc_dev *nfc_dev,
+       }
+       pn533_poll_create_mod_list(dev, im_protocols, tm_protocols);
++      if (!dev->poll_mod_count) {
++              nfc_err(dev->dev,
++                      "Poll mod list is empty\n");
++              return -EINVAL;
++      }
+       /* Do not always start polling from the same modulation */
+       get_random_bytes(&rand_mod, sizeof(rand_mod));
+-- 
+2.43.0
+
diff --git a/queue-5.4/r8152-factor-out-oob-link-list-waits.patch b/queue-5.4/r8152-factor-out-oob-link-list-waits.patch
new file mode 100644 (file)
index 0000000..e8e5cca
--- /dev/null
@@ -0,0 +1,184 @@
+From 084fce2514c700dab072fb0b7eb6f584d46cc1e2 Mon Sep 17 00:00:00 2001
+From: Sasha Levin <sashal@kernel.org>
+Date: Tue, 1 Oct 2019 01:35:57 -0700
+Subject: r8152: Factor out OOB link list waits
+
+From: Prashant Malani <pmalani@chromium.org>
+
+[ Upstream commit 5f71c84038d39def573744a145c573758f52a949 ]
+
+The same for-loop check for the LINK_LIST_READY bit of an OOB_CTRL
+register is used in several places. Factor these out into a single
+function to reduce the lines of code.
+
+Change-Id: I20e8f327045a72acc0a83e2d145ae2993ab62915
+Signed-off-by: Prashant Malani <pmalani@chromium.org>
+Reviewed-by: Grant Grundler <grundler@chromium.org>
+Acked-by: Hayes Wang <hayeswang@realtek.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Stable-dep-of: a699781c79ec ("ethtool: check device is present when getting link settings")
+Signed-off-by: Sasha Levin <sashal@kernel.org>
+---
+ drivers/net/usb/r8152.c | 73 ++++++++++++-----------------------------
+ 1 file changed, 21 insertions(+), 52 deletions(-)
+
+diff --git a/drivers/net/usb/r8152.c b/drivers/net/usb/r8152.c
+index 472b02bcfcbf4..92b51c4c46f57 100644
+--- a/drivers/net/usb/r8152.c
++++ b/drivers/net/usb/r8152.c
+@@ -3372,11 +3372,23 @@ static void r8152b_hw_phy_cfg(struct r8152 *tp)
+       set_bit(PHY_RESET, &tp->flags);
+ }
+-static void r8152b_exit_oob(struct r8152 *tp)
++static void wait_oob_link_list_ready(struct r8152 *tp)
+ {
+       u32 ocp_data;
+       int i;
++      for (i = 0; i < 1000; i++) {
++              ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
++              if (ocp_data & LINK_LIST_READY)
++                      break;
++              usleep_range(1000, 2000);
++      }
++}
++
++static void r8152b_exit_oob(struct r8152 *tp)
++{
++      u32 ocp_data;
++
+       ocp_data = ocp_read_dword(tp, MCU_TYPE_PLA, PLA_RCR);
+       ocp_data &= ~RCR_ACPT_ALL;
+       ocp_write_dword(tp, MCU_TYPE_PLA, PLA_RCR, ocp_data);
+@@ -3394,23 +3406,13 @@ static void r8152b_exit_oob(struct r8152 *tp)
+       ocp_data &= ~MCU_BORW_EN;
+       ocp_write_word(tp, MCU_TYPE_PLA, PLA_SFF_STS_7, ocp_data);
+-      for (i = 0; i < 1000; i++) {
+-              ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
+-              if (ocp_data & LINK_LIST_READY)
+-                      break;
+-              usleep_range(1000, 2000);
+-      }
++      wait_oob_link_list_ready(tp);
+       ocp_data = ocp_read_word(tp, MCU_TYPE_PLA, PLA_SFF_STS_7);
+       ocp_data |= RE_INIT_LL;
+       ocp_write_word(tp, MCU_TYPE_PLA, PLA_SFF_STS_7, ocp_data);
+-      for (i = 0; i < 1000; i++) {
+-              ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
+-              if (ocp_data & LINK_LIST_READY)
+-                      break;
+-              usleep_range(1000, 2000);
+-      }
++      wait_oob_link_list_ready(tp);
+       rtl8152_nic_reset(tp);
+@@ -3452,7 +3454,6 @@ static void r8152b_exit_oob(struct r8152 *tp)
+ static void r8152b_enter_oob(struct r8152 *tp)
+ {
+       u32 ocp_data;
+-      int i;
+       ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
+       ocp_data &= ~NOW_IS_OOB;
+@@ -3464,23 +3465,13 @@ static void r8152b_enter_oob(struct r8152 *tp)
+       rtl_disable(tp);
+-      for (i = 0; i < 1000; i++) {
+-              ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
+-              if (ocp_data & LINK_LIST_READY)
+-                      break;
+-              usleep_range(1000, 2000);
+-      }
++      wait_oob_link_list_ready(tp);
+       ocp_data = ocp_read_word(tp, MCU_TYPE_PLA, PLA_SFF_STS_7);
+       ocp_data |= RE_INIT_LL;
+       ocp_write_word(tp, MCU_TYPE_PLA, PLA_SFF_STS_7, ocp_data);
+-      for (i = 0; i < 1000; i++) {
+-              ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
+-              if (ocp_data & LINK_LIST_READY)
+-                      break;
+-              usleep_range(1000, 2000);
+-      }
++      wait_oob_link_list_ready(tp);
+       ocp_write_word(tp, MCU_TYPE_PLA, PLA_RMS, RTL8152_RMS);
+@@ -3705,7 +3696,6 @@ static void r8153b_hw_phy_cfg(struct r8152 *tp)
+ static void r8153_first_init(struct r8152 *tp)
+ {
+       u32 ocp_data;
+-      int i;
+       rxdy_gated_en(tp, true);
+       r8153_teredo_off(tp);
+@@ -3725,23 +3715,13 @@ static void r8153_first_init(struct r8152 *tp)
+       ocp_data &= ~MCU_BORW_EN;
+       ocp_write_word(tp, MCU_TYPE_PLA, PLA_SFF_STS_7, ocp_data);
+-      for (i = 0; i < 1000; i++) {
+-              ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
+-              if (ocp_data & LINK_LIST_READY)
+-                      break;
+-              usleep_range(1000, 2000);
+-      }
++      wait_oob_link_list_ready(tp);
+       ocp_data = ocp_read_word(tp, MCU_TYPE_PLA, PLA_SFF_STS_7);
+       ocp_data |= RE_INIT_LL;
+       ocp_write_word(tp, MCU_TYPE_PLA, PLA_SFF_STS_7, ocp_data);
+-      for (i = 0; i < 1000; i++) {
+-              ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
+-              if (ocp_data & LINK_LIST_READY)
+-                      break;
+-              usleep_range(1000, 2000);
+-      }
++      wait_oob_link_list_ready(tp);
+       rtl_rx_vlan_en(tp, tp->netdev->features & NETIF_F_HW_VLAN_CTAG_RX);
+@@ -3766,7 +3746,6 @@ static void r8153_first_init(struct r8152 *tp)
+ static void r8153_enter_oob(struct r8152 *tp)
+ {
+       u32 ocp_data;
+-      int i;
+       ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
+       ocp_data &= ~NOW_IS_OOB;
+@@ -3775,23 +3754,13 @@ static void r8153_enter_oob(struct r8152 *tp)
+       rtl_disable(tp);
+       rtl_reset_bmu(tp);
+-      for (i = 0; i < 1000; i++) {
+-              ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
+-              if (ocp_data & LINK_LIST_READY)
+-                      break;
+-              usleep_range(1000, 2000);
+-      }
++      wait_oob_link_list_ready(tp);
+       ocp_data = ocp_read_word(tp, MCU_TYPE_PLA, PLA_SFF_STS_7);
+       ocp_data |= RE_INIT_LL;
+       ocp_write_word(tp, MCU_TYPE_PLA, PLA_SFF_STS_7, ocp_data);
+-      for (i = 0; i < 1000; i++) {
+-              ocp_data = ocp_read_byte(tp, MCU_TYPE_PLA, PLA_OOB_CTRL);
+-              if (ocp_data & LINK_LIST_READY)
+-                      break;
+-              usleep_range(1000, 2000);
+-      }
++      wait_oob_link_list_ready(tp);
+       ocp_data = tp->netdev->mtu + VLAN_ETH_HLEN + ETH_FCS_LEN;
+       ocp_write_word(tp, MCU_TYPE_PLA, PLA_RMS, ocp_data);
+-- 
+2.43.0
+
index f20684fa285b1adb204a828eb61c668278d0c909..abe37c042ebcf8e3042e99536305fb061d577d0c 100644 (file)
@@ -117,3 +117,10 @@ ata-libata-core-fix-null-pointer-dereference-on-error.patch
 cgroup-cpuset-prevent-uaf-in-proc_cpuset_show.patch
 net-rds-fix-possible-deadlock-in-rds_message_put.patch
 soundwire-stream-fix-programming-slave-ports-for-non-continous-port-maps.patch
+r8152-factor-out-oob-link-list-waits.patch
+ethtool-check-device-is-present-when-getting-link-se.patch
+gtp-fix-a-potential-null-pointer-dereference.patch
+net-busy-poll-use-ktime_get_ns-instead-of-local_cloc.patch
+nfc-pn533-add-dev_up-dev_down-hooks-to-phy_ops.patch
+nfc-pn533-add-autopoll-capability.patch
+nfc-pn533-add-poll-mod-list-filling-check.patch