--- /dev/null
+From 8d92e992a785f35d23f845206cf8c6cafbc264e0 Mon Sep 17 00:00:00 2001
+From: Eugeniy Paltsev <Eugeniy.Paltsev@synopsys.com>
+Date: Wed, 11 Mar 2020 19:26:43 +0300
+Subject: ARC: define __ALIGN_STR and __ALIGN symbols for ARC
+
+From: Eugeniy Paltsev <Eugeniy.Paltsev@synopsys.com>
+
+commit 8d92e992a785f35d23f845206cf8c6cafbc264e0 upstream.
+
+The default defintions use fill pattern 0x90 for padding which for ARC
+generates unintended "ldh_s r12,[r0,0x20]" corresponding to opcode 0x9090
+
+So use ".align 4" which insert a "nop_s" instruction instead.
+
+Cc: stable@vger.kernel.org
+Acked-by: Vineet Gupta <vgupta@synopsys.com>
+Signed-off-by: Eugeniy Paltsev <Eugeniy.Paltsev@synopsys.com>
+Signed-off-by: Vineet Gupta <vgupta@synopsys.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/arc/include/asm/linkage.h | 2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/arch/arc/include/asm/linkage.h
++++ b/arch/arc/include/asm/linkage.h
+@@ -29,6 +29,8 @@
+ .endm
+
+ #define ASM_NL ` /* use '`' to mark new line in macro */
++#define __ALIGN .align 4
++#define __ALIGN_STR __stringify(__ALIGN)
+
+ /* annotation for data we want in DCCM - if enabled in .config */
+ .macro ARCFP_DATA nm
--- /dev/null
+From dcd6589b11d3b1e71f516a87a7b9646ed356b4c0 Mon Sep 17 00:00:00 2001
+From: Tejun Heo <tj@kernel.org>
+Date: Tue, 10 Mar 2020 13:07:46 -0400
+Subject: blk-iocost: fix incorrect vtime comparison in iocg_is_idle()
+
+From: Tejun Heo <tj@kernel.org>
+
+commit dcd6589b11d3b1e71f516a87a7b9646ed356b4c0 upstream.
+
+vtimes may wrap and time_before/after64() should be used to determine
+whether a given vtime is before or after another. iocg_is_idle() was
+incorrectly using plain "<" comparison do determine whether done_vtime
+is before vtime. Here, the only thing we're interested in is whether
+done_vtime matches vtime which indicates that there's nothing in
+flight. Let's test for inequality instead.
+
+Signed-off-by: Tejun Heo <tj@kernel.org>
+Fixes: 7caa47151ab2 ("blkcg: implement blk-iocost")
+Cc: stable@vger.kernel.org # v5.4+
+Signed-off-by: Jens Axboe <axboe@kernel.dk>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ block/blk-iocost.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/block/blk-iocost.c
++++ b/block/blk-iocost.c
+@@ -1318,7 +1318,7 @@ static bool iocg_is_idle(struct ioc_gq *
+ return false;
+
+ /* is something in flight? */
+- if (atomic64_read(&iocg->done_vtime) < atomic64_read(&iocg->vtime))
++ if (atomic64_read(&iocg->done_vtime) != atomic64_read(&iocg->vtime))
+ return false;
+
+ return true;
--- /dev/null
+From d6c066fda90d578aacdf19771a027ed484a79825 Mon Sep 17 00:00:00 2001
+From: Vladis Dronov <vdronov@redhat.com>
+Date: Sun, 8 Mar 2020 09:08:55 +0100
+Subject: efi: Add a sanity check to efivar_store_raw()
+
+From: Vladis Dronov <vdronov@redhat.com>
+
+commit d6c066fda90d578aacdf19771a027ed484a79825 upstream.
+
+Add a sanity check to efivar_store_raw() the same way
+efivar_{attr,size,data}_read() and efivar_show_raw() have it.
+
+Signed-off-by: Vladis Dronov <vdronov@redhat.com>
+Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
+Signed-off-by: Ingo Molnar <mingo@kernel.org>
+Cc: <stable@vger.kernel.org>
+Link: https://lore.kernel.org/r/20200305084041.24053-3-vdronov@redhat.com
+Link: https://lore.kernel.org/r/20200308080859.21568-25-ardb@kernel.org
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/firmware/efi/efivars.c | 3 +++
+ 1 file changed, 3 insertions(+)
+
+--- a/drivers/firmware/efi/efivars.c
++++ b/drivers/firmware/efi/efivars.c
+@@ -208,6 +208,9 @@ efivar_store_raw(struct efivar_entry *en
+ u8 *data;
+ int err;
+
++ if (!entry || !buf)
++ return -EINVAL;
++
+ if (in_compat_syscall()) {
+ struct compat_efi_variable *compat;
+
--- /dev/null
+From 286d3250c9d6437340203fb64938bea344729a0e Mon Sep 17 00:00:00 2001
+From: Vladis Dronov <vdronov@redhat.com>
+Date: Sun, 8 Mar 2020 09:08:54 +0100
+Subject: efi: Fix a race and a buffer overflow while reading efivars via sysfs
+
+From: Vladis Dronov <vdronov@redhat.com>
+
+commit 286d3250c9d6437340203fb64938bea344729a0e upstream.
+
+There is a race and a buffer overflow corrupting a kernel memory while
+reading an EFI variable with a size more than 1024 bytes via the older
+sysfs method. This happens because accessing struct efi_variable in
+efivar_{attr,size,data}_read() and friends is not protected from
+a concurrent access leading to a kernel memory corruption and, at best,
+to a crash. The race scenario is the following:
+
+CPU0: CPU1:
+efivar_attr_read()
+ var->DataSize = 1024;
+ efivar_entry_get(... &var->DataSize)
+ down_interruptible(&efivars_lock)
+ efivar_attr_read() // same EFI var
+ var->DataSize = 1024;
+ efivar_entry_get(... &var->DataSize)
+ down_interruptible(&efivars_lock)
+ virt_efi_get_variable()
+ // returns EFI_BUFFER_TOO_SMALL but
+ // var->DataSize is set to a real
+ // var size more than 1024 bytes
+ up(&efivars_lock)
+ virt_efi_get_variable()
+ // called with var->DataSize set
+ // to a real var size, returns
+ // successfully and overwrites
+ // a 1024-bytes kernel buffer
+ up(&efivars_lock)
+
+This can be reproduced by concurrent reading of an EFI variable which size
+is more than 1024 bytes:
+
+ ts# for cpu in $(seq 0 $(nproc --ignore=1)); do ( taskset -c $cpu \
+ cat /sys/firmware/efi/vars/KEKDefault*/size & ) ; done
+
+Fix this by using a local variable for a var's data buffer size so it
+does not get overwritten.
+
+Fixes: e14ab23dde12b80d ("efivars: efivar_entry API")
+Reported-by: Bob Sanders <bob.sanders@hpe.com> and the LTP testsuite
+Signed-off-by: Vladis Dronov <vdronov@redhat.com>
+Signed-off-by: Ard Biesheuvel <ardb@kernel.org>
+Signed-off-by: Ingo Molnar <mingo@kernel.org>
+Cc: <stable@vger.kernel.org>
+Link: https://lore.kernel.org/r/20200305084041.24053-2-vdronov@redhat.com
+Link: https://lore.kernel.org/r/20200308080859.21568-24-ardb@kernel.org
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/firmware/efi/efivars.c | 29 ++++++++++++++++++++---------
+ 1 file changed, 20 insertions(+), 9 deletions(-)
+
+--- a/drivers/firmware/efi/efivars.c
++++ b/drivers/firmware/efi/efivars.c
+@@ -83,13 +83,16 @@ static ssize_t
+ efivar_attr_read(struct efivar_entry *entry, char *buf)
+ {
+ struct efi_variable *var = &entry->var;
++ unsigned long size = sizeof(var->Data);
+ char *str = buf;
++ int ret;
+
+ if (!entry || !buf)
+ return -EINVAL;
+
+- var->DataSize = 1024;
+- if (efivar_entry_get(entry, &var->Attributes, &var->DataSize, var->Data))
++ ret = efivar_entry_get(entry, &var->Attributes, &size, var->Data);
++ var->DataSize = size;
++ if (ret)
+ return -EIO;
+
+ if (var->Attributes & EFI_VARIABLE_NON_VOLATILE)
+@@ -116,13 +119,16 @@ static ssize_t
+ efivar_size_read(struct efivar_entry *entry, char *buf)
+ {
+ struct efi_variable *var = &entry->var;
++ unsigned long size = sizeof(var->Data);
+ char *str = buf;
++ int ret;
+
+ if (!entry || !buf)
+ return -EINVAL;
+
+- var->DataSize = 1024;
+- if (efivar_entry_get(entry, &var->Attributes, &var->DataSize, var->Data))
++ ret = efivar_entry_get(entry, &var->Attributes, &size, var->Data);
++ var->DataSize = size;
++ if (ret)
+ return -EIO;
+
+ str += sprintf(str, "0x%lx\n", var->DataSize);
+@@ -133,12 +139,15 @@ static ssize_t
+ efivar_data_read(struct efivar_entry *entry, char *buf)
+ {
+ struct efi_variable *var = &entry->var;
++ unsigned long size = sizeof(var->Data);
++ int ret;
+
+ if (!entry || !buf)
+ return -EINVAL;
+
+- var->DataSize = 1024;
+- if (efivar_entry_get(entry, &var->Attributes, &var->DataSize, var->Data))
++ ret = efivar_entry_get(entry, &var->Attributes, &size, var->Data);
++ var->DataSize = size;
++ if (ret)
+ return -EIO;
+
+ memcpy(buf, var->Data, var->DataSize);
+@@ -250,14 +259,16 @@ efivar_show_raw(struct efivar_entry *ent
+ {
+ struct efi_variable *var = &entry->var;
+ struct compat_efi_variable *compat;
++ unsigned long datasize = sizeof(var->Data);
+ size_t size;
++ int ret;
+
+ if (!entry || !buf)
+ return 0;
+
+- var->DataSize = 1024;
+- if (efivar_entry_get(entry, &entry->var.Attributes,
+- &entry->var.DataSize, entry->var.Data))
++ ret = efivar_entry_get(entry, &var->Attributes, &datasize, var->Data);
++ var->DataSize = datasize;
++ if (ret)
+ return -EIO;
+
+ if (in_compat_syscall()) {
--- /dev/null
+From 2b4eae95c7361e0a147b838715c8baa1380a428f Mon Sep 17 00:00:00 2001
+From: Eric Biggers <ebiggers@google.com>
+Date: Thu, 5 Mar 2020 00:41:38 -0800
+Subject: fscrypt: don't evict dirty inodes after removing key
+
+From: Eric Biggers <ebiggers@google.com>
+
+commit 2b4eae95c7361e0a147b838715c8baa1380a428f upstream.
+
+After FS_IOC_REMOVE_ENCRYPTION_KEY removes a key, it syncs the
+filesystem and tries to get and put all inodes that were unlocked by the
+key so that unused inodes get evicted via fscrypt_drop_inode().
+Normally, the inodes are all clean due to the sync.
+
+However, after the filesystem is sync'ed, userspace can modify and close
+one of the files. (Userspace is *supposed* to close the files before
+removing the key. But it doesn't always happen, and the kernel can't
+assume it.) This causes the inode to be dirtied and have i_count == 0.
+Then, fscrypt_drop_inode() failed to consider this case and indicated
+that the inode can be dropped, causing the write to be lost.
+
+On f2fs, other problems such as a filesystem freeze could occur due to
+the inode being freed while still on f2fs's dirty inode list.
+
+Fix this bug by making fscrypt_drop_inode() only drop clean inodes.
+
+I've written an xfstest which detects this bug on ext4, f2fs, and ubifs.
+
+Fixes: b1c0ec3599f4 ("fscrypt: add FS_IOC_REMOVE_ENCRYPTION_KEY ioctl")
+Cc: <stable@vger.kernel.org> # v5.4+
+Link: https://lore.kernel.org/r/20200305084138.653498-1-ebiggers@kernel.org
+Signed-off-by: Eric Biggers <ebiggers@google.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/crypto/keysetup.c | 9 +++++++++
+ 1 file changed, 9 insertions(+)
+
+--- a/fs/crypto/keysetup.c
++++ b/fs/crypto/keysetup.c
+@@ -515,6 +515,15 @@ int fscrypt_drop_inode(struct inode *ino
+ mk = ci->ci_master_key->payload.data[0];
+
+ /*
++ * With proper, non-racy use of FS_IOC_REMOVE_ENCRYPTION_KEY, all inodes
++ * protected by the key were cleaned by sync_filesystem(). But if
++ * userspace is still using the files, inodes can be dirtied between
++ * then and now. We mustn't lose any writes, so skip dirty inodes here.
++ */
++ if (inode->i_state & I_DIRTY_ALL)
++ return 0;
++
++ /*
+ * Note: since we aren't holding ->mk_secret_sem, the result here can
+ * immediately become outdated. But there's no correctness problem with
+ * unnecessarily evicting. Nor is there a correctness problem with not
--- /dev/null
+From d9815bff6b379ff46981bea9dfeb146081eab314 Mon Sep 17 00:00:00 2001
+From: Artem Savkov <asavkov@redhat.com>
+Date: Fri, 6 Mar 2020 18:43:17 +0100
+Subject: ftrace: Return the first found result in lookup_rec()
+
+From: Artem Savkov <asavkov@redhat.com>
+
+commit d9815bff6b379ff46981bea9dfeb146081eab314 upstream.
+
+It appears that ip ranges can overlap so. In that case lookup_rec()
+returns whatever results it got last even if it found nothing in last
+searched page.
+
+This breaks an obscure livepatch late module patching usecase:
+ - load livepatch
+ - load the patched module
+ - unload livepatch
+ - try to load livepatch again
+
+To fix this return from lookup_rec() as soon as it found the record
+containing searched-for ip. This used to be this way prior lookup_rec()
+introduction.
+
+Link: http://lkml.kernel.org/r/20200306174317.21699-1-asavkov@redhat.com
+
+Cc: stable@vger.kernel.org
+Fixes: 7e16f581a817 ("ftrace: Separate out functionality from ftrace_location_range()")
+Signed-off-by: Artem Savkov <asavkov@redhat.com>
+Signed-off-by: Steven Rostedt (VMware) <rostedt@goodmis.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ kernel/trace/ftrace.c | 2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/kernel/trace/ftrace.c
++++ b/kernel/trace/ftrace.c
+@@ -1552,6 +1552,8 @@ static struct dyn_ftrace *lookup_rec(uns
+ rec = bsearch(&key, pg->records, pg->index,
+ sizeof(struct dyn_ftrace),
+ ftrace_cmp_recs);
++ if (rec)
++ break;
+ }
+ return rec;
+ }
--- /dev/null
+From 3e8cb8b2eaeb22f540f1cbc00cbb594047b7ba89 Mon Sep 17 00:00:00 2001
+From: Miklos Szeredi <mszeredi@redhat.com>
+Date: Thu, 13 Feb 2020 09:16:07 +0100
+Subject: fuse: fix stack use after return
+
+From: Miklos Szeredi <mszeredi@redhat.com>
+
+commit 3e8cb8b2eaeb22f540f1cbc00cbb594047b7ba89 upstream.
+
+Normal, synchronous requests will have their args allocated on the stack.
+After the FR_FINISHED bit is set by receiving the reply from the userspace
+fuse server, the originating task may return and reuse the stack frame,
+resulting in an Oops if the args structure is dereferenced.
+
+Fix by setting a flag in the request itself upon initializing, indicating
+whether it has an asynchronous ->end() callback.
+
+Reported-by: Kyle Sanderson <kyle.leet@gmail.com>
+Reported-by: Michael Stapelberg <michael+lkml@stapelberg.ch>
+Fixes: 2b319d1f6f92 ("fuse: don't dereference req->args on finished request")
+Cc: <stable@vger.kernel.org> # v5.4
+Tested-by: Michael Stapelberg <michael+lkml@stapelberg.ch>
+Signed-off-by: Miklos Szeredi <mszeredi@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/fuse/dev.c | 6 +++---
+ fs/fuse/fuse_i.h | 2 ++
+ 2 files changed, 5 insertions(+), 3 deletions(-)
+
+--- a/fs/fuse/dev.c
++++ b/fs/fuse/dev.c
+@@ -276,12 +276,10 @@ static void flush_bg_queue(struct fuse_c
+ void fuse_request_end(struct fuse_conn *fc, struct fuse_req *req)
+ {
+ struct fuse_iqueue *fiq = &fc->iq;
+- bool async;
+
+ if (test_and_set_bit(FR_FINISHED, &req->flags))
+ goto put_request;
+
+- async = req->args->end;
+ /*
+ * test_and_set_bit() implies smp_mb() between bit
+ * changing and below intr_entry check. Pairs with
+@@ -324,7 +322,7 @@ void fuse_request_end(struct fuse_conn *
+ wake_up(&req->waitq);
+ }
+
+- if (async)
++ if (test_bit(FR_ASYNC, &req->flags))
+ req->args->end(fc, req->args, req->out.h.error);
+ put_request:
+ fuse_put_request(fc, req);
+@@ -471,6 +469,8 @@ static void fuse_args_to_req(struct fuse
+ req->in.h.opcode = args->opcode;
+ req->in.h.nodeid = args->nodeid;
+ req->args = args;
++ if (args->end)
++ __set_bit(FR_ASYNC, &req->flags);
+ }
+
+ ssize_t fuse_simple_request(struct fuse_conn *fc, struct fuse_args *args)
+--- a/fs/fuse/fuse_i.h
++++ b/fs/fuse/fuse_i.h
+@@ -301,6 +301,7 @@ struct fuse_io_priv {
+ * FR_SENT: request is in userspace, waiting for an answer
+ * FR_FINISHED: request is finished
+ * FR_PRIVATE: request is on private list
++ * FR_ASYNC: request is asynchronous
+ */
+ enum fuse_req_flag {
+ FR_ISREPLY,
+@@ -314,6 +315,7 @@ enum fuse_req_flag {
+ FR_SENT,
+ FR_FINISHED,
+ FR_PRIVATE,
++ FR_ASYNC,
+ };
+
+ /**
--- /dev/null
+From 21039132650281de06a169cbe8a0f7e5c578fd8b Mon Sep 17 00:00:00 2001
+From: Al Viro <viro@zeniv.linux.org.uk>
+Date: Tue, 10 Mar 2020 09:31:41 -0400
+Subject: gfs2_atomic_open(): fix O_EXCL|O_CREAT handling on cold dcache
+
+From: Al Viro <viro@zeniv.linux.org.uk>
+
+commit 21039132650281de06a169cbe8a0f7e5c578fd8b upstream.
+
+with the way fs/namei.c:do_last() had been done, ->atomic_open()
+instances needed to recognize the case when existing file got
+found with O_EXCL|O_CREAT, either by falling back to finish_no_open()
+or failing themselves. gfs2 one didn't.
+
+Fixes: 6d4ade986f9c (GFS2: Add atomic_open support)
+Cc: stable@kernel.org # v3.11
+Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/gfs2/inode.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/fs/gfs2/inode.c
++++ b/fs/gfs2/inode.c
+@@ -1248,7 +1248,7 @@ static int gfs2_atomic_open(struct inode
+ if (!(file->f_mode & FMODE_OPENED))
+ return finish_no_open(file, d);
+ dput(d);
+- return 0;
++ return excl && (flags & O_CREAT) ? -EEXIST : 0;
+ }
+
+ BUG_ON(d != NULL);
--- /dev/null
+From 9be8bc4dd6177cf992b93b0bd014c4f611283896 Mon Sep 17 00:00:00 2001
+From: Jarkko Nikula <jarkko.nikula@linux.intel.com>
+Date: Thu, 13 Feb 2020 17:15:03 +0200
+Subject: i2c: designware-pci: Fix BUG_ON during device removal
+
+From: Jarkko Nikula <jarkko.nikula@linux.intel.com>
+
+commit 9be8bc4dd6177cf992b93b0bd014c4f611283896 upstream.
+
+Function i2c_dw_pci_remove() -> pci_free_irq_vectors() ->
+pci_disable_msi() -> free_msi_irqs() will throw a BUG_ON() for MSI
+enabled device since the driver has not released the requested IRQ before
+calling the pci_free_irq_vectors().
+
+Here driver requests an IRQ using devm_request_irq() but automatic
+release happens only after remove callback. Fix this by explicitly
+freeing the IRQ before calling pci_free_irq_vectors().
+
+Fixes: 21aa3983d619 ("i2c: designware-pci: Switch over to MSI interrupts")
+Cc: stable@vger.kernel.org # v5.4+
+Signed-off-by: Jarkko Nikula <jarkko.nikula@linux.intel.com>
+Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
+Signed-off-by: Wolfram Sang <wsa@the-dreams.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/i2c/busses/i2c-designware-pcidrv.c | 1 +
+ 1 file changed, 1 insertion(+)
+
+--- a/drivers/i2c/busses/i2c-designware-pcidrv.c
++++ b/drivers/i2c/busses/i2c-designware-pcidrv.c
+@@ -313,6 +313,7 @@ static void i2c_dw_pci_remove(struct pci
+ pm_runtime_get_noresume(&pdev->dev);
+
+ i2c_del_adapter(&dev->adapter);
++ devm_free_irq(&pdev->dev, dev->irq, dev);
+ pci_free_irq_vectors(pdev);
+ }
+
--- /dev/null
+From 65ac74f1de3334852fb7d9b1b430fa5a06524276 Mon Sep 17 00:00:00 2001
+From: Marc Zyngier <maz@kernel.org>
+Date: Wed, 4 Mar 2020 11:11:17 +0000
+Subject: iommu/dma: Fix MSI reservation allocation
+
+From: Marc Zyngier <maz@kernel.org>
+
+commit 65ac74f1de3334852fb7d9b1b430fa5a06524276 upstream.
+
+The way cookie_init_hw_msi_region() allocates the iommu_dma_msi_page
+structures doesn't match the way iommu_put_dma_cookie() frees them.
+
+The former performs a single allocation of all the required structures,
+while the latter tries to free them one at a time. It doesn't quite
+work for the main use case (the GICv3 ITS where the range is 64kB)
+when the base granule size is 4kB.
+
+This leads to a nice slab corruption on teardown, which is easily
+observable by simply creating a VF on a SRIOV-capable device, and
+tearing it down immediately (no need to even make use of it).
+Fortunately, this only affects systems where the ITS isn't translated
+by the SMMU, which are both rare and non-standard.
+
+Fix it by allocating iommu_dma_msi_page structures one at a time.
+
+Fixes: 7c1b058c8b5a3 ("iommu/dma: Handle IOMMU API reserved regions")
+Signed-off-by: Marc Zyngier <maz@kernel.org>
+Reviewed-by: Eric Auger <eric.auger@redhat.com>
+Cc: Robin Murphy <robin.murphy@arm.com>
+Cc: Joerg Roedel <jroedel@suse.de>
+Cc: Will Deacon <will@kernel.org>
+Cc: stable@vger.kernel.org
+Reviewed-by: Robin Murphy <robin.murphy@arm.com>
+Signed-off-by: Joerg Roedel <jroedel@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/iommu/dma-iommu.c | 16 ++++++++--------
+ 1 file changed, 8 insertions(+), 8 deletions(-)
+
+--- a/drivers/iommu/dma-iommu.c
++++ b/drivers/iommu/dma-iommu.c
+@@ -177,15 +177,15 @@ static int cookie_init_hw_msi_region(str
+ start -= iova_offset(iovad, start);
+ num_pages = iova_align(iovad, end - start) >> iova_shift(iovad);
+
+- msi_page = kcalloc(num_pages, sizeof(*msi_page), GFP_KERNEL);
+- if (!msi_page)
+- return -ENOMEM;
+-
+ for (i = 0; i < num_pages; i++) {
+- msi_page[i].phys = start;
+- msi_page[i].iova = start;
+- INIT_LIST_HEAD(&msi_page[i].list);
+- list_add(&msi_page[i].list, &cookie->msi_page_list);
++ msi_page = kmalloc(sizeof(*msi_page), GFP_KERNEL);
++ if (!msi_page)
++ return -ENOMEM;
++
++ msi_page->phys = start;
++ msi_page->iova = start;
++ INIT_LIST_HEAD(&msi_page->list);
++ list_add(&msi_page->list, &cookie->msi_page_list);
+ start += iovad->granule;
+ }
+
--- /dev/null
+From 59833696442c674acbbd297772ba89e7ad8c753d Mon Sep 17 00:00:00 2001
+From: Hans de Goede <hdegoede@redhat.com>
+Date: Mon, 9 Mar 2020 15:01:37 +0100
+Subject: iommu/vt-d: dmar: replace WARN_TAINT with pr_warn + add_taint
+
+From: Hans de Goede <hdegoede@redhat.com>
+
+commit 59833696442c674acbbd297772ba89e7ad8c753d upstream.
+
+Quoting from the comment describing the WARN functions in
+include/asm-generic/bug.h:
+
+ * WARN(), WARN_ON(), WARN_ON_ONCE, and so on can be used to report
+ * significant kernel issues that need prompt attention if they should ever
+ * appear at runtime.
+ *
+ * Do not use these macros when checking for invalid external inputs
+
+The (buggy) firmware tables which the dmar code was calling WARN_TAINT
+for really are invalid external inputs. They are not under the kernel's
+control and the issues in them cannot be fixed by a kernel update.
+So logging a backtrace, which invites bug reports to be filed about this,
+is not helpful.
+
+Some distros, e.g. Fedora, have tools watching for the kernel backtraces
+logged by the WARN macros and offer the user an option to file a bug for
+this when these are encountered. The WARN_TAINT in warn_invalid_dmar()
++ another iommu WARN_TAINT, addressed in another patch, have lead to over
+a 100 bugs being filed this way.
+
+This commit replaces the WARN_TAINT("...") calls, with
+pr_warn(FW_BUG "...") + add_taint(TAINT_FIRMWARE_WORKAROUND, ...) calls
+avoiding the backtrace and thus also avoiding bug-reports being filed
+about this against the kernel.
+
+Fixes: fd0c8894893c ("intel-iommu: Set a more specific taint flag for invalid BIOS DMAR tables")
+Fixes: e625b4a95d50 ("iommu/vt-d: Parse ANDD records")
+Signed-off-by: Hans de Goede <hdegoede@redhat.com>
+Signed-off-by: Joerg Roedel <jroedel@suse.de>
+Acked-by: Lu Baolu <baolu.lu@linux.intel.com>
+Cc: stable@vger.kernel.org
+Link: https://lore.kernel.org/r/20200309140138.3753-2-hdegoede@redhat.com
+BugLink: https://bugzilla.redhat.com/show_bug.cgi?id=1564895
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/iommu/dmar.c | 11 ++++++-----
+ 1 file changed, 6 insertions(+), 5 deletions(-)
+
+--- a/drivers/iommu/dmar.c
++++ b/drivers/iommu/dmar.c
+@@ -440,12 +440,13 @@ static int __init dmar_parse_one_andd(st
+
+ /* Check for NUL termination within the designated length */
+ if (strnlen(andd->device_name, header->length - 8) == header->length - 8) {
+- WARN_TAINT(1, TAINT_FIRMWARE_WORKAROUND,
++ pr_warn(FW_BUG
+ "Your BIOS is broken; ANDD object name is not NUL-terminated\n"
+ "BIOS vendor: %s; Ver: %s; Product Version: %s\n",
+ dmi_get_system_info(DMI_BIOS_VENDOR),
+ dmi_get_system_info(DMI_BIOS_VERSION),
+ dmi_get_system_info(DMI_PRODUCT_VERSION));
++ add_taint(TAINT_FIRMWARE_WORKAROUND, LOCKDEP_STILL_OK);
+ return -EINVAL;
+ }
+ pr_info("ANDD device: %x name: %s\n", andd->device_number,
+@@ -471,14 +472,14 @@ static int dmar_parse_one_rhsa(struct ac
+ return 0;
+ }
+ }
+- WARN_TAINT(
+- 1, TAINT_FIRMWARE_WORKAROUND,
++ pr_warn(FW_BUG
+ "Your BIOS is broken; RHSA refers to non-existent DMAR unit at %llx\n"
+ "BIOS vendor: %s; Ver: %s; Product Version: %s\n",
+ drhd->reg_base_addr,
+ dmi_get_system_info(DMI_BIOS_VENDOR),
+ dmi_get_system_info(DMI_BIOS_VERSION),
+ dmi_get_system_info(DMI_PRODUCT_VERSION));
++ add_taint(TAINT_FIRMWARE_WORKAROUND, LOCKDEP_STILL_OK);
+
+ return 0;
+ }
+@@ -827,14 +828,14 @@ int __init dmar_table_init(void)
+
+ static void warn_invalid_dmar(u64 addr, const char *message)
+ {
+- WARN_TAINT_ONCE(
+- 1, TAINT_FIRMWARE_WORKAROUND,
++ pr_warn_once(FW_BUG
+ "Your BIOS is broken; DMAR reported at address %llx%s!\n"
+ "BIOS vendor: %s; Ver: %s; Product Version: %s\n",
+ addr, message,
+ dmi_get_system_info(DMI_BIOS_VENDOR),
+ dmi_get_system_info(DMI_BIOS_VERSION),
+ dmi_get_system_info(DMI_PRODUCT_VERSION));
++ add_taint(TAINT_FIRMWARE_WORKAROUND, LOCKDEP_STILL_OK);
+ }
+
+ static int __ref
--- /dev/null
+From 96788c7a7f1e7206519d4d736f89a2072dcfe0fc Mon Sep 17 00:00:00 2001
+From: Hans de Goede <hdegoede@redhat.com>
+Date: Mon, 9 Mar 2020 15:01:38 +0100
+Subject: iommu/vt-d: dmar_parse_one_rmrr: replace WARN_TAINT with pr_warn + add_taint
+
+From: Hans de Goede <hdegoede@redhat.com>
+
+commit 96788c7a7f1e7206519d4d736f89a2072dcfe0fc upstream.
+
+Quoting from the comment describing the WARN functions in
+include/asm-generic/bug.h:
+
+ * WARN(), WARN_ON(), WARN_ON_ONCE, and so on can be used to report
+ * significant kernel issues that need prompt attention if they should ever
+ * appear at runtime.
+ *
+ * Do not use these macros when checking for invalid external inputs
+
+The (buggy) firmware tables which the dmar code was calling WARN_TAINT
+for really are invalid external inputs. They are not under the kernel's
+control and the issues in them cannot be fixed by a kernel update.
+So logging a backtrace, which invites bug reports to be filed about this,
+is not helpful.
+
+Some distros, e.g. Fedora, have tools watching for the kernel backtraces
+logged by the WARN macros and offer the user an option to file a bug for
+this when these are encountered. The WARN_TAINT in dmar_parse_one_rmrr
++ another iommu WARN_TAINT, addressed in another patch, have lead to over
+a 100 bugs being filed this way.
+
+This commit replaces the WARN_TAINT("...") call, with a
+pr_warn(FW_BUG "...") + add_taint(TAINT_FIRMWARE_WORKAROUND, ...) call
+avoiding the backtrace and thus also avoiding bug-reports being filed
+about this against the kernel.
+
+Fixes: f5a68bb0752e ("iommu/vt-d: Mark firmware tainted if RMRR fails sanity check")
+Signed-off-by: Hans de Goede <hdegoede@redhat.com>
+Signed-off-by: Joerg Roedel <jroedel@suse.de>
+Acked-by: Lu Baolu <baolu.lu@linux.intel.com>
+Cc: stable@vger.kernel.org
+Cc: Barret Rhoden <brho@google.com>
+Link: https://lore.kernel.org/r/20200309140138.3753-3-hdegoede@redhat.com
+BugLink: https://bugzilla.redhat.com/show_bug.cgi?id=1808874
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/iommu/intel-iommu.c | 6 ++++--
+ 1 file changed, 4 insertions(+), 2 deletions(-)
+
+--- a/drivers/iommu/intel-iommu.c
++++ b/drivers/iommu/intel-iommu.c
+@@ -4330,14 +4330,16 @@ int __init dmar_parse_one_rmrr(struct ac
+ struct dmar_rmrr_unit *rmrru;
+
+ rmrr = (struct acpi_dmar_reserved_memory *)header;
+- if (arch_rmrr_sanity_check(rmrr))
+- WARN_TAINT(1, TAINT_FIRMWARE_WORKAROUND,
++ if (arch_rmrr_sanity_check(rmrr)) {
++ pr_warn(FW_BUG
+ "Your BIOS is broken; bad RMRR [%#018Lx-%#018Lx]\n"
+ "BIOS vendor: %s; Ver: %s; Product Version: %s\n",
+ rmrr->base_address, rmrr->end_address,
+ dmi_get_system_info(DMI_BIOS_VENDOR),
+ dmi_get_system_info(DMI_BIOS_VERSION),
+ dmi_get_system_info(DMI_PRODUCT_VERSION));
++ add_taint(TAINT_FIRMWARE_WORKAROUND, LOCKDEP_STILL_OK);
++ }
+
+ rmrru = kzalloc(sizeof(*rmrru), GFP_KERNEL);
+ if (!rmrru)
--- /dev/null
+From 77a1bce84bba01f3f143d77127b72e872b573795 Mon Sep 17 00:00:00 2001
+From: Yonghyun Hwang <yonghyun@google.com>
+Date: Wed, 26 Feb 2020 12:30:06 -0800
+Subject: iommu/vt-d: Fix a bug in intel_iommu_iova_to_phys() for huge page
+
+From: Yonghyun Hwang <yonghyun@google.com>
+
+commit 77a1bce84bba01f3f143d77127b72e872b573795 upstream.
+
+intel_iommu_iova_to_phys() has a bug when it translates an IOVA for a huge
+page onto its corresponding physical address. This commit fixes the bug by
+accomodating the level of page entry for the IOVA and adds IOVA's lower
+address to the physical address.
+
+Cc: <stable@vger.kernel.org>
+Acked-by: Lu Baolu <baolu.lu@linux.intel.com>
+Reviewed-by: Moritz Fischer <mdf@kernel.org>
+Signed-off-by: Yonghyun Hwang <yonghyun@google.com>
+Fixes: 3871794642579 ("VT-d: Changes to support KVM")
+Signed-off-by: Joerg Roedel <jroedel@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/iommu/intel-iommu.c | 6 ++++--
+ 1 file changed, 4 insertions(+), 2 deletions(-)
+
+--- a/drivers/iommu/intel-iommu.c
++++ b/drivers/iommu/intel-iommu.c
+@@ -5568,8 +5568,10 @@ static phys_addr_t intel_iommu_iova_to_p
+ u64 phys = 0;
+
+ pte = pfn_to_dma_pte(dmar_domain, iova >> VTD_PAGE_SHIFT, &level);
+- if (pte)
+- phys = dma_pte_addr(pte);
++ if (pte && dma_pte_present(pte))
++ phys = dma_pte_addr(pte) +
++ (iova & (BIT_MASK(level_to_offset_bits(level) +
++ VTD_PAGE_SHIFT) - 1));
+
+ return phys;
+ }
--- /dev/null
+From 02d715b4a8182f4887d82df82a7b83aced647760 Mon Sep 17 00:00:00 2001
+From: Amol Grover <frextrite@gmail.com>
+Date: Sun, 23 Feb 2020 22:25:39 +0530
+Subject: iommu/vt-d: Fix RCU list debugging warnings
+
+From: Amol Grover <frextrite@gmail.com>
+
+commit 02d715b4a8182f4887d82df82a7b83aced647760 upstream.
+
+dmar_drhd_units is traversed using list_for_each_entry_rcu()
+outside of an RCU read side critical section but under the
+protection of dmar_global_lock. Hence add corresponding lockdep
+expression to silence the following false-positive warnings:
+
+[ 1.603975] =============================
+[ 1.603976] WARNING: suspicious RCU usage
+[ 1.603977] 5.5.4-stable #17 Not tainted
+[ 1.603978] -----------------------------
+[ 1.603980] drivers/iommu/intel-iommu.c:4769 RCU-list traversed in non-reader section!!
+
+[ 1.603869] =============================
+[ 1.603870] WARNING: suspicious RCU usage
+[ 1.603872] 5.5.4-stable #17 Not tainted
+[ 1.603874] -----------------------------
+[ 1.603875] drivers/iommu/dmar.c:293 RCU-list traversed in non-reader section!!
+
+Tested-by: Madhuparna Bhowmik <madhuparnabhowmik10@gmail.com>
+Signed-off-by: Amol Grover <frextrite@gmail.com>
+Cc: stable@vger.kernel.org
+Acked-by: Lu Baolu <baolu.lu@linux.intel.com>
+Signed-off-by: Joerg Roedel <jroedel@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ include/linux/dmar.h | 8 +++++---
+ 1 file changed, 5 insertions(+), 3 deletions(-)
+
+--- a/include/linux/dmar.h
++++ b/include/linux/dmar.h
+@@ -69,8 +69,9 @@ struct dmar_pci_notify_info {
+ extern struct rw_semaphore dmar_global_lock;
+ extern struct list_head dmar_drhd_units;
+
+-#define for_each_drhd_unit(drhd) \
+- list_for_each_entry_rcu(drhd, &dmar_drhd_units, list)
++#define for_each_drhd_unit(drhd) \
++ list_for_each_entry_rcu(drhd, &dmar_drhd_units, list, \
++ dmar_rcu_check())
+
+ #define for_each_active_drhd_unit(drhd) \
+ list_for_each_entry_rcu(drhd, &dmar_drhd_units, list) \
+@@ -81,7 +82,8 @@ extern struct list_head dmar_drhd_units;
+ if (i=drhd->iommu, drhd->ignored) {} else
+
+ #define for_each_iommu(i, drhd) \
+- list_for_each_entry_rcu(drhd, &dmar_drhd_units, list) \
++ list_for_each_entry_rcu(drhd, &dmar_drhd_units, list, \
++ dmar_rcu_check()) \
+ if (i=drhd->iommu, 0) {} else
+
+ static inline bool dmar_rcu_check(void)
--- /dev/null
+From 443d372d6a96cd94ad119e5c14bb4d63a536a7f6 Mon Sep 17 00:00:00 2001
+From: Takashi Iwai <tiwai@suse.de>
+Date: Wed, 5 Feb 2020 10:31:46 +0100
+Subject: ipmi_si: Avoid spurious errors for optional IRQs
+
+From: Takashi Iwai <tiwai@suse.de>
+
+commit 443d372d6a96cd94ad119e5c14bb4d63a536a7f6 upstream.
+
+Although the IRQ assignment in ipmi_si driver is optional,
+platform_get_irq() spews error messages unnecessarily:
+ ipmi_si dmi-ipmi-si.0: IRQ index 0 not found
+
+Fix this by switching to platform_get_irq_optional().
+
+Cc: stable@vger.kernel.org # 5.4.x
+Cc: John Donnelly <john.p.donnelly@oracle.com>
+Fixes: 7723f4c5ecdb ("driver core: platform: Add an error message to platform_get_irq*()")
+Reported-and-tested-by: Patrick Vo <patrick.vo@hpe.com>
+Signed-off-by: Takashi Iwai <tiwai@suse.de>
+Message-Id: <20200205093146.1352-1-tiwai@suse.de>
+Signed-off-by: Corey Minyard <cminyard@mvista.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/char/ipmi/ipmi_si_platform.c | 4 ++--
+ 1 file changed, 2 insertions(+), 2 deletions(-)
+
+--- a/drivers/char/ipmi/ipmi_si_platform.c
++++ b/drivers/char/ipmi/ipmi_si_platform.c
+@@ -194,7 +194,7 @@ static int platform_ipmi_probe(struct pl
+ else
+ io.slave_addr = slave_addr;
+
+- io.irq = platform_get_irq(pdev, 0);
++ io.irq = platform_get_irq_optional(pdev, 0);
+ if (io.irq > 0)
+ io.irq_setup = ipmi_std_irq_setup;
+ else
+@@ -378,7 +378,7 @@ static int acpi_ipmi_probe(struct platfo
+ io.irq = tmp;
+ io.irq_setup = acpi_gpe_irq_setup;
+ } else {
+- int irq = platform_get_irq(pdev, 0);
++ int irq = platform_get_irq_optional(pdev, 0);
+
+ if (irq > 0) {
+ io.irq = irq;
--- /dev/null
+From 95fa10103dabc38be5de8efdfced5e67576ed896 Mon Sep 17 00:00:00 2001
+From: Vitaly Kuznetsov <vkuznets@redhat.com>
+Date: Mon, 9 Mar 2020 16:52:11 +0100
+Subject: KVM: nVMX: avoid NULL pointer dereference with incorrect EVMCS GPAs
+
+From: Vitaly Kuznetsov <vkuznets@redhat.com>
+
+commit 95fa10103dabc38be5de8efdfced5e67576ed896 upstream.
+
+When an EVMCS enabled L1 guest on KVM will tries doing enlightened VMEnter
+with EVMCS GPA = 0 the host crashes because the
+
+evmcs_gpa != vmx->nested.hv_evmcs_vmptr
+
+condition in nested_vmx_handle_enlightened_vmptrld() will evaluate to
+false (as nested.hv_evmcs_vmptr is zeroed after init). The crash will
+happen on vmx->nested.hv_evmcs pointer dereference.
+
+Another problematic EVMCS ptr value is '-1' but it only causes host crash
+after nested_release_evmcs() invocation. The problem is exactly the same as
+with '0', we mistakenly think that the EVMCS pointer hasn't changed and
+thus nested.hv_evmcs_vmptr is valid.
+
+Resolve the issue by adding an additional !vmx->nested.hv_evmcs
+check to nested_vmx_handle_enlightened_vmptrld(), this way we will
+always be trying kvm_vcpu_map() when nested.hv_evmcs is NULL
+and this is supposed to catch all invalid EVMCS GPAs.
+
+Also, initialize hv_evmcs_vmptr to '0' in nested_release_evmcs()
+to be consistent with initialization where we don't currently
+set hv_evmcs_vmptr to '-1'.
+
+Cc: stable@vger.kernel.org
+Signed-off-by: Vitaly Kuznetsov <vkuznets@redhat.com>
+Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/x86/kvm/vmx/nested.c | 5 +++--
+ 1 file changed, 3 insertions(+), 2 deletions(-)
+
+--- a/arch/x86/kvm/vmx/nested.c
++++ b/arch/x86/kvm/vmx/nested.c
+@@ -234,7 +234,7 @@ static inline void nested_release_evmcs(
+ return;
+
+ kvm_vcpu_unmap(vcpu, &vmx->nested.hv_evmcs_map, true);
+- vmx->nested.hv_evmcs_vmptr = -1ull;
++ vmx->nested.hv_evmcs_vmptr = 0;
+ vmx->nested.hv_evmcs = NULL;
+ }
+
+@@ -1932,7 +1932,8 @@ static int nested_vmx_handle_enlightened
+ if (!nested_enlightened_vmentry(vcpu, &evmcs_gpa))
+ return 1;
+
+- if (unlikely(evmcs_gpa != vmx->nested.hv_evmcs_vmptr)) {
++ if (unlikely(!vmx->nested.hv_evmcs ||
++ evmcs_gpa != vmx->nested.hv_evmcs_vmptr)) {
+ if (!vmx->nested.hv_evmcs)
+ vmx->nested.current_vmptr = -1ull;
+
--- /dev/null
+From 342993f96ab24d5864ab1216f46c0b199c2baf8e Mon Sep 17 00:00:00 2001
+From: Vitaly Kuznetsov <vkuznets@redhat.com>
+Date: Tue, 3 Mar 2020 15:33:15 +0100
+Subject: KVM: x86: clear stale x86_emulate_ctxt->intercept value
+
+From: Vitaly Kuznetsov <vkuznets@redhat.com>
+
+commit 342993f96ab24d5864ab1216f46c0b199c2baf8e upstream.
+
+After commit 07721feee46b ("KVM: nVMX: Don't emulate instructions in guest
+mode") Hyper-V guests on KVM stopped booting with:
+
+ kvm_nested_vmexit: rip fffff802987d6169 reason EPT_VIOLATION info1 181
+ info2 0 int_info 0 int_info_err 0
+ kvm_page_fault: address febd0000 error_code 181
+ kvm_emulate_insn: 0:fffff802987d6169: f3 a5
+ kvm_emulate_insn: 0:fffff802987d6169: f3 a5 FAIL
+ kvm_inj_exception: #UD (0x0)
+
+"f3 a5" is a "rep movsw" instruction, which should not be intercepted
+at all. Commit c44b4c6ab80e ("KVM: emulate: clean up initializations in
+init_decode_cache") reduced the number of fields cleared by
+init_decode_cache() claiming that they are being cleared elsewhere,
+'intercept', however, is left uncleared if the instruction does not have
+any of the "slow path" flags (NotImpl, Stack, Op3264, Sse, Mmx, CheckPerm,
+NearBranch, No16 and of course Intercept itself).
+
+Fixes: c44b4c6ab80e ("KVM: emulate: clean up initializations in init_decode_cache")
+Fixes: 07721feee46b ("KVM: nVMX: Don't emulate instructions in guest mode")
+Cc: stable@vger.kernel.org
+Suggested-by: Paolo Bonzini <pbonzini@redhat.com>
+Signed-off-by: Vitaly Kuznetsov <vkuznets@redhat.com>
+Reviewed-by: Sean Christopherson <sean.j.christopherson@intel.com>
+Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/x86/kvm/emulate.c | 1 +
+ 1 file changed, 1 insertion(+)
+
+--- a/arch/x86/kvm/emulate.c
++++ b/arch/x86/kvm/emulate.c
+@@ -5195,6 +5195,7 @@ int x86_decode_insn(struct x86_emulate_c
+ ctxt->fetch.ptr = ctxt->fetch.data;
+ ctxt->fetch.end = ctxt->fetch.data + insn_len;
+ ctxt->opcode_len = 1;
++ ctxt->intercept = x86_intercept_none;
+ if (insn_len > 0)
+ memcpy(ctxt->fetch.data, insn, insn_len);
+ else {
--- /dev/null
+From bcf3588d8ed3517e6ffaf083f034812aee9dc8e2 Mon Sep 17 00:00:00 2001
+From: Wolfram Sang <wsa@the-dreams.de>
+Date: Tue, 3 Mar 2020 13:50:46 +0100
+Subject: macintosh: windfarm: fix MODINFO regression
+
+From: Wolfram Sang <wsa@the-dreams.de>
+
+commit bcf3588d8ed3517e6ffaf083f034812aee9dc8e2 upstream.
+
+Commit af503716ac14 made sure OF devices get an OF style modalias with
+I2C events. It assumed all in-tree users were converted, yet it missed
+some Macintosh drivers.
+
+Add an OF module device table for all windfarm drivers to make them
+automatically load again.
+
+Fixes: af503716ac14 ("i2c: core: report OF style module alias for devices registered via OF")
+Link: https://bugzilla.kernel.org/show_bug.cgi?id=199471
+Reported-by: Erhard Furtner <erhard_f@mailbox.org>
+Tested-by: Erhard Furtner <erhard_f@mailbox.org>
+Acked-by: Michael Ellerman <mpe@ellerman.id.au> (powerpc)
+Signed-off-by: Wolfram Sang <wsa@the-dreams.de>
+Cc: stable@kernel.org # v4.17+
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/macintosh/windfarm_ad7417_sensor.c | 7 +++++++
+ drivers/macintosh/windfarm_fcu_controls.c | 7 +++++++
+ drivers/macintosh/windfarm_lm75_sensor.c | 16 +++++++++++++++-
+ drivers/macintosh/windfarm_lm87_sensor.c | 7 +++++++
+ drivers/macintosh/windfarm_max6690_sensor.c | 7 +++++++
+ drivers/macintosh/windfarm_smu_sat.c | 7 +++++++
+ 6 files changed, 50 insertions(+), 1 deletion(-)
+
+--- a/drivers/macintosh/windfarm_ad7417_sensor.c
++++ b/drivers/macintosh/windfarm_ad7417_sensor.c
+@@ -312,9 +312,16 @@ static const struct i2c_device_id wf_ad7
+ };
+ MODULE_DEVICE_TABLE(i2c, wf_ad7417_id);
+
++static const struct of_device_id wf_ad7417_of_id[] = {
++ { .compatible = "ad7417", },
++ { }
++};
++MODULE_DEVICE_TABLE(of, wf_ad7417_of_id);
++
+ static struct i2c_driver wf_ad7417_driver = {
+ .driver = {
+ .name = "wf_ad7417",
++ .of_match_table = wf_ad7417_of_id,
+ },
+ .probe = wf_ad7417_probe,
+ .remove = wf_ad7417_remove,
+--- a/drivers/macintosh/windfarm_fcu_controls.c
++++ b/drivers/macintosh/windfarm_fcu_controls.c
+@@ -580,9 +580,16 @@ static const struct i2c_device_id wf_fcu
+ };
+ MODULE_DEVICE_TABLE(i2c, wf_fcu_id);
+
++static const struct of_device_id wf_fcu_of_id[] = {
++ { .compatible = "fcu", },
++ { }
++};
++MODULE_DEVICE_TABLE(of, wf_fcu_of_id);
++
+ static struct i2c_driver wf_fcu_driver = {
+ .driver = {
+ .name = "wf_fcu",
++ .of_match_table = wf_fcu_of_id,
+ },
+ .probe = wf_fcu_probe,
+ .remove = wf_fcu_remove,
+--- a/drivers/macintosh/windfarm_lm75_sensor.c
++++ b/drivers/macintosh/windfarm_lm75_sensor.c
+@@ -14,6 +14,7 @@
+ #include <linux/init.h>
+ #include <linux/wait.h>
+ #include <linux/i2c.h>
++#include <linux/of_device.h>
+ #include <asm/prom.h>
+ #include <asm/machdep.h>
+ #include <asm/io.h>
+@@ -91,9 +92,14 @@ static int wf_lm75_probe(struct i2c_clie
+ const struct i2c_device_id *id)
+ {
+ struct wf_lm75_sensor *lm;
+- int rc, ds1775 = id->driver_data;
++ int rc, ds1775;
+ const char *name, *loc;
+
++ if (id)
++ ds1775 = id->driver_data;
++ else
++ ds1775 = !!of_device_get_match_data(&client->dev);
++
+ DBG("wf_lm75: creating %s device at address 0x%02x\n",
+ ds1775 ? "ds1775" : "lm75", client->addr);
+
+@@ -164,9 +170,17 @@ static const struct i2c_device_id wf_lm7
+ };
+ MODULE_DEVICE_TABLE(i2c, wf_lm75_id);
+
++static const struct of_device_id wf_lm75_of_id[] = {
++ { .compatible = "lm75", .data = (void *)0},
++ { .compatible = "ds1775", .data = (void *)1 },
++ { }
++};
++MODULE_DEVICE_TABLE(of, wf_lm75_of_id);
++
+ static struct i2c_driver wf_lm75_driver = {
+ .driver = {
+ .name = "wf_lm75",
++ .of_match_table = wf_lm75_of_id,
+ },
+ .probe = wf_lm75_probe,
+ .remove = wf_lm75_remove,
+--- a/drivers/macintosh/windfarm_lm87_sensor.c
++++ b/drivers/macintosh/windfarm_lm87_sensor.c
+@@ -166,9 +166,16 @@ static const struct i2c_device_id wf_lm8
+ };
+ MODULE_DEVICE_TABLE(i2c, wf_lm87_id);
+
++static const struct of_device_id wf_lm87_of_id[] = {
++ { .compatible = "lm87cimt", },
++ { }
++};
++MODULE_DEVICE_TABLE(of, wf_lm87_of_id);
++
+ static struct i2c_driver wf_lm87_driver = {
+ .driver = {
+ .name = "wf_lm87",
++ .of_match_table = wf_lm87_of_id,
+ },
+ .probe = wf_lm87_probe,
+ .remove = wf_lm87_remove,
+--- a/drivers/macintosh/windfarm_max6690_sensor.c
++++ b/drivers/macintosh/windfarm_max6690_sensor.c
+@@ -120,9 +120,16 @@ static const struct i2c_device_id wf_max
+ };
+ MODULE_DEVICE_TABLE(i2c, wf_max6690_id);
+
++static const struct of_device_id wf_max6690_of_id[] = {
++ { .compatible = "max6690", },
++ { }
++};
++MODULE_DEVICE_TABLE(of, wf_max6690_of_id);
++
+ static struct i2c_driver wf_max6690_driver = {
+ .driver = {
+ .name = "wf_max6690",
++ .of_match_table = wf_max6690_of_id,
+ },
+ .probe = wf_max6690_probe,
+ .remove = wf_max6690_remove,
+--- a/drivers/macintosh/windfarm_smu_sat.c
++++ b/drivers/macintosh/windfarm_smu_sat.c
+@@ -341,9 +341,16 @@ static const struct i2c_device_id wf_sat
+ };
+ MODULE_DEVICE_TABLE(i2c, wf_sat_id);
+
++static const struct of_device_id wf_sat_of_id[] = {
++ { .compatible = "smu-sat", },
++ { }
++};
++MODULE_DEVICE_TABLE(of, wf_sat_of_id);
++
+ static struct i2c_driver wf_sat_driver = {
+ .driver = {
+ .name = "wf_smu_sat",
++ .of_match_table = wf_sat_of_id,
+ },
+ .probe = wf_sat_probe,
+ .remove = wf_sat_remove,
--- /dev/null
+From 130ab8819d81bd96f1a71e8461a8f73edf1fbe82 Mon Sep 17 00:00:00 2001
+From: "H. Nikolaus Schaller" <hns@goldelico.com>
+Date: Fri, 6 Mar 2020 18:28:30 +0100
+Subject: MIPS: DTS: CI20: fix interrupt for pcf8563 RTC
+
+From: H. Nikolaus Schaller <hns@goldelico.com>
+
+commit 130ab8819d81bd96f1a71e8461a8f73edf1fbe82 upstream.
+
+Interrupts should not be specified by interrupt line but by
+gpio parent and reference.
+
+Fixes: 73f2b940474d ("MIPS: CI20: DTS: Add I2C nodes")
+Cc: stable@vger.kernel.org
+Signed-off-by: H. Nikolaus Schaller <hns@goldelico.com>
+Reviewed-by: Paul Cercueil <paul@crapouillou.net>
+Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/mips/boot/dts/ingenic/ci20.dts | 5 ++++-
+ 1 file changed, 4 insertions(+), 1 deletion(-)
+
+--- a/arch/mips/boot/dts/ingenic/ci20.dts
++++ b/arch/mips/boot/dts/ingenic/ci20.dts
+@@ -4,6 +4,7 @@
+ #include "jz4780.dtsi"
+ #include <dt-bindings/clock/ingenic,tcu.h>
+ #include <dt-bindings/gpio/gpio.h>
++#include <dt-bindings/interrupt-controller/irq.h>
+ #include <dt-bindings/regulator/active-semi,8865-regulator.h>
+
+ / {
+@@ -270,7 +271,9 @@
+ rtc@51 {
+ compatible = "nxp,pcf8563";
+ reg = <0x51>;
+- interrupts = <110>;
++
++ interrupt-parent = <&gpf>;
++ interrupts = <30 IRQ_TYPE_LEVEL_LOW>;
+ };
+ };
+
--- /dev/null
+From e8d87a0b822d4b3d9a94a5da915f93aa1b674c93 Mon Sep 17 00:00:00 2001
+From: "H. Nikolaus Schaller" <hns@goldelico.com>
+Date: Fri, 6 Mar 2020 18:27:58 +0100
+Subject: MIPS: DTS: CI20: fix PMU definitions for ACT8600
+
+From: H. Nikolaus Schaller <hns@goldelico.com>
+
+commit e8d87a0b822d4b3d9a94a5da915f93aa1b674c93 upstream.
+
+There is a ACT8600 on the CI20 board and the bindings of the
+ACT8865 driver have changed without updating the CI20 device
+tree. Therefore the PMU can not be probed successfully and
+is running in power-on reset state.
+
+Fix DT to match the latest act8865-regulator bindings.
+
+Fixes: 73f2b940474d ("MIPS: CI20: DTS: Add I2C nodes")
+Cc: stable@vger.kernel.org
+Signed-off-by: H. Nikolaus Schaller <hns@goldelico.com>
+Reviewed-by: Paul Cercueil <paul@crapouillou.net>
+Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/mips/boot/dts/ingenic/ci20.dts | 39 ++++++++++++++++++++++--------------
+ 1 file changed, 24 insertions(+), 15 deletions(-)
+
+--- a/arch/mips/boot/dts/ingenic/ci20.dts
++++ b/arch/mips/boot/dts/ingenic/ci20.dts
+@@ -4,6 +4,7 @@
+ #include "jz4780.dtsi"
+ #include <dt-bindings/clock/ingenic,tcu.h>
+ #include <dt-bindings/gpio/gpio.h>
++#include <dt-bindings/regulator/active-semi,8865-regulator.h>
+
+ / {
+ compatible = "img,ci20", "ingenic,jz4780";
+@@ -163,63 +164,71 @@
+
+ regulators {
+ vddcore: SUDCDC1 {
+- regulator-name = "VDDCORE";
++ regulator-name = "DCDC_REG1";
+ regulator-min-microvolt = <1100000>;
+ regulator-max-microvolt = <1100000>;
+ regulator-always-on;
+ };
+ vddmem: SUDCDC2 {
+- regulator-name = "VDDMEM";
++ regulator-name = "DCDC_REG2";
+ regulator-min-microvolt = <1500000>;
+ regulator-max-microvolt = <1500000>;
+ regulator-always-on;
+ };
+ vcc_33: SUDCDC3 {
+- regulator-name = "VCC33";
++ regulator-name = "DCDC_REG3";
+ regulator-min-microvolt = <3300000>;
+ regulator-max-microvolt = <3300000>;
+ regulator-always-on;
+ };
+ vcc_50: SUDCDC4 {
+- regulator-name = "VCC50";
++ regulator-name = "SUDCDC_REG4";
+ regulator-min-microvolt = <5000000>;
+ regulator-max-microvolt = <5000000>;
+ regulator-always-on;
+ };
+ vcc_25: LDO_REG5 {
+- regulator-name = "VCC25";
++ regulator-name = "LDO_REG5";
+ regulator-min-microvolt = <2500000>;
+ regulator-max-microvolt = <2500000>;
+ regulator-always-on;
+ };
+ wifi_io: LDO_REG6 {
+- regulator-name = "WIFIIO";
++ regulator-name = "LDO_REG6";
+ regulator-min-microvolt = <2500000>;
+ regulator-max-microvolt = <2500000>;
+ regulator-always-on;
+ };
+ vcc_28: LDO_REG7 {
+- regulator-name = "VCC28";
++ regulator-name = "LDO_REG7";
+ regulator-min-microvolt = <2800000>;
+ regulator-max-microvolt = <2800000>;
+ regulator-always-on;
+ };
+ vcc_15: LDO_REG8 {
+- regulator-name = "VCC15";
++ regulator-name = "LDO_REG8";
+ regulator-min-microvolt = <1500000>;
+ regulator-max-microvolt = <1500000>;
+ regulator-always-on;
+ };
+- vcc_18: LDO_REG9 {
+- regulator-name = "VCC18";
+- regulator-min-microvolt = <1800000>;
+- regulator-max-microvolt = <1800000>;
++ vrtc_18: LDO_REG9 {
++ regulator-name = "LDO_REG9";
++ /* Despite the datasheet stating 3.3V
++ * for REG9 and the driver expecting that,
++ * REG9 outputs 1.8V.
++ * Likely the CI20 uses a proprietary
++ * factory programmed chip variant.
++ * Since this is a simple on/off LDO the
++ * exact values do not matter.
++ */
++ regulator-min-microvolt = <3300000>;
++ regulator-max-microvolt = <3300000>;
+ regulator-always-on;
+ };
+ vcc_11: LDO_REG10 {
+- regulator-name = "VCC11";
+- regulator-min-microvolt = <1100000>;
+- regulator-max-microvolt = <1100000>;
++ regulator-name = "LDO_REG10";
++ regulator-min-microvolt = <1200000>;
++ regulator-max-microvolt = <1200000>;
+ regulator-always-on;
+ };
+ };
--- /dev/null
+From 8e029eb0bcd6a7fab6dc9191152c085784c31ee6 Mon Sep 17 00:00:00 2001
+From: Paul Cercueil <paul@crapouillou.net>
+Date: Tue, 25 Feb 2020 12:28:09 -0300
+Subject: MIPS: Fix CONFIG_MIPS_CMDLINE_DTB_EXTEND handling
+
+From: Paul Cercueil <paul@crapouillou.net>
+
+commit 8e029eb0bcd6a7fab6dc9191152c085784c31ee6 upstream.
+
+The CONFIG_MIPS_CMDLINE_DTB_EXTEND option is used so that the kernel
+arguments provided in the 'bootargs' property in devicetree are extended
+with the kernel arguments provided by the bootloader.
+
+The code was broken, as it didn't actually take any of the kernel
+arguments provided in devicetree when that option was set.
+
+Fixes: 7784cac69735 ("MIPS: cmdline: Clean up boot_command_line initialization")
+Cc: stable@vger.kernel.org
+Signed-off-by: Paul Cercueil <paul@crapouillou.net>
+Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/mips/kernel/setup.c | 3 ++-
+ 1 file changed, 2 insertions(+), 1 deletion(-)
+
+--- a/arch/mips/kernel/setup.c
++++ b/arch/mips/kernel/setup.c
+@@ -606,7 +606,8 @@ static void __init bootcmdline_init(char
+ * If we're configured to take boot arguments from DT, look for those
+ * now.
+ */
+- if (IS_ENABLED(CONFIG_MIPS_CMDLINE_FROM_DTB))
++ if (IS_ENABLED(CONFIG_MIPS_CMDLINE_FROM_DTB) ||
++ IS_ENABLED(CONFIG_MIPS_CMDLINE_DTB_EXTEND))
+ of_scan_flat_dt(bootcmdline_scan_chosen, &dt_bootargs);
+ #endif
+
--- /dev/null
+From b102f0c522cf668c8382c56a4f771b37d011cda2 Mon Sep 17 00:00:00 2001
+From: Felix Fietkau <nbd@nbd.name>
+Date: Thu, 20 Feb 2020 12:41:39 +0100
+Subject: mt76: fix array overflow on receiving too many fragments for a packet
+
+From: Felix Fietkau <nbd@nbd.name>
+
+commit b102f0c522cf668c8382c56a4f771b37d011cda2 upstream.
+
+If the hardware receives an oversized packet with too many rx fragments,
+skb_shinfo(skb)->frags can overflow and corrupt memory of adjacent pages.
+This becomes especially visible if it corrupts the freelist pointer of
+a slab page.
+
+Cc: stable@vger.kernel.org
+Signed-off-by: Felix Fietkau <nbd@nbd.name>
+Signed-off-by: Kalle Valo <kvalo@codeaurora.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/net/wireless/mediatek/mt76/dma.c | 9 ++++++---
+ 1 file changed, 6 insertions(+), 3 deletions(-)
+
+--- a/drivers/net/wireless/mediatek/mt76/dma.c
++++ b/drivers/net/wireless/mediatek/mt76/dma.c
+@@ -447,10 +447,13 @@ mt76_add_fragment(struct mt76_dev *dev,
+ struct page *page = virt_to_head_page(data);
+ int offset = data - page_address(page);
+ struct sk_buff *skb = q->rx_head;
++ struct skb_shared_info *shinfo = skb_shinfo(skb);
+
+- offset += q->buf_offset;
+- skb_add_rx_frag(skb, skb_shinfo(skb)->nr_frags, page, offset, len,
+- q->buf_size);
++ if (shinfo->nr_frags < ARRAY_SIZE(shinfo->frags)) {
++ offset += q->buf_offset;
++ skb_add_rx_frag(skb, shinfo->nr_frags, page, offset, len,
++ q->buf_size);
++ }
+
+ if (more)
+ return;
--- /dev/null
+From f967140dfb7442e2db0868b03b961f9c59418a1b Mon Sep 17 00:00:00 2001
+From: Kim Phillips <kim.phillips@amd.com>
+Date: Wed, 11 Mar 2020 14:13:21 -0500
+Subject: perf/amd/uncore: Replace manual sampling check with CAP_NO_INTERRUPT flag
+
+From: Kim Phillips <kim.phillips@amd.com>
+
+commit f967140dfb7442e2db0868b03b961f9c59418a1b upstream.
+
+Enable the sampling check in kernel/events/core.c::perf_event_open(),
+which returns the more appropriate -EOPNOTSUPP.
+
+BEFORE:
+
+ $ sudo perf record -a -e instructions,l3_request_g1.caching_l3_cache_accesses true
+ Error:
+ The sys_perf_event_open() syscall returned with 22 (Invalid argument) for event (l3_request_g1.caching_l3_cache_accesses).
+ /bin/dmesg | grep -i perf may provide additional information.
+
+With nothing relevant in dmesg.
+
+AFTER:
+
+ $ sudo perf record -a -e instructions,l3_request_g1.caching_l3_cache_accesses true
+ Error:
+ l3_request_g1.caching_l3_cache_accesses: PMU Hardware doesn't support sampling/overflow-interrupts. Try 'perf stat'
+
+Fixes: c43ca5091a37 ("perf/x86/amd: Add support for AMD NB and L2I "uncore" counters")
+Signed-off-by: Kim Phillips <kim.phillips@amd.com>
+Signed-off-by: Borislav Petkov <bp@suse.de>
+Acked-by: Peter Zijlstra <peterz@infradead.org>
+Cc: stable@vger.kernel.org
+Link: https://lkml.kernel.org/r/20200311191323.13124-1-kim.phillips@amd.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/x86/events/amd/uncore.c | 17 +++++++----------
+ 1 file changed, 7 insertions(+), 10 deletions(-)
+
+--- a/arch/x86/events/amd/uncore.c
++++ b/arch/x86/events/amd/uncore.c
+@@ -190,15 +190,12 @@ static int amd_uncore_event_init(struct
+
+ /*
+ * NB and Last level cache counters (MSRs) are shared across all cores
+- * that share the same NB / Last level cache. Interrupts can be directed
+- * to a single target core, however, event counts generated by processes
+- * running on other cores cannot be masked out. So we do not support
+- * sampling and per-thread events.
++ * that share the same NB / Last level cache. On family 16h and below,
++ * Interrupts can be directed to a single target core, however, event
++ * counts generated by processes running on other cores cannot be masked
++ * out. So we do not support sampling and per-thread events via
++ * CAP_NO_INTERRUPT, and we do not enable counter overflow interrupts:
+ */
+- if (is_sampling_event(event) || event->attach_state & PERF_ATTACH_TASK)
+- return -EINVAL;
+-
+- /* and we do not enable counter overflow interrupts */
+ hwc->config = event->attr.config & AMD64_RAW_EVENT_MASK_NB;
+ hwc->idx = -1;
+
+@@ -306,7 +303,7 @@ static struct pmu amd_nb_pmu = {
+ .start = amd_uncore_start,
+ .stop = amd_uncore_stop,
+ .read = amd_uncore_read,
+- .capabilities = PERF_PMU_CAP_NO_EXCLUDE,
++ .capabilities = PERF_PMU_CAP_NO_EXCLUDE | PERF_PMU_CAP_NO_INTERRUPT,
+ };
+
+ static struct pmu amd_llc_pmu = {
+@@ -317,7 +314,7 @@ static struct pmu amd_llc_pmu = {
+ .start = amd_uncore_start,
+ .stop = amd_uncore_stop,
+ .read = amd_uncore_read,
+- .capabilities = PERF_PMU_CAP_NO_EXCLUDE,
++ .capabilities = PERF_PMU_CAP_NO_EXCLUDE | PERF_PMU_CAP_NO_INTERRUPT,
+ };
+
+ static struct amd_uncore *amd_uncore_alloc(unsigned int cpu)
--- /dev/null
+From b26ebfe12f34f372cf041c6f801fa49c3fb382c5 Mon Sep 17 00:00:00 2001
+From: Corey Minyard <cminyard@mvista.com>
+Date: Fri, 6 Mar 2020 11:23:14 -0600
+Subject: pid: Fix error return value in some cases
+
+From: Corey Minyard <cminyard@mvista.com>
+
+commit b26ebfe12f34f372cf041c6f801fa49c3fb382c5 upstream.
+
+Recent changes to alloc_pid() allow the pid number to be specified on
+the command line. If set_tid_size is set, then the code scanning the
+levels will hard-set retval to -EPERM, overriding it's previous -ENOMEM
+value.
+
+After the code scanning the levels, there are error returns that do not
+set retval, assuming it is still set to -ENOMEM.
+
+So set retval back to -ENOMEM after scanning the levels.
+
+Fixes: 49cb2fc42ce4 ("fork: extend clone3() to support setting a PID")
+Signed-off-by: Corey Minyard <cminyard@mvista.com>
+Acked-by: Christian Brauner <christian.brauner@ubuntu.com>
+Cc: Andrei Vagin <avagin@gmail.com>
+Cc: Dmitry Safonov <0x7f454c46@gmail.com>
+Cc: Oleg Nesterov <oleg@redhat.com>
+Cc: Adrian Reber <areber@redhat.com>
+Cc: <stable@vger.kernel.org> # 5.5
+Link: https://lore.kernel.org/r/20200306172314.12232-1-minyard@acm.org
+[christian.brauner@ubuntu.com: fixup commit message]
+Signed-off-by: Christian Brauner <christian.brauner@ubuntu.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ kernel/pid.c | 2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/kernel/pid.c
++++ b/kernel/pid.c
+@@ -247,6 +247,8 @@ struct pid *alloc_pid(struct pid_namespa
+ tmp = tmp->parent;
+ }
+
++ retval = -ENOMEM;
++
+ if (unlikely(is_child_reaper(pid))) {
+ if (pid_ns_prepare_proc(ns))
+ goto out_free;
--- /dev/null
+From 5e6bdd37c5526ef01326df5dabb93011ee89237e Mon Sep 17 00:00:00 2001
+From: Stefan Haberland <sth@linux.ibm.com>
+Date: Thu, 12 Mar 2020 14:17:15 +0100
+Subject: s390/dasd: fix data corruption for thin provisioned devices
+
+From: Stefan Haberland <sth@linux.ibm.com>
+
+commit 5e6bdd37c5526ef01326df5dabb93011ee89237e upstream.
+
+Devices are formatted in multiple of tracks.
+For an Extent Space Efficient (ESE) volume we get errors when accessing
+unformatted tracks. In this case the driver either formats the track on
+the flight for write requests or returns zero data for read requests.
+
+In case a request spans multiple tracks, the indication of an unformatted
+track presented for the first track is incorrectly applied to all tracks
+covered by the request. As a result, tracks containing data will be handled
+as empty, resulting in zero data being returned on read, or overwriting
+existing data with zero on write.
+
+Fix by determining the track that gets the NRF error.
+For write requests only format the track that is surely not formatted.
+For Read requests all tracks before have returned valid data and should not
+be touched.
+All tracks after the unformatted track might be formatted or not. Those are
+returned to the blocklayer to build a new request.
+
+When using alias devices there is a chance that multiple write requests
+trigger a format of the same track which might lead to data loss. Ensure
+that a track is formatted only once by maintaining a list of currently
+processed tracks.
+
+Fixes: 5e2b17e712cf ("s390/dasd: Add dynamic formatting support for ESE volumes")
+Cc: stable@vger.kernel.org # 5.3+
+Signed-off-by: Stefan Haberland <sth@linux.ibm.com>
+Reviewed-by: Jan Hoeppner <hoeppner@linux.ibm.com>
+Reviewed-by: Peter Oberparleiter <oberpar@linux.ibm.com>
+Signed-off-by: Jens Axboe <axboe@kernel.dk>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/s390/block/dasd.c | 27 ++++++
+ drivers/s390/block/dasd_eckd.c | 163 +++++++++++++++++++++++++++++++++++++++--
+ drivers/s390/block/dasd_int.h | 15 +++
+ 3 files changed, 193 insertions(+), 12 deletions(-)
+
+--- a/drivers/s390/block/dasd.c
++++ b/drivers/s390/block/dasd.c
+@@ -178,6 +178,8 @@ struct dasd_block *dasd_alloc_block(void
+ (unsigned long) block);
+ INIT_LIST_HEAD(&block->ccw_queue);
+ spin_lock_init(&block->queue_lock);
++ INIT_LIST_HEAD(&block->format_list);
++ spin_lock_init(&block->format_lock);
+ timer_setup(&block->timer, dasd_block_timeout, 0);
+ spin_lock_init(&block->profile.lock);
+
+@@ -1779,20 +1781,26 @@ void dasd_int_handler(struct ccw_device
+
+ if (dasd_ese_needs_format(cqr->block, irb)) {
+ if (rq_data_dir((struct request *)cqr->callback_data) == READ) {
+- device->discipline->ese_read(cqr);
++ device->discipline->ese_read(cqr, irb);
+ cqr->status = DASD_CQR_SUCCESS;
+ cqr->stopclk = now;
+ dasd_device_clear_timer(device);
+ dasd_schedule_device_bh(device);
+ return;
+ }
+- fcqr = device->discipline->ese_format(device, cqr);
++ fcqr = device->discipline->ese_format(device, cqr, irb);
+ if (IS_ERR(fcqr)) {
++ if (PTR_ERR(fcqr) == -EINVAL) {
++ cqr->status = DASD_CQR_ERROR;
++ return;
++ }
+ /*
+ * If we can't format now, let the request go
+ * one extra round. Maybe we can format later.
+ */
+ cqr->status = DASD_CQR_QUEUED;
++ dasd_schedule_device_bh(device);
++ return;
+ } else {
+ fcqr->status = DASD_CQR_QUEUED;
+ cqr->status = DASD_CQR_QUEUED;
+@@ -2748,11 +2756,13 @@ static void __dasd_cleanup_cqr(struct da
+ {
+ struct request *req;
+ blk_status_t error = BLK_STS_OK;
++ unsigned int proc_bytes;
+ int status;
+
+ req = (struct request *) cqr->callback_data;
+ dasd_profile_end(cqr->block, cqr, req);
+
++ proc_bytes = cqr->proc_bytes;
+ status = cqr->block->base->discipline->free_cp(cqr, req);
+ if (status < 0)
+ error = errno_to_blk_status(status);
+@@ -2783,7 +2793,18 @@ static void __dasd_cleanup_cqr(struct da
+ blk_mq_end_request(req, error);
+ blk_mq_run_hw_queues(req->q, true);
+ } else {
+- blk_mq_complete_request(req);
++ /*
++ * Partial completed requests can happen with ESE devices.
++ * During read we might have gotten a NRF error and have to
++ * complete a request partially.
++ */
++ if (proc_bytes) {
++ blk_update_request(req, BLK_STS_OK,
++ blk_rq_bytes(req) - proc_bytes);
++ blk_mq_requeue_request(req, true);
++ } else {
++ blk_mq_complete_request(req);
++ }
+ }
+ }
+
+--- a/drivers/s390/block/dasd_eckd.c
++++ b/drivers/s390/block/dasd_eckd.c
+@@ -207,6 +207,45 @@ static void set_ch_t(struct ch_t *geo, _
+ geo->head |= head;
+ }
+
++/*
++ * calculate failing track from sense data depending if
++ * it is an EAV device or not
++ */
++static int dasd_eckd_track_from_irb(struct irb *irb, struct dasd_device *device,
++ sector_t *track)
++{
++ struct dasd_eckd_private *private = device->private;
++ u8 *sense = NULL;
++ u32 cyl;
++ u8 head;
++
++ sense = dasd_get_sense(irb);
++ if (!sense) {
++ DBF_DEV_EVENT(DBF_WARNING, device, "%s",
++ "ESE error no sense data\n");
++ return -EINVAL;
++ }
++ if (!(sense[27] & DASD_SENSE_BIT_2)) {
++ DBF_DEV_EVENT(DBF_WARNING, device, "%s",
++ "ESE error no valid track data\n");
++ return -EINVAL;
++ }
++
++ if (sense[27] & DASD_SENSE_BIT_3) {
++ /* enhanced addressing */
++ cyl = sense[30] << 20;
++ cyl |= (sense[31] & 0xF0) << 12;
++ cyl |= sense[28] << 8;
++ cyl |= sense[29];
++ } else {
++ cyl = sense[29] << 8;
++ cyl |= sense[30];
++ }
++ head = sense[31] & 0x0F;
++ *track = cyl * private->rdc_data.trk_per_cyl + head;
++ return 0;
++}
++
+ static int set_timestamp(struct ccw1 *ccw, struct DE_eckd_data *data,
+ struct dasd_device *device)
+ {
+@@ -2986,6 +3025,37 @@ static int dasd_eckd_format_device(struc
+ 0, NULL);
+ }
+
++static bool test_and_set_format_track(struct dasd_format_entry *to_format,
++ struct dasd_block *block)
++{
++ struct dasd_format_entry *format;
++ unsigned long flags;
++ bool rc = false;
++
++ spin_lock_irqsave(&block->format_lock, flags);
++ list_for_each_entry(format, &block->format_list, list) {
++ if (format->track == to_format->track) {
++ rc = true;
++ goto out;
++ }
++ }
++ list_add_tail(&to_format->list, &block->format_list);
++
++out:
++ spin_unlock_irqrestore(&block->format_lock, flags);
++ return rc;
++}
++
++static void clear_format_track(struct dasd_format_entry *format,
++ struct dasd_block *block)
++{
++ unsigned long flags;
++
++ spin_lock_irqsave(&block->format_lock, flags);
++ list_del_init(&format->list);
++ spin_unlock_irqrestore(&block->format_lock, flags);
++}
++
+ /*
+ * Callback function to free ESE format requests.
+ */
+@@ -2993,15 +3063,19 @@ static void dasd_eckd_ese_format_cb(stru
+ {
+ struct dasd_device *device = cqr->startdev;
+ struct dasd_eckd_private *private = device->private;
++ struct dasd_format_entry *format = data;
+
++ clear_format_track(format, cqr->basedev->block);
+ private->count--;
+ dasd_ffree_request(cqr, device);
+ }
+
+ static struct dasd_ccw_req *
+-dasd_eckd_ese_format(struct dasd_device *startdev, struct dasd_ccw_req *cqr)
++dasd_eckd_ese_format(struct dasd_device *startdev, struct dasd_ccw_req *cqr,
++ struct irb *irb)
+ {
+ struct dasd_eckd_private *private;
++ struct dasd_format_entry *format;
+ struct format_data_t fdata;
+ unsigned int recs_per_trk;
+ struct dasd_ccw_req *fcqr;
+@@ -3011,23 +3085,39 @@ dasd_eckd_ese_format(struct dasd_device
+ struct request *req;
+ sector_t first_trk;
+ sector_t last_trk;
++ sector_t curr_trk;
+ int rc;
+
+ req = cqr->callback_data;
+- base = cqr->block->base;
++ block = cqr->block;
++ base = block->base;
+ private = base->private;
+- block = base->block;
+ blksize = block->bp_block;
+ recs_per_trk = recs_per_track(&private->rdc_data, 0, blksize);
++ format = &startdev->format_entry;
+
+ first_trk = blk_rq_pos(req) >> block->s2b_shift;
+ sector_div(first_trk, recs_per_trk);
+ last_trk =
+ (blk_rq_pos(req) + blk_rq_sectors(req) - 1) >> block->s2b_shift;
+ sector_div(last_trk, recs_per_trk);
++ rc = dasd_eckd_track_from_irb(irb, base, &curr_trk);
++ if (rc)
++ return ERR_PTR(rc);
++
++ if (curr_trk < first_trk || curr_trk > last_trk) {
++ DBF_DEV_EVENT(DBF_WARNING, startdev,
++ "ESE error track %llu not within range %llu - %llu\n",
++ curr_trk, first_trk, last_trk);
++ return ERR_PTR(-EINVAL);
++ }
++ format->track = curr_trk;
++ /* test if track is already in formatting by another thread */
++ if (test_and_set_format_track(format, block))
++ return ERR_PTR(-EEXIST);
+
+- fdata.start_unit = first_trk;
+- fdata.stop_unit = last_trk;
++ fdata.start_unit = curr_trk;
++ fdata.stop_unit = curr_trk;
+ fdata.blksize = blksize;
+ fdata.intensity = private->uses_cdl ? DASD_FMT_INT_COMPAT : 0;
+
+@@ -3044,6 +3134,7 @@ dasd_eckd_ese_format(struct dasd_device
+ return fcqr;
+
+ fcqr->callback = dasd_eckd_ese_format_cb;
++ fcqr->callback_data = (void *) format;
+
+ return fcqr;
+ }
+@@ -3051,29 +3142,87 @@ dasd_eckd_ese_format(struct dasd_device
+ /*
+ * When data is read from an unformatted area of an ESE volume, this function
+ * returns zeroed data and thereby mimics a read of zero data.
++ *
++ * The first unformatted track is the one that got the NRF error, the address is
++ * encoded in the sense data.
++ *
++ * All tracks before have returned valid data and should not be touched.
++ * All tracks after the unformatted track might be formatted or not. This is
++ * currently not known, remember the processed data and return the remainder of
++ * the request to the blocklayer in __dasd_cleanup_cqr().
+ */
+-static void dasd_eckd_ese_read(struct dasd_ccw_req *cqr)
++static int dasd_eckd_ese_read(struct dasd_ccw_req *cqr, struct irb *irb)
+ {
++ struct dasd_eckd_private *private;
++ sector_t first_trk, last_trk;
++ sector_t first_blk, last_blk;
+ unsigned int blksize, off;
++ unsigned int recs_per_trk;
+ struct dasd_device *base;
+ struct req_iterator iter;
++ struct dasd_block *block;
++ unsigned int skip_block;
++ unsigned int blk_count;
+ struct request *req;
+ struct bio_vec bv;
++ sector_t curr_trk;
++ sector_t end_blk;
+ char *dst;
++ int rc;
+
+ req = (struct request *) cqr->callback_data;
+ base = cqr->block->base;
+ blksize = base->block->bp_block;
++ block = cqr->block;
++ private = base->private;
++ skip_block = 0;
++ blk_count = 0;
++
++ recs_per_trk = recs_per_track(&private->rdc_data, 0, blksize);
++ first_trk = first_blk = blk_rq_pos(req) >> block->s2b_shift;
++ sector_div(first_trk, recs_per_trk);
++ last_trk = last_blk =
++ (blk_rq_pos(req) + blk_rq_sectors(req) - 1) >> block->s2b_shift;
++ sector_div(last_trk, recs_per_trk);
++ rc = dasd_eckd_track_from_irb(irb, base, &curr_trk);
++ if (rc)
++ return rc;
++
++ /* sanity check if the current track from sense data is valid */
++ if (curr_trk < first_trk || curr_trk > last_trk) {
++ DBF_DEV_EVENT(DBF_WARNING, base,
++ "ESE error track %llu not within range %llu - %llu\n",
++ curr_trk, first_trk, last_trk);
++ return -EINVAL;
++ }
++
++ /*
++ * if not the first track got the NRF error we have to skip over valid
++ * blocks
++ */
++ if (curr_trk != first_trk)
++ skip_block = curr_trk * recs_per_trk - first_blk;
++
++ /* we have no information beyond the current track */
++ end_blk = (curr_trk + 1) * recs_per_trk;
+
+ rq_for_each_segment(bv, req, iter) {
+ dst = page_address(bv.bv_page) + bv.bv_offset;
+ for (off = 0; off < bv.bv_len; off += blksize) {
+- if (dst && rq_data_dir(req) == READ) {
++ if (first_blk + blk_count >= end_blk) {
++ cqr->proc_bytes = blk_count * blksize;
++ return 0;
++ }
++ if (dst && !skip_block) {
+ dst += off;
+ memset(dst, 0, blksize);
++ } else {
++ skip_block--;
+ }
++ blk_count++;
+ }
+ }
++ return 0;
+ }
+
+ /*
+--- a/drivers/s390/block/dasd_int.h
++++ b/drivers/s390/block/dasd_int.h
+@@ -187,6 +187,7 @@ struct dasd_ccw_req {
+
+ void (*callback)(struct dasd_ccw_req *, void *data);
+ void *callback_data;
++ unsigned int proc_bytes; /* bytes for partial completion */
+ };
+
+ /*
+@@ -387,8 +388,9 @@ struct dasd_discipline {
+ int (*ext_pool_warn_thrshld)(struct dasd_device *);
+ int (*ext_pool_oos)(struct dasd_device *);
+ int (*ext_pool_exhaust)(struct dasd_device *, struct dasd_ccw_req *);
+- struct dasd_ccw_req *(*ese_format)(struct dasd_device *, struct dasd_ccw_req *);
+- void (*ese_read)(struct dasd_ccw_req *);
++ struct dasd_ccw_req *(*ese_format)(struct dasd_device *,
++ struct dasd_ccw_req *, struct irb *);
++ int (*ese_read)(struct dasd_ccw_req *, struct irb *);
+ };
+
+ extern struct dasd_discipline *dasd_diag_discipline_pointer;
+@@ -474,6 +476,11 @@ struct dasd_profile {
+ spinlock_t lock;
+ };
+
++struct dasd_format_entry {
++ struct list_head list;
++ sector_t track;
++};
++
+ struct dasd_device {
+ /* Block device stuff. */
+ struct dasd_block *block;
+@@ -539,6 +546,7 @@ struct dasd_device {
+ struct dentry *debugfs_dentry;
+ struct dentry *hosts_dentry;
+ struct dasd_profile profile;
++ struct dasd_format_entry format_entry;
+ };
+
+ struct dasd_block {
+@@ -564,6 +572,9 @@ struct dasd_block {
+
+ struct dentry *debugfs_dentry;
+ struct dasd_profile profile;
++
++ struct list_head format_list;
++ spinlock_t format_lock;
+ };
+
+ struct dasd_attention_data {
ktest-add-timeout-for-ssh-sync-testing.patch
block-fix-partition-support-for-host-aware-zoned-block-devices.patch
cifs_atomic_open-fix-double-put-on-late-allocation-failure.patch
+gfs2_atomic_open-fix-o_excl-o_creat-handling-on-cold-dcache.patch
+kvm-x86-clear-stale-x86_emulate_ctxt-intercept-value.patch
+kvm-nvmx-avoid-null-pointer-dereference-with-incorrect-evmcs-gpas.patch
+arc-define-__align_str-and-__align-symbols-for-arc.patch
+fuse-fix-stack-use-after-return.patch
+mips-dts-ci20-fix-pmu-definitions-for-act8600.patch
+mips-dts-ci20-fix-interrupt-for-pcf8563-rtc.patch
+mips-fix-config_mips_cmdline_dtb_extend-handling.patch
+s390-dasd-fix-data-corruption-for-thin-provisioned-devices.patch
+ipmi_si-avoid-spurious-errors-for-optional-irqs.patch
+ftrace-return-the-first-found-result-in-lookup_rec.patch
+blk-iocost-fix-incorrect-vtime-comparison-in-iocg_is_idle.patch
+fscrypt-don-t-evict-dirty-inodes-after-removing-key.patch
+pid-fix-error-return-value-in-some-cases.patch
+macintosh-windfarm-fix-modinfo-regression.patch
+x86-ioremap-map-efi-runtime-services-data-as-encrypted-for-sev.patch
+efi-fix-a-race-and-a-buffer-overflow-while-reading-efivars-via-sysfs.patch
+efi-add-a-sanity-check-to-efivar_store_raw.patch
+i2c-designware-pci-fix-bug_on-during-device-removal.patch
+mt76-fix-array-overflow-on-receiving-too-many-fragments-for-a-packet.patch
+perf-amd-uncore-replace-manual-sampling-check-with-cap_no_interrupt-flag.patch
+x86-mce-fix-logic-and-comments-around-msr_ppin_ctl.patch
+iommu-dma-fix-msi-reservation-allocation.patch
+iommu-vt-d-dmar-replace-warn_taint-with-pr_warn-add_taint.patch
+iommu-vt-d-dmar_parse_one_rmrr-replace-warn_taint-with-pr_warn-add_taint.patch
+iommu-vt-d-fix-rcu-list-debugging-warnings.patch
+iommu-vt-d-fix-a-bug-in-intel_iommu_iova_to_phys-for-huge-page.patch
--- /dev/null
+From 985e537a4082b4635754a57f4f95430790afee6a Mon Sep 17 00:00:00 2001
+From: Tom Lendacky <thomas.lendacky@amd.com>
+Date: Tue, 10 Mar 2020 18:35:57 +0100
+Subject: x86/ioremap: Map EFI runtime services data as encrypted for SEV
+
+From: Tom Lendacky <thomas.lendacky@amd.com>
+
+commit 985e537a4082b4635754a57f4f95430790afee6a upstream.
+
+The dmidecode program fails to properly decode the SMBIOS data supplied
+by OVMF/UEFI when running in an SEV guest. The SMBIOS area, under SEV, is
+encrypted and resides in reserved memory that is marked as EFI runtime
+services data.
+
+As a result, when memremap() is attempted for the SMBIOS data, it
+can't be mapped as regular RAM (through try_ram_remap()) and, since
+the address isn't part of the iomem resources list, it isn't mapped
+encrypted through the fallback ioremap().
+
+Add a new __ioremap_check_other() to deal with memory types like
+EFI_RUNTIME_SERVICES_DATA which are not covered by the resource ranges.
+
+This allows any runtime services data which has been created encrypted,
+to be mapped encrypted too.
+
+ [ bp: Move functionality to a separate function. ]
+
+Signed-off-by: Tom Lendacky <thomas.lendacky@amd.com>
+Signed-off-by: Borislav Petkov <bp@suse.de>
+Reviewed-by: Joerg Roedel <jroedel@suse.de>
+Tested-by: Joerg Roedel <jroedel@suse.de>
+Cc: <stable@vger.kernel.org> # 5.3
+Link: https://lkml.kernel.org/r/2d9e16eb5b53dc82665c95c6764b7407719df7a0.1582645327.git.thomas.lendacky@amd.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/x86/mm/ioremap.c | 18 ++++++++++++++++++
+ 1 file changed, 18 insertions(+)
+
+--- a/arch/x86/mm/ioremap.c
++++ b/arch/x86/mm/ioremap.c
+@@ -106,6 +106,19 @@ static unsigned int __ioremap_check_encr
+ return 0;
+ }
+
++/*
++ * The EFI runtime services data area is not covered by walk_mem_res(), but must
++ * be mapped encrypted when SEV is active.
++ */
++static void __ioremap_check_other(resource_size_t addr, struct ioremap_desc *desc)
++{
++ if (!sev_active())
++ return;
++
++ if (efi_mem_type(addr) == EFI_RUNTIME_SERVICES_DATA)
++ desc->flags |= IORES_MAP_ENCRYPTED;
++}
++
+ static int __ioremap_collect_map_flags(struct resource *res, void *arg)
+ {
+ struct ioremap_desc *desc = arg;
+@@ -124,6 +137,9 @@ static int __ioremap_collect_map_flags(s
+ * To avoid multiple resource walks, this function walks resources marked as
+ * IORESOURCE_MEM and IORESOURCE_BUSY and looking for system RAM and/or a
+ * resource described not as IORES_DESC_NONE (e.g. IORES_DESC_ACPI_TABLES).
++ *
++ * After that, deal with misc other ranges in __ioremap_check_other() which do
++ * not fall into the above category.
+ */
+ static void __ioremap_check_mem(resource_size_t addr, unsigned long size,
+ struct ioremap_desc *desc)
+@@ -135,6 +151,8 @@ static void __ioremap_check_mem(resource
+ memset(desc, 0, sizeof(struct ioremap_desc));
+
+ walk_mem_res(start, end, desc, __ioremap_collect_map_flags);
++
++ __ioremap_check_other(addr, desc);
+ }
+
+ /*
--- /dev/null
+From 59b5809655bdafb0767d3fd00a3e41711aab07e6 Mon Sep 17 00:00:00 2001
+From: Tony Luck <tony.luck@intel.com>
+Date: Tue, 25 Feb 2020 17:17:37 -0800
+Subject: x86/mce: Fix logic and comments around MSR_PPIN_CTL
+
+From: Tony Luck <tony.luck@intel.com>
+
+commit 59b5809655bdafb0767d3fd00a3e41711aab07e6 upstream.
+
+There are two implemented bits in the PPIN_CTL MSR:
+
+Bit 0: LockOut (R/WO)
+ Set 1 to prevent further writes to MSR_PPIN_CTL.
+
+Bit 1: Enable_PPIN (R/W)
+ If 1, enables MSR_PPIN to be accessible using RDMSR.
+ If 0, an attempt to read MSR_PPIN will cause #GP.
+
+So there are four defined values:
+ 0: PPIN is disabled, PPIN_CTL may be updated
+ 1: PPIN is disabled. PPIN_CTL is locked against updates
+ 2: PPIN is enabled. PPIN_CTL may be updated
+ 3: PPIN is enabled. PPIN_CTL is locked against updates
+
+Code would only enable the X86_FEATURE_INTEL_PPIN feature for case "2".
+When it should have done so for both case "2" and case "3".
+
+Fix the final test to just check for the enable bit. Also fix some of
+the other comments in this function.
+
+Fixes: 3f5a7896a509 ("x86/mce: Include the PPIN in MCE records when available")
+Signed-off-by: Tony Luck <tony.luck@intel.com>
+Signed-off-by: Borislav Petkov <bp@suse.de>
+Cc: <stable@vger.kernel.org>
+Link: https://lkml.kernel.org/r/20200226011737.9958-1-tony.luck@intel.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/x86/kernel/cpu/mce/intel.c | 9 +++++----
+ 1 file changed, 5 insertions(+), 4 deletions(-)
+
+--- a/arch/x86/kernel/cpu/mce/intel.c
++++ b/arch/x86/kernel/cpu/mce/intel.c
+@@ -492,17 +492,18 @@ static void intel_ppin_init(struct cpuin
+ return;
+
+ if ((val & 3UL) == 1UL) {
+- /* PPIN available but disabled: */
++ /* PPIN locked in disabled mode */
+ return;
+ }
+
+- /* If PPIN is disabled, but not locked, try to enable: */
+- if (!(val & 3UL)) {
++ /* If PPIN is disabled, try to enable */
++ if (!(val & 2UL)) {
+ wrmsrl_safe(MSR_PPIN_CTL, val | 2UL);
+ rdmsrl_safe(MSR_PPIN_CTL, &val);
+ }
+
+- if ((val & 3UL) == 2UL)
++ /* Is the enable bit set? */
++ if (val & 2UL)
+ set_cpu_cap(c, X86_FEATURE_INTEL_PPIN);
+ }
+ }