]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
4.14-stable patches
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 18 Dec 2017 12:00:42 +0000 (13:00 +0100)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 18 Dec 2017 12:00:42 +0000 (13:00 +0100)
added patches:
arm64-fix-config_debug_wx-address-reporting.patch
arm64-initialise-high_memory-global-variable-earlier.patch
arm64-mm-fix-pte_mkclean-pte_mkdirty-semantics.patch
autofs-fix-careless-error-in-recent-commit.patch
ceph-drop-negative-child-dentries-before-try-pruning-inode-s-alias.patch
dm-fix-various-targets-to-dm_register_target-after-module-__init-resources-created.patch
dmaengine-dmatest-move-callback-wait-queue-to-thread-context.patch
eeprom-at24-change-nvmem-stride-to-1.patch
ext4-add-missing-error-check-in-__ext4_new_inode.patch
ext4-fix-crash-when-a-directory-s-i_size-is-too-small.patch
ext4-fix-fdatasync-2-after-fallocate-2-operation.patch
ext4-support-fast-symlinks-from-ext3-file-systems.patch
ib-core-bound-check-alternate-path-port-number.patch
ib-core-don-t-enforce-pkey-security-on-smi-mads.patch
iw_cxgb4-only-insert-drain-cqes-if-wq-is-flushed.patch
kernel-make-groups_sort-calling-a-responsibility-group_info-allocators.patch
mm-oom_reaper-fix-memory-corruption.patch
mmc-core-apply-no_cmd23-quirk-to-some-specific-cards.patch
nfs-don-t-wait-on-commit-in-nfs_commit_inode-if-there-were-no-commit-requests.patch
ovl-pass-ovl_get_nlink-parameters-in-right-order.patch
ovl-update-ctx-pos-on-impure-dir-iteration.patch
posix-timer-properly-check-sigevent-sigev_notify.patch
revert-exec-avoid-rlimit_stack-races-with-prlimit.patch
sched-rt-do-not-pull-from-current-cpu-if-only-one-cpu-to-pull.patch
scsi-core-fix-a-scsi_show_rq-null-pointer-dereference.patch
scsi-libsas-fix-length-error-in-sas_smp_handler.patch
sunrpc-fix-a-race-in-the-receive-code-path.patch
tracing-allocate-mask_str-buffer-dynamically.patch
usb-core-prevent-malicious-bnuminterfaces-overflow.patch
usb-uas-and-storage-add-us_fl_broken_fua-for-another-jmicron-jms567-id.patch
usb-xhci-fix-tds-for-mtk-xhci1.1.patch
usbip-fix-stub_rx-get_pipe-to-validate-endpoint-number.patch
usbip-fix-stub_rx-harden-cmd_submit-path-to-handle-malicious-input.patch
usbip-fix-stub_send_ret_submit-vulnerability-to-null-transfer_buffer.patch
usbip-prevent-vhci_hcd-driver-from-leaking-a-socket-pointer-address.patch
x86-boot-compressed-64-detect-and-handle-5-level-paging-at-boot-time.patch
x86-boot-compressed-64-print-error-if-5-level-paging-is-not-supported.patch
xhci-don-t-add-a-virt_dev-to-the-devs-array-before-it-s-fully-allocated.patch

39 files changed:
queue-4.14/arm64-fix-config_debug_wx-address-reporting.patch [new file with mode: 0644]
queue-4.14/arm64-initialise-high_memory-global-variable-earlier.patch [new file with mode: 0644]
queue-4.14/arm64-mm-fix-pte_mkclean-pte_mkdirty-semantics.patch [new file with mode: 0644]
queue-4.14/autofs-fix-careless-error-in-recent-commit.patch [new file with mode: 0644]
queue-4.14/ceph-drop-negative-child-dentries-before-try-pruning-inode-s-alias.patch [new file with mode: 0644]
queue-4.14/dm-fix-various-targets-to-dm_register_target-after-module-__init-resources-created.patch [new file with mode: 0644]
queue-4.14/dmaengine-dmatest-move-callback-wait-queue-to-thread-context.patch [new file with mode: 0644]
queue-4.14/eeprom-at24-change-nvmem-stride-to-1.patch [new file with mode: 0644]
queue-4.14/ext4-add-missing-error-check-in-__ext4_new_inode.patch [new file with mode: 0644]
queue-4.14/ext4-fix-crash-when-a-directory-s-i_size-is-too-small.patch [new file with mode: 0644]
queue-4.14/ext4-fix-fdatasync-2-after-fallocate-2-operation.patch [new file with mode: 0644]
queue-4.14/ext4-support-fast-symlinks-from-ext3-file-systems.patch [new file with mode: 0644]
queue-4.14/ib-core-bound-check-alternate-path-port-number.patch [new file with mode: 0644]
queue-4.14/ib-core-don-t-enforce-pkey-security-on-smi-mads.patch [new file with mode: 0644]
queue-4.14/iw_cxgb4-only-insert-drain-cqes-if-wq-is-flushed.patch [new file with mode: 0644]
queue-4.14/kernel-make-groups_sort-calling-a-responsibility-group_info-allocators.patch [new file with mode: 0644]
queue-4.14/mm-oom_reaper-fix-memory-corruption.patch [new file with mode: 0644]
queue-4.14/mmc-core-apply-no_cmd23-quirk-to-some-specific-cards.patch [new file with mode: 0644]
queue-4.14/nfs-don-t-wait-on-commit-in-nfs_commit_inode-if-there-were-no-commit-requests.patch [new file with mode: 0644]
queue-4.14/ovl-pass-ovl_get_nlink-parameters-in-right-order.patch [new file with mode: 0644]
queue-4.14/ovl-update-ctx-pos-on-impure-dir-iteration.patch [new file with mode: 0644]
queue-4.14/posix-timer-properly-check-sigevent-sigev_notify.patch [new file with mode: 0644]
queue-4.14/revert-exec-avoid-rlimit_stack-races-with-prlimit.patch [new file with mode: 0644]
queue-4.14/sched-rt-do-not-pull-from-current-cpu-if-only-one-cpu-to-pull.patch [new file with mode: 0644]
queue-4.14/scsi-core-fix-a-scsi_show_rq-null-pointer-dereference.patch [new file with mode: 0644]
queue-4.14/scsi-libsas-fix-length-error-in-sas_smp_handler.patch [new file with mode: 0644]
queue-4.14/series
queue-4.14/sunrpc-fix-a-race-in-the-receive-code-path.patch [new file with mode: 0644]
queue-4.14/tracing-allocate-mask_str-buffer-dynamically.patch [new file with mode: 0644]
queue-4.14/usb-core-prevent-malicious-bnuminterfaces-overflow.patch [new file with mode: 0644]
queue-4.14/usb-uas-and-storage-add-us_fl_broken_fua-for-another-jmicron-jms567-id.patch [new file with mode: 0644]
queue-4.14/usb-xhci-fix-tds-for-mtk-xhci1.1.patch [new file with mode: 0644]
queue-4.14/usbip-fix-stub_rx-get_pipe-to-validate-endpoint-number.patch [new file with mode: 0644]
queue-4.14/usbip-fix-stub_rx-harden-cmd_submit-path-to-handle-malicious-input.patch [new file with mode: 0644]
queue-4.14/usbip-fix-stub_send_ret_submit-vulnerability-to-null-transfer_buffer.patch [new file with mode: 0644]
queue-4.14/usbip-prevent-vhci_hcd-driver-from-leaking-a-socket-pointer-address.patch [new file with mode: 0644]
queue-4.14/x86-boot-compressed-64-detect-and-handle-5-level-paging-at-boot-time.patch [new file with mode: 0644]
queue-4.14/x86-boot-compressed-64-print-error-if-5-level-paging-is-not-supported.patch [new file with mode: 0644]
queue-4.14/xhci-don-t-add-a-virt_dev-to-the-devs-array-before-it-s-fully-allocated.patch [new file with mode: 0644]

