--- /dev/null
+From ec6446d5304b3c3dd692a1e244df7e40bbb5af36 Mon Sep 17 00:00:00 2001
+From: Kajol Jain <kjain@linux.ibm.com>
+Date: Tue, 13 Jul 2021 13:12:16 +0530
+Subject: fpga: dfl: fme: Fix cpu hotplug issue in performance reporting
+
+From: Kajol Jain <kjain@linux.ibm.com>
+
+commit ec6446d5304b3c3dd692a1e244df7e40bbb5af36 upstream.
+
+The performance reporting driver added cpu hotplug
+feature but it didn't add pmu migration call in cpu
+offline function.
+This can create an issue incase the current designated
+cpu being used to collect fme pmu data got offline,
+as based on current code we are not migrating fme pmu to
+new target cpu. Because of that perf will still try to
+fetch data from that offline cpu and hence we will not
+get counter data.
+
+Patch fixed this issue by adding pmu_migrate_context call
+in fme_perf_offline_cpu function.
+
+Fixes: 724142f8c42a ("fpga: dfl: fme: add performance reporting support")
+Cc: stable@vger.kernel.org
+Tested-by: Xu Yilun <yilun.xu@intel.com>
+Acked-by: Wu Hao <hao.wu@intel.com>
+Signed-off-by: Kajol Jain <kjain@linux.ibm.com>
+Signed-off-by: Moritz Fischer <mdf@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/fpga/dfl-fme-perf.c | 2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/drivers/fpga/dfl-fme-perf.c
++++ b/drivers/fpga/dfl-fme-perf.c
+@@ -953,6 +953,8 @@ static int fme_perf_offline_cpu(unsigned
+ return 0;
+
+ priv->cpu = target;
++ perf_pmu_migrate_context(&priv->pmu, cpu, target);
++
+ return 0;
+ }
+
--- /dev/null
+From 9a936d6c3d3d6c33ecbadf72dccdb567b5cd3c72 Mon Sep 17 00:00:00 2001
+From: "Maciej W. Rozycki" <macro@orcam.me.uk>
+Date: Sat, 26 Jun 2021 06:11:13 +0200
+Subject: MIPS: Malta: Do not byte-swap accesses to the CBUS UART
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Maciej W. Rozycki <macro@orcam.me.uk>
+
+commit 9a936d6c3d3d6c33ecbadf72dccdb567b5cd3c72 upstream.
+
+Correct big-endian accesses to the CBUS UART, a Malta on-board discrete
+TI16C550C part wired directly to the system controller's device bus, and
+do not use byte swapping with the 32-bit accesses to the device.
+
+The CBUS is used for devices such as the boot flash memory needed early
+on in system bootstrap even before PCI has been initialised. Therefore
+it uses the system controller's device bus, which follows the endianness
+set with the CPU, which means no byte-swapping is ever required for data
+accesses to CBUS, unlike with PCI.
+
+The CBUS UART uses the UPIO_MEM32 access method, that is the `readl' and
+`writel' MMIO accessors, which on the MIPS platform imply byte-swapping
+with PCI systems. Consequently the wrong byte lane is accessed with the
+big-endian configuration and the UART is not correctly accessed.
+
+As it happens the UPIO_MEM32BE access method makes use of the `ioread32'
+and `iowrite32' MMIO accessors, which still use `readl' and `writel'
+respectively, however they byte-swap data passed, effectively cancelling
+swapping done with the accessors themselves and making it suitable for
+the CBUS UART.
+
+Make the CBUS UART switch between UPIO_MEM32 and UPIO_MEM32BE then,
+based on the endianness selected. With this change in place the device
+is correctly recognised with big-endian Malta at boot, along with the
+Super I/O devices behind PCI:
+
+Serial: 8250/16550 driver, 5 ports, IRQ sharing enabled
+printk: console [ttyS0] disabled
+serial8250.0: ttyS0 at I/O 0x3f8 (irq = 4, base_baud = 115200) is a 16550A
+printk: console [ttyS0] enabled
+printk: bootconsole [uart8250] disabled
+serial8250.0: ttyS1 at I/O 0x2f8 (irq = 3, base_baud = 115200) is a 16550A
+serial8250.0: ttyS2 at MMIO 0x1f000900 (irq = 20, base_baud = 230400) is a 16550A
+
+Fixes: e7c4782f92fc ("[MIPS] Put an end to <asm/serial.h>'s long and annyoing existence")
+Cc: stable@vger.kernel.org # v2.6.23+
+Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
+Signed-off-by: Maciej W. Rozycki <macro@orcam.me.uk>
+Link: https://lore.kernel.org/r/alpine.DEB.2.21.2106260524430.37803@angie.orcam.me.uk
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ arch/mips/mti-malta/malta-platform.c | 3 ++-
+ 1 file changed, 2 insertions(+), 1 deletion(-)
+
+--- a/arch/mips/mti-malta/malta-platform.c
++++ b/arch/mips/mti-malta/malta-platform.c
+@@ -47,7 +47,8 @@ static struct plat_serial8250_port uart8
+ .mapbase = 0x1f000900, /* The CBUS UART */
+ .irq = MIPS_CPU_IRQ_BASE + MIPSCPU_INT_MB2,
+ .uartclk = 3686400, /* Twice the usual clk! */
+- .iotype = UPIO_MEM32,
++ .iotype = IS_ENABLED(CONFIG_CPU_BIG_ENDIAN) ?
++ UPIO_MEM32BE : UPIO_MEM32,
+ .flags = CBUS_UART_FLAGS,
+ .regshift = 3,
+ },
--- /dev/null
+From 4e9505064f58d1252805952f8547a5b7dbc5c111 Mon Sep 17 00:00:00 2001
+From: Dmitry Safonov <dima@arista.com>
+Date: Sat, 17 Jul 2021 16:02:21 +0100
+Subject: net/xfrm/compat: Copy xfrm_spdattr_type_t atributes
+
+From: Dmitry Safonov <dima@arista.com>
+
+commit 4e9505064f58d1252805952f8547a5b7dbc5c111 upstream.
+
+The attribute-translator has to take in mind maxtype, that is
+xfrm_link::nla_max. When it is set, attributes are not of xfrm_attr_type_t.
+Currently, they can be only XFRMA_SPD_MAX (message XFRM_MSG_NEWSPDINFO),
+their UABI is the same for 64/32-bit, so just copy them.
+
+Thanks to YueHaibing for reporting this:
+In xfrm_user_rcv_msg_compat() if maxtype is not zero and less than
+XFRMA_MAX, nlmsg_parse_deprecated() do not initialize attrs array fully.
+xfrm_xlate32() will access uninit 'attrs[i]' while iterating all attrs
+array.
+
+KASAN: probably user-memory-access in range [0x0000000041b58ab0-0x0000000041b58ab7]
+CPU: 0 PID: 15799 Comm: syz-executor.2 Tainted: G W 5.14.0-rc1-syzkaller #0
+RIP: 0010:nla_type include/net/netlink.h:1130 [inline]
+RIP: 0010:xfrm_xlate32_attr net/xfrm/xfrm_compat.c:410 [inline]
+RIP: 0010:xfrm_xlate32 net/xfrm/xfrm_compat.c:532 [inline]
+RIP: 0010:xfrm_user_rcv_msg_compat+0x5e5/0x1070 net/xfrm/xfrm_compat.c:577
+[...]
+Call Trace:
+ xfrm_user_rcv_msg+0x556/0x8b0 net/xfrm/xfrm_user.c:2774
+ netlink_rcv_skb+0x153/0x420 net/netlink/af_netlink.c:2504
+ xfrm_netlink_rcv+0x6b/0x90 net/xfrm/xfrm_user.c:2824
+ netlink_unicast_kernel net/netlink/af_netlink.c:1314 [inline]
+ netlink_unicast+0x533/0x7d0 net/netlink/af_netlink.c:1340
+ netlink_sendmsg+0x86d/0xdb0 net/netlink/af_netlink.c:1929
+ sock_sendmsg_nosec net/socket.c:702 [inline]
+
+Fixes: 5106f4a8acff ("xfrm/compat: Add 32=>64-bit messages translator")
+Cc: <stable@kernel.org>
+Reported-by: YueHaibing <yuehaibing@huawei.com>
+Signed-off-by: Dmitry Safonov <dima@arista.com>
+Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/xfrm/xfrm_compat.c | 49 ++++++++++++++++++++++++++++++++++++++++++++-----
+ 1 file changed, 44 insertions(+), 5 deletions(-)
+
+--- a/net/xfrm/xfrm_compat.c
++++ b/net/xfrm/xfrm_compat.c
+@@ -298,8 +298,16 @@ static int xfrm_xlate64(struct sk_buff *
+ len = nlmsg_attrlen(nlh_src, xfrm_msg_min[type]);
+
+ nla_for_each_attr(nla, attrs, len, remaining) {
+- int err = xfrm_xlate64_attr(dst, nla);
++ int err;
+
++ switch (type) {
++ case XFRM_MSG_NEWSPDINFO:
++ err = xfrm_nla_cpy(dst, nla, nla_len(nla));
++ break;
++ default:
++ err = xfrm_xlate64_attr(dst, nla);
++ break;
++ }
+ if (err)
+ return err;
+ }
+@@ -341,7 +349,8 @@ static int xfrm_alloc_compat(struct sk_b
+
+ /* Calculates len of translated 64-bit message. */
+ static size_t xfrm_user_rcv_calculate_len64(const struct nlmsghdr *src,
+- struct nlattr *attrs[XFRMA_MAX+1])
++ struct nlattr *attrs[XFRMA_MAX + 1],
++ int maxtype)
+ {
+ size_t len = nlmsg_len(src);
+
+@@ -358,10 +367,20 @@ static size_t xfrm_user_rcv_calculate_le
+ case XFRM_MSG_POLEXPIRE:
+ len += 8;
+ break;
++ case XFRM_MSG_NEWSPDINFO:
++ /* attirbutes are xfrm_spdattr_type_t, not xfrm_attr_type_t */
++ return len;
+ default:
+ break;
+ }
+
++ /* Unexpected for anything, but XFRM_MSG_NEWSPDINFO, please
++ * correct both 64=>32-bit and 32=>64-bit translators to copy
++ * new attributes.
++ */
++ if (WARN_ON_ONCE(maxtype))
++ return len;
++
+ if (attrs[XFRMA_SA])
+ len += 4;
+ if (attrs[XFRMA_POLICY])
+@@ -440,7 +459,8 @@ static int xfrm_xlate32_attr(void *dst,
+
+ static int xfrm_xlate32(struct nlmsghdr *dst, const struct nlmsghdr *src,
+ struct nlattr *attrs[XFRMA_MAX+1],
+- size_t size, u8 type, struct netlink_ext_ack *extack)
++ size_t size, u8 type, int maxtype,
++ struct netlink_ext_ack *extack)
+ {
+ size_t pos;
+ int i;
+@@ -520,6 +540,25 @@ static int xfrm_xlate32(struct nlmsghdr
+ }
+ pos = dst->nlmsg_len;
+
++ if (maxtype) {
++ /* attirbutes are xfrm_spdattr_type_t, not xfrm_attr_type_t */
++ WARN_ON_ONCE(src->nlmsg_type != XFRM_MSG_NEWSPDINFO);
++
++ for (i = 1; i <= maxtype; i++) {
++ int err;
++
++ if (!attrs[i])
++ continue;
++
++ /* just copy - no need for translation */
++ err = xfrm_attr_cpy32(dst, &pos, attrs[i], size,
++ nla_len(attrs[i]), nla_len(attrs[i]));
++ if (err)
++ return err;
++ }
++ return 0;
++ }
++
+ for (i = 1; i < XFRMA_MAX + 1; i++) {
+ int err;
+
+@@ -564,7 +603,7 @@ static struct nlmsghdr *xfrm_user_rcv_ms
+ if (err < 0)
+ return ERR_PTR(err);
+
+- len = xfrm_user_rcv_calculate_len64(h32, attrs);
++ len = xfrm_user_rcv_calculate_len64(h32, attrs, maxtype);
+ /* The message doesn't need translation */
+ if (len == nlmsg_len(h32))
+ return NULL;
+@@ -574,7 +613,7 @@ static struct nlmsghdr *xfrm_user_rcv_ms
+ if (!h64)
+ return ERR_PTR(-ENOMEM);
+
+- err = xfrm_xlate32(h64, h32, attrs, len, type, extack);
++ err = xfrm_xlate32(h64, h32, attrs, len, type, maxtype, extack);
+ if (err < 0) {
+ kvfree(h64);
+ return ERR_PTR(err);
--- /dev/null
+From 9d7a6c95f62bc335b62aaf9d50590122bd03a796 Mon Sep 17 00:00:00 2001
+From: Marco Elver <elver@google.com>
+Date: Mon, 5 Jul 2021 10:44:52 +0200
+Subject: perf: Fix required permissions if sigtrap is requested
+
+From: Marco Elver <elver@google.com>
+
+commit 9d7a6c95f62bc335b62aaf9d50590122bd03a796 upstream.
+
+If perf_event_open() is called with another task as target and
+perf_event_attr::sigtrap is set, and the target task's user does not
+match the calling user, also require the CAP_KILL capability or
+PTRACE_MODE_ATTACH permissions.
+
+Otherwise, with the CAP_PERFMON capability alone it would be possible
+for a user to send SIGTRAP signals via perf events to another user's
+tasks. This could potentially result in those tasks being terminated if
+they cannot handle SIGTRAP signals.
+
+Note: The check complements the existing capability check, but is not
+supposed to supersede the ptrace_may_access() check. At a high level we
+now have:
+
+ capable of CAP_PERFMON and (CAP_KILL if sigtrap)
+ OR
+ ptrace_may_access(...) // also checks for same thread-group and uid
+
+Fixes: 97ba62b27867 ("perf: Add support for SIGTRAP on perf events")
+Reported-by: Dmitry Vyukov <dvyukov@google.com>
+Signed-off-by: Marco Elver <elver@google.com>
+Signed-off-by: Peter Zijlstra (Intel) <peterz@infradead.org>
+Acked-by: Dmitry Vyukov <dvyukov@google.com>
+Cc: <stable@vger.kernel.org> # 5.13+
+Link: https://lore.kernel.org/r/20210705084453.2151729-1-elver@google.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ kernel/events/core.c | 25 ++++++++++++++++++++++++-
+ 1 file changed, 24 insertions(+), 1 deletion(-)
+
+--- a/kernel/events/core.c
++++ b/kernel/events/core.c
+@@ -12159,10 +12159,33 @@ SYSCALL_DEFINE5(perf_event_open,
+ }
+
+ if (task) {
++ unsigned int ptrace_mode = PTRACE_MODE_READ_REALCREDS;
++ bool is_capable;
++
+ err = down_read_interruptible(&task->signal->exec_update_lock);
+ if (err)
+ goto err_file;
+
++ is_capable = perfmon_capable();
++ if (attr.sigtrap) {
++ /*
++ * perf_event_attr::sigtrap sends signals to the other
++ * task. Require the current task to also have
++ * CAP_KILL.
++ */
++ rcu_read_lock();
++ is_capable &= ns_capable(__task_cred(task)->user_ns, CAP_KILL);
++ rcu_read_unlock();
++
++ /*
++ * If the required capabilities aren't available, checks
++ * for ptrace permissions: upgrade to ATTACH, since
++ * sending signals can effectively change the target
++ * task.
++ */
++ ptrace_mode = PTRACE_MODE_ATTACH_REALCREDS;
++ }
++
+ /*
+ * Preserve ptrace permission check for backwards compatibility.
+ *
+@@ -12172,7 +12195,7 @@ SYSCALL_DEFINE5(perf_event_open,
+ * perf_event_exit_task() that could imply).
+ */
+ err = -EACCES;
+- if (!perfmon_capable() && !ptrace_may_access(task, PTRACE_MODE_READ_REALCREDS))
++ if (!is_capable && !ptrace_may_access(task, ptrace_mode))
+ goto err_cred;
+ }
+
--- /dev/null
+From 853a9ae29e978d37f5dfa72622a68c9ae3d7fa89 Mon Sep 17 00:00:00 2001
+From: Johan Hovold <johan@kernel.org>
+Date: Wed, 14 Jul 2021 10:04:27 +0200
+Subject: serial: 8250: fix handle_irq locking
+
+From: Johan Hovold <johan@kernel.org>
+
+commit 853a9ae29e978d37f5dfa72622a68c9ae3d7fa89 upstream.
+
+The 8250 handle_irq callback is not just called from the interrupt
+handler but also from a timer callback when polling (e.g. for ports
+without an interrupt line). Consequently the callback must explicitly
+disable interrupts to avoid a potential deadlock with another interrupt
+in polled mode.
+
+Add back an irqrestore-version of the sysrq port-unlock helper and use
+it in the 8250 callbacks that need it.
+
+Fixes: 75f4e830fa9c ("serial: do not restore interrupt state in sysrq helper")
+Cc: stable@vger.kernel.org # 5.13
+Cc: Joel Stanley <joel@jms.id.au>
+Cc: Andrew Jeffery <andrew@aj.id.au>
+Reported-by: kernel test robot <oliver.sang@intel.com>
+Signed-off-by: Johan Hovold <johan@kernel.org>
+Link: https://lore.kernel.org/r/20210714080427.28164-1-johan@kernel.org
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/tty/serial/8250/8250_aspeed_vuart.c | 5 +++--
+ drivers/tty/serial/8250/8250_fsl.c | 5 +++--
+ drivers/tty/serial/8250/8250_port.c | 5 +++--
+ include/linux/serial_core.h | 24 ++++++++++++++++++++++++
+ 4 files changed, 33 insertions(+), 6 deletions(-)
+
+--- a/drivers/tty/serial/8250/8250_aspeed_vuart.c
++++ b/drivers/tty/serial/8250/8250_aspeed_vuart.c
+@@ -320,6 +320,7 @@ static int aspeed_vuart_handle_irq(struc
+ {
+ struct uart_8250_port *up = up_to_u8250p(port);
+ unsigned int iir, lsr;
++ unsigned long flags;
+ int space, count;
+
+ iir = serial_port_in(port, UART_IIR);
+@@ -327,7 +328,7 @@ static int aspeed_vuart_handle_irq(struc
+ if (iir & UART_IIR_NO_INT)
+ return 0;
+
+- spin_lock(&port->lock);
++ spin_lock_irqsave(&port->lock, flags);
+
+ lsr = serial_port_in(port, UART_LSR);
+
+@@ -363,7 +364,7 @@ static int aspeed_vuart_handle_irq(struc
+ if (lsr & UART_LSR_THRE)
+ serial8250_tx_chars(up);
+
+- uart_unlock_and_check_sysrq(port);
++ uart_unlock_and_check_sysrq_irqrestore(port, flags);
+
+ return 1;
+ }
+--- a/drivers/tty/serial/8250/8250_fsl.c
++++ b/drivers/tty/serial/8250/8250_fsl.c
+@@ -30,10 +30,11 @@ struct fsl8250_data {
+ int fsl8250_handle_irq(struct uart_port *port)
+ {
+ unsigned char lsr, orig_lsr;
++ unsigned long flags;
+ unsigned int iir;
+ struct uart_8250_port *up = up_to_u8250p(port);
+
+- spin_lock(&up->port.lock);
++ spin_lock_irqsave(&up->port.lock, flags);
+
+ iir = port->serial_in(port, UART_IIR);
+ if (iir & UART_IIR_NO_INT) {
+@@ -82,7 +83,7 @@ int fsl8250_handle_irq(struct uart_port
+
+ up->lsr_saved_flags = orig_lsr;
+
+- uart_unlock_and_check_sysrq(&up->port);
++ uart_unlock_and_check_sysrq_irqrestore(&up->port, flags);
+
+ return 1;
+ }
+--- a/drivers/tty/serial/8250/8250_port.c
++++ b/drivers/tty/serial/8250/8250_port.c
+@@ -1899,11 +1899,12 @@ int serial8250_handle_irq(struct uart_po
+ unsigned char status;
+ struct uart_8250_port *up = up_to_u8250p(port);
+ bool skip_rx = false;
++ unsigned long flags;
+
+ if (iir & UART_IIR_NO_INT)
+ return 0;
+
+- spin_lock(&port->lock);
++ spin_lock_irqsave(&port->lock, flags);
+
+ status = serial_port_in(port, UART_LSR);
+
+@@ -1929,7 +1930,7 @@ int serial8250_handle_irq(struct uart_po
+ (up->ier & UART_IER_THRI))
+ serial8250_tx_chars(up);
+
+- uart_unlock_and_check_sysrq(port);
++ uart_unlock_and_check_sysrq_irqrestore(port, flags);
+
+ return 1;
+ }
+--- a/include/linux/serial_core.h
++++ b/include/linux/serial_core.h
+@@ -517,6 +517,25 @@ static inline void uart_unlock_and_check
+ if (sysrq_ch)
+ handle_sysrq(sysrq_ch);
+ }
++
++static inline void uart_unlock_and_check_sysrq_irqrestore(struct uart_port *port,
++ unsigned long flags)
++{
++ int sysrq_ch;
++
++ if (!port->has_sysrq) {
++ spin_unlock_irqrestore(&port->lock, flags);
++ return;
++ }
++
++ sysrq_ch = port->sysrq_ch;
++ port->sysrq_ch = 0;
++
++ spin_unlock_irqrestore(&port->lock, flags);
++
++ if (sysrq_ch)
++ handle_sysrq(sysrq_ch);
++}
+ #else /* CONFIG_MAGIC_SYSRQ_SERIAL */
+ static inline int uart_handle_sysrq_char(struct uart_port *port, unsigned int ch)
+ {
+@@ -530,6 +549,11 @@ static inline void uart_unlock_and_check
+ {
+ spin_unlock(&port->lock);
+ }
++static inline void uart_unlock_and_check_sysrq_irqrestore(struct uart_port *port,
++ unsigned long flags)
++{
++ spin_unlock_irqrestore(&port->lock, flags);
++}
+ #endif /* CONFIG_MAGIC_SYSRQ_SERIAL */
+
+ /*
--- /dev/null
+From e5227c51090e165db4b48dcaa300605bfced7014 Mon Sep 17 00:00:00 2001
+From: "Maciej W. Rozycki" <macro@orcam.me.uk>
+Date: Sat, 26 Jun 2021 06:11:05 +0200
+Subject: serial: 8250: Mask out floating 16/32-bit bus bits
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Maciej W. Rozycki <macro@orcam.me.uk>
+
+commit e5227c51090e165db4b48dcaa300605bfced7014 upstream.
+
+Make sure only actual 8 bits of the IIR register are used in determining
+the port type in `autoconfig'.
+
+The `serial_in' port accessor returns the `unsigned int' type, meaning
+that with UPIO_AU, UPIO_MEM16, UPIO_MEM32, and UPIO_MEM32BE access types
+more than 8 bits of data are returned, of which the high order bits will
+often come from bus lines that are left floating in the data phase. For
+example with the MIPS Malta board's CBUS UART, where the registers are
+aligned on 8-byte boundaries and which uses 32-bit accesses, data as
+follows is returned:
+
+YAMON> dump -32 0xbf000900 0x40
+
+BF000900: 1F000942 1F000942 1F000900 1F000900 ...B...B........
+BF000910: 1F000901 1F000901 1F000900 1F000900 ................
+BF000920: 1F000900 1F000900 1F000960 1F000960 ...........`...`
+BF000930: 1F000900 1F000900 1F0009FF 1F0009FF ................
+
+YAMON>
+
+Evidently high-order 24 bits return values previously driven in the
+address phase (the 3 highest order address bits used with the command
+above are masked out in the simple virtual address mapping used here and
+come out at zeros on the external bus), a common scenario with bus lines
+left floating, due to bus capacitance.
+
+Consequently when the value of IIR, mapped at 0x1f000910, is retrieved
+in `autoconfig', it comes out at 0x1f0009c1 and when it is right-shifted
+by 6 and then assigned to 8-bit `scratch' variable, the value calculated
+is 0x27, not one of 0, 1, 2, 3 expected in port type determination.
+
+Fix the issue then, by assigning the value returned from `serial_in' to
+`scratch' first, which masks out 24 high-order bits retrieved, and only
+then right-shift the resulting 8-bit data quantity, producing the value
+of 3 in this case, as expected. Fix the same issue in `serial_dl_read'.
+
+The problem first appeared with Linux 2.6.9-rc3 which predates our repo
+history, but the origin could be identified with the old MIPS/Linux repo
+also at: <git://git.kernel.org/pub/scm/linux/kernel/git/ralf/linux.git>
+as commit e0d2356c0777 ("Merge with Linux 2.6.9-rc3."), where code in
+`serial_in' was updated with this case:
+
++ case UPIO_MEM32:
++ return readl(up->port.membase + offset);
++
+
+which made it produce results outside the unsigned 8-bit range for the
+first time, though obviously it is system dependent what actual values
+appear in the high order bits retrieved and it may well have been zeros
+in the relevant positions with the system the change originally was
+intended for. It is at that point that code in `autoconf' should have
+been updated accordingly, but clearly it was overlooked.
+
+Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2")
+Cc: stable@vger.kernel.org # v2.6.12+
+Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
+Signed-off-by: Maciej W. Rozycki <macro@orcam.me.uk>
+Link: https://lore.kernel.org/r/alpine.DEB.2.21.2106260516220.37803@angie.orcam.me.uk
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/tty/serial/8250/8250_port.c | 12 +++++++++---
+ 1 file changed, 9 insertions(+), 3 deletions(-)
+
+--- a/drivers/tty/serial/8250/8250_port.c
++++ b/drivers/tty/serial/8250/8250_port.c
+@@ -311,7 +311,11 @@ static const struct serial8250_config ua
+ /* Uart divisor latch read */
+ static int default_serial_dl_read(struct uart_8250_port *up)
+ {
+- return serial_in(up, UART_DLL) | serial_in(up, UART_DLM) << 8;
++ /* Assign these in pieces to truncate any bits above 7. */
++ unsigned char dll = serial_in(up, UART_DLL);
++ unsigned char dlm = serial_in(up, UART_DLM);
++
++ return dll | dlm << 8;
+ }
+
+ /* Uart divisor latch write */
+@@ -1297,9 +1301,11 @@ static void autoconfig(struct uart_8250_
+ serial_out(up, UART_LCR, 0);
+
+ serial_out(up, UART_FCR, UART_FCR_ENABLE_FIFO);
+- scratch = serial_in(up, UART_IIR) >> 6;
+
+- switch (scratch) {
++ /* Assign this as it is to truncate any bits above 7. */
++ scratch = serial_in(up, UART_IIR);
++
++ switch (scratch >> 6) {
+ case 0:
+ autoconfig_8250(up);
+ break;
--- /dev/null
+From 7c4a509d3815a260c423c0633bd73695250ac26d Mon Sep 17 00:00:00 2001
+From: Zhiyong Tao <zhiyong.tao@mediatek.com>
+Date: Thu, 29 Jul 2021 16:46:40 +0800
+Subject: serial: 8250_mtk: fix uart corruption issue when rx power off
+
+From: Zhiyong Tao <zhiyong.tao@mediatek.com>
+
+commit 7c4a509d3815a260c423c0633bd73695250ac26d upstream.
+
+Fix uart corruption issue when rx power off.
+Add spin lock in mtk8250_dma_rx_complete function in APDMA mode.
+
+when uart is used as a communication port with external device(GPS).
+when external device(GPS) power off, the power of rx pin is also from
+1.8v to 0v. Even if there is not any data in rx. But uart rx pin can
+capture the data "0".
+If uart don't receive any data in specified cycle, uart will generates
+BI(Break interrupt) interrupt.
+If external device(GPS) power off, we found that BI interrupt appeared
+continuously and very frequently.
+When uart interrupt type is BI, uart IRQ handler(8250 framwork
+API:serial8250_handle_irq) will push data to tty buffer.
+mtk8250_dma_rx_complete is a task of mtk_uart_apdma_rx_handler.
+mtk8250_dma_rx_complete priority is lower than uart irq
+handler(serial8250_handle_irq).
+if we are in process of mtk8250_dma_rx_complete, uart appear BI
+interrupt:1)serial8250_handle_irq will priority execution.2)it may cause
+write tty buffer conflict in mtk8250_dma_rx_complete.
+So the spin lock protect the rx receive data process is not break.
+
+Signed-off-by: Zhiyong Tao <zhiyong.tao@mediatek.com>
+Cc: stable <stable@vger.kernel.org>
+Link: https://lore.kernel.org/r/20210729084640.17613-2-zhiyong.tao@mediatek.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/tty/serial/8250/8250_mtk.c | 5 +++++
+ 1 file changed, 5 insertions(+)
+
+--- a/drivers/tty/serial/8250/8250_mtk.c
++++ b/drivers/tty/serial/8250/8250_mtk.c
+@@ -93,10 +93,13 @@ static void mtk8250_dma_rx_complete(void
+ struct dma_tx_state state;
+ int copied, total, cnt;
+ unsigned char *ptr;
++ unsigned long flags;
+
+ if (data->rx_status == DMA_RX_SHUTDOWN)
+ return;
+
++ spin_lock_irqsave(&up->port.lock, flags);
++
+ dmaengine_tx_status(dma->rxchan, dma->rx_cookie, &state);
+ total = dma->rx_size - state.residue;
+ cnt = total;
+@@ -120,6 +123,8 @@ static void mtk8250_dma_rx_complete(void
+ tty_flip_buffer_push(tty_port);
+
+ mtk8250_rx_dma(up);
++
++ spin_unlock_irqrestore(&up->port.lock, flags);
+ }
+
+ static void mtk8250_rx_dma(struct uart_8250_port *up)
--- /dev/null
+From 341abd693d10e5f337a51f140ae3e7a1ae0febf6 Mon Sep 17 00:00:00 2001
+From: Mario Kleiner <mario.kleiner.de@gmail.com>
+Date: Thu, 29 Jul 2021 06:33:06 +0200
+Subject: serial: 8250_pci: Avoid irq sharing for MSI(-X) interrupts.
+
+From: Mario Kleiner <mario.kleiner.de@gmail.com>
+
+commit 341abd693d10e5f337a51f140ae3e7a1ae0febf6 upstream.
+
+This attempts to fix a bug found with a serial port card which uses
+an MCS9922 chip, one of the 4 models for which MSI-X interrupts are
+currently supported. I don't possess such a card, and i'm not
+experienced with the serial subsystem, so this patch is based on what
+i think i found as a likely reason for failure, based on walking the
+user who actually owns the card through some diagnostic.
+
+The user who reported the problem finds the following in his dmesg
+output for the relevant ttyS4 and ttyS5:
+
+[ 0.580425] serial 0000:02:00.0: enabling device (0000 -> 0003)
+[ 0.601448] 0000:02:00.0: ttyS4 at I/O 0x3010 (irq = 125, base_baud = 115200) is a ST16650V2
+[ 0.603089] serial 0000:02:00.1: enabling device (0000 -> 0003)
+[ 0.624119] 0000:02:00.1: ttyS5 at I/O 0x3000 (irq = 126, base_baud = 115200) is a ST16650V2
+...
+[ 6.323784] genirq: Flags mismatch irq 128. 00000080 (ttyS5) vs. 00000000 (xhci_hcd)
+[ 6.324128] genirq: Flags mismatch irq 128. 00000080 (ttyS5) vs. 00000000 (xhci_hcd)
+...
+
+Output of setserial -a:
+
+/dev/ttyS4, Line 4, UART: 16650V2, Port: 0x3010, IRQ: 127
+ Baud_base: 115200, close_delay: 50, divisor: 0
+ closing_wait: 3000
+ Flags: spd_normal skip_test
+
+This suggests to me that the serial driver wants to register and share a
+MSI/MSI-X irq 128 with the xhci_hcd driver, whereas the xhci driver does
+not want to share the irq, as flags 0x00000080 (== IRQF_SHARED) from the
+serial port driver means to share the irq, and this mismatch ends in some
+failed irq init?
+
+With this setup, data reception works very unreliable, with dropped data,
+already at a transmission rate of only a 16 Bytes chunk every 1/120th of
+a second, ie. 1920 Bytes/sec, presumably due to rx fifo overflow due to
+mishandled or not used at all rx irq's?
+
+See full discussion thread with attempted diagnosis at:
+
+https://psychtoolbox.discourse.group/t/issues-with-iscan-serial-port-recording/3886
+
+Disabling the use of MSI interrupts for the serial port pci card did
+fix the reliability problems. The user executed the following sequence
+of commands to achieve this:
+
+echo 0000:02:00.0 | sudo tee /sys/bus/pci/drivers/serial/unbind
+echo 0000:02:00.1 | sudo tee /sys/bus/pci/drivers/serial/unbind
+
+echo 0 | sudo tee /sys/bus/pci/devices/0000:02:00.0/msi_bus
+echo 0 | sudo tee /sys/bus/pci/devices/0000:02:00.1/msi_bus
+
+echo 0000:02:00.0 | sudo tee /sys/bus/pci/drivers/serial/bind
+echo 0000:02:00.1 | sudo tee /sys/bus/pci/drivers/serial/bind
+
+This resulted in the following log output:
+
+[ 82.179021] pci 0000:02:00.0: MSI/MSI-X disallowed for future drivers
+[ 87.003031] pci 0000:02:00.1: MSI/MSI-X disallowed for future drivers
+[ 98.537010] 0000:02:00.0: ttyS4 at I/O 0x3010 (irq = 17, base_baud = 115200) is a ST16650V2
+[ 103.648124] 0000:02:00.1: ttyS5 at I/O 0x3000 (irq = 18, base_baud = 115200) is a ST16650V2
+
+This patch attempts to fix the problem by disabling irq sharing when
+using MSI irq's. Note that all i know for sure is that disabling MSI
+irq's fixed the problem for the user, so this patch could be wrong and
+is untested. Please review with caution, keeping this in mind.
+
+Fixes: 8428413b1d14 ("serial: 8250_pci: Implement MSI(-X) support")
+Cc: Ralf Ramsauer <ralf.ramsauer@oth-regensburg.de>
+Cc: stable <stable@vger.kernel.org>
+Reviewed-by: Andy Shevchenko <andy.shevchenko@gmail.com>
+Signed-off-by: Mario Kleiner <mario.kleiner.de@gmail.com>
+Link: https://lore.kernel.org/r/20210729043306.18528-1-mario.kleiner.de@gmail.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/tty/serial/8250/8250_pci.c | 1 +
+ 1 file changed, 1 insertion(+)
+
+--- a/drivers/tty/serial/8250/8250_pci.c
++++ b/drivers/tty/serial/8250/8250_pci.c
+@@ -3970,6 +3970,7 @@ pciserial_init_ports(struct pci_dev *dev
+ if (pci_match_id(pci_use_msi, dev)) {
+ dev_dbg(&dev->dev, "Using MSI(-X) interrupts\n");
+ pci_set_master(dev);
++ uart.port.flags &= ~UPF_SHARE_IRQ;
+ rc = pci_alloc_irq_vectors(dev, 1, 1, PCI_IRQ_ALL_TYPES);
+ } else {
+ dev_dbg(&dev->dev, "Using legacy interrupts\n");
--- /dev/null
+From 7f0909db761535aefafa77031062603a71557267 Mon Sep 17 00:00:00 2001
+From: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
+Date: Tue, 13 Jul 2021 13:17:39 +0300
+Subject: serial: 8250_pci: Enumerate Elkhart Lake UARTs via dedicated driver
+
+From: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
+
+commit 7f0909db761535aefafa77031062603a71557267 upstream.
+
+Elkhart Lake UARTs are PCI enumerated Synopsys DesignWare v4.0+ UART
+integrated with Intel iDMA 32-bit DMA controller. There is a specific
+driver to handle them, i.e. 8250_lpss. Hence, disable 8250_pci
+enumeration for these UARTs.
+
+Fixes: 1b91d97c66ef ("serial: 8250_lpss: Add ->setup() for Elkhart Lake ports")
+Fixes: 4f912b898dc2 ("serial: 8250_lpss: Enable HS UART on Elkhart Lake")
+Cc: stable <stable@vger.kernel.org>
+Signed-off-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
+Link: https://lore.kernel.org/r/20210713101739.36962-1-andriy.shevchenko@linux.intel.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/tty/serial/8250/8250_pci.c | 6 ++++++
+ 1 file changed, 6 insertions(+)
+
+--- a/drivers/tty/serial/8250/8250_pci.c
++++ b/drivers/tty/serial/8250/8250_pci.c
+@@ -3804,6 +3804,12 @@ static const struct pci_device_id blackl
+ { PCI_VDEVICE(INTEL, 0x0f0c), },
+ { PCI_VDEVICE(INTEL, 0x228a), },
+ { PCI_VDEVICE(INTEL, 0x228c), },
++ { PCI_VDEVICE(INTEL, 0x4b96), },
++ { PCI_VDEVICE(INTEL, 0x4b97), },
++ { PCI_VDEVICE(INTEL, 0x4b98), },
++ { PCI_VDEVICE(INTEL, 0x4b99), },
++ { PCI_VDEVICE(INTEL, 0x4b9a), },
++ { PCI_VDEVICE(INTEL, 0x4b9b), },
+ { PCI_VDEVICE(INTEL, 0x9ce3), },
+ { PCI_VDEVICE(INTEL, 0x9ce4), },
+
--- /dev/null
+From cc9ca4d95846cbbece48d9cd385550f8fba6a3c1 Mon Sep 17 00:00:00 2001
+From: Jon Hunter <jonathanh@nvidia.com>
+Date: Wed, 30 Jun 2021 13:56:43 +0100
+Subject: serial: tegra: Only print FIFO error message when an error occurs
+
+From: Jon Hunter <jonathanh@nvidia.com>
+
+commit cc9ca4d95846cbbece48d9cd385550f8fba6a3c1 upstream.
+
+The Tegra serial driver always prints an error message when enabling the
+FIFO for devices that have support for checking the FIFO enable status.
+Fix this by displaying the error message, only when an error occurs.
+
+Finally, update the error message to make it clear that enabling the
+FIFO failed and display the error code.
+
+Fixes: 222dcdff3405 ("serial: tegra: check for FIFO mode enabled status")
+Cc: <stable@vger.kernel.org>
+Acked-by: Thierry Reding <treding@nvidia.com>
+Signed-off-by: Jon Hunter <jonathanh@nvidia.com>
+Link: https://lore.kernel.org/r/20210630125643.264264-1-jonathanh@nvidia.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/tty/serial/serial-tegra.c | 6 ++++--
+ 1 file changed, 4 insertions(+), 2 deletions(-)
+
+--- a/drivers/tty/serial/serial-tegra.c
++++ b/drivers/tty/serial/serial-tegra.c
+@@ -1045,9 +1045,11 @@ static int tegra_uart_hw_init(struct teg
+
+ if (tup->cdata->fifo_mode_enable_status) {
+ ret = tegra_uart_wait_fifo_mode_enabled(tup);
+- dev_err(tup->uport.dev, "FIFO mode not enabled\n");
+- if (ret < 0)
++ if (ret < 0) {
++ dev_err(tup->uport.dev,
++ "Failed to enable FIFO mode: %d\n", ret);
+ return ret;
++ }
+ } else {
+ /*
+ * For all tegra devices (up to t210), there is a hardware
pipe-increase-minimum-default-pipe-size-to-2-pages.patch
ext4-fix-potential-htree-corruption-when-growing-large_dir-directories.patch
revert-thunderbolt-hide-authorized-attribute-if-router-does-not-support-pcie-tunnels.patch
+serial-tegra-only-print-fifo-error-message-when-an-error-occurs.patch
+serial-8250_mtk-fix-uart-corruption-issue-when-rx-power-off.patch
+serial-8250-mask-out-floating-16-32-bit-bus-bits.patch
+serial-8250-fix-handle_irq-locking.patch
+mips-malta-do-not-byte-swap-accesses-to-the-cbus-uart.patch
+serial-8250_pci-enumerate-elkhart-lake-uarts-via-dedicated-driver.patch
+serial-8250_pci-avoid-irq-sharing-for-msi-x-interrupts.patch
+fpga-dfl-fme-fix-cpu-hotplug-issue-in-performance-reporting.patch
+timers-move-clearing-of-base-timer_running-under-base-lock.patch
+virt-acrn-do-hcall_destroy_vm-before-resource-release.patch
+perf-fix-required-permissions-if-sigtrap-is-requested.patch
+xfrm-fix-rcu-vs-hash_resize_mutex-lock-inversion.patch
+net-xfrm-compat-copy-xfrm_spdattr_type_t-atributes.patch
--- /dev/null
+From bb7262b295472eb6858b5c49893954794027cd84 Mon Sep 17 00:00:00 2001
+From: Thomas Gleixner <tglx@linutronix.de>
+Date: Sun, 6 Dec 2020 22:40:07 +0100
+Subject: timers: Move clearing of base::timer_running under base:: Lock
+
+From: Thomas Gleixner <tglx@linutronix.de>
+
+commit bb7262b295472eb6858b5c49893954794027cd84 upstream.
+
+syzbot reported KCSAN data races vs. timer_base::timer_running being set to
+NULL without holding base::lock in expire_timers().
+
+This looks innocent and most reads are clearly not problematic, but
+Frederic identified an issue which is:
+
+ int data = 0;
+
+ void timer_func(struct timer_list *t)
+ {
+ data = 1;
+ }
+
+ CPU 0 CPU 1
+ ------------------------------ --------------------------
+ base = lock_timer_base(timer, &flags); raw_spin_unlock(&base->lock);
+ if (base->running_timer != timer) call_timer_fn(timer, fn, baseclk);
+ ret = detach_if_pending(timer, base, true); base->running_timer = NULL;
+ raw_spin_unlock_irqrestore(&base->lock, flags); raw_spin_lock(&base->lock);
+
+ x = data;
+
+If the timer has previously executed on CPU 1 and then CPU 0 can observe
+base->running_timer == NULL and returns, assuming the timer has completed,
+but it's not guaranteed on all architectures. The comment for
+del_timer_sync() makes that guarantee. Moving the assignment under
+base->lock prevents this.
+
+For non-RT kernel it's performance wise completely irrelevant whether the
+store happens before or after taking the lock. For an RT kernel moving the
+store under the lock requires an extra unlock/lock pair in the case that
+there is a waiter for the timer, but that's not the end of the world.
+
+Reported-by: syzbot+aa7c2385d46c5eba0b89@syzkaller.appspotmail.com
+Reported-by: syzbot+abea4558531bae1ba9fe@syzkaller.appspotmail.com
+Fixes: 030dcdd197d7 ("timers: Prepare support for PREEMPT_RT")
+Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
+Tested-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
+Link: https://lore.kernel.org/r/87lfea7gw8.fsf@nanos.tec.linutronix.de
+Cc: stable@vger.kernel.org
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ kernel/time/timer.c | 6 ++++--
+ 1 file changed, 4 insertions(+), 2 deletions(-)
+
+--- a/kernel/time/timer.c
++++ b/kernel/time/timer.c
+@@ -1279,8 +1279,10 @@ static inline void timer_base_unlock_exp
+ static void timer_sync_wait_running(struct timer_base *base)
+ {
+ if (atomic_read(&base->timer_waiters)) {
++ raw_spin_unlock_irq(&base->lock);
+ spin_unlock(&base->expiry_lock);
+ spin_lock(&base->expiry_lock);
++ raw_spin_lock_irq(&base->lock);
+ }
+ }
+
+@@ -1471,14 +1473,14 @@ static void expire_timers(struct timer_b
+ if (timer->flags & TIMER_IRQSAFE) {
+ raw_spin_unlock(&base->lock);
+ call_timer_fn(timer, fn, baseclk);
+- base->running_timer = NULL;
+ raw_spin_lock(&base->lock);
++ base->running_timer = NULL;
+ } else {
+ raw_spin_unlock_irq(&base->lock);
+ call_timer_fn(timer, fn, baseclk);
++ raw_spin_lock_irq(&base->lock);
+ base->running_timer = NULL;
+ timer_sync_wait_running(base);
+- raw_spin_lock_irq(&base->lock);
+ }
+ }
+ }
--- /dev/null
+From 4c4c1257b844ffe5d0933684e612f92c4b78e120 Mon Sep 17 00:00:00 2001
+From: Shuo Liu <shuo.a.liu@intel.com>
+Date: Thu, 22 Jul 2021 14:27:36 +0800
+Subject: virt: acrn: Do hcall_destroy_vm() before resource release
+
+From: Shuo Liu <shuo.a.liu@intel.com>
+
+commit 4c4c1257b844ffe5d0933684e612f92c4b78e120 upstream.
+
+The ACRN hypervisor has scenarios which could run a real-time guest VM.
+The real-time guest VM occupies dedicated CPU cores, be assigned with
+dedicated PCI devices. It can run without the Service VM after boot up.
+hcall_destroy_vm() returns failure when a real-time guest VM refuses.
+The clearing of flag ACRN_VM_FLAG_DESTROYED causes some kernel resource
+double-freed in a later acrn_vm_destroy().
+
+Do hcall_destroy_vm() before resource release to drop this chance to
+destroy the VM if hypercall fails.
+
+Fixes: 9c5137aedd11 ("virt: acrn: Introduce VM management interfaces")
+Cc: stable <stable@vger.kernel.org>
+Signed-off-by: Shuo Liu <shuo.a.liu@intel.com>
+Signed-off-by: Fei Li <fei1.li@intel.com>
+Link: https://lore.kernel.org/r/20210722062736.15050-1-fei1.li@intel.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ drivers/virt/acrn/vm.c | 16 ++++++++--------
+ 1 file changed, 8 insertions(+), 8 deletions(-)
+
+--- a/drivers/virt/acrn/vm.c
++++ b/drivers/virt/acrn/vm.c
+@@ -64,6 +64,14 @@ int acrn_vm_destroy(struct acrn_vm *vm)
+ test_and_set_bit(ACRN_VM_FLAG_DESTROYED, &vm->flags))
+ return 0;
+
++ ret = hcall_destroy_vm(vm->vmid);
++ if (ret < 0) {
++ dev_err(acrn_dev.this_device,
++ "Failed to destroy VM %u\n", vm->vmid);
++ clear_bit(ACRN_VM_FLAG_DESTROYED, &vm->flags);
++ return ret;
++ }
++
+ /* Remove from global VM list */
+ write_lock_bh(&acrn_vm_list_lock);
+ list_del_init(&vm->list);
+@@ -78,14 +86,6 @@ int acrn_vm_destroy(struct acrn_vm *vm)
+ vm->monitor_page = NULL;
+ }
+
+- ret = hcall_destroy_vm(vm->vmid);
+- if (ret < 0) {
+- dev_err(acrn_dev.this_device,
+- "Failed to destroy VM %u\n", vm->vmid);
+- clear_bit(ACRN_VM_FLAG_DESTROYED, &vm->flags);
+- return ret;
+- }
+-
+ acrn_vm_all_ram_unmap(vm);
+
+ dev_dbg(acrn_dev.this_device, "VM %u destroyed.\n", vm->vmid);
--- /dev/null
+From 2580d3f40022642452dd8422bfb8c22e54cf84bb Mon Sep 17 00:00:00 2001
+From: Frederic Weisbecker <frederic@kernel.org>
+Date: Mon, 28 Jun 2021 15:34:28 +0200
+Subject: xfrm: Fix RCU vs hash_resize_mutex lock inversion
+
+From: Frederic Weisbecker <frederic@kernel.org>
+
+commit 2580d3f40022642452dd8422bfb8c22e54cf84bb upstream.
+
+xfrm_bydst_resize() calls synchronize_rcu() while holding
+hash_resize_mutex. But then on PREEMPT_RT configurations,
+xfrm_policy_lookup_bytype() may acquire that mutex while running in an
+RCU read side critical section. This results in a deadlock.
+
+In fact the scope of hash_resize_mutex is way beyond the purpose of
+xfrm_policy_lookup_bytype() to just fetch a coherent and stable policy
+for a given destination/direction, along with other details.
+
+The lower level net->xfrm.xfrm_policy_lock, which among other things
+protects per destination/direction references to policy entries, is
+enough to serialize and benefit from priority inheritance against the
+write side. As a bonus, it makes it officially a per network namespace
+synchronization business where a policy table resize on namespace A
+shouldn't block a policy lookup on namespace B.
+
+Fixes: 77cc278f7b20 (xfrm: policy: Use sequence counters with associated lock)
+Cc: stable@vger.kernel.org
+Cc: Ahmed S. Darwish <a.darwish@linutronix.de>
+Cc: Peter Zijlstra (Intel) <peterz@infradead.org>
+Cc: Varad Gautam <varad.gautam@suse.com>
+Cc: Steffen Klassert <steffen.klassert@secunet.com>
+Cc: Herbert Xu <herbert@gondor.apana.org.au>
+Cc: David S. Miller <davem@davemloft.net>
+Signed-off-by: Frederic Weisbecker <frederic@kernel.org>
+Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ include/net/netns/xfrm.h | 1 +
+ net/xfrm/xfrm_policy.c | 17 ++++++++---------
+ 2 files changed, 9 insertions(+), 9 deletions(-)
+
+--- a/include/net/netns/xfrm.h
++++ b/include/net/netns/xfrm.h
+@@ -74,6 +74,7 @@ struct netns_xfrm {
+ #endif
+ spinlock_t xfrm_state_lock;
+ seqcount_spinlock_t xfrm_state_hash_generation;
++ seqcount_spinlock_t xfrm_policy_hash_generation;
+
+ spinlock_t xfrm_policy_lock;
+ struct mutex xfrm_cfg_mutex;
+--- a/net/xfrm/xfrm_policy.c
++++ b/net/xfrm/xfrm_policy.c
+@@ -155,7 +155,6 @@ static struct xfrm_policy_afinfo const _
+ __read_mostly;
+
+ static struct kmem_cache *xfrm_dst_cache __ro_after_init;
+-static __read_mostly seqcount_mutex_t xfrm_policy_hash_generation;
+
+ static struct rhashtable xfrm_policy_inexact_table;
+ static const struct rhashtable_params xfrm_pol_inexact_params;
+@@ -585,7 +584,7 @@ static void xfrm_bydst_resize(struct net
+ return;
+
+ spin_lock_bh(&net->xfrm.xfrm_policy_lock);
+- write_seqcount_begin(&xfrm_policy_hash_generation);
++ write_seqcount_begin(&net->xfrm.xfrm_policy_hash_generation);
+
+ odst = rcu_dereference_protected(net->xfrm.policy_bydst[dir].table,
+ lockdep_is_held(&net->xfrm.xfrm_policy_lock));
+@@ -596,7 +595,7 @@ static void xfrm_bydst_resize(struct net
+ rcu_assign_pointer(net->xfrm.policy_bydst[dir].table, ndst);
+ net->xfrm.policy_bydst[dir].hmask = nhashmask;
+
+- write_seqcount_end(&xfrm_policy_hash_generation);
++ write_seqcount_end(&net->xfrm.xfrm_policy_hash_generation);
+ spin_unlock_bh(&net->xfrm.xfrm_policy_lock);
+
+ synchronize_rcu();
+@@ -1245,7 +1244,7 @@ static void xfrm_hash_rebuild(struct wor
+ } while (read_seqretry(&net->xfrm.policy_hthresh.lock, seq));
+
+ spin_lock_bh(&net->xfrm.xfrm_policy_lock);
+- write_seqcount_begin(&xfrm_policy_hash_generation);
++ write_seqcount_begin(&net->xfrm.xfrm_policy_hash_generation);
+
+ /* make sure that we can insert the indirect policies again before
+ * we start with destructive action.
+@@ -1354,7 +1353,7 @@ static void xfrm_hash_rebuild(struct wor
+
+ out_unlock:
+ __xfrm_policy_inexact_flush(net);
+- write_seqcount_end(&xfrm_policy_hash_generation);
++ write_seqcount_end(&net->xfrm.xfrm_policy_hash_generation);
+ spin_unlock_bh(&net->xfrm.xfrm_policy_lock);
+
+ mutex_unlock(&hash_resize_mutex);
+@@ -2095,9 +2094,9 @@ static struct xfrm_policy *xfrm_policy_l
+ rcu_read_lock();
+ retry:
+ do {
+- sequence = read_seqcount_begin(&xfrm_policy_hash_generation);
++ sequence = read_seqcount_begin(&net->xfrm.xfrm_policy_hash_generation);
+ chain = policy_hash_direct(net, daddr, saddr, family, dir);
+- } while (read_seqcount_retry(&xfrm_policy_hash_generation, sequence));
++ } while (read_seqcount_retry(&net->xfrm.xfrm_policy_hash_generation, sequence));
+
+ ret = NULL;
+ hlist_for_each_entry_rcu(pol, chain, bydst) {
+@@ -2128,7 +2127,7 @@ static struct xfrm_policy *xfrm_policy_l
+ }
+
+ skip_inexact:
+- if (read_seqcount_retry(&xfrm_policy_hash_generation, sequence))
++ if (read_seqcount_retry(&net->xfrm.xfrm_policy_hash_generation, sequence))
+ goto retry;
+
+ if (ret && !xfrm_pol_hold_rcu(ret))
+@@ -4084,6 +4083,7 @@ static int __net_init xfrm_net_init(stru
+ /* Initialize the per-net locks here */
+ spin_lock_init(&net->xfrm.xfrm_state_lock);
+ spin_lock_init(&net->xfrm.xfrm_policy_lock);
++ seqcount_spinlock_init(&net->xfrm.xfrm_policy_hash_generation, &net->xfrm.xfrm_policy_lock);
+ mutex_init(&net->xfrm.xfrm_cfg_mutex);
+
+ rv = xfrm_statistics_init(net);
+@@ -4128,7 +4128,6 @@ void __init xfrm_init(void)
+ {
+ register_pernet_subsys(&xfrm_net_ops);
+ xfrm_dev_init();
+- seqcount_mutex_init(&xfrm_policy_hash_generation, &hash_resize_mutex);
+ xfrm_input_init();
+
+ #ifdef CONFIG_XFRM_ESPINTCP