diff --git a/queue-4.14/arm64-fix-config_debug_wx-address-reporting.patch b/queue-4.14/arm64-fix-config_debug_wx-address-reporting.patch
new file mode 100644 (file)
index 0000000..5636089
--- /dev/null
@@ -0,0 +1,41 @@
+From 1d08a044cf12aee37dfd54837558e3295287b343 Mon Sep 17 00:00:00 2001
+From: Mark Rutland <mark.rutland@arm.com>
+Date: Wed, 13 Dec 2017 11:45:42 +0000
+Subject: arm64: fix CONFIG_DEBUG_WX address reporting
+
+From: Mark Rutland <mark.rutland@arm.com>
+
+commit 1d08a044cf12aee37dfd54837558e3295287b343 upstream.
+
+In ptdump_check_wx(), we pass walk_pgd() a start address of 0 (rather
+than VA_START) for the init_mm. This means that any reported W&X
+addresses are offset by VA_START, which is clearly wrong and can make
+them appear like userspace addresses.
+
+Fix this by telling the ptdump code that we're walking init_mm starting
+at VA_START. We don't need to update the addr_markers, since these are
+still valid bounds regardless.
+
+Fixes: 1404d6f13e47 ("arm64: dump: Add checking for writable and exectuable pages")
+Signed-off-by: Mark Rutland <mark.rutland@arm.com>
+Cc: Kees Cook <keescook@chromium.org>
+Cc: Laura Abbott <labbott@redhat.com>
+Reported-by: Timur Tabi <timur@codeaurora.org>
+Signed-off-by: Will Deacon <will.deacon@arm.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/arm64/mm/dump.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/arch/arm64/mm/dump.c
++++ b/arch/arm64/mm/dump.c
+@@ -389,7 +389,7 @@ void ptdump_check_wx(void)
+               .check_wx = true,
+       };
+-      walk_pgd(&st, &init_mm, 0);
++      walk_pgd(&st, &init_mm, VA_START);
+       note_page(&st, 0, 0, 0);
+       if (st.wx_pages || st.uxn_pages)
+               pr_warn("Checked W+X mappings: FAILED, %lu W+X pages found, %lu non-UXN pages found\n",
diff --git a/queue-4.14/arm64-initialise-high_memory-global-variable-earlier.patch b/queue-4.14/arm64-initialise-high_memory-global-variable-earlier.patch
new file mode 100644 (file)
index 0000000..abfbb19
--- /dev/null
@@ -0,0 +1,48 @@
+From f24e5834a2c3f6c5f814a417f858226f0a010ade Mon Sep 17 00:00:00 2001
+From: Steve Capper <steve.capper@arm.com>
+Date: Mon, 4 Dec 2017 14:13:05 +0000
+Subject: arm64: Initialise high_memory global variable earlier
+
+From: Steve Capper <steve.capper@arm.com>
+
+commit f24e5834a2c3f6c5f814a417f858226f0a010ade upstream.
+
+The high_memory global variable is used by
+cma_declare_contiguous(.) before it is defined.
+
+We don't notice this as we compute __pa(high_memory - 1), and it looks
+like we're processing a VA from the direct linear map.
+
+This problem becomes apparent when we flip the kernel virtual address
+space and the linear map is moved to the bottom of the kernel VA space.
+
+This patch moves the initialisation of high_memory before it used.
+
+Fixes: f7426b983a6a ("mm: cma: adjust address limit to avoid hitting low/high memory boundary")
+Signed-off-by: Steve Capper <steve.capper@arm.com>
+Signed-off-by: Will Deacon <will.deacon@arm.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/arm64/mm/init.c |    3 ++-
+ 1 file changed, 2 insertions(+), 1 deletion(-)
+
+--- a/arch/arm64/mm/init.c
++++ b/arch/arm64/mm/init.c
+@@ -476,6 +476,8 @@ void __init arm64_memblock_init(void)
+       reserve_elfcorehdr();
++      high_memory = __va(memblock_end_of_DRAM() - 1) + 1;
++
+       dma_contiguous_reserve(arm64_dma_phys_limit);
+       memblock_allow_resize();
+@@ -502,7 +504,6 @@ void __init bootmem_init(void)
+       sparse_init();
+       zone_sizes_init(min, max);
+-      high_memory = __va((max << PAGE_SHIFT) - 1) + 1;
+       memblock_dump_all();
+ }
diff --git a/queue-4.14/arm64-mm-fix-pte_mkclean-pte_mkdirty-semantics.patch b/queue-4.14/arm64-mm-fix-pte_mkclean-pte_mkdirty-semantics.patch
new file mode 100644 (file)
index 0000000..6c7f2c8
--- /dev/null
@@ -0,0 +1,108 @@
+From 8781bcbc5e69d7da69e84c7044ca0284848d5d01 Mon Sep 17 00:00:00 2001
+From: Steve Capper <steve.capper@arm.com>
+Date: Fri, 1 Dec 2017 17:22:14 +0000
+Subject: arm64: mm: Fix pte_mkclean, pte_mkdirty semantics
+
+From: Steve Capper <steve.capper@arm.com>
+
+commit 8781bcbc5e69d7da69e84c7044ca0284848d5d01 upstream.
+
+On systems with hardware dirty bit management, the ltp madvise09 unit
+test fails due to dirty bit information being lost and pages being
+incorrectly freed.
+
+This was bisected to:
+       arm64: Ignore hardware dirty bit updates in ptep_set_wrprotect()
+
+Reverting this commit leads to a separate problem, that the unit test
+retains pages that should have been dropped due to the function
+madvise_free_pte_range(.) not cleaning pte's properly.
+
+Currently pte_mkclean only clears the software dirty bit, thus the
+following code sequence can appear:
+
+       pte = pte_mkclean(pte);
+       if (pte_dirty(pte))
+               // this condition can return true with HW DBM!
+
+This patch also adjusts pte_mkclean to set PTE_RDONLY thus effectively
+clearing both the SW and HW dirty information.
+
+In order for this to function on systems without HW DBM, we need to
+also adjust pte_mkdirty to remove the read only bit from writable pte's
+to avoid infinite fault loops.
+
+Fixes: 64c26841b349 ("arm64: Ignore hardware dirty bit updates in ptep_set_wrprotect()")
+Reported-by: Bhupinder Thakur <bhupinder.thakur@linaro.org>
+Tested-by: Bhupinder Thakur <bhupinder.thakur@linaro.org>
+Reviewed-by: Catalin Marinas <catalin.marinas@arm.com>
+Signed-off-by: Steve Capper <steve.capper@arm.com>
+Signed-off-by: Will Deacon <will.deacon@arm.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/arm64/include/asm/pgtable.h |   33 ++++++++++++++++++---------------
+ 1 file changed, 18 insertions(+), 15 deletions(-)
+
+--- a/arch/arm64/include/asm/pgtable.h
++++ b/arch/arm64/include/asm/pgtable.h
+@@ -149,12 +149,20 @@ static inline pte_t pte_mkwrite(pte_t pt
+ static inline pte_t pte_mkclean(pte_t pte)
+ {
+-      return clear_pte_bit(pte, __pgprot(PTE_DIRTY));
++      pte = clear_pte_bit(pte, __pgprot(PTE_DIRTY));
++      pte = set_pte_bit(pte, __pgprot(PTE_RDONLY));
++
++      return pte;
+ }
+ static inline pte_t pte_mkdirty(pte_t pte)
+ {
+-      return set_pte_bit(pte, __pgprot(PTE_DIRTY));
++      pte = set_pte_bit(pte, __pgprot(PTE_DIRTY));
++
++      if (pte_write(pte))
++              pte = clear_pte_bit(pte, __pgprot(PTE_RDONLY));
++
++      return pte;
+ }
+ static inline pte_t pte_mkold(pte_t pte)
+@@ -642,28 +650,23 @@ static inline pmd_t pmdp_huge_get_and_cl
+ #endif /* CONFIG_TRANSPARENT_HUGEPAGE */
+ /*
+- * ptep_set_wrprotect - mark read-only while preserving the hardware update of
+- * the Access Flag.
++ * ptep_set_wrprotect - mark read-only while trasferring potential hardware
++ * dirty status (PTE_DBM && !PTE_RDONLY) to the software PTE_DIRTY bit.
+  */
+ #define __HAVE_ARCH_PTEP_SET_WRPROTECT
+ static inline void ptep_set_wrprotect(struct mm_struct *mm, unsigned long address, pte_t *ptep)
+ {
+       pte_t old_pte, pte;
+-      /*
+-       * ptep_set_wrprotect() is only called on CoW mappings which are
+-       * private (!VM_SHARED) with the pte either read-only (!PTE_WRITE &&
+-       * PTE_RDONLY) or writable and software-dirty (PTE_WRITE &&
+-       * !PTE_RDONLY && PTE_DIRTY); see is_cow_mapping() and
+-       * protection_map[]. There is no race with the hardware update of the
+-       * dirty state: clearing of PTE_RDONLY when PTE_WRITE (a.k.a. PTE_DBM)
+-       * is set.
+-       */
+-      VM_WARN_ONCE(pte_write(*ptep) && !pte_dirty(*ptep),
+-                   "%s: potential race with hardware DBM", __func__);
+       pte = READ_ONCE(*ptep);
+       do {
+               old_pte = pte;
++              /*
++               * If hardware-dirty (PTE_WRITE/DBM bit set and PTE_RDONLY
++               * clear), set the PTE_DIRTY bit.
++               */
++              if (pte_hw_dirty(pte))
++                      pte = pte_mkdirty(pte);
+               pte = pte_wrprotect(pte);
+               pte_val(pte) = cmpxchg_relaxed(&pte_val(*ptep),
+                                              pte_val(old_pte), pte_val(pte));
diff --git a/queue-4.14/autofs-fix-careless-error-in-recent-commit.patch b/queue-4.14/autofs-fix-careless-error-in-recent-commit.patch
new file mode 100644 (file)
index 0000000..e630351
--- /dev/null
@@ -0,0 +1,36 @@
+From 302ec300ef8a545a7fc7f667e5fd743b091c2eeb Mon Sep 17 00:00:00 2001
+From: NeilBrown <neilb@suse.com>
+Date: Thu, 14 Dec 2017 15:32:38 -0800
+Subject: autofs: fix careless error in recent commit
+
+From: NeilBrown <neilb@suse.com>
+
+commit 302ec300ef8a545a7fc7f667e5fd743b091c2eeb upstream.
+
+Commit ecc0c469f277 ("autofs: don't fail mount for transient error") was
+meant to replace an 'if' with a 'switch', but instead added the 'switch'
+leaving the case in place.
+
+Link: http://lkml.kernel.org/r/87zi6wstmw.fsf@notabene.neil.brown.name
+Fixes: ecc0c469f277 ("autofs: don't fail mount for transient error")
+Reported-by: Ben Hutchings <ben.hutchings@codethink.co.uk>
+Signed-off-by: NeilBrown <neilb@suse.com>
+Cc: Ian Kent <raven@themaw.net>
+Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
+Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/autofs4/waitq.c |    1 -
+ 1 file changed, 1 deletion(-)
+
+--- a/fs/autofs4/waitq.c
++++ b/fs/autofs4/waitq.c
+@@ -170,7 +170,6 @@ static void autofs4_notify_daemon(struct
+       mutex_unlock(&sbi->wq_mutex);
+-      if (autofs4_write(sbi, pipe, &pkt, pktsz))
+       switch (ret = autofs4_write(sbi, pipe, &pkt, pktsz)) {
+       case 0:
+               break;
diff --git a/queue-4.14/ceph-drop-negative-child-dentries-before-try-pruning-inode-s-alias.patch b/queue-4.14/ceph-drop-negative-child-dentries-before-try-pruning-inode-s-alias.patch
new file mode 100644 (file)
index 0000000..93c7ae5
--- /dev/null
@@ -0,0 +1,85 @@
+From 040d786032bf59002d374b86d75b04d97624005c Mon Sep 17 00:00:00 2001
+From: "Yan, Zheng" <zyan@redhat.com>
+Date: Thu, 30 Nov 2017 11:59:22 +0800
+Subject: ceph: drop negative child dentries before try pruning inode's alias
+
+From: Yan, Zheng <zyan@redhat.com>
+
+commit 040d786032bf59002d374b86d75b04d97624005c upstream.
+
+Negative child dentry holds reference on inode's alias, it makes
+d_prune_aliases() do nothing.
+
+Signed-off-by: "Yan, Zheng" <zyan@redhat.com>
+Reviewed-by: Jeff Layton <jlayton@redhat.com>
+Signed-off-by: Ilya Dryomov <idryomov@gmail.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/ceph/mds_client.c |   42 ++++++++++++++++++++++++++++++++++++++----
+ 1 file changed, 38 insertions(+), 4 deletions(-)
+
+--- a/fs/ceph/mds_client.c
++++ b/fs/ceph/mds_client.c
+@@ -1428,6 +1428,29 @@ static int __close_session(struct ceph_m
+       return request_close_session(mdsc, session);
+ }
++static bool drop_negative_children(struct dentry *dentry)
++{
++      struct dentry *child;
++      bool all_negative = true;
++
++      if (!d_is_dir(dentry))
++              goto out;
++
++      spin_lock(&dentry->d_lock);
++      list_for_each_entry(child, &dentry->d_subdirs, d_child) {
++              if (d_really_is_positive(child)) {
++                      all_negative = false;
++                      break;
++              }
++      }
++      spin_unlock(&dentry->d_lock);
++
++      if (all_negative)
++              shrink_dcache_parent(dentry);
++out:
++      return all_negative;
++}
++
+ /*
+  * Trim old(er) caps.
+  *
+@@ -1473,16 +1496,27 @@ static int trim_caps_cb(struct inode *in
+       if ((used | wanted) & ~oissued & mine)
+               goto out;   /* we need these caps */
+-      session->s_trim_caps--;
+       if (oissued) {
+               /* we aren't the only cap.. just remove us */
+               __ceph_remove_cap(cap, true);
++              session->s_trim_caps--;
+       } else {
++              struct dentry *dentry;
+               /* try dropping referring dentries */
+               spin_unlock(&ci->i_ceph_lock);
+-              d_prune_aliases(inode);
+-              dout("trim_caps_cb %p cap %p  pruned, count now %d\n",
+-                   inode, cap, atomic_read(&inode->i_count));
++              dentry = d_find_any_alias(inode);
++              if (dentry && drop_negative_children(dentry)) {
++                      int count;
++                      dput(dentry);
++                      d_prune_aliases(inode);
++                      count = atomic_read(&inode->i_count);
++                      if (count == 1)
++                              session->s_trim_caps--;
++                      dout("trim_caps_cb %p cap %p pruned, count now %d\n",
++                           inode, cap, count);
++              } else {
++                      dput(dentry);
++              }
+               return 0;
+       }
diff --git a/queue-4.14/dm-fix-various-targets-to-dm_register_target-after-module-__init-resources-created.patch b/queue-4.14/dm-fix-various-targets-to-dm_register_target-after-module-__init-resources-created.patch
new file mode 100644 (file)
index 0000000..025ab5c
--- /dev/null
@@ -0,0 +1,250 @@
+From 7e6358d244e4706fe612a77b9c36519a33600ac0 Mon Sep 17 00:00:00 2001
+From: "monty_pavel@sina.com" <monty_pavel@sina.com>
+Date: Sat, 25 Nov 2017 01:43:50 +0800
+Subject: dm: fix various targets to dm_register_target after module __init resources created
+
+From: monty_pavel@sina.com <monty_pavel@sina.com>
+
+commit 7e6358d244e4706fe612a77b9c36519a33600ac0 upstream.
+
+A NULL pointer is seen if two concurrent "vgchange -ay -K <vg name>"
+processes race to load the dm-thin-pool module:
+
+ PID: 25992 TASK: ffff883cd7d23500 CPU: 4 COMMAND: "vgchange"
+  #0 [ffff883cd743d600] machine_kexec at ffffffff81038fa9
+  0000001 [ffff883cd743d660] crash_kexec at ffffffff810c5992
+  0000002 [ffff883cd743d730] oops_end at ffffffff81515c90
+  0000003 [ffff883cd743d760] no_context at ffffffff81049f1b
+  0000004 [ffff883cd743d7b0] __bad_area_nosemaphore at ffffffff8104a1a5
+  0000005 [ffff883cd743d800] bad_area at ffffffff8104a2ce
+  0000006 [ffff883cd743d830] __do_page_fault at ffffffff8104aa6f
+  0000007 [ffff883cd743d950] do_page_fault at ffffffff81517bae
+  0000008 [ffff883cd743d980] page_fault at ffffffff81514f95
+     [exception RIP: kmem_cache_alloc+108]
+     RIP: ffffffff8116ef3c RSP: ffff883cd743da38 RFLAGS: 00010046
+     RAX: 0000000000000004 RBX: ffffffff81121b90 RCX: ffff881bf1e78cc0
+     RDX: 0000000000000000 RSI: 00000000000000d0 RDI: 0000000000000000
+     RBP: ffff883cd743da68 R8: ffff881bf1a4eb00 R9: 0000000080042000
+     R10: 0000000000002000 R11: 0000000000000000 R12: 00000000000000d0
+     R13: 0000000000000000 R14: 00000000000000d0 R15: 0000000000000246
+     ORIG_RAX: ffffffffffffffff CS: 0010 SS: 0018
+  0000009 [ffff883cd743da70] mempool_alloc_slab at ffffffff81121ba5
+ 0000010 [ffff883cd743da80] mempool_create_node at ffffffff81122083
+ 0000011 [ffff883cd743dad0] mempool_create at ffffffff811220f4
+ 0000012 [ffff883cd743dae0] pool_ctr at ffffffffa08de049 [dm_thin_pool]
+ 0000013 [ffff883cd743dbd0] dm_table_add_target at ffffffffa0005f2f [dm_mod]
+ 0000014 [ffff883cd743dc30] table_load at ffffffffa0008ba9 [dm_mod]
+ 0000015 [ffff883cd743dc90] ctl_ioctl at ffffffffa0009dc4 [dm_mod]
+
+The race results in a NULL pointer because:
+
+Process A (vgchange -ay -K):
+       a. send DM_LIST_VERSIONS_CMD ioctl;
+       b. pool_target not registered;
+       c. modprobe dm_thin_pool and wait until end.
+
+Process B (vgchange -ay -K):
+       a. send DM_LIST_VERSIONS_CMD ioctl;
+       b. pool_target registered;
+       c. table_load->dm_table_add_target->pool_ctr;
+       d. _new_mapping_cache is NULL and panic.
+Note:
+       1. process A and process B are two concurrent processes.
+       2. pool_target can be detected by process B but
+       _new_mapping_cache initialization has not ended.
+
+To fix dm-thin-pool, and other targets (cache, multipath, and snapshot)
+with the same problem, simply dm_register_target() after all resources
+created during module init (as labelled with __init) are finished.
+
+Signed-off-by: monty <monty_pavel@sina.com>
+Signed-off-by: Mike Snitzer <snitzer@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/md/dm-cache-target.c |   12 +++++-----
+ drivers/md/dm-mpath.c        |   18 ++++++++--------
+ drivers/md/dm-snap.c         |   48 +++++++++++++++++++++----------------------
+ drivers/md/dm-thin.c         |   22 ++++++++-----------
+ 4 files changed, 49 insertions(+), 51 deletions(-)
+
+--- a/drivers/md/dm-cache-target.c
++++ b/drivers/md/dm-cache-target.c
+@@ -3554,18 +3554,18 @@ static int __init dm_cache_init(void)
+ {
+       int r;
+-      r = dm_register_target(&cache_target);
+-      if (r) {
+-              DMERR("cache target registration failed: %d", r);
+-              return r;
+-      }
+-
+       migration_cache = KMEM_CACHE(dm_cache_migration, 0);
+       if (!migration_cache) {
+               dm_unregister_target(&cache_target);
+               return -ENOMEM;
+       }
++      r = dm_register_target(&cache_target);
++      if (r) {
++              DMERR("cache target registration failed: %d", r);
++              return r;
++      }
++
+       return 0;
+ }
+--- a/drivers/md/dm-mpath.c
++++ b/drivers/md/dm-mpath.c
+@@ -1965,13 +1965,6 @@ static int __init dm_multipath_init(void
+ {
+       int r;
+-      r = dm_register_target(&multipath_target);
+-      if (r < 0) {
+-              DMERR("request-based register failed %d", r);
+-              r = -EINVAL;
+-              goto bad_register_target;
+-      }
+-
+       kmultipathd = alloc_workqueue("kmpathd", WQ_MEM_RECLAIM, 0);
+       if (!kmultipathd) {
+               DMERR("failed to create workqueue kmpathd");
+@@ -1993,13 +1986,20 @@ static int __init dm_multipath_init(void
+               goto bad_alloc_kmpath_handlerd;
+       }
++      r = dm_register_target(&multipath_target);
++      if (r < 0) {
++              DMERR("request-based register failed %d", r);
++              r = -EINVAL;
++              goto bad_register_target;
++      }
++
+       return 0;
++bad_register_target:
++      destroy_workqueue(kmpath_handlerd);
+ bad_alloc_kmpath_handlerd:
+       destroy_workqueue(kmultipathd);
+ bad_alloc_kmultipathd:
+-      dm_unregister_target(&multipath_target);
+-bad_register_target:
+       return r;
+ }
+--- a/drivers/md/dm-snap.c
++++ b/drivers/md/dm-snap.c
+@@ -2411,24 +2411,6 @@ static int __init dm_snapshot_init(void)
+               return r;
+       }
+-      r = dm_register_target(&snapshot_target);
+-      if (r < 0) {
+-              DMERR("snapshot target register failed %d", r);
+-              goto bad_register_snapshot_target;
+-      }
+-
+-      r = dm_register_target(&origin_target);
+-      if (r < 0) {
+-              DMERR("Origin target register failed %d", r);
+-              goto bad_register_origin_target;
+-      }
+-
+-      r = dm_register_target(&merge_target);
+-      if (r < 0) {
+-              DMERR("Merge target register failed %d", r);
+-              goto bad_register_merge_target;
+-      }
+-
+       r = init_origin_hash();
+       if (r) {
+               DMERR("init_origin_hash failed.");
+@@ -2449,19 +2431,37 @@ static int __init dm_snapshot_init(void)
+               goto bad_pending_cache;
+       }
++      r = dm_register_target(&snapshot_target);
++      if (r < 0) {
++              DMERR("snapshot target register failed %d", r);
++              goto bad_register_snapshot_target;
++      }
++
++      r = dm_register_target(&origin_target);
++      if (r < 0) {
++              DMERR("Origin target register failed %d", r);
++              goto bad_register_origin_target;
++      }
++
++      r = dm_register_target(&merge_target);
++      if (r < 0) {
++              DMERR("Merge target register failed %d", r);
++              goto bad_register_merge_target;
++      }
++
+       return 0;
+-bad_pending_cache:
+-      kmem_cache_destroy(exception_cache);
+-bad_exception_cache:
+-      exit_origin_hash();
+-bad_origin_hash:
+-      dm_unregister_target(&merge_target);
+ bad_register_merge_target:
+       dm_unregister_target(&origin_target);
+ bad_register_origin_target:
+       dm_unregister_target(&snapshot_target);
+ bad_register_snapshot_target:
++      kmem_cache_destroy(pending_cache);
++bad_pending_cache:
++      kmem_cache_destroy(exception_cache);
++bad_exception_cache:
++      exit_origin_hash();
++bad_origin_hash:
+       dm_exception_store_exit();
+       return r;
+--- a/drivers/md/dm-thin.c
++++ b/drivers/md/dm-thin.c
+@@ -4355,30 +4355,28 @@ static struct target_type thin_target =
+ static int __init dm_thin_init(void)
+ {
+-      int r;
++      int r = -ENOMEM;
+       pool_table_init();
++      _new_mapping_cache = KMEM_CACHE(dm_thin_new_mapping, 0);
++      if (!_new_mapping_cache)
++              return r;
++
+       r = dm_register_target(&thin_target);
+       if (r)
+-              return r;
++              goto bad_new_mapping_cache;
+       r = dm_register_target(&pool_target);
+       if (r)
+-              goto bad_pool_target;
+-
+-      r = -ENOMEM;
+-
+-      _new_mapping_cache = KMEM_CACHE(dm_thin_new_mapping, 0);
+-      if (!_new_mapping_cache)
+-              goto bad_new_mapping_cache;
++              goto bad_thin_target;
+       return 0;
+-bad_new_mapping_cache:
+-      dm_unregister_target(&pool_target);
+-bad_pool_target:
++bad_thin_target:
+       dm_unregister_target(&thin_target);
++bad_new_mapping_cache:
++      kmem_cache_destroy(_new_mapping_cache);
+       return r;
+ }
diff --git a/queue-4.14/dmaengine-dmatest-move-callback-wait-queue-to-thread-context.patch b/queue-4.14/dmaengine-dmatest-move-callback-wait-queue-to-thread-context.patch
new file mode 100644 (file)
index 0000000..41d6f23
--- /dev/null
@@ -0,0 +1,159 @@
+From 6f6a23a213be51728502b88741ba6a10cda2441d Mon Sep 17 00:00:00 2001
+From: Adam Wallis <awallis@codeaurora.org>
+Date: Mon, 27 Nov 2017 10:45:01 -0500
+Subject: dmaengine: dmatest: move callback wait queue to thread context
+
+From: Adam Wallis <awallis@codeaurora.org>
+
+commit 6f6a23a213be51728502b88741ba6a10cda2441d upstream.
+
+Commit adfa543e7314 ("dmatest: don't use set_freezable_with_signal()")
+introduced a bug (that is in fact documented by the patch commit text)
+that leaves behind a dangling pointer. Since the done_wait structure is
+allocated on the stack, future invocations to the DMATEST can produce
+undesirable results (e.g., corrupted spinlocks).
+
+Commit a9df21e34b42 ("dmaengine: dmatest: warn user when dma test times
+out") attempted to WARN the user that the stack was likely corrupted but
+did not fix the actual issue.
+
+This patch fixes the issue by pushing the wait queue and callback
+structs into the the thread structure. If a failure occurs due to time,
+dmaengine_terminate_all will force the callback to safely call
+wake_up_all() without possibility of using a freed pointer.
+
+Bug: https://bugzilla.kernel.org/show_bug.cgi?id=197605
+Fixes: adfa543e7314 ("dmatest: don't use set_freezable_with_signal()")
+Reviewed-by: Sinan Kaya <okaya@codeaurora.org>
+Suggested-by: Shunyong Yang <shunyong.yang@hxt-semitech.com>
+Signed-off-by: Adam Wallis <awallis@codeaurora.org>
+Signed-off-by: Vinod Koul <vinod.koul@intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/dma/dmatest.c |   55 ++++++++++++++++++++++++++++----------------------
+ 1 file changed, 31 insertions(+), 24 deletions(-)
+
+--- a/drivers/dma/dmatest.c
++++ b/drivers/dma/dmatest.c
+@@ -155,6 +155,12 @@ MODULE_PARM_DESC(run, "Run the test (def
+ #define PATTERN_COUNT_MASK    0x1f
+ #define PATTERN_MEMSET_IDX    0x01
++/* poor man's completion - we want to use wait_event_freezable() on it */
++struct dmatest_done {
++      bool                    done;
++      wait_queue_head_t       *wait;
++};
++
+ struct dmatest_thread {
+       struct list_head        node;
+       struct dmatest_info     *info;
+@@ -165,6 +171,8 @@ struct dmatest_thread {
+       u8                      **dsts;
+       u8                      **udsts;
+       enum dma_transaction_type type;
++      wait_queue_head_t done_wait;
++      struct dmatest_done test_done;
+       bool                    done;
+ };
+@@ -342,18 +350,25 @@ static unsigned int dmatest_verify(u8 **
+       return error_count;
+ }
+-/* poor man's completion - we want to use wait_event_freezable() on it */
+-struct dmatest_done {
+-      bool                    done;
+-      wait_queue_head_t       *wait;
+-};
+ static void dmatest_callback(void *arg)
+ {
+       struct dmatest_done *done = arg;
+-
+-      done->done = true;
+-      wake_up_all(done->wait);
++      struct dmatest_thread *thread =
++              container_of(arg, struct dmatest_thread, done_wait);
++      if (!thread->done) {
++              done->done = true;
++              wake_up_all(done->wait);
++      } else {
++              /*
++               * If thread->done, it means that this callback occurred
++               * after the parent thread has cleaned up. This can
++               * happen in the case that driver doesn't implement
++               * the terminate_all() functionality and a dma operation
++               * did not occur within the timeout period
++               */
++              WARN(1, "dmatest: Kernel memory may be corrupted!!\n");
++      }
+ }
+ static unsigned int min_odd(unsigned int x, unsigned int y)
+@@ -424,9 +439,8 @@ static unsigned long long dmatest_KBs(s6
+  */
+ static int dmatest_func(void *data)
+ {
+-      DECLARE_WAIT_QUEUE_HEAD_ONSTACK(done_wait);
+       struct dmatest_thread   *thread = data;
+-      struct dmatest_done     done = { .wait = &done_wait };
++      struct dmatest_done     *done = &thread->test_done;
+       struct dmatest_info     *info;
+       struct dmatest_params   *params;
+       struct dma_chan         *chan;
+@@ -673,9 +687,9 @@ static int dmatest_func(void *data)
+                       continue;
+               }
+-              done.done = false;
++              done->done = false;
+               tx->callback = dmatest_callback;
+-              tx->callback_param = &done;
++              tx->callback_param = done;
+               cookie = tx->tx_submit(tx);
+               if (dma_submit_error(cookie)) {
+@@ -688,21 +702,12 @@ static int dmatest_func(void *data)
+               }
+               dma_async_issue_pending(chan);
+-              wait_event_freezable_timeout(done_wait, done.done,
++              wait_event_freezable_timeout(thread->done_wait, done->done,
+                                            msecs_to_jiffies(params->timeout));
+               status = dma_async_is_tx_complete(chan, cookie, NULL, NULL);
+-              if (!done.done) {
+-                      /*
+-                       * We're leaving the timed out dma operation with
+-                       * dangling pointer to done_wait.  To make this
+-                       * correct, we'll need to allocate wait_done for
+-                       * each test iteration and perform "who's gonna
+-                       * free it this time?" dancing.  For now, just
+-                       * leave it dangling.
+-                       */
+-                      WARN(1, "dmatest: Kernel stack may be corrupted!!\n");
++              if (!done->done) {
+                       dmaengine_unmap_put(um);
+                       result("test timed out", total_tests, src_off, dst_off,
+                              len, 0);
+@@ -789,7 +794,7 @@ err_thread_type:
+               dmatest_KBs(runtime, total_len), ret);
+       /* terminate all transfers on specified channels */
+-      if (ret)
++      if (ret || failed_tests)
+               dmaengine_terminate_all(chan);
+       thread->done = true;
+@@ -849,6 +854,8 @@ static int dmatest_add_threads(struct dm
+               thread->info = info;
+               thread->chan = dtc->chan;
+               thread->type = type;
++              thread->test_done.wait = &thread->done_wait;
++              init_waitqueue_head(&thread->done_wait);
+               smp_wmb();
+               thread->task = kthread_create(dmatest_func, thread, "%s-%s%u",
+                               dma_chan_name(chan), op, i);
diff --git a/queue-4.14/eeprom-at24-change-nvmem-stride-to-1.patch b/queue-4.14/eeprom-at24-change-nvmem-stride-to-1.patch
new file mode 100644 (file)
index 0000000..a447b5d
--- /dev/null
@@ -0,0 +1,34 @@
+From 7f6d2ecd3d7acaf205ea7b3e96f9ffc55b92298b Mon Sep 17 00:00:00 2001
+From: David Lechner <david@lechnology.com>
+Date: Sun, 3 Dec 2017 19:54:41 -0600
+Subject: eeprom: at24: change nvmem stride to 1
+
+From: David Lechner <david@lechnology.com>
+
+commit 7f6d2ecd3d7acaf205ea7b3e96f9ffc55b92298b upstream.
+
+Trying to read the MAC address from an eeprom that has an offset that
+is not a multiple of 4 causes an error currently.
+
+Fix it by changing the nvmem stride to 1.
+
+Signed-off-by: David Lechner <david@lechnology.com>
+[Bartosz: tweaked the commit message]
+Signed-off-by: Bartosz Golaszewski <brgl@bgdev.pl>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/misc/eeprom/at24.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/drivers/misc/eeprom/at24.c
++++ b/drivers/misc/eeprom/at24.c
+@@ -776,7 +776,7 @@ static int at24_probe(struct i2c_client
+       at24->nvmem_config.reg_read = at24_read;
+       at24->nvmem_config.reg_write = at24_write;
+       at24->nvmem_config.priv = at24;
+-      at24->nvmem_config.stride = 4;
++      at24->nvmem_config.stride = 1;
+       at24->nvmem_config.word_size = 1;
+       at24->nvmem_config.size = chip.byte_len;
diff --git a/queue-4.14/ext4-add-missing-error-check-in-__ext4_new_inode.patch b/queue-4.14/ext4-add-missing-error-check-in-__ext4_new_inode.patch
new file mode 100644 (file)
index 0000000..aac8cec
--- /dev/null
@@ -0,0 +1,34 @@
+From 996fc4477a0ea28226b30d175f053fb6f9a4fa36 Mon Sep 17 00:00:00 2001
+From: Theodore Ts'o <tytso@mit.edu>
+Date: Sun, 10 Dec 2017 23:44:11 -0500
+Subject: ext4: add missing error check in __ext4_new_inode()
+
+From: Theodore Ts'o <tytso@mit.edu>
+
+commit 996fc4477a0ea28226b30d175f053fb6f9a4fa36 upstream.
+
+It's possible for ext4_get_acl() to return an ERR_PTR.  So we need to
+add a check for this case in __ext4_new_inode().  Otherwise on an
+error we can end up oops the kernel.
+
+This was getting triggered by xfstests generic/388, which is a test
+which exercises the shutdown code path.
+
+Signed-off-by: Theodore Ts'o <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/ext4/ialloc.c |    2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/fs/ext4/ialloc.c
++++ b/fs/ext4/ialloc.c
+@@ -816,6 +816,8 @@ struct inode *__ext4_new_inode(handle_t
+ #ifdef CONFIG_EXT4_FS_POSIX_ACL
+               struct posix_acl *p = get_acl(dir, ACL_TYPE_DEFAULT);
++              if (IS_ERR(p))
++                      return ERR_CAST(p);
+               if (p) {
+                       int acl_size = p->a_count * sizeof(ext4_acl_entry);
diff --git a/queue-4.14/ext4-fix-crash-when-a-directory-s-i_size-is-too-small.patch b/queue-4.14/ext4-fix-crash-when-a-directory-s-i_size-is-too-small.patch
new file mode 100644 (file)
index 0000000..59a26f3
--- /dev/null
@@ -0,0 +1,57 @@
+From 9d5afec6b8bd46d6ed821aa1579634437f58ef1f Mon Sep 17 00:00:00 2001
+From: Chandan Rajendra <chandan@linux.vnet.ibm.com>
+Date: Mon, 11 Dec 2017 15:00:57 -0500
+Subject: ext4: fix crash when a directory's i_size is too small
+
+From: Chandan Rajendra <chandan@linux.vnet.ibm.com>
+
+commit 9d5afec6b8bd46d6ed821aa1579634437f58ef1f upstream.
+
+On a ppc64 machine, when mounting a fuzzed ext2 image (generated by
+fsfuzzer) the following call trace is seen,
+
+VFS: brelse: Trying to free free buffer
+WARNING: CPU: 1 PID: 6913 at /root/repos/linux/fs/buffer.c:1165 .__brelse.part.6+0x24/0x40
+.__brelse.part.6+0x20/0x40 (unreliable)
+.ext4_find_entry+0x384/0x4f0
+.ext4_lookup+0x84/0x250
+.lookup_slow+0xdc/0x230
+.walk_component+0x268/0x400
+.path_lookupat+0xec/0x2d0
+.filename_lookup+0x9c/0x1d0
+.vfs_statx+0x98/0x140
+.SyS_newfstatat+0x48/0x80
+system_call+0x58/0x6c
+
+This happens because the directory that ext4_find_entry() looks up has
+inode->i_size that is less than the block size of the filesystem. This
+causes 'nblocks' to have a value of zero. ext4_bread_batch() ends up not
+reading any of the directory file's blocks. This renders the entries in
+bh_use[] array to continue to have garbage data. buffer_uptodate() on
+bh_use[0] can then return a zero value upon which brelse() function is
+invoked.
+
+This commit fixes the bug by returning -ENOENT when the directory file
+has no associated blocks.
+
+Reported-by: Abdul Haleem <abdhalee@linux.vnet.ibm.com>
+Signed-off-by: Chandan Rajendra <chandan@linux.vnet.ibm.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/ext4/namei.c |    4 ++++
+ 1 file changed, 4 insertions(+)
+
+--- a/fs/ext4/namei.c
++++ b/fs/ext4/namei.c
+@@ -1399,6 +1399,10 @@ static struct buffer_head * ext4_find_en
+                              "falling back\n"));
+       }
+       nblocks = dir->i_size >> EXT4_BLOCK_SIZE_BITS(sb);
++      if (!nblocks) {
++              ret = NULL;
++              goto cleanup_and_exit;
++      }
+       start = EXT4_I(dir)->i_dir_start_lookup;
+       if (start >= nblocks)
+               start = 0;
diff --git a/queue-4.14/ext4-fix-fdatasync-2-after-fallocate-2-operation.patch b/queue-4.14/ext4-fix-fdatasync-2-after-fallocate-2-operation.patch
new file mode 100644 (file)
index 0000000..34c13f1
--- /dev/null
@@ -0,0 +1,43 @@
+From c894aa97577e47d3066b27b32499ecf899bfa8b0 Mon Sep 17 00:00:00 2001
+From: Eryu Guan <eguan@redhat.com>
+Date: Sun, 3 Dec 2017 22:52:51 -0500
+Subject: ext4: fix fdatasync(2) after fallocate(2) operation
+
+From: Eryu Guan <eguan@redhat.com>
+
+commit c894aa97577e47d3066b27b32499ecf899bfa8b0 upstream.
+
+Currently, fallocate(2) with KEEP_SIZE followed by a fdatasync(2)
+then crash, we'll see wrong allocated block number (stat -c %b), the
+blocks allocated beyond EOF are all lost. fstests generic/468
+exposes this bug.
+
+Commit 67a7d5f561f4 ("ext4: fix fdatasync(2) after extent
+manipulation operations") fixed all the other extent manipulation
+operation paths such as hole punch, zero range, collapse range etc.,
+but forgot the fallocate case.
+
+So similarly, fix it by recording the correct journal tid in ext4
+inode in fallocate(2) path, so that ext4_sync_file() will wait for
+the right tid to be committed on fdatasync(2).
+
+This addresses the test failure in xfstests test generic/468.
+
+Signed-off-by: Eryu Guan <eguan@redhat.com>
+Signed-off-by: Theodore Ts'o <tytso@mit.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/ext4/extents.c |    1 +
+ 1 file changed, 1 insertion(+)
+
+--- a/fs/ext4/extents.c
++++ b/fs/ext4/extents.c
+@@ -4722,6 +4722,7 @@ retry:
+                                                   EXT4_INODE_EOFBLOCKS);
+               }
+               ext4_mark_inode_dirty(handle, inode);
++              ext4_update_inode_fsync_trans(handle, inode, 1);
+               ret2 = ext4_journal_stop(handle);
+               if (ret2)
+                       break;
diff --git a/queue-4.14/ext4-support-fast-symlinks-from-ext3-file-systems.patch b/queue-4.14/ext4-support-fast-symlinks-from-ext3-file-systems.patch
new file mode 100644 (file)
index 0000000..1501e5a
--- /dev/null
@@ -0,0 +1,52 @@
+From fc82228a5e3860502dbf3bfa4a9570cb7093cf7f Mon Sep 17 00:00:00 2001
+From: Andi Kleen <ak@linux.intel.com>
+Date: Sun, 3 Dec 2017 20:38:01 -0500
+Subject: ext4: support fast symlinks from ext3 file systems
+
+From: Andi Kleen <ak@linux.intel.com>
+
+commit fc82228a5e3860502dbf3bfa4a9570cb7093cf7f upstream.
+
+407cd7fb83c0 (ext4: change fast symlink test to not rely on i_blocks)
+broke ~10 years old ext3 file systems created by 2.6.17. Any ELF
+executable fails because the /lib/ld-linux.so.2 fast symlink
+cannot be read anymore.
+
+The patch assumed fast symlinks were created in a specific way,
+but that's not true on these really old file systems.
+
+The new behavior is apparently needed only with the large EA inode
+feature.
+
+Revert to the old behavior if the large EA inode feature is not set.
+
+This makes my old VM boot again.
+
+Fixes: 407cd7fb83c0 (ext4: change fast symlink test to not rely on i_blocks)
+Signed-off-by: Andi Kleen <ak@linux.intel.com>
+Signed-off-by: Theodore Ts'o <tytso@mit.edu>
+Reviewed-by: Andreas Dilger <adilger@dilger.ca>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/ext4/inode.c |    9 +++++++++
+ 1 file changed, 9 insertions(+)
+
+--- a/fs/ext4/inode.c
++++ b/fs/ext4/inode.c
+@@ -149,6 +149,15 @@ static int ext4_meta_trans_blocks(struct
+  */
+ int ext4_inode_is_fast_symlink(struct inode *inode)
+ {
++      if (!(EXT4_I(inode)->i_flags & EXT4_EA_INODE_FL)) {
++              int ea_blocks = EXT4_I(inode)->i_file_acl ?
++                              EXT4_CLUSTER_SIZE(inode->i_sb) >> 9 : 0;
++
++              if (ext4_has_inline_data(inode))
++                      return 0;
++
++              return (S_ISLNK(inode->i_mode) && inode->i_blocks - ea_blocks == 0);
++      }
+       return S_ISLNK(inode->i_mode) && inode->i_size &&
+              (inode->i_size < EXT4_N_BLOCKS * 4);
+ }
diff --git a/queue-4.14/ib-core-bound-check-alternate-path-port-number.patch b/queue-4.14/ib-core-bound-check-alternate-path-port-number.patch
new file mode 100644 (file)
index 0000000..c0bda44
--- /dev/null
@@ -0,0 +1,38 @@
+From 4cae8ff136782d77b108cb3a5ba53e60597ba3a6 Mon Sep 17 00:00:00 2001
+From: Daniel Jurgens <danielj@mellanox.com>
+Date: Tue, 5 Dec 2017 22:30:01 +0200
+Subject: IB/core: Bound check alternate path port number
+
+From: Daniel Jurgens <danielj@mellanox.com>
+
+commit 4cae8ff136782d77b108cb3a5ba53e60597ba3a6 upstream.
+
+The alternate port number is used as an array index in the IB
+security implementation, invalid values can result in a kernel panic.
+
+Fixes: d291f1a65232 ("IB/core: Enforce PKey security on QPs")
+Signed-off-by: Daniel Jurgens <danielj@mellanox.com>
+Reviewed-by: Parav Pandit <parav@mellanox.com>
+Signed-off-by: Leon Romanovsky <leon@kernel.org>
+Signed-off-by: Doug Ledford <dledford@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/infiniband/core/uverbs_cmd.c |    6 ++++++
+ 1 file changed, 6 insertions(+)
+
+--- a/drivers/infiniband/core/uverbs_cmd.c
++++ b/drivers/infiniband/core/uverbs_cmd.c
+@@ -1982,6 +1982,12 @@ static int modify_qp(struct ib_uverbs_fi
+               goto release_qp;
+       }
++      if ((cmd->base.attr_mask & IB_QP_ALT_PATH) &&
++          !rdma_is_port_valid(qp->device, cmd->base.alt_port_num)) {
++              ret = -EINVAL;
++              goto release_qp;
++      }
++
+       attr->qp_state            = cmd->base.qp_state;
+       attr->cur_qp_state        = cmd->base.cur_qp_state;
+       attr->path_mtu            = cmd->base.path_mtu;
diff --git a/queue-4.14/ib-core-don-t-enforce-pkey-security-on-smi-mads.patch b/queue-4.14/ib-core-don-t-enforce-pkey-security-on-smi-mads.patch
new file mode 100644 (file)
index 0000000..a8927ad
--- /dev/null
@@ -0,0 +1,45 @@
+From 0fbe8f575b15585eec3326e43708fbbc024e8486 Mon Sep 17 00:00:00 2001
+From: Daniel Jurgens <danielj@mellanox.com>
+Date: Tue, 5 Dec 2017 22:30:02 +0200
+Subject: IB/core: Don't enforce PKey security on SMI MADs
+
+From: Daniel Jurgens <danielj@mellanox.com>
+
+commit 0fbe8f575b15585eec3326e43708fbbc024e8486 upstream.
+
+Per the infiniband spec an SMI MAD can have any PKey. Checking the pkey
+on SMI MADs is not necessary, and it seems that some older adapters
+using the mthca driver don't follow the convention of using the default
+PKey, resulting in false denials, or errors querying the PKey cache.
+
+SMI MAD security is still enforced, only agents allowed to manage the
+subnet are able to receive or send SMI MADs.
+
+Reported-by: Chris Blake <chrisrblake93@gmail.com>
+Fixes: 47a2b338fe63 ("IB/core: Enforce security on management datagrams")
+Signed-off-by: Daniel Jurgens <danielj@mellanox.com>
+Reviewed-by: Parav Pandit <parav@mellanox.com>
+Signed-off-by: Leon Romanovsky <leon@kernel.org>
+Signed-off-by: Doug Ledford <dledford@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/infiniband/core/security.c |    7 +++++--
+ 1 file changed, 5 insertions(+), 2 deletions(-)
+
+--- a/drivers/infiniband/core/security.c
++++ b/drivers/infiniband/core/security.c
+@@ -739,8 +739,11 @@ int ib_mad_enforce_security(struct ib_ma
+       if (!rdma_protocol_ib(map->agent.device, map->agent.port_num))
+               return 0;
+-      if (map->agent.qp->qp_type == IB_QPT_SMI && !map->agent.smp_allowed)
+-              return -EACCES;
++      if (map->agent.qp->qp_type == IB_QPT_SMI) {
++              if (!map->agent.smp_allowed)
++                      return -EACCES;
++              return 0;
++      }
+       return ib_security_pkey_access(map->agent.device,
+                                      map->agent.port_num,
diff --git a/queue-4.14/iw_cxgb4-only-insert-drain-cqes-if-wq-is-flushed.patch b/queue-4.14/iw_cxgb4-only-insert-drain-cqes-if-wq-is-flushed.patch
new file mode 100644 (file)
index 0000000..76a3195
--- /dev/null
@@ -0,0 +1,75 @@
+From c058ecf6e455fac7346d46197a02398ead90851f Mon Sep 17 00:00:00 2001
+From: Steve Wise <swise@opengridcomputing.com>
+Date: Mon, 27 Nov 2017 13:16:32 -0800
+Subject: iw_cxgb4: only insert drain cqes if wq is flushed
+
+From: Steve Wise <swise@opengridcomputing.com>
+
+commit c058ecf6e455fac7346d46197a02398ead90851f upstream.
+
+Only insert our special drain CQEs to support ib_drain_sq/rq() after
+the wq is flushed. Otherwise, existing but not yet polled CQEs can be
+returned out of order to the user application.  This can happen when the
+QP has exited RTS but not yet flushed the QP, which can happen during
+a normal close (vs abortive close).
+
+In addition never count the drain CQEs when determining how many CQEs
+need to be synthesized during the flush operation.  This latter issue
+should never happen if the QP is properly flushed before inserting the
+drain CQE, but I wanted to avoid corrupting the CQ state.  So we handle
+it and log a warning once.
+
+Fixes: 4fe7c2962e11 ("iw_cxgb4: refactor sq/rq drain logic")
+Signed-off-by: Steve Wise <swise@opengridcomputing.com>
+Signed-off-by: Jason Gunthorpe <jgg@mellanox.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/infiniband/hw/cxgb4/cq.c |    5 +++++
+ drivers/infiniband/hw/cxgb4/qp.c |   14 ++++++++++++--
+ 2 files changed, 17 insertions(+), 2 deletions(-)
+
+--- a/drivers/infiniband/hw/cxgb4/cq.c
++++ b/drivers/infiniband/hw/cxgb4/cq.c
+@@ -410,6 +410,11 @@ next_cqe:
+ static int cqe_completes_wr(struct t4_cqe *cqe, struct t4_wq *wq)
+ {
++      if (CQE_OPCODE(cqe) == C4IW_DRAIN_OPCODE) {
++              WARN_ONCE(1, "Unexpected DRAIN CQE qp id %u!\n", wq->sq.qid);
++              return 0;
++      }
++
+       if (CQE_OPCODE(cqe) == FW_RI_TERMINATE)
+               return 0;
+--- a/drivers/infiniband/hw/cxgb4/qp.c
++++ b/drivers/infiniband/hw/cxgb4/qp.c
+@@ -868,7 +868,12 @@ int c4iw_post_send(struct ib_qp *ibqp, s
+       qhp = to_c4iw_qp(ibqp);
+       spin_lock_irqsave(&qhp->lock, flag);
+-      if (t4_wq_in_error(&qhp->wq)) {
++
++      /*
++       * If the qp has been flushed, then just insert a special
++       * drain cqe.
++       */
++      if (qhp->wq.flushed) {
+               spin_unlock_irqrestore(&qhp->lock, flag);
+               complete_sq_drain_wr(qhp, wr);
+               return err;
+@@ -1012,7 +1017,12 @@ int c4iw_post_receive(struct ib_qp *ibqp
+       qhp = to_c4iw_qp(ibqp);
+       spin_lock_irqsave(&qhp->lock, flag);
+-      if (t4_wq_in_error(&qhp->wq)) {
++
++      /*
++       * If the qp has been flushed, then just insert a special
++       * drain cqe.
++       */
++      if (qhp->wq.flushed) {
+               spin_unlock_irqrestore(&qhp->lock, flag);
+               complete_rq_drain_wr(qhp, wr);
+               return err;
diff --git a/queue-4.14/kernel-make-groups_sort-calling-a-responsibility-group_info-allocators.patch b/queue-4.14/kernel-make-groups_sort-calling-a-responsibility-group_info-allocators.patch
new file mode 100644 (file)
index 0000000..6de8807
--- /dev/null
@@ -0,0 +1,153 @@
+From bdcf0a423ea1c40bbb40e7ee483b50fc8aa3d758 Mon Sep 17 00:00:00 2001
+From: Thiago Rafael Becker <thiago.becker@gmail.com>
+Date: Thu, 14 Dec 2017 15:33:12 -0800
+Subject: kernel: make groups_sort calling a responsibility group_info allocators
+
+From: Thiago Rafael Becker <thiago.becker@gmail.com>
+
+commit bdcf0a423ea1c40bbb40e7ee483b50fc8aa3d758 upstream.
+
+In testing, we found that nfsd threads may call set_groups in parallel
+for the same entry cached in auth.unix.gid, racing in the call of
+groups_sort, corrupting the groups for that entry and leading to
+permission denials for the client.
+
+This patch:
+ - Make groups_sort globally visible.
+ - Move the call to groups_sort to the modifiers of group_info
+ - Remove the call to groups_sort from set_groups
+
+Link: http://lkml.kernel.org/r/20171211151420.18655-1-thiago.becker@gmail.com
+Signed-off-by: Thiago Rafael Becker <thiago.becker@gmail.com>
+Reviewed-by: Matthew Wilcox <mawilcox@microsoft.com>
+Reviewed-by: NeilBrown <neilb@suse.com>
+Acked-by: "J. Bruce Fields" <bfields@fieldses.org>
+Cc: Al Viro <viro@zeniv.linux.org.uk>
+Cc: Martin Schwidefsky <schwidefsky@de.ibm.com>
+Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
+Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/s390/kernel/compat_linux.c   |    1 +
+ fs/nfsd/auth.c                    |    3 +++
+ include/linux/cred.h              |    1 +
+ kernel/groups.c                   |    5 +++--
+ kernel/uid16.c                    |    1 +
+ net/sunrpc/auth_gss/gss_rpc_xdr.c |    1 +
+ net/sunrpc/auth_gss/svcauth_gss.c |    1 +
+ net/sunrpc/svcauth_unix.c         |    2 ++
+ 8 files changed, 13 insertions(+), 2 deletions(-)
+
+--- a/arch/s390/kernel/compat_linux.c
++++ b/arch/s390/kernel/compat_linux.c
+@@ -263,6 +263,7 @@ COMPAT_SYSCALL_DEFINE2(s390_setgroups16,
+               return retval;
+       }
++      groups_sort(group_info);
+       retval = set_current_groups(group_info);
+       put_group_info(group_info);
+--- a/fs/nfsd/auth.c
++++ b/fs/nfsd/auth.c
+@@ -60,6 +60,9 @@ int nfsd_setuser(struct svc_rqst *rqstp,
+                               gi->gid[i] = exp->ex_anon_gid;
+                       else
+                               gi->gid[i] = rqgi->gid[i];
++
++                      /* Each thread allocates its own gi, no race */
++                      groups_sort(gi);
+               }
+       } else {
+               gi = get_group_info(rqgi);
+--- a/include/linux/cred.h
++++ b/include/linux/cred.h
+@@ -83,6 +83,7 @@ extern int set_current_groups(struct gro
+ extern void set_groups(struct cred *, struct group_info *);
+ extern int groups_search(const struct group_info *, kgid_t);
+ extern bool may_setgroups(void);
++extern void groups_sort(struct group_info *);
+ /*
+  * The security context of a task
+--- a/kernel/groups.c
++++ b/kernel/groups.c
+@@ -86,11 +86,12 @@ static int gid_cmp(const void *_a, const
+       return gid_gt(a, b) - gid_lt(a, b);
+ }
+-static void groups_sort(struct group_info *group_info)
++void groups_sort(struct group_info *group_info)
+ {
+       sort(group_info->gid, group_info->ngroups, sizeof(*group_info->gid),
+            gid_cmp, NULL);
+ }
++EXPORT_SYMBOL(groups_sort);
+ /* a simple bsearch */
+ int groups_search(const struct group_info *group_info, kgid_t grp)
+@@ -122,7 +123,6 @@ int groups_search(const struct group_inf
+ void set_groups(struct cred *new, struct group_info *group_info)
+ {
+       put_group_info(new->group_info);
+-      groups_sort(group_info);
+       get_group_info(group_info);
+       new->group_info = group_info;
+ }
+@@ -206,6 +206,7 @@ SYSCALL_DEFINE2(setgroups, int, gidsetsi
+               return retval;
+       }
++      groups_sort(group_info);
+       retval = set_current_groups(group_info);
+       put_group_info(group_info);
+--- a/kernel/uid16.c
++++ b/kernel/uid16.c
+@@ -192,6 +192,7 @@ SYSCALL_DEFINE2(setgroups16, int, gidset
+               return retval;
+       }
++      groups_sort(group_info);
+       retval = set_current_groups(group_info);
+       put_group_info(group_info);
+--- a/net/sunrpc/auth_gss/gss_rpc_xdr.c
++++ b/net/sunrpc/auth_gss/gss_rpc_xdr.c
+@@ -231,6 +231,7 @@ static int gssx_dec_linux_creds(struct x
+                       goto out_free_groups;
+               creds->cr_group_info->gid[i] = kgid;
+       }
++      groups_sort(creds->cr_group_info);
+       return 0;
+ out_free_groups:
+--- a/net/sunrpc/auth_gss/svcauth_gss.c
++++ b/net/sunrpc/auth_gss/svcauth_gss.c
+@@ -481,6 +481,7 @@ static int rsc_parse(struct cache_detail
+                               goto out;
+                       rsci.cred.cr_group_info->gid[i] = kgid;
+               }
++              groups_sort(rsci.cred.cr_group_info);
+               /* mech name */
+               len = qword_get(&mesg, buf, mlen);
+--- a/net/sunrpc/svcauth_unix.c
++++ b/net/sunrpc/svcauth_unix.c
+@@ -520,6 +520,7 @@ static int unix_gid_parse(struct cache_d
+               ug.gi->gid[i] = kgid;
+       }
++      groups_sort(ug.gi);
+       ugp = unix_gid_lookup(cd, uid);
+       if (ugp) {
+               struct cache_head *ch;
+@@ -819,6 +820,7 @@ svcauth_unix_accept(struct svc_rqst *rqs
+               kgid_t kgid = make_kgid(&init_user_ns, svc_getnl(argv));
+               cred->cr_group_info->gid[i] = kgid;
+       }
++      groups_sort(cred->cr_group_info);
+       if (svc_getu32(argv) != htonl(RPC_AUTH_NULL) || svc_getu32(argv) != 0) {
+               *authp = rpc_autherr_badverf;
+               return SVC_DENIED;
diff --git a/queue-4.14/mm-oom_reaper-fix-memory-corruption.patch b/queue-4.14/mm-oom_reaper-fix-memory-corruption.patch
new file mode 100644 (file)
index 0000000..ecc15ff
--- /dev/null
@@ -0,0 +1,137 @@
+From 4837fe37adff1d159904f0c013471b1ecbcb455e Mon Sep 17 00:00:00 2001
+From: Michal Hocko <mhocko@suse.com>
+Date: Thu, 14 Dec 2017 15:33:15 -0800
+Subject: mm, oom_reaper: fix memory corruption
+
+From: Michal Hocko <mhocko@suse.com>
+
+commit 4837fe37adff1d159904f0c013471b1ecbcb455e upstream.
+
+David Rientjes has reported the following memory corruption while the
+oom reaper tries to unmap the victims address space
+
+  BUG: Bad page map in process oom_reaper  pte:6353826300000000 pmd:00000000
+  addr:00007f50cab1d000 vm_flags:08100073 anon_vma:ffff9eea335603f0 mapping:          (null) index:7f50cab1d
+  file:          (null) fault:          (null) mmap:          (null) readpage:          (null)
+  CPU: 2 PID: 1001 Comm: oom_reaper
+  Call Trace:
+     unmap_page_range+0x1068/0x1130
+     __oom_reap_task_mm+0xd5/0x16b
+     oom_reaper+0xff/0x14c
+     kthread+0xc1/0xe0
+
+Tetsuo Handa has noticed that the synchronization inside exit_mmap is
+insufficient.  We only synchronize with the oom reaper if
+tsk_is_oom_victim which is not true if the final __mmput is called from
+a different context than the oom victim exit path.  This can trivially
+happen from context of any task which has grabbed mm reference (e.g.  to
+read /proc/<pid>/ file which requires mm etc.).
+
+The race would look like this
+
+  oom_reaper           oom_victim              task
+                                               mmget_not_zero
+                       do_exit
+                         mmput
+  __oom_reap_task_mm                           mmput
+                                                 __mmput
+                                                   exit_mmap
+                                                     remove_vma
+    unmap_page_range
+
+Fix this issue by providing a new mm_is_oom_victim() helper which
+operates on the mm struct rather than a task.  Any context which
+operates on a remote mm struct should use this helper in place of
+tsk_is_oom_victim.  The flag is set in mark_oom_victim and never cleared
+so it is stable in the exit_mmap path.
+
+Debugged by Tetsuo Handa.
+
+Link: http://lkml.kernel.org/r/20171210095130.17110-1-mhocko@kernel.org
+Fixes: 212925802454 ("mm: oom: let oom_reap_task and exit_mmap run concurrently")
+Signed-off-by: Michal Hocko <mhocko@suse.com>
+Reported-by: David Rientjes <rientjes@google.com>
+Acked-by: David Rientjes <rientjes@google.com>
+Cc: Tetsuo Handa <penguin-kernel@I-love.SAKURA.ne.jp>
+Cc: Andrea Argangeli <andrea@kernel.org>
+Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
+Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ include/linux/oom.h            |    9 +++++++++
+ include/linux/sched/coredump.h |    1 +
+ mm/mmap.c                      |   10 +++++-----
+ mm/oom_kill.c                  |    4 +++-
+ 4 files changed, 18 insertions(+), 6 deletions(-)
+
+--- a/include/linux/oom.h
++++ b/include/linux/oom.h
+@@ -67,6 +67,15 @@ static inline bool tsk_is_oom_victim(str
+ }
+ /*
++ * Use this helper if tsk->mm != mm and the victim mm needs a special
++ * handling. This is guaranteed to stay true after once set.
++ */
++static inline bool mm_is_oom_victim(struct mm_struct *mm)
++{
++      return test_bit(MMF_OOM_VICTIM, &mm->flags);
++}
++
++/*
+  * Checks whether a page fault on the given mm is still reliable.
+  * This is no longer true if the oom reaper started to reap the
+  * address space which is reflected by MMF_UNSTABLE flag set in
+--- a/include/linux/sched/coredump.h
++++ b/include/linux/sched/coredump.h
+@@ -70,6 +70,7 @@ static inline int get_dumpable(struct mm
+ #define MMF_UNSTABLE          22      /* mm is unstable for copy_from_user */
+ #define MMF_HUGE_ZERO_PAGE    23      /* mm has ever used the global huge zero page */
+ #define MMF_DISABLE_THP               24      /* disable THP for all VMAs */
++#define MMF_OOM_VICTIM                25      /* mm is the oom victim */
+ #define MMF_DISABLE_THP_MASK  (1 << MMF_DISABLE_THP)
+ #define MMF_INIT_MASK         (MMF_DUMPABLE_MASK | MMF_DUMP_FILTER_MASK |\
+--- a/mm/mmap.c
++++ b/mm/mmap.c
+@@ -3004,20 +3004,20 @@ void exit_mmap(struct mm_struct *mm)
+       /* Use -1 here to ensure all VMAs in the mm are unmapped */
+       unmap_vmas(&tlb, vma, 0, -1);
+-      set_bit(MMF_OOM_SKIP, &mm->flags);
+-      if (unlikely(tsk_is_oom_victim(current))) {
++      if (unlikely(mm_is_oom_victim(mm))) {
+               /*
+                * Wait for oom_reap_task() to stop working on this
+                * mm. Because MMF_OOM_SKIP is already set before
+                * calling down_read(), oom_reap_task() will not run
+                * on this "mm" post up_write().
+                *
+-               * tsk_is_oom_victim() cannot be set from under us
+-               * either because current->mm is already set to NULL
++               * mm_is_oom_victim() cannot be set from under us
++               * either because victim->mm is already set to NULL
+                * under task_lock before calling mmput and oom_mm is
+-               * set not NULL by the OOM killer only if current->mm
++               * set not NULL by the OOM killer only if victim->mm
+                * is found not NULL while holding the task_lock.
+                */
++              set_bit(MMF_OOM_SKIP, &mm->flags);
+               down_write(&mm->mmap_sem);
+               up_write(&mm->mmap_sem);
+       }
+--- a/mm/oom_kill.c
++++ b/mm/oom_kill.c
+@@ -673,8 +673,10 @@ static void mark_oom_victim(struct task_
+               return;
+       /* oom_mm is bound to the signal struct life time. */
+-      if (!cmpxchg(&tsk->signal->oom_mm, NULL, mm))
++      if (!cmpxchg(&tsk->signal->oom_mm, NULL, mm)) {
+               mmgrab(tsk->signal->oom_mm);
++              set_bit(MMF_OOM_VICTIM, &mm->flags);
++      }
+       /*
+        * Make sure that the task is woken up from uninterruptible sleep
diff --git a/queue-4.14/mmc-core-apply-no_cmd23-quirk-to-some-specific-cards.patch b/queue-4.14/mmc-core-apply-no_cmd23-quirk-to-some-specific-cards.patch
new file mode 100644 (file)
index 0000000..b1348b2
--- /dev/null
@@ -0,0 +1,76 @@
+From 91516a2a4734614d62ee3ed921f8f88acc67c000 Mon Sep 17 00:00:00 2001
+From: Christoph Fritz <chf.fritz@googlemail.com>
+Date: Sat, 9 Dec 2017 23:47:55 +0100
+Subject: mmc: core: apply NO_CMD23 quirk to some specific cards
+
+From: Christoph Fritz <chf.fritz@googlemail.com>
+
+commit 91516a2a4734614d62ee3ed921f8f88acc67c000 upstream.
+
+To get an usdhc Apacer and some ATP SD cards work reliable, CMD23 needs
+to be disabled.  This has been tested on i.MX6 (sdhci-esdhc) and rk3288
+(dw_mmc-rockchip).
+
+Without this patch on i.MX6 (sdhci-esdhc):
+
+ $ dd if=/dev/urandom of=/mnt/test bs=1M count=10 conv=fsync
+
+    | <mmc0: starting CMD23 arg 00000400 flags 00000015>
+    | mmc0: starting CMD25 arg 00a71f00 flags 000000b5
+    | mmc0:     blksz 512 blocks 1024 flags 00000100 tsac 3000 ms nsac 0
+    | mmc0:     CMD12 arg 00000000 flags 0000049d
+    | sdhci [sdhci_irq()]: *** mmc0 got interrupt: 0x00000001
+    | mmc0: Timeout waiting for hardware interrupt.
+
+Without this patch on rk3288 (dw_mmc-rockchip):
+
+    | mmc1: Card stuck in programming state! mmcblk1 card_busy_detect
+    | dwmmc_rockchip ff0c0000.dwmmc: Busy; trying anyway
+    | mmc_host mmc1: Bus speed (slot 0) = 400000Hz (slot req 400000Hz,
+    | actual 400000HZ div = 0)
+    | mmc1: card never left busy state
+    | mmc1: tried to reset card, got error -110
+    | blk_update_request: I/O error, dev mmcblk1, sector 139778
+    | Buffer I/O error on dev mmcblk1p1, logical block 131586, lost async
+    | page write
+
+Signed-off-by: Christoph Fritz <chf.fritz@googlemail.com>
+Signed-off-by: Ulf Hansson <ulf.hansson@linaro.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/mmc/core/card.h   |    2 ++
+ drivers/mmc/core/quirks.h |    8 ++++++++
+ 2 files changed, 10 insertions(+)
+
+--- a/drivers/mmc/core/card.h
++++ b/drivers/mmc/core/card.h
+@@ -75,9 +75,11 @@ struct mmc_fixup {
+ #define EXT_CSD_REV_ANY (-1u)
+ #define CID_MANFID_SANDISK      0x2
++#define CID_MANFID_ATP          0x9
+ #define CID_MANFID_TOSHIBA      0x11
+ #define CID_MANFID_MICRON       0x13
+ #define CID_MANFID_SAMSUNG      0x15
++#define CID_MANFID_APACER       0x27
+ #define CID_MANFID_KINGSTON     0x70
+ #define CID_MANFID_HYNIX      0x90
+--- a/drivers/mmc/core/quirks.h
++++ b/drivers/mmc/core/quirks.h
+@@ -53,6 +53,14 @@ static const struct mmc_fixup mmc_blk_fi
+                 MMC_QUIRK_BLK_NO_CMD23),
+       /*
++       * Some SD cards lockup while using CMD23 multiblock transfers.
++       */
++      MMC_FIXUP("AF SD", CID_MANFID_ATP, CID_OEMID_ANY, add_quirk_sd,
++                MMC_QUIRK_BLK_NO_CMD23),
++      MMC_FIXUP("APUSD", CID_MANFID_APACER, 0x5048, add_quirk_sd,
++                MMC_QUIRK_BLK_NO_CMD23),
++
++      /*
+        * Some MMC cards need longer data read timeout than indicated in CSD.
+        */
+       MMC_FIXUP(CID_NAME_ANY, CID_MANFID_MICRON, 0x200, add_quirk_mmc,
diff --git a/queue-4.14/nfs-don-t-wait-on-commit-in-nfs_commit_inode-if-there-were-no-commit-requests.patch b/queue-4.14/nfs-don-t-wait-on-commit-in-nfs_commit_inode-if-there-were-no-commit-requests.patch
new file mode 100644 (file)
index 0000000..9815bc8
--- /dev/null
@@ -0,0 +1,66 @@
+From dc4fd9ab01ab379ae5af522b3efd4187a7c30a31 Mon Sep 17 00:00:00 2001
+From: Scott Mayhew <smayhew@redhat.com>
+Date: Fri, 8 Dec 2017 16:00:12 -0500
+Subject: nfs: don't wait on commit in nfs_commit_inode() if there were no commit requests
+
+From: Scott Mayhew <smayhew@redhat.com>
+
+commit dc4fd9ab01ab379ae5af522b3efd4187a7c30a31 upstream.
+
+If there were no commit requests, then nfs_commit_inode() should not
+wait on the commit or mark the inode dirty, otherwise the following
+BUG_ON can be triggered:
+
+[ 1917.130762] kernel BUG at fs/inode.c:578!
+[ 1917.130766] Oops: Exception in kernel mode, sig: 5 [#1]
+[ 1917.130768] SMP NR_CPUS=2048 NUMA pSeries
+[ 1917.130772] Modules linked in: iscsi_tcp libiscsi_tcp libiscsi scsi_transport_iscsi blocklayoutdriver rpcsec_gss_krb5 auth_rpcgss nfsv4 dns_resolver nfs lockd grace fscache sunrpc sg nx_crypto pseries_rng ip_tables xfs libcrc32c sd_mod crc_t10dif crct10dif_generic crct10dif_common ibmvscsi scsi_transport_srp ibmveth scsi_tgt dm_mirror dm_region_hash dm_log dm_mod
+[ 1917.130805] CPU: 2 PID: 14923 Comm: umount.nfs4 Tainted: G               ------------ T 3.10.0-768.el7.ppc64 #1
+[ 1917.130810] task: c0000005ecd88040 ti: c00000004cea0000 task.ti: c00000004cea0000
+[ 1917.130813] NIP: c000000000354178 LR: c000000000354160 CTR: c00000000012db80
+[ 1917.130816] REGS: c00000004cea3720 TRAP: 0700   Tainted: G               ------------ T  (3.10.0-768.el7.ppc64)
+[ 1917.130820] MSR: 8000000100029032 <SF,EE,ME,IR,DR,RI>  CR: 22002822  XER: 20000000
+[ 1917.130828] CFAR: c00000000011f594 SOFTE: 1
+GPR00: c000000000354160 c00000004cea39a0 c0000000014c4700 c0000000018cc750
+GPR04: 000000000000c750 80c0000000000000 0600000000000000 04eeb76bea749a03
+GPR08: 0000000000000034 c0000000018cc758 0000000000000001 d000000005e619e8
+GPR12: c00000000012db80 c000000007b31200 0000000000000000 0000000000000000
+GPR16: 0000000000000000 0000000000000000 0000000000000000 0000000000000000
+GPR20: 0000000000000000 0000000000000000 0000000000000000 0000000000000000
+GPR24: 0000000000000000 c000000000dfc3ec 0000000000000000 c0000005eefc02c0
+GPR28: d0000000079dbd50 c0000005b94a02c0 c0000005b94a0250 c0000005b94a01c8
+[ 1917.130867] NIP [c000000000354178] .evict+0x1c8/0x350
+[ 1917.130871] LR [c000000000354160] .evict+0x1b0/0x350
+[ 1917.130873] Call Trace:
+[ 1917.130876] [c00000004cea39a0] [c000000000354160] .evict+0x1b0/0x350 (unreliable)
+[ 1917.130880] [c00000004cea3a30] [c0000000003558cc] .evict_inodes+0x13c/0x270
+[ 1917.130884] [c00000004cea3af0] [c000000000327d20] .kill_anon_super+0x70/0x1e0
+[ 1917.130896] [c00000004cea3b80] [d000000005e43e30] .nfs_kill_super+0x20/0x60 [nfs]
+[ 1917.130900] [c00000004cea3c00] [c000000000328a20] .deactivate_locked_super+0xa0/0x1b0
+[ 1917.130903] [c00000004cea3c80] [c00000000035ba54] .cleanup_mnt+0xd4/0x180
+[ 1917.130907] [c00000004cea3d10] [c000000000119034] .task_work_run+0x114/0x150
+[ 1917.130912] [c00000004cea3db0] [c00000000001ba6c] .do_notify_resume+0xcc/0x100
+[ 1917.130916] [c00000004cea3e30] [c00000000000a7b0] .ret_from_except_lite+0x5c/0x60
+[ 1917.130919] Instruction dump:
+[ 1917.130921] 7fc3f378 486734b5 60000000 387f00a0 38800003 4bdcb365 60000000 e95f00a0
+[ 1917.130927] 694a0060 7d4a0074 794ad182 694a0001 <0b0a0000> 892d02a4 2f890000 40de0134
+
+Signed-off-by: Scott Mayhew <smayhew@redhat.com>
+Signed-off-by: Anna Schumaker <Anna.Schumaker@Netapp.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/nfs/write.c |    2 ++
+ 1 file changed, 2 insertions(+)
+
+--- a/fs/nfs/write.c
++++ b/fs/nfs/write.c
+@@ -1889,6 +1889,8 @@ int nfs_commit_inode(struct inode *inode
+       if (res)
+               error = nfs_generic_commit_list(inode, &head, how, &cinfo);
+       nfs_commit_end(cinfo.mds);
++      if (res == 0)
++              return res;
+       if (error < 0)
+               goto out_error;
+       if (!may_wait)
diff --git a/queue-4.14/ovl-pass-ovl_get_nlink-parameters-in-right-order.patch b/queue-4.14/ovl-pass-ovl_get_nlink-parameters-in-right-order.patch
new file mode 100644 (file)
index 0000000..d393e8b
--- /dev/null
@@ -0,0 +1,34 @@
+From 08d8f8a5b094b66b29936e8751b4a818b8db1207 Mon Sep 17 00:00:00 2001
+From: Vivek Goyal <vgoyal@redhat.com>
+Date: Mon, 27 Nov 2017 10:12:44 -0500
+Subject: ovl: Pass ovl_get_nlink() parameters in right order
+
+From: Vivek Goyal <vgoyal@redhat.com>
+
+commit 08d8f8a5b094b66b29936e8751b4a818b8db1207 upstream.
+
+Right now we seem to be passing index as "lowerdentry" and origin.dentry
+as "upperdentry". IIUC, we should pass these parameters in reversed order
+and this looks like a bug.
+
+Signed-off-by: Vivek Goyal <vgoyal@redhat.com>
+Acked-by: Amir Goldstein <amir73il@gmail.com>
+Fixes: caf70cb2ba5d ("ovl: cleanup orphan index entries")
+Signed-off-by: Miklos Szeredi <mszeredi@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/overlayfs/namei.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/fs/overlayfs/namei.c
++++ b/fs/overlayfs/namei.c
+@@ -437,7 +437,7 @@ int ovl_verify_index(struct dentry *inde
+       /* Check if index is orphan and don't warn before cleaning it */
+       if (d_inode(index)->i_nlink == 1 &&
+-          ovl_get_nlink(index, origin.dentry, 0) == 0)
++          ovl_get_nlink(origin.dentry, index, 0) == 0)
+               err = -ENOENT;
+       dput(origin.dentry);
diff --git a/queue-4.14/ovl-update-ctx-pos-on-impure-dir-iteration.patch b/queue-4.14/ovl-update-ctx-pos-on-impure-dir-iteration.patch
new file mode 100644 (file)
index 0000000..7f60425
--- /dev/null
@@ -0,0 +1,37 @@
+From b02a16e6413a2f782e542ef60bad9ff6bf212f8a Mon Sep 17 00:00:00 2001
+From: Amir Goldstein <amir73il@gmail.com>
+Date: Wed, 29 Nov 2017 07:35:21 +0200
+Subject: ovl: update ctx->pos on impure dir iteration
+
+From: Amir Goldstein <amir73il@gmail.com>
+
+commit b02a16e6413a2f782e542ef60bad9ff6bf212f8a upstream.
+
+This fixes a regression with readdir of impure dir in overlayfs
+that is shared to VM via 9p fs.
+
+Reported-by: Miguel Bernal Marin <miguel.bernal.marin@linux.intel.com>
+Fixes: 4edb83bb1041 ("ovl: constant d_ino for non-merge dirs")
+Signed-off-by: Amir Goldstein <amir73il@gmail.com>
+Tested-by: Miguel Bernal Marin <miguel.bernal.marin@linux.intel.com>
+Signed-off-by: Miklos Szeredi <mszeredi@redhat.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/overlayfs/readdir.c |    5 ++++-
+ 1 file changed, 4 insertions(+), 1 deletion(-)
+
+--- a/fs/overlayfs/readdir.c
++++ b/fs/overlayfs/readdir.c
+@@ -645,7 +645,10 @@ static int ovl_iterate_real(struct file
+                       return PTR_ERR(rdt.cache);
+       }
+-      return iterate_dir(od->realfile, &rdt.ctx);
++      err = iterate_dir(od->realfile, &rdt.ctx);
++      ctx->pos = rdt.ctx.pos;
++
++      return err;
+ }
diff --git a/queue-4.14/posix-timer-properly-check-sigevent-sigev_notify.patch b/queue-4.14/posix-timer-properly-check-sigevent-sigev_notify.patch
new file mode 100644 (file)
index 0000000..14ba545
--- /dev/null
@@ -0,0 +1,91 @@
+From cef31d9af908243421258f1df35a4a644604efbe Mon Sep 17 00:00:00 2001
+From: Thomas Gleixner <tglx@linutronix.de>
+Date: Fri, 15 Dec 2017 10:32:03 +0100
+Subject: posix-timer: Properly check sigevent->sigev_notify
+
+From: Thomas Gleixner <tglx@linutronix.de>
+
+commit cef31d9af908243421258f1df35a4a644604efbe upstream.
+
+timer_create() specifies via sigevent->sigev_notify the signal delivery for
+the new timer. The valid modes are SIGEV_NONE, SIGEV_SIGNAL, SIGEV_THREAD
+and (SIGEV_SIGNAL | SIGEV_THREAD_ID).
+
+The sanity check in good_sigevent() is only checking the valid combination
+for the SIGEV_THREAD_ID bit, i.e. SIGEV_SIGNAL, but if SIGEV_THREAD_ID is
+not set it accepts any random value.
+
+This has no real effects on the posix timer and signal delivery code, but
+it affects show_timer() which handles the output of /proc/$PID/timers. That
+function uses a string array to pretty print sigev_notify. The access to
+that array has no bound checks, so random sigev_notify cause access beyond
+the array bounds.
+
+Add proper checks for the valid notify modes and remove the SIGEV_THREAD_ID
+masking from various code pathes as SIGEV_NONE can never be set in
+combination with SIGEV_THREAD_ID.
+
+Reported-by: Eric Biggers <ebiggers3@gmail.com>
+Reported-by: Dmitry Vyukov <dvyukov@google.com>
+Reported-by: Alexey Dobriyan <adobriyan@gmail.com>
+Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
+Cc: John Stultz <john.stultz@linaro.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ kernel/time/posix-timers.c |   29 +++++++++++++++++------------
+ 1 file changed, 17 insertions(+), 12 deletions(-)
+
+--- a/kernel/time/posix-timers.c
++++ b/kernel/time/posix-timers.c
+@@ -434,17 +434,22 @@ static struct pid *good_sigevent(sigeven
+ {
+       struct task_struct *rtn = current->group_leader;
+-      if ((event->sigev_notify & SIGEV_THREAD_ID ) &&
+-              (!(rtn = find_task_by_vpid(event->sigev_notify_thread_id)) ||
+-               !same_thread_group(rtn, current) ||
+-               (event->sigev_notify & ~SIGEV_THREAD_ID) != SIGEV_SIGNAL))
++      switch (event->sigev_notify) {
++      case SIGEV_SIGNAL | SIGEV_THREAD_ID:
++              rtn = find_task_by_vpid(event->sigev_notify_thread_id);
++              if (!rtn || !same_thread_group(rtn, current))
++                      return NULL;
++              /* FALLTHRU */
++      case SIGEV_SIGNAL:
++      case SIGEV_THREAD:
++              if (event->sigev_signo <= 0 || event->sigev_signo > SIGRTMAX)
++                      return NULL;
++              /* FALLTHRU */
++      case SIGEV_NONE:
++              return task_pid(rtn);
++      default:
+               return NULL;
+-
+-      if (((event->sigev_notify & ~SIGEV_THREAD_ID) != SIGEV_NONE) &&
+-          ((event->sigev_signo <= 0) || (event->sigev_signo > SIGRTMAX)))
+-              return NULL;
+-
+-      return task_pid(rtn);
++      }
+ }
+ static struct k_itimer * alloc_posix_timer(void)
+@@ -669,7 +674,7 @@ void common_timer_get(struct k_itimer *t
+       struct timespec64 ts64;
+       bool sig_none;
+-      sig_none = (timr->it_sigev_notify & ~SIGEV_THREAD_ID) == SIGEV_NONE;
++      sig_none = timr->it_sigev_notify == SIGEV_NONE;
+       iv = timr->it_interval;
+       /* interval timer ? */
+@@ -856,7 +861,7 @@ int common_timer_set(struct k_itimer *ti
+       timr->it_interval = timespec64_to_ktime(new_setting->it_interval);
+       expires = timespec64_to_ktime(new_setting->it_value);
+-      sigev_none = (timr->it_sigev_notify & ~SIGEV_THREAD_ID) == SIGEV_NONE;
++      sigev_none = timr->it_sigev_notify == SIGEV_NONE;
+       kc->timer_arm(timr, expires, flags & TIMER_ABSTIME, sigev_none);
+       timr->it_active = !sigev_none;
diff --git a/queue-4.14/revert-exec-avoid-rlimit_stack-races-with-prlimit.patch b/queue-4.14/revert-exec-avoid-rlimit_stack-races-with-prlimit.patch
new file mode 100644 (file)
index 0000000..2e2f080
--- /dev/null
@@ -0,0 +1,48 @@
+From 779f4e1c6c7c661db40dfebd6dd6bda7b5f88aa3 Mon Sep 17 00:00:00 2001
+From: Kees Cook <keescook@chromium.org>
+Date: Tue, 12 Dec 2017 11:28:38 -0800
+Subject: Revert "exec: avoid RLIMIT_STACK races with prlimit()"
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Kees Cook <keescook@chromium.org>
+
+commit 779f4e1c6c7c661db40dfebd6dd6bda7b5f88aa3 upstream.
+
+This reverts commit 04e35f4495dd560db30c25efca4eecae8ec8c375.
+
+SELinux runs with secureexec for all non-"noatsecure" domain transitions,
+which means lots of processes end up hitting the stack hard-limit change
+that was introduced in order to fix a race with prlimit(). That race fix
+will need to be redesigned.
+
+Reported-by: Laura Abbott <labbott@redhat.com>
+Reported-by: Tomáš Trnka <trnka@scm.com>
+Signed-off-by: Kees Cook <keescook@chromium.org>
+Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ fs/exec.c |    7 +------
+ 1 file changed, 1 insertion(+), 6 deletions(-)
+
+--- a/fs/exec.c
++++ b/fs/exec.c
+@@ -1340,15 +1340,10 @@ void setup_new_exec(struct linux_binprm
+                * avoid bad behavior from the prior rlimits. This has to
+                * happen before arch_pick_mmap_layout(), which examines
+                * RLIMIT_STACK, but after the point of no return to avoid
+-               * races from other threads changing the limits. This also
+-               * must be protected from races with prlimit() calls.
++               * needing to clean up the change on failure.
+                */
+-              task_lock(current->group_leader);
+               if (current->signal->rlim[RLIMIT_STACK].rlim_cur > _STK_LIM)
+                       current->signal->rlim[RLIMIT_STACK].rlim_cur = _STK_LIM;
+-              if (current->signal->rlim[RLIMIT_STACK].rlim_max > _STK_LIM)
+-                      current->signal->rlim[RLIMIT_STACK].rlim_max = _STK_LIM;
+-              task_unlock(current->group_leader);
+       }
+       arch_pick_mmap_layout(current->mm);
diff --git a/queue-4.14/sched-rt-do-not-pull-from-current-cpu-if-only-one-cpu-to-pull.patch b/queue-4.14/sched-rt-do-not-pull-from-current-cpu-if-only-one-cpu-to-pull.patch
new file mode 100644 (file)
index 0000000..2668ebd
--- /dev/null
@@ -0,0 +1,82 @@
+From f73c52a5bcd1710994e53fbccc378c42b97a06b6 Mon Sep 17 00:00:00 2001
+From: Steven Rostedt <rostedt@goodmis.org>
+Date: Sat, 2 Dec 2017 13:04:54 -0500
+Subject: sched/rt: Do not pull from current CPU if only one CPU to pull
+
+From: Steven Rostedt <rostedt@goodmis.org>
+
+commit f73c52a5bcd1710994e53fbccc378c42b97a06b6 upstream.
+
+Daniel Wagner reported a crash on the BeagleBone Black SoC.
+
+This is a single CPU architecture, and does not have a functional
+arch_send_call_function_single_ipi() implementation which can crash
+the kernel if that is called.
+
+As it only has one CPU, it shouldn't be called, but if the kernel is
+compiled for SMP, the push/pull RT scheduling logic now calls it for
+irq_work if the one CPU is overloaded, it can use that function to call
+itself and crash the kernel.
+
+Ideally, we should disable the SCHED_FEAT(RT_PUSH_IPI) if the system
+only has a single CPU. But SCHED_FEAT is a constant if sched debugging
+is turned off. Another fix can also be used, and this should also help
+with normal SMP machines. That is, do not initiate the pull code if
+there's only one RT overloaded CPU, and that CPU happens to be the
+current CPU that is scheduling in a lower priority task.
+
+Even on a system with many CPUs, if there's many RT tasks waiting to
+run on a single CPU, and that CPU schedules in another RT task of lower
+priority, it will initiate the PULL logic in case there's a higher
+priority RT task on another CPU that is waiting to run. But if there is
+no other CPU with waiting RT tasks, it will initiate the RT pull logic
+on itself (as it still has RT tasks waiting to run). This is a wasted
+effort.
+
+Not only does this help with SMP code where the current CPU is the only
+one with RT overloaded tasks, it should also solve the issue that
+Daniel encountered, because it will prevent the PULL logic from
+executing, as there's only one CPU on the system, and the check added
+here will cause it to exit the RT pull code.
+
+Reported-by: Daniel Wagner <wagi@monom.org>
+Signed-off-by: Steven Rostedt (VMware) <rostedt@goodmis.org>
+Acked-by: Peter Zijlstra <peterz@infradead.org>
+Cc: Linus Torvalds <torvalds@linux-foundation.org>
+Cc: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
+Cc: Thomas Gleixner <tglx@linutronix.de>
+Cc: linux-rt-users <linux-rt-users@vger.kernel.org>
+Fixes: 4bdced5c9 ("sched/rt: Simplify the IPI based RT balancing logic")
+Link: http://lkml.kernel.org/r/20171202130454.4cbbfe8d@vmware.local.home
+Signed-off-by: Ingo Molnar <mingo@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ kernel/sched/rt.c |    8 +++++++-
+ 1 file changed, 7 insertions(+), 1 deletion(-)
+
+--- a/kernel/sched/rt.c
++++ b/kernel/sched/rt.c
+@@ -2034,8 +2034,9 @@ static void pull_rt_task(struct rq *this
+       bool resched = false;
+       struct task_struct *p;
+       struct rq *src_rq;
++      int rt_overload_count = rt_overloaded(this_rq);
+-      if (likely(!rt_overloaded(this_rq)))
++      if (likely(!rt_overload_count))
+               return;
+       /*
+@@ -2044,6 +2045,11 @@ static void pull_rt_task(struct rq *this
+        */
+       smp_rmb();
++      /* If we are the only overloaded CPU do nothing */
++      if (rt_overload_count == 1 &&
++          cpumask_test_cpu(this_rq->cpu, this_rq->rd->rto_mask))
++              return;
++
+ #ifdef HAVE_RT_PUSH_IPI
+       if (sched_feat(RT_PUSH_IPI)) {
+               tell_cpu_to_push(this_rq);
diff --git a/queue-4.14/scsi-core-fix-a-scsi_show_rq-null-pointer-dereference.patch b/queue-4.14/scsi-core-fix-a-scsi_show_rq-null-pointer-dereference.patch
new file mode 100644 (file)
index 0000000..49acbcd
--- /dev/null
@@ -0,0 +1,89 @@
+From 14e3062fb18532175af4d1c4073597999f7a2248 Mon Sep 17 00:00:00 2001
+From: Bart Van Assche <bart.vanassche@wdc.com>
+Date: Tue, 5 Dec 2017 16:57:51 -0800
+Subject: scsi: core: Fix a scsi_show_rq() NULL pointer dereference
+
+From: Bart Van Assche <bart.vanassche@wdc.com>
+
+commit 14e3062fb18532175af4d1c4073597999f7a2248 upstream.
+
+Avoid that scsi_show_rq() triggers a NULL pointer dereference if called
+after sd_uninit_command(). Swap the NULL pointer assignment and the
+mempool_free() call in sd_uninit_command() to make it less likely that
+scsi_show_rq() triggers a use-after-free. Note: even with these changes
+scsi_show_rq() can trigger a use-after-free but that's a lesser evil
+than e.g. suppressing debug information for T10 PI Type 2 commands
+completely. This patch fixes the following oops:
+
+BUG: unable to handle kernel NULL pointer dereference at (null)
+IP: scsi_format_opcode_name+0x1a/0x1c0
+CPU: 1 PID: 1881 Comm: cat Not tainted 4.14.0-rc2.blk_mq_io_hang+ #516
+Call Trace:
+ __scsi_format_command+0x27/0xc0
+ scsi_show_rq+0x5c/0xc0
+ __blk_mq_debugfs_rq_show+0x116/0x130
+ blk_mq_debugfs_rq_show+0xe/0x10
+ seq_read+0xfe/0x3b0
+ full_proxy_read+0x54/0x90
+ __vfs_read+0x37/0x160
+ vfs_read+0x96/0x130
+ SyS_read+0x55/0xc0
+ entry_SYSCALL_64_fastpath+0x1a/0xa5
+
+[mkp: added Type 2]
+
+Fixes: 0eebd005dd07 ("scsi: Implement blk_mq_ops.show_rq()")
+Reported-by: Ming Lei <ming.lei@redhat.com>
+Signed-off-by: Bart Van Assche <bart.vanassche@wdc.com>
+Cc: James E.J. Bottomley <jejb@linux.vnet.ibm.com>
+Cc: Martin K. Petersen <martin.petersen@oracle.com>
+Cc: Ming Lei <ming.lei@redhat.com>
+Cc: Christoph Hellwig <hch@lst.de>
+Cc: Hannes Reinecke <hare@suse.com>
+Cc: Johannes Thumshirn <jthumshirn@suse.de>
+Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/scsi/scsi_debugfs.c |    6 ++++--
+ drivers/scsi/sd.c           |    4 +++-
+ 2 files changed, 7 insertions(+), 3 deletions(-)
+
+--- a/drivers/scsi/scsi_debugfs.c
++++ b/drivers/scsi/scsi_debugfs.c
+@@ -8,9 +8,11 @@ void scsi_show_rq(struct seq_file *m, st
+ {
+       struct scsi_cmnd *cmd = container_of(scsi_req(rq), typeof(*cmd), req);
+       int msecs = jiffies_to_msecs(jiffies - cmd->jiffies_at_alloc);
+-      char buf[80];
++      const u8 *const cdb = READ_ONCE(cmd->cmnd);
++      char buf[80] = "(?)";
+-      __scsi_format_command(buf, sizeof(buf), cmd->cmnd, cmd->cmd_len);
++      if (cdb)
++              __scsi_format_command(buf, sizeof(buf), cdb, cmd->cmd_len);
+       seq_printf(m, ", .cmd=%s, .retries=%d, allocated %d.%03d s ago", buf,
+                  cmd->retries, msecs / 1000, msecs % 1000);
+ }
+--- a/drivers/scsi/sd.c
++++ b/drivers/scsi/sd.c
+@@ -1284,6 +1284,7 @@ static int sd_init_command(struct scsi_c
+ static void sd_uninit_command(struct scsi_cmnd *SCpnt)
+ {
+       struct request *rq = SCpnt->request;
++      u8 *cmnd;
+       if (SCpnt->flags & SCMD_ZONE_WRITE_LOCK)
+               sd_zbc_write_unlock_zone(SCpnt);
+@@ -1292,9 +1293,10 @@ static void sd_uninit_command(struct scs
+               __free_page(rq->special_vec.bv_page);
+       if (SCpnt->cmnd != scsi_req(rq)->cmd) {
+-              mempool_free(SCpnt->cmnd, sd_cdb_pool);
++              cmnd = SCpnt->cmnd;
+               SCpnt->cmnd = NULL;
+               SCpnt->cmd_len = 0;
++              mempool_free(cmnd, sd_cdb_pool);
+       }
+ }
diff --git a/queue-4.14/scsi-libsas-fix-length-error-in-sas_smp_handler.patch b/queue-4.14/scsi-libsas-fix-length-error-in-sas_smp_handler.patch
new file mode 100644 (file)
index 0000000..c1b11b6
--- /dev/null
@@ -0,0 +1,66 @@
+From 621f6401fdeefe96dfe9eab4b167c7c39f552bb0 Mon Sep 17 00:00:00 2001
+From: Jason Yan <yanaijie@huawei.com>
+Date: Mon, 11 Dec 2017 15:03:33 +0800
+Subject: scsi: libsas: fix length error in sas_smp_handler()
+
+From: Jason Yan <yanaijie@huawei.com>
+
+commit 621f6401fdeefe96dfe9eab4b167c7c39f552bb0 upstream.
+
+The return value of smp_execute_task_sg() is the untransferred residual,
+but bsg_job_done() requires the length of payload received. This makes
+SMP passthrough commands from userland by sg ioctl to libsas get a wrong
+response. The userland tools such as smp_utils failed because of these
+wrong responses:
+
+~#smp_discover /dev/bsg/expander-2\:13
+response too short, len=0
+~#smp_discover /dev/bsg/expander-2\:134
+response too short, len=0
+
+Fix this by passing the actual received length to bsg_job_done(). And if
+smp_execute_task_sg() returns 0, this means received length is exactly
+the buffer length.
+
+[mkp: typo]
+
+Fixes: 651a01364994 ("scsi: scsi_transport_sas: switch to bsg-lib for SMP passthrough")
+Signed-off-by: Jason Yan <yanaijie@huawei.com>
+Reported-by: chenqilin <chenqilin2@huawei.com>
+Tested-by: chenqilin <chenqilin2@huawei.com>
+CC: Christoph Hellwig <hch@lst.de>
+Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/scsi/libsas/sas_expander.c |   10 +++++-----
+ 1 file changed, 5 insertions(+), 5 deletions(-)
+
+--- a/drivers/scsi/libsas/sas_expander.c
++++ b/drivers/scsi/libsas/sas_expander.c
+@@ -2145,7 +2145,7 @@ void sas_smp_handler(struct bsg_job *job
+               struct sas_rphy *rphy)
+ {
+       struct domain_device *dev;
+-      unsigned int reslen = 0;
++      unsigned int rcvlen = 0;
+       int ret = -EINVAL;
+       /* no rphy means no smp target support (ie aic94xx host) */
+@@ -2179,12 +2179,12 @@ void sas_smp_handler(struct bsg_job *job
+       ret = smp_execute_task_sg(dev, job->request_payload.sg_list,
+                       job->reply_payload.sg_list);
+-      if (ret > 0) {
+-              /* positive number is the untransferred residual */
+-              reslen = ret;
++      if (ret >= 0) {
++              /* bsg_job_done() requires the length received  */
++              rcvlen = job->reply_payload.payload_len - ret;
+               ret = 0;
+       }
+ out:
+-      bsg_job_done(job, ret, reslen);
++      bsg_job_done(job, ret, rcvlen);
+ }
index 0d43823764af6922de505fab3b1b3168c36d0a32..aa174f5c3c9fd0f41be02627e8cb78eb49faf362 100644 (file)
@@ -6,3 +6,41 @@ crypto-salsa20-fix-blkcipher_walk-api-usage.patch
 crypto-af_alg-fix-null-pointer-dereference-in.patch
 cifs-fix-null-deref-in-smb2_read.patch
 string.h-workaround-for-increased-stack-usage.patch
+autofs-fix-careless-error-in-recent-commit.patch
+kernel-make-groups_sort-calling-a-responsibility-group_info-allocators.patch
+mm-oom_reaper-fix-memory-corruption.patch
+tracing-allocate-mask_str-buffer-dynamically.patch
+usb-uas-and-storage-add-us_fl_broken_fua-for-another-jmicron-jms567-id.patch
+usb-core-prevent-malicious-bnuminterfaces-overflow.patch
+ovl-pass-ovl_get_nlink-parameters-in-right-order.patch
+ovl-update-ctx-pos-on-impure-dir-iteration.patch
+usbip-fix-stub_rx-get_pipe-to-validate-endpoint-number.patch
+usbip-fix-stub_rx-harden-cmd_submit-path-to-handle-malicious-input.patch
+usbip-prevent-vhci_hcd-driver-from-leaking-a-socket-pointer-address.patch
+usbip-fix-stub_send_ret_submit-vulnerability-to-null-transfer_buffer.patch
+mmc-core-apply-no_cmd23-quirk-to-some-specific-cards.patch
+ceph-drop-negative-child-dentries-before-try-pruning-inode-s-alias.patch
+usb-xhci-fix-tds-for-mtk-xhci1.1.patch
+xhci-don-t-add-a-virt_dev-to-the-devs-array-before-it-s-fully-allocated.patch
+ib-core-bound-check-alternate-path-port-number.patch
+ib-core-don-t-enforce-pkey-security-on-smi-mads.patch
+nfs-don-t-wait-on-commit-in-nfs_commit_inode-if-there-were-no-commit-requests.patch
+arm64-mm-fix-pte_mkclean-pte_mkdirty-semantics.patch
+arm64-initialise-high_memory-global-variable-earlier.patch
+arm64-fix-config_debug_wx-address-reporting.patch
+scsi-core-fix-a-scsi_show_rq-null-pointer-dereference.patch
+scsi-libsas-fix-length-error-in-sas_smp_handler.patch
+sched-rt-do-not-pull-from-current-cpu-if-only-one-cpu-to-pull.patch
+dm-fix-various-targets-to-dm_register_target-after-module-__init-resources-created.patch
+sunrpc-fix-a-race-in-the-receive-code-path.patch
+iw_cxgb4-only-insert-drain-cqes-if-wq-is-flushed.patch
+x86-boot-compressed-64-detect-and-handle-5-level-paging-at-boot-time.patch
+x86-boot-compressed-64-print-error-if-5-level-paging-is-not-supported.patch
+eeprom-at24-change-nvmem-stride-to-1.patch
+posix-timer-properly-check-sigevent-sigev_notify.patch
+dmaengine-dmatest-move-callback-wait-queue-to-thread-context.patch
+revert-exec-avoid-rlimit_stack-races-with-prlimit.patch
+ext4-support-fast-symlinks-from-ext3-file-systems.patch
+ext4-fix-fdatasync-2-after-fallocate-2-operation.patch
+ext4-add-missing-error-check-in-__ext4_new_inode.patch
+ext4-fix-crash-when-a-directory-s-i_size-is-too-small.patch
diff --git a/queue-4.14/sunrpc-fix-a-race-in-the-receive-code-path.patch b/queue-4.14/sunrpc-fix-a-race-in-the-receive-code-path.patch
new file mode 100644 (file)
index 0000000..09e9c0d
--- /dev/null
@@ -0,0 +1,80 @@
+From 90d91b0cd371193d9dbfa9beacab8ab9a4cb75e0 Mon Sep 17 00:00:00 2001
+From: Trond Myklebust <trond.myklebust@primarydata.com>
+Date: Thu, 14 Dec 2017 21:24:08 -0500
+Subject: SUNRPC: Fix a race in the receive code path
+
+From: Trond Myklebust <trond.myklebust@primarydata.com>
+
+commit 90d91b0cd371193d9dbfa9beacab8ab9a4cb75e0 upstream.
+
+We must ensure that the call to rpc_sleep_on() in xprt_transmit() cannot
+race with the call to xprt_complete_rqst().
+
+Reported-by: Chuck Lever <chuck.lever@oracle.com>
+Link: https://bugzilla.linux-nfs.org/show_bug.cgi?id=317
+Fixes: ce7c252a8c74 ("SUNRPC: Add a separate spinlock to protect..")
+Reviewed-by: Chuck Lever <chuck.lever@oracle.com>
+Signed-off-by: Trond Myklebust <trond.myklebust@primarydata.com>
+Signed-off-by: Anna Schumaker <Anna.Schumaker@Netapp.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ net/sunrpc/xprt.c |   28 +++++++++++++++++++---------
+ 1 file changed, 19 insertions(+), 9 deletions(-)
+
+--- a/net/sunrpc/xprt.c
++++ b/net/sunrpc/xprt.c
+@@ -1001,6 +1001,7 @@ void xprt_transmit(struct rpc_task *task
+ {
+       struct rpc_rqst *req = task->tk_rqstp;
+       struct rpc_xprt *xprt = req->rq_xprt;
++      unsigned int connect_cookie;
+       int status, numreqs;
+       dprintk("RPC: %5u xprt_transmit(%u)\n", task->tk_pid, req->rq_slen);
+@@ -1024,6 +1025,7 @@ void xprt_transmit(struct rpc_task *task
+       } else if (!req->rq_bytes_sent)
+               return;
++      connect_cookie = xprt->connect_cookie;
+       req->rq_xtime = ktime_get();
+       status = xprt->ops->send_request(task);
+       trace_xprt_transmit(xprt, req->rq_xid, status);
+@@ -1047,20 +1049,28 @@ void xprt_transmit(struct rpc_task *task
+       xprt->stat.bklog_u += xprt->backlog.qlen;
+       xprt->stat.sending_u += xprt->sending.qlen;
+       xprt->stat.pending_u += xprt->pending.qlen;
++      spin_unlock_bh(&xprt->transport_lock);
+-      /* Don't race with disconnect */
+-      if (!xprt_connected(xprt))
+-              task->tk_status = -ENOTCONN;
+-      else {
++      req->rq_connect_cookie = connect_cookie;
++      if (rpc_reply_expected(task) && !READ_ONCE(req->rq_reply_bytes_recvd)) {
+               /*
+-               * Sleep on the pending queue since
+-               * we're expecting a reply.
++               * Sleep on the pending queue if we're expecting a reply.
++               * The spinlock ensures atomicity between the test of
++               * req->rq_reply_bytes_recvd, and the call to rpc_sleep_on().
+                */
+-              if (!req->rq_reply_bytes_recvd && rpc_reply_expected(task))
++              spin_lock(&xprt->recv_lock);
++              if (!req->rq_reply_bytes_recvd) {
+                       rpc_sleep_on(&xprt->pending, task, xprt_timer);
+-              req->rq_connect_cookie = xprt->connect_cookie;
++                      /*
++                       * Send an extra queue wakeup call if the
++                       * connection was dropped in case the call to
++                       * rpc_sleep_on() raced.
++                       */
++                      if (!xprt_connected(xprt))
++                              xprt_wake_pending_tasks(xprt, -ENOTCONN);
++              }
++              spin_unlock(&xprt->recv_lock);
+       }
+-      spin_unlock_bh(&xprt->transport_lock);
+ }
+ static void xprt_add_backlog(struct rpc_xprt *xprt, struct rpc_task *task)
diff --git a/queue-4.14/tracing-allocate-mask_str-buffer-dynamically.patch b/queue-4.14/tracing-allocate-mask_str-buffer-dynamically.patch
new file mode 100644 (file)
index 0000000..b13a3c9
--- /dev/null
@@ -0,0 +1,97 @@
+From 90e406f96f630c07d631a021fd4af10aac913e77 Mon Sep 17 00:00:00 2001
+From: Changbin Du <changbin.du@intel.com>
+Date: Thu, 30 Nov 2017 11:39:43 +0800
+Subject: tracing: Allocate mask_str buffer dynamically
+
+From: Changbin Du <changbin.du@intel.com>
+
+commit 90e406f96f630c07d631a021fd4af10aac913e77 upstream.
+
+The default NR_CPUS can be very large, but actual possible nr_cpu_ids
+usually is very small. For my x86 distribution, the NR_CPUS is 8192 and
+nr_cpu_ids is 4. About 2 pages are wasted.
+
+Most machines don't have so many CPUs, so define a array with NR_CPUS
+just wastes memory. So let's allocate the buffer dynamically when need.
+
+With this change, the mutext tracing_cpumask_update_lock also can be
+removed now, which was used to protect mask_str.
+
+Link: http://lkml.kernel.org/r/1512013183-19107-1-git-send-email-changbin.du@intel.com
+
+Fixes: 36dfe9252bd4c ("ftrace: make use of tracing_cpumask")
+Signed-off-by: Changbin Du <changbin.du@intel.com>
+Signed-off-by: Steven Rostedt (VMware) <rostedt@goodmis.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ kernel/trace/trace.c |   29 +++++++++--------------------
+ 1 file changed, 9 insertions(+), 20 deletions(-)
+
+--- a/kernel/trace/trace.c
++++ b/kernel/trace/trace.c
+@@ -4178,37 +4178,30 @@ static const struct file_operations show
+       .llseek         = seq_lseek,
+ };
+-/*
+- * The tracer itself will not take this lock, but still we want
+- * to provide a consistent cpumask to user-space:
+- */
+-static DEFINE_MUTEX(tracing_cpumask_update_lock);
+-
+-/*
+- * Temporary storage for the character representation of the
+- * CPU bitmask (and one more byte for the newline):
+- */
+-static char mask_str[NR_CPUS + 1];
+-
+ static ssize_t
+ tracing_cpumask_read(struct file *filp, char __user *ubuf,
+                    size_t count, loff_t *ppos)
+ {
+       struct trace_array *tr = file_inode(filp)->i_private;
++      char *mask_str;
+       int len;
+-      mutex_lock(&tracing_cpumask_update_lock);
++      len = snprintf(NULL, 0, "%*pb\n",
++                     cpumask_pr_args(tr->tracing_cpumask)) + 1;
++      mask_str = kmalloc(len, GFP_KERNEL);
++      if (!mask_str)
++              return -ENOMEM;
+-      len = snprintf(mask_str, count, "%*pb\n",
++      len = snprintf(mask_str, len, "%*pb\n",
+                      cpumask_pr_args(tr->tracing_cpumask));
+       if (len >= count) {
+               count = -EINVAL;
+               goto out_err;
+       }
+-      count = simple_read_from_buffer(ubuf, count, ppos, mask_str, NR_CPUS+1);
++      count = simple_read_from_buffer(ubuf, count, ppos, mask_str, len);
+ out_err:
+-      mutex_unlock(&tracing_cpumask_update_lock);
++      kfree(mask_str);
+       return count;
+ }
+@@ -4228,8 +4221,6 @@ tracing_cpumask_write(struct file *filp,
+       if (err)
+               goto err_unlock;
+-      mutex_lock(&tracing_cpumask_update_lock);
+-
+       local_irq_disable();
+       arch_spin_lock(&tr->max_lock);
+       for_each_tracing_cpu(cpu) {
+@@ -4252,8 +4243,6 @@ tracing_cpumask_write(struct file *filp,
+       local_irq_enable();
+       cpumask_copy(tr->tracing_cpumask, tracing_cpumask_new);
+-
+-      mutex_unlock(&tracing_cpumask_update_lock);
+       free_cpumask_var(tracing_cpumask_new);
+       return count;
diff --git a/queue-4.14/usb-core-prevent-malicious-bnuminterfaces-overflow.patch b/queue-4.14/usb-core-prevent-malicious-bnuminterfaces-overflow.patch
new file mode 100644 (file)
index 0000000..dadf0d7
--- /dev/null
@@ -0,0 +1,47 @@
+From 48a4ff1c7bb5a32d2e396b03132d20d552c0eca7 Mon Sep 17 00:00:00 2001
+From: Alan Stern <stern@rowland.harvard.edu>
+Date: Tue, 12 Dec 2017 14:25:13 -0500
+Subject: USB: core: prevent malicious bNumInterfaces overflow
+
+From: Alan Stern <stern@rowland.harvard.edu>
+
+commit 48a4ff1c7bb5a32d2e396b03132d20d552c0eca7 upstream.
+
+A malicious USB device with crafted descriptors can cause the kernel
+to access unallocated memory by setting the bNumInterfaces value too
+high in a configuration descriptor.  Although the value is adjusted
+during parsing, this adjustment is skipped in one of the error return
+paths.
+
+This patch prevents the problem by setting bNumInterfaces to 0
+initially.  The existing code already sets it to the proper value
+after parsing is complete.
+
+Signed-off-by: Alan Stern <stern@rowland.harvard.edu>
+Reported-by: Andrey Konovalov <andreyknvl@google.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/usb/core/config.c |    4 +++-
+ 1 file changed, 3 insertions(+), 1 deletion(-)
+
+--- a/drivers/usb/core/config.c
++++ b/drivers/usb/core/config.c
+@@ -555,6 +555,9 @@ static int usb_parse_configuration(struc
+       unsigned iad_num = 0;
+       memcpy(&config->desc, buffer, USB_DT_CONFIG_SIZE);
++      nintf = nintf_orig = config->desc.bNumInterfaces;
++      config->desc.bNumInterfaces = 0;        // Adjusted later
++
+       if (config->desc.bDescriptorType != USB_DT_CONFIG ||
+           config->desc.bLength < USB_DT_CONFIG_SIZE ||
+           config->desc.bLength > size) {
+@@ -568,7 +571,6 @@ static int usb_parse_configuration(struc
+       buffer += config->desc.bLength;
+       size -= config->desc.bLength;
+-      nintf = nintf_orig = config->desc.bNumInterfaces;
+       if (nintf > USB_MAXINTERFACES) {
+               dev_warn(ddev, "config %d has too many interfaces: %d, "
+                   "using maximum allowed: %d\n",
diff --git a/queue-4.14/usb-uas-and-storage-add-us_fl_broken_fua-for-another-jmicron-jms567-id.patch b/queue-4.14/usb-uas-and-storage-add-us_fl_broken_fua-for-another-jmicron-jms567-id.patch
new file mode 100644 (file)
index 0000000..2a07024
--- /dev/null
@@ -0,0 +1,65 @@
+From 62354454625741f0569c2cbe45b2d192f8fd258e Mon Sep 17 00:00:00 2001
+From: David Kozub <zub@linux.fjfi.cvut.cz>
+Date: Tue, 5 Dec 2017 22:40:04 +0100
+Subject: USB: uas and storage: Add US_FL_BROKEN_FUA for another JMicron JMS567 ID
+
+From: David Kozub <zub@linux.fjfi.cvut.cz>
+
+commit 62354454625741f0569c2cbe45b2d192f8fd258e upstream.
+
+There is another JMS567-based USB3 UAS enclosure (152d:0578) that fails
+with the following error:
+
+[sda] tag#0 FAILED Result: hostbyte=DID_OK driverbyte=DRIVER_SENSE
+[sda] tag#0 Sense Key : Illegal Request [current]
+[sda] tag#0 Add. Sense: Invalid field in cdb
+
+The issue occurs both with UAS (occasionally) and mass storage
+(immediately after mounting a FS on a disk in the enclosure).
+
+Enabling US_FL_BROKEN_FUA quirk solves this issue.
+
+This patch adds an UNUSUAL_DEV with US_FL_BROKEN_FUA for the enclosure
+for both UAS and mass storage.
+
+Signed-off-by: David Kozub <zub@linux.fjfi.cvut.cz>
+Acked-by: Alan Stern <stern@rowland.harvard.edu>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/usb/storage/unusual_devs.h |    7 +++++++
+ drivers/usb/storage/unusual_uas.h  |    7 +++++++
+ 2 files changed, 14 insertions(+)
+
+--- a/drivers/usb/storage/unusual_devs.h
++++ b/drivers/usb/storage/unusual_devs.h
+@@ -2113,6 +2113,13 @@ UNUSUAL_DEV(  0x152d, 0x0567, 0x0114, 0x
+               USB_SC_DEVICE, USB_PR_DEVICE, NULL,
+               US_FL_BROKEN_FUA ),
++/* Reported by David Kozub <zub@linux.fjfi.cvut.cz> */
++UNUSUAL_DEV(0x152d, 0x0578, 0x0000, 0x9999,
++              "JMicron",
++              "JMS567",
++              USB_SC_DEVICE, USB_PR_DEVICE, NULL,
++              US_FL_BROKEN_FUA),
++
+ /*
+  * Reported by Alexandre Oliva <oliva@lsd.ic.unicamp.br>
+  * JMicron responds to USN and several other SCSI ioctls with a
+--- a/drivers/usb/storage/unusual_uas.h
++++ b/drivers/usb/storage/unusual_uas.h
+@@ -142,6 +142,13 @@ UNUSUAL_DEV(0x152d, 0x0567, 0x0000, 0x99
+               USB_SC_DEVICE, USB_PR_DEVICE, NULL,
+               US_FL_BROKEN_FUA | US_FL_NO_REPORT_OPCODES),
++/* Reported-by: David Kozub <zub@linux.fjfi.cvut.cz> */
++UNUSUAL_DEV(0x152d, 0x0578, 0x0000, 0x9999,
++              "JMicron",
++              "JMS567",
++              USB_SC_DEVICE, USB_PR_DEVICE, NULL,
++              US_FL_BROKEN_FUA),
++
+ /* Reported-by: Hans de Goede <hdegoede@redhat.com> */
+ UNUSUAL_DEV(0x2109, 0x0711, 0x0000, 0x9999,
+               "VIA",
diff --git a/queue-4.14/usb-xhci-fix-tds-for-mtk-xhci1.1.patch b/queue-4.14/usb-xhci-fix-tds-for-mtk-xhci1.1.patch
new file mode 100644 (file)
index 0000000..97fada5
--- /dev/null
@@ -0,0 +1,47 @@
+From 72b663a99c074a8d073e7ecdae446cfb024ef551 Mon Sep 17 00:00:00 2001
+From: Chunfeng Yun <chunfeng.yun@mediatek.com>
+Date: Fri, 8 Dec 2017 18:10:06 +0200
+Subject: usb: xhci: fix TDS for MTK xHCI1.1
+
+From: Chunfeng Yun <chunfeng.yun@mediatek.com>
+
+commit 72b663a99c074a8d073e7ecdae446cfb024ef551 upstream.
+
+For MTK's xHCI 1.0 or latter, TD size is the number of max
+packet sized packets remaining in the TD, not including
+this TRB (following spec).
+
+For MTK's xHCI 0.96 and older, TD size is the number of max
+packet sized packets remaining in the TD, including this TRB
+(not following spec).
+
+Signed-off-by: Chunfeng Yun <chunfeng.yun@mediatek.com>
+Signed-off-by: Mathias Nyman <mathias.nyman@linux.intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/usb/host/xhci-ring.c |    6 +++---
+ 1 file changed, 3 insertions(+), 3 deletions(-)
+
+--- a/drivers/usb/host/xhci-ring.c
++++ b/drivers/usb/host/xhci-ring.c
+@@ -3121,7 +3121,7 @@ static u32 xhci_td_remainder(struct xhci
+ {
+       u32 maxp, total_packet_count;
+-      /* MTK xHCI is mostly 0.97 but contains some features from 1.0 */
++      /* MTK xHCI 0.96 contains some features from 1.0 */
+       if (xhci->hci_version < 0x100 && !(xhci->quirks & XHCI_MTK_HOST))
+               return ((td_total_len - transferred) >> 10);
+@@ -3130,8 +3130,8 @@ static u32 xhci_td_remainder(struct xhci
+           trb_buff_len == td_total_len)
+               return 0;
+-      /* for MTK xHCI, TD size doesn't include this TRB */
+-      if (xhci->quirks & XHCI_MTK_HOST)
++      /* for MTK xHCI 0.96, TD size include this TRB, but not in 1.x */
++      if ((xhci->quirks & XHCI_MTK_HOST) && (xhci->hci_version < 0x100))
+               trb_buff_len = 0;
+       maxp = usb_endpoint_maxp(&urb->ep->desc);
diff --git a/queue-4.14/usbip-fix-stub_rx-get_pipe-to-validate-endpoint-number.patch b/queue-4.14/usbip-fix-stub_rx-get_pipe-to-validate-endpoint-number.patch
new file mode 100644 (file)
index 0000000..ae59a2f
--- /dev/null
@@ -0,0 +1,71 @@
+From 635f545a7e8be7596b9b2b6a43cab6bbd5a88e43 Mon Sep 17 00:00:00 2001
+From: Shuah Khan <shuahkh@osg.samsung.com>
+Date: Thu, 7 Dec 2017 14:16:47 -0700
+Subject: usbip: fix stub_rx: get_pipe() to validate endpoint number
+
+From: Shuah Khan <shuahkh@osg.samsung.com>
+
+commit 635f545a7e8be7596b9b2b6a43cab6bbd5a88e43 upstream.
+
+get_pipe() routine doesn't validate the input endpoint number
+and uses to reference ep_in and ep_out arrays. Invalid endpoint
+number can trigger BUG(). Range check the epnum and returning
+error instead of calling BUG().
+
+Change caller stub_recv_cmd_submit() to handle the get_pipe()
+error return.
+
+Reported-by: Secunia Research <vuln@secunia.com>
+Signed-off-by: Shuah Khan <shuahkh@osg.samsung.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/usb/usbip/stub_rx.c |   18 +++++++++++-------
+ 1 file changed, 11 insertions(+), 7 deletions(-)
+
+--- a/drivers/usb/usbip/stub_rx.c
++++ b/drivers/usb/usbip/stub_rx.c
+@@ -342,15 +342,15 @@ static int get_pipe(struct stub_device *
+       struct usb_host_endpoint *ep;
+       struct usb_endpoint_descriptor *epd = NULL;
++      if (epnum < 0 || epnum > 15)
++              goto err_ret;
++
+       if (dir == USBIP_DIR_IN)
+               ep = udev->ep_in[epnum & 0x7f];
+       else
+               ep = udev->ep_out[epnum & 0x7f];
+-      if (!ep) {
+-              dev_err(&sdev->udev->dev, "no such endpoint?, %d\n",
+-                      epnum);
+-              BUG();
+-      }
++      if (!ep)
++              goto err_ret;
+       epd = &ep->desc;
+       if (usb_endpoint_xfer_control(epd)) {
+@@ -381,9 +381,10 @@ static int get_pipe(struct stub_device *
+                       return usb_rcvisocpipe(udev, epnum);
+       }
++err_ret:
+       /* NOT REACHED */
+-      dev_err(&sdev->udev->dev, "get pipe, epnum %d\n", epnum);
+-      return 0;
++      dev_err(&sdev->udev->dev, "get pipe() invalid epnum %d\n", epnum);
++      return -1;
+ }
+ static void masking_bogus_flags(struct urb *urb)
+@@ -449,6 +450,9 @@ static void stub_recv_cmd_submit(struct
+       struct usb_device *udev = sdev->udev;
+       int pipe = get_pipe(sdev, pdu->base.ep, pdu->base.direction);
++      if (pipe == -1)
++              return;
++
+       priv = stub_priv_alloc(sdev, pdu);
+       if (!priv)
+               return;
diff --git a/queue-4.14/usbip-fix-stub_rx-harden-cmd_submit-path-to-handle-malicious-input.patch b/queue-4.14/usbip-fix-stub_rx-harden-cmd_submit-path-to-handle-malicious-input.patch
new file mode 100644 (file)
index 0000000..e0c7cb9
--- /dev/null
@@ -0,0 +1,106 @@
+From c6688ef9f29762e65bce325ef4acd6c675806366 Mon Sep 17 00:00:00 2001
+From: Shuah Khan <shuahkh@osg.samsung.com>
+Date: Thu, 7 Dec 2017 14:16:48 -0700
+Subject: usbip: fix stub_rx: harden CMD_SUBMIT path to handle malicious input
+
+From: Shuah Khan <shuahkh@osg.samsung.com>
+
+commit c6688ef9f29762e65bce325ef4acd6c675806366 upstream.
+
+Harden CMD_SUBMIT path to handle malicious input that could trigger
+large memory allocations. Add checks to validate transfer_buffer_length
+and number_of_packets to protect against bad input requesting for
+unbounded memory allocations. Validate early in get_pipe() and return
+failure.
+
+Reported-by: Secunia Research <vuln@secunia.com>
+Signed-off-by: Shuah Khan <shuahkh@osg.samsung.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/usb/usbip/stub_rx.c |   35 +++++++++++++++++++++++++++++++----
+ 1 file changed, 31 insertions(+), 4 deletions(-)
+
+--- a/drivers/usb/usbip/stub_rx.c
++++ b/drivers/usb/usbip/stub_rx.c
+@@ -336,11 +336,13 @@ static struct stub_priv *stub_priv_alloc
+       return priv;
+ }
+-static int get_pipe(struct stub_device *sdev, int epnum, int dir)
++static int get_pipe(struct stub_device *sdev, struct usbip_header *pdu)
+ {
+       struct usb_device *udev = sdev->udev;
+       struct usb_host_endpoint *ep;
+       struct usb_endpoint_descriptor *epd = NULL;
++      int epnum = pdu->base.ep;
++      int dir = pdu->base.direction;
+       if (epnum < 0 || epnum > 15)
+               goto err_ret;
+@@ -353,6 +355,15 @@ static int get_pipe(struct stub_device *
+               goto err_ret;
+       epd = &ep->desc;
++
++      /* validate transfer_buffer_length */
++      if (pdu->u.cmd_submit.transfer_buffer_length > INT_MAX) {
++              dev_err(&sdev->udev->dev,
++                      "CMD_SUBMIT: -EMSGSIZE transfer_buffer_length %d\n",
++                      pdu->u.cmd_submit.transfer_buffer_length);
++              return -1;
++      }
++
+       if (usb_endpoint_xfer_control(epd)) {
+               if (dir == USBIP_DIR_OUT)
+                       return usb_sndctrlpipe(udev, epnum);
+@@ -375,6 +386,21 @@ static int get_pipe(struct stub_device *
+       }
+       if (usb_endpoint_xfer_isoc(epd)) {
++              /* validate packet size and number of packets */
++              unsigned int maxp, packets, bytes;
++
++              maxp = usb_endpoint_maxp(epd);
++              maxp *= usb_endpoint_maxp_mult(epd);
++              bytes = pdu->u.cmd_submit.transfer_buffer_length;
++              packets = DIV_ROUND_UP(bytes, maxp);
++
++              if (pdu->u.cmd_submit.number_of_packets < 0 ||
++                  pdu->u.cmd_submit.number_of_packets > packets) {
++                      dev_err(&sdev->udev->dev,
++                              "CMD_SUBMIT: isoc invalid num packets %d\n",
++                              pdu->u.cmd_submit.number_of_packets);
++                      return -1;
++              }
+               if (dir == USBIP_DIR_OUT)
+                       return usb_sndisocpipe(udev, epnum);
+               else
+@@ -383,7 +409,7 @@ static int get_pipe(struct stub_device *
+ err_ret:
+       /* NOT REACHED */
+-      dev_err(&sdev->udev->dev, "get pipe() invalid epnum %d\n", epnum);
++      dev_err(&sdev->udev->dev, "CMD_SUBMIT: invalid epnum %d\n", epnum);
+       return -1;
+ }
+@@ -448,7 +474,7 @@ static void stub_recv_cmd_submit(struct
+       struct stub_priv *priv;
+       struct usbip_device *ud = &sdev->ud;
+       struct usb_device *udev = sdev->udev;
+-      int pipe = get_pipe(sdev, pdu->base.ep, pdu->base.direction);
++      int pipe = get_pipe(sdev, pdu);
+       if (pipe == -1)
+               return;
+@@ -470,7 +496,8 @@ static void stub_recv_cmd_submit(struct
+       }
+       /* allocate urb transfer buffer, if needed */
+-      if (pdu->u.cmd_submit.transfer_buffer_length > 0) {
++      if (pdu->u.cmd_submit.transfer_buffer_length > 0 &&
++          pdu->u.cmd_submit.transfer_buffer_length <= INT_MAX) {
+               priv->urb->transfer_buffer =
+                       kzalloc(pdu->u.cmd_submit.transfer_buffer_length,
+                               GFP_KERNEL);
diff --git a/queue-4.14/usbip-fix-stub_send_ret_submit-vulnerability-to-null-transfer_buffer.patch b/queue-4.14/usbip-fix-stub_send_ret_submit-vulnerability-to-null-transfer_buffer.patch
new file mode 100644 (file)
index 0000000..9a2c705
--- /dev/null
@@ -0,0 +1,38 @@
+From be6123df1ea8f01ee2f896a16c2b7be3e4557a5a Mon Sep 17 00:00:00 2001
+From: Shuah Khan <shuahkh@osg.samsung.com>
+Date: Thu, 7 Dec 2017 14:16:50 -0700
+Subject: usbip: fix stub_send_ret_submit() vulnerability to null transfer_buffer
+
+From: Shuah Khan <shuahkh@osg.samsung.com>
+
+commit be6123df1ea8f01ee2f896a16c2b7be3e4557a5a upstream.
+
+stub_send_ret_submit() handles urb with a potential null transfer_buffer,
+when it replays a packet with potential malicious data that could contain
+a null buffer. Add a check for the condition when actual_length > 0 and
+transfer_buffer is null.
+
+Reported-by: Secunia Research <vuln@secunia.com>
+Signed-off-by: Shuah Khan <shuahkh@osg.samsung.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/usb/usbip/stub_tx.c |    7 +++++++
+ 1 file changed, 7 insertions(+)
+
+--- a/drivers/usb/usbip/stub_tx.c
++++ b/drivers/usb/usbip/stub_tx.c
+@@ -181,6 +181,13 @@ static int stub_send_ret_submit(struct s
+               memset(&pdu_header, 0, sizeof(pdu_header));
+               memset(&msg, 0, sizeof(msg));
++              if (urb->actual_length > 0 && !urb->transfer_buffer) {
++                      dev_err(&sdev->udev->dev,
++                              "urb: actual_length %d transfer_buffer null\n",
++                              urb->actual_length);
++                      return -1;
++              }
++
+               if (usb_pipetype(urb->pipe) == PIPE_ISOCHRONOUS)
+                       iovnum = 2 + urb->number_of_packets;
+               else
diff --git a/queue-4.14/usbip-prevent-vhci_hcd-driver-from-leaking-a-socket-pointer-address.patch b/queue-4.14/usbip-prevent-vhci_hcd-driver-from-leaking-a-socket-pointer-address.patch
new file mode 100644 (file)
index 0000000..f15b877
--- /dev/null
@@ -0,0 +1,129 @@
+From 2f2d0088eb93db5c649d2a5e34a3800a8a935fc5 Mon Sep 17 00:00:00 2001
+From: Shuah Khan <shuahkh@osg.samsung.com>
+Date: Thu, 7 Dec 2017 14:16:49 -0700
+Subject: usbip: prevent vhci_hcd driver from leaking a socket pointer address
+
+From: Shuah Khan <shuahkh@osg.samsung.com>
+
+commit 2f2d0088eb93db5c649d2a5e34a3800a8a935fc5 upstream.
+
+When a client has a USB device attached over IP, the vhci_hcd driver is
+locally leaking a socket pointer address via the
+
+/sys/devices/platform/vhci_hcd/status file (world-readable) and in debug
+output when "usbip --debug port" is run.
+
+Fix it to not leak. The socket pointer address is not used at the moment
+and it was made visible as a convenient way to find IP address from socket
+pointer address by looking up /proc/net/{tcp,tcp6}.
+
+As this opens a security hole, the fix replaces socket pointer address with
+sockfd.
+
+Reported-by: Secunia Research <vuln@secunia.com>
+Signed-off-by: Shuah Khan <shuahkh@osg.samsung.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/usb/usbip/usbip_common.h     |    1 +
+ drivers/usb/usbip/vhci_sysfs.c       |   25 ++++++++++++++++---------
+ tools/usb/usbip/libsrc/vhci_driver.c |    8 ++++----
+ 3 files changed, 21 insertions(+), 13 deletions(-)
+
+--- a/drivers/usb/usbip/usbip_common.h
++++ b/drivers/usb/usbip/usbip_common.h
+@@ -270,6 +270,7 @@ struct usbip_device {
+       /* lock for status */
+       spinlock_t lock;
++      int sockfd;
+       struct socket *tcp_socket;
+       struct task_struct *tcp_rx;
+--- a/drivers/usb/usbip/vhci_sysfs.c
++++ b/drivers/usb/usbip/vhci_sysfs.c
+@@ -31,15 +31,20 @@
+ /*
+  * output example:
+- * hub port sta spd dev      socket           local_busid
+- * hs  0000 004 000 00000000         c5a7bb80 1-2.3
++ * hub port sta spd dev       sockfd    local_busid
++ * hs  0000 004 000 00000000  3         1-2.3
+  * ................................................
+- * ss  0008 004 000 00000000         d8cee980 2-3.4
++ * ss  0008 004 000 00000000  4         2-3.4
+  * ................................................
+  *
+- * IP address can be retrieved from a socket pointer address by looking
+- * up /proc/net/{tcp,tcp6}. Also, a userland program may remember a
+- * port number and its peer IP address.
++ * Output includes socket fd instead of socket pointer address to avoid
++ * leaking kernel memory address in:
++ *    /sys/devices/platform/vhci_hcd.0/status and in debug output.
++ * The socket pointer address is not used at the moment and it was made
++ * visible as a convenient way to find IP address from socket pointer
++ * address by looking up /proc/net/{tcp,tcp6}. As this opens a security
++ * hole, the change is made to use sockfd instead.
++ *
+  */
+ static void port_show_vhci(char **out, int hub, int port, struct vhci_device *vdev)
+ {
+@@ -53,8 +58,8 @@ static void port_show_vhci(char **out, i
+       if (vdev->ud.status == VDEV_ST_USED) {
+               *out += sprintf(*out, "%03u %08x ",
+                                     vdev->speed, vdev->devid);
+-              *out += sprintf(*out, "%16p %s",
+-                                    vdev->ud.tcp_socket,
++              *out += sprintf(*out, "%u %s",
++                                    vdev->ud.sockfd,
+                                     dev_name(&vdev->udev->dev));
+       } else {
+@@ -174,7 +179,8 @@ static ssize_t nports_show(struct device
+       char *s = out;
+       /*
+-       * Half the ports are for SPEED_HIGH and half for SPEED_SUPER, thus the * 2.
++       * Half the ports are for SPEED_HIGH and half for SPEED_SUPER,
++       * thus the * 2.
+        */
+       out += sprintf(out, "%d\n", VHCI_PORTS * vhci_num_controllers);
+       return out - s;
+@@ -380,6 +386,7 @@ static ssize_t store_attach(struct devic
+       vdev->devid         = devid;
+       vdev->speed         = speed;
++      vdev->ud.sockfd     = sockfd;
+       vdev->ud.tcp_socket = socket;
+       vdev->ud.status     = VDEV_ST_NOTASSIGNED;
+--- a/tools/usb/usbip/libsrc/vhci_driver.c
++++ b/tools/usb/usbip/libsrc/vhci_driver.c
+@@ -50,14 +50,14 @@ static int parse_status(const char *valu
+       while (*c != '\0') {
+               int port, status, speed, devid;
+-              unsigned long socket;
++              int sockfd;
+               char lbusid[SYSFS_BUS_ID_SIZE];
+               struct usbip_imported_device *idev;
+               char hub[3];
+-              ret = sscanf(c, "%2s  %d %d %d %x %lx %31s\n",
++              ret = sscanf(c, "%2s  %d %d %d %x %u %31s\n",
+                               hub, &port, &status, &speed,
+-                              &devid, &socket, lbusid);
++                              &devid, &sockfd, lbusid);
+               if (ret < 5) {
+                       dbg("sscanf failed: %d", ret);
+@@ -66,7 +66,7 @@ static int parse_status(const char *valu
+               dbg("hub %s port %d status %d speed %d devid %x",
+                               hub, port, status, speed, devid);
+-              dbg("socket %lx lbusid %s", socket, lbusid);
++              dbg("sockfd %u lbusid %s", sockfd, lbusid);
+               /* if a device is connected, look at it */
+               idev = &vhci_driver->idev[port];
diff --git a/queue-4.14/x86-boot-compressed-64-detect-and-handle-5-level-paging-at-boot-time.patch b/queue-4.14/x86-boot-compressed-64-detect-and-handle-5-level-paging-at-boot-time.patch
new file mode 100644 (file)
index 0000000..4a63ea5
--- /dev/null
@@ -0,0 +1,101 @@
+From 08529078d8d9adf689bf39cc38d53979a0869970 Mon Sep 17 00:00:00 2001
+From: "Kirill A. Shutemov" <kirill.shutemov@linux.intel.com>
+Date: Mon, 4 Dec 2017 15:40:55 +0300
+Subject: x86/boot/compressed/64: Detect and handle 5-level paging at boot-time
+
+From: Kirill A. Shutemov <kirill.shutemov@linux.intel.com>
+
+commit 08529078d8d9adf689bf39cc38d53979a0869970 upstream.
+
+Prerequisite for fixing the current problem of instantaneous reboots when a
+5-level paging kernel is booted on 4-level paging hardware.
+
+At the same time this change prepares the decompression code to boot-time
+switching between 4- and 5-level paging.
+
+[ tglx: Folded the GCC < 5 fix. ]
+
+Fixes: 77ef56e4f0fb ("x86: Enable 5-level paging support via CONFIG_X86_5LEVEL=y")
+Signed-off-by: Kirill A. Shutemov <kirill.shutemov@linux.intel.com>
+Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
+Cc: Andi Kleen <ak@linux.intel.com>
+Cc: Andy Lutomirski <luto@amacapital.net>
+Cc: linux-mm@kvack.org
+Cc: Cyrill Gorcunov <gorcunov@openvz.org>
+Cc: Borislav Petkov <bp@suse.de>
+Cc: Linus Torvalds <torvalds@linux-foundation.org>
+Link: https://lkml.kernel.org/r/20171204124059.63515-2-kirill.shutemov@linux.intel.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/x86/boot/compressed/Makefile     |    1 +
+ arch/x86/boot/compressed/head_64.S    |   16 ++++++++++++----
+ arch/x86/boot/compressed/pgtable_64.c |   28 ++++++++++++++++++++++++++++
+ 3 files changed, 41 insertions(+), 4 deletions(-)
+
+--- a/arch/x86/boot/compressed/Makefile
++++ b/arch/x86/boot/compressed/Makefile
+@@ -78,6 +78,7 @@ vmlinux-objs-$(CONFIG_EARLY_PRINTK) += $
+ vmlinux-objs-$(CONFIG_RANDOMIZE_BASE) += $(obj)/kaslr.o
+ ifdef CONFIG_X86_64
+       vmlinux-objs-$(CONFIG_RANDOMIZE_BASE) += $(obj)/pagetable.o
++      vmlinux-objs-y += $(obj)/pgtable_64.o
+ endif
+ $(obj)/eboot.o: KBUILD_CFLAGS += -fshort-wchar -mno-red-zone
+--- a/arch/x86/boot/compressed/head_64.S
++++ b/arch/x86/boot/compressed/head_64.S
+@@ -289,10 +289,18 @@ ENTRY(startup_64)
+       leaq    boot_stack_end(%rbx), %rsp
+ #ifdef CONFIG_X86_5LEVEL
+-      /* Check if 5-level paging has already enabled */
+-      movq    %cr4, %rax
+-      testl   $X86_CR4_LA57, %eax
+-      jnz     lvl5
++      /*
++       * Check if we need to enable 5-level paging.
++       * RSI holds real mode data and need to be preserved across
++       * a function call.
++       */
++      pushq   %rsi
++      call    l5_paging_required
++      popq    %rsi
++
++      /* If l5_paging_required() returned zero, we're done here. */
++      cmpq    $0, %rax
++      je      lvl5
+       /*
+        * At this point we are in long mode with 4-level paging enabled,
+--- /dev/null
++++ b/arch/x86/boot/compressed/pgtable_64.c
+@@ -0,0 +1,28 @@
++#include <asm/processor.h>
++
++/*
++ * __force_order is used by special_insns.h asm code to force instruction
++ * serialization.
++ *
++ * It is not referenced from the code, but GCC < 5 with -fPIE would fail
++ * due to an undefined symbol. Define it to make these ancient GCCs work.
++ */
++unsigned long __force_order;
++
++int l5_paging_required(void)
++{
++      /* Check if leaf 7 is supported. */
++
++      if (native_cpuid_eax(0) < 7)
++              return 0;
++
++      /* Check if la57 is supported. */
++      if (!(native_cpuid_ecx(7) & (1 << (X86_FEATURE_LA57 & 31))))
++              return 0;
++
++      /* Check if 5-level paging has already been enabled. */
++      if (native_read_cr4() & X86_CR4_LA57)
++              return 0;
++
++      return 1;
++}
diff --git a/queue-4.14/x86-boot-compressed-64-print-error-if-5-level-paging-is-not-supported.patch b/queue-4.14/x86-boot-compressed-64-print-error-if-5-level-paging-is-not-supported.patch
new file mode 100644 (file)
index 0000000..cb28472
--- /dev/null
@@ -0,0 +1,68 @@
+From 6d7e0ba2d2be9e50cccba213baf07e0e183c1b24 Mon Sep 17 00:00:00 2001
+From: "Kirill A. Shutemov" <kirill.shutemov@linux.intel.com>
+Date: Mon, 4 Dec 2017 15:40:56 +0300
+Subject: x86/boot/compressed/64: Print error if 5-level paging is not supported
+
+From: Kirill A. Shutemov <kirill.shutemov@linux.intel.com>
+
+commit 6d7e0ba2d2be9e50cccba213baf07e0e183c1b24 upstream.
+
+If the machine does not support the paging mode for which the kernel was
+compiled, the boot process cannot continue.
+
+It's not possible to let the kernel detect the mismatch as it does not even
+reach the point where cpu features can be evaluted due to a triple fault in
+the KASLR setup.
+
+Instead of instantaneous silent reboot, emit an error message which gives
+the user the information why the boot fails.
+
+Fixes: 77ef56e4f0fb ("x86: Enable 5-level paging support via CONFIG_X86_5LEVEL=y")
+Reported-by: Borislav Petkov <bp@suse.de>
+Signed-off-by: Kirill A. Shutemov <kirill.shutemov@linux.intel.com>
+Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
+Tested-by: Borislav Petkov <bp@suse.de>
+Cc: Andi Kleen <ak@linux.intel.com>
+Cc: Andy Lutomirski <luto@amacapital.net>
+Cc: linux-mm@kvack.org
+Cc: Cyrill Gorcunov <gorcunov@openvz.org>
+Cc: Linus Torvalds <torvalds@linux-foundation.org>
+Link: https://lkml.kernel.org/r/20171204124059.63515-3-kirill.shutemov@linux.intel.com
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/x86/boot/compressed/misc.c |   16 ++++++++++++++++
+ 1 file changed, 16 insertions(+)
+
+--- a/arch/x86/boot/compressed/misc.c
++++ b/arch/x86/boot/compressed/misc.c
+@@ -169,6 +169,16 @@ void __puthex(unsigned long value)
+       }
+ }
++static bool l5_supported(void)
++{
++      /* Check if leaf 7 is supported. */
++      if (native_cpuid_eax(0) < 7)
++              return 0;
++
++      /* Check if la57 is supported. */
++      return native_cpuid_ecx(7) & (1 << (X86_FEATURE_LA57 & 31));
++}
++
+ #if CONFIG_X86_NEED_RELOCS
+ static void handle_relocations(void *output, unsigned long output_len,
+                              unsigned long virt_addr)
+@@ -362,6 +372,12 @@ asmlinkage __visible void *extract_kerne
+       console_init();
+       debug_putstr("early console in extract_kernel\n");
++      if (IS_ENABLED(CONFIG_X86_5LEVEL) && !l5_supported()) {
++              error("This linux kernel as configured requires 5-level paging\n"
++                      "This CPU does not support the required 'cr4.la57' feature\n"
++                      "Unable to boot - please use a kernel appropriate for your CPU\n");
++      }
++
+       free_mem_ptr     = heap;        /* Heap */
+       free_mem_end_ptr = heap + BOOT_HEAP_SIZE;
diff --git a/queue-4.14/xhci-don-t-add-a-virt_dev-to-the-devs-array-before-it-s-fully-allocated.patch b/queue-4.14/xhci-don-t-add-a-virt_dev-to-the-devs-array-before-it-s-fully-allocated.patch
new file mode 100644 (file)
index 0000000..fa0ece7
--- /dev/null
@@ -0,0 +1,62 @@
+From 5d9b70f7d52eb14bb37861c663bae44de9521c35 Mon Sep 17 00:00:00 2001
+From: Mathias Nyman <mathias.nyman@linux.intel.com>
+Date: Fri, 8 Dec 2017 18:10:05 +0200
+Subject: xhci: Don't add a virt_dev to the devs array before it's fully allocated
+
+From: Mathias Nyman <mathias.nyman@linux.intel.com>
+
+commit 5d9b70f7d52eb14bb37861c663bae44de9521c35 upstream.
+
+Avoid null pointer dereference if some function is walking through the
+devs array accessing members of a new virt_dev that is mid allocation.
+
+Add the virt_dev to xhci->devs[i] _after_ the virt_device and all its
+members are properly allocated.
+
+issue found by KASAN: null-ptr-deref in xhci_find_slot_id_by_port
+
+"Quick analysis suggests that xhci_alloc_virt_device() is not mutex
+protected. If so, there is a time frame where xhci->devs[slot_id] is set
+but not fully initialized. Specifically, xhci->devs[i]->udev can be NULL."
+
+Signed-off-by: Mathias Nyman <mathias.nyman@linux.intel.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/usb/host/xhci-mem.c |   15 +++++++++++----
+ 1 file changed, 11 insertions(+), 4 deletions(-)
+
+--- a/drivers/usb/host/xhci-mem.c
++++ b/drivers/usb/host/xhci-mem.c
+@@ -983,10 +983,9 @@ int xhci_alloc_virt_device(struct xhci_h
+               return 0;
+       }
+-      xhci->devs[slot_id] = kzalloc(sizeof(*xhci->devs[slot_id]), flags);
+-      if (!xhci->devs[slot_id])
++      dev = kzalloc(sizeof(*dev), flags);
++      if (!dev)
+               return 0;
+-      dev = xhci->devs[slot_id];
+       /* Allocate the (output) device context that will be used in the HC. */
+       dev->out_ctx = xhci_alloc_container_ctx(xhci, XHCI_CTX_TYPE_DEVICE, flags);
+@@ -1027,9 +1026,17 @@ int xhci_alloc_virt_device(struct xhci_h
+       trace_xhci_alloc_virt_device(dev);
++      xhci->devs[slot_id] = dev;
++
+       return 1;
+ fail:
+-      xhci_free_virt_device(xhci, slot_id);
++
++      if (dev->in_ctx)
++              xhci_free_container_ctx(xhci, dev->in_ctx);
++      if (dev->out_ctx)
++              xhci_free_container_ctx(xhci, dev->out_ctx);
++      kfree(dev);
++
+       return 0;
+ }