--- /dev/null
+From bdc3478f90cd4d2928197f36629d5cf93b64dbe9 Mon Sep 17 00:00:00 2001
+From: Marcel Hasler <mahasler@gmail.com>
+Date: Thu, 27 Oct 2016 00:42:27 +0200
+Subject: ALSA: usb-audio: Add quirk for Syntek STK1160
+
+From: Marcel Hasler <mahasler@gmail.com>
+
+commit bdc3478f90cd4d2928197f36629d5cf93b64dbe9 upstream.
+
+The stk1160 chip needs QUIRK_AUDIO_ALIGN_TRANSFER. This patch resolves
+the issue reported on the mailing list
+(http://marc.info/?l=linux-sound&m=139223599126215&w=2) and also fixes
+bug 180071 (https://bugzilla.kernel.org/show_bug.cgi?id=180071).
+
+Signed-off-by: Marcel Hasler <mahasler@gmail.com>
+Signed-off-by: Takashi Iwai <tiwai@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ sound/usb/quirks-table.h | 17 +++++++++++++++++
+ 1 file changed, 17 insertions(+)
+
+--- a/sound/usb/quirks-table.h
++++ b/sound/usb/quirks-table.h
+@@ -2959,6 +2959,23 @@ AU0828_DEVICE(0x2040, 0x7270, "Hauppauge
+ }
+ },
+
++/* Syntek STK1160 */
++{
++ .match_flags = USB_DEVICE_ID_MATCH_DEVICE |
++ USB_DEVICE_ID_MATCH_INT_CLASS |
++ USB_DEVICE_ID_MATCH_INT_SUBCLASS,
++ .idVendor = 0x05e1,
++ .idProduct = 0x0408,
++ .bInterfaceClass = USB_CLASS_AUDIO,
++ .bInterfaceSubClass = USB_SUBCLASS_AUDIOCONTROL,
++ .driver_info = (unsigned long) &(const struct snd_usb_audio_quirk) {
++ .vendor_name = "Syntek",
++ .product_name = "STK1160",
++ .ifnum = QUIRK_ANY_INTERFACE,
++ .type = QUIRK_AUDIO_ALIGN_TRANSFER
++ }
++},
++
+ /* Digidesign Mbox */
+ {
+ /* Thanks to Clemens Ladisch <clemens@ladisch.de> */
--- /dev/null
+From 0a3ffab93fe52530602fe47cd74802cffdb19c05 Mon Sep 17 00:00:00 2001
+From: =?UTF-8?q?Arve=20Hj=C3=B8nnev=C3=A5g?= <arve@android.com>
+Date: Mon, 24 Oct 2016 15:20:29 +0200
+Subject: ANDROID: binder: Add strong ref checks
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Arve Hjønnevåg <arve@android.com>
+
+commit 0a3ffab93fe52530602fe47cd74802cffdb19c05 upstream.
+
+Prevent using a binder_ref with only weak references where a strong
+reference is required.
+
+Signed-off-by: Arve Hjønnevåg <arve@android.com>
+Signed-off-by: Martijn Coenen <maco@android.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/staging/android/binder.c | 30 +++++++++++++++++++++---------
+ 1 file changed, 21 insertions(+), 9 deletions(-)
+
+--- a/drivers/staging/android/binder.c
++++ b/drivers/staging/android/binder.c
+@@ -998,7 +998,7 @@ static int binder_dec_node(struct binder
+
+
+ static struct binder_ref *binder_get_ref(struct binder_proc *proc,
+- uint32_t desc)
++ u32 desc, bool need_strong_ref)
+ {
+ struct rb_node *n = proc->refs_by_desc.rb_node;
+ struct binder_ref *ref;
+@@ -1006,12 +1006,16 @@ static struct binder_ref *binder_get_ref
+ while (n) {
+ ref = rb_entry(n, struct binder_ref, rb_node_desc);
+
+- if (desc < ref->desc)
++ if (desc < ref->desc) {
+ n = n->rb_left;
+- else if (desc > ref->desc)
++ } else if (desc > ref->desc) {
+ n = n->rb_right;
+- else
++ } else if (need_strong_ref && !ref->strong) {
++ binder_user_error("tried to use weak ref as strong ref\n");
++ return NULL;
++ } else {
+ return ref;
++ }
+ }
+ return NULL;
+ }
+@@ -1281,7 +1285,10 @@ static void binder_transaction_buffer_re
+ } break;
+ case BINDER_TYPE_HANDLE:
+ case BINDER_TYPE_WEAK_HANDLE: {
+- struct binder_ref *ref = binder_get_ref(proc, fp->handle);
++ struct binder_ref *ref;
++
++ ref = binder_get_ref(proc, fp->handle,
++ fp->type == BINDER_TYPE_HANDLE);
+
+ if (ref == NULL) {
+ pr_err("transaction release %d bad handle %d\n",
+@@ -1375,7 +1382,7 @@ static void binder_transaction(struct bi
+ if (tr->target.handle) {
+ struct binder_ref *ref;
+
+- ref = binder_get_ref(proc, tr->target.handle);
++ ref = binder_get_ref(proc, tr->target.handle, true);
+ if (ref == NULL) {
+ binder_user_error("%d:%d got transaction to invalid handle\n",
+ proc->pid, thread->pid);
+@@ -1568,7 +1575,10 @@ static void binder_transaction(struct bi
+ } break;
+ case BINDER_TYPE_HANDLE:
+ case BINDER_TYPE_WEAK_HANDLE: {
+- struct binder_ref *ref = binder_get_ref(proc, fp->handle);
++ struct binder_ref *ref;
++
++ ref = binder_get_ref(proc, fp->handle,
++ fp->type == BINDER_TYPE_HANDLE);
+
+ if (ref == NULL) {
+ binder_user_error("%d:%d got transaction with invalid handle, %d\n",
+@@ -1767,7 +1777,9 @@ static int binder_thread_write(struct bi
+ ref->desc);
+ }
+ } else
+- ref = binder_get_ref(proc, target);
++ ref = binder_get_ref(proc, target,
++ cmd == BC_ACQUIRE ||
++ cmd == BC_RELEASE);
+ if (ref == NULL) {
+ binder_user_error("%d:%d refcount change on invalid ref %d\n",
+ proc->pid, thread->pid, target);
+@@ -1963,7 +1975,7 @@ static int binder_thread_write(struct bi
+ if (get_user(cookie, (binder_uintptr_t __user *)ptr))
+ return -EFAULT;
+ ptr += sizeof(binder_uintptr_t);
+- ref = binder_get_ref(proc, target);
++ ref = binder_get_ref(proc, target, false);
+ if (ref == NULL) {
+ binder_user_error("%d:%d %s invalid ref %d\n",
+ proc->pid, thread->pid,
--- /dev/null
+From 4afb604e2d14d429ac9e1fd84b952602853b2df5 Mon Sep 17 00:00:00 2001
+From: =?UTF-8?q?Arve=20Hj=C3=B8nnev=C3=A5g?= <arve@android.com>
+Date: Mon, 24 Oct 2016 15:20:30 +0200
+Subject: ANDROID: binder: Clear binder and cookie when setting handle in flat binder struct
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Arve Hjønnevåg <arve@android.com>
+
+commit 4afb604e2d14d429ac9e1fd84b952602853b2df5 upstream.
+
+Prevents leaking pointers between processes
+
+Signed-off-by: Arve Hjønnevåg <arve@android.com>
+Signed-off-by: Martijn Coenen <maco@android.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/staging/android/binder.c | 5 +++++
+ 1 file changed, 5 insertions(+)
+
+--- a/drivers/staging/android/binder.c
++++ b/drivers/staging/android/binder.c
+@@ -1563,7 +1563,9 @@ static void binder_transaction(struct bi
+ fp->type = BINDER_TYPE_HANDLE;
+ else
+ fp->type = BINDER_TYPE_WEAK_HANDLE;
++ fp->binder = 0;
+ fp->handle = ref->desc;
++ fp->cookie = 0;
+ binder_inc_ref(ref, fp->type == BINDER_TYPE_HANDLE,
+ &thread->todo);
+
+@@ -1608,7 +1610,9 @@ static void binder_transaction(struct bi
+ return_error = BR_FAILED_REPLY;
+ goto err_binder_get_ref_for_node_failed;
+ }
++ fp->binder = 0;
+ fp->handle = new_ref->desc;
++ fp->cookie = 0;
+ binder_inc_ref(new_ref, fp->type == BINDER_TYPE_HANDLE, NULL);
+ trace_binder_transaction_ref_to_ref(t, ref,
+ new_ref);
+@@ -1655,6 +1659,7 @@ static void binder_transaction(struct bi
+ binder_debug(BINDER_DEBUG_TRANSACTION,
+ " fd %d -> %d\n", fp->handle, target_fd);
+ /* TODO: fput? */
++ fp->binder = 0;
+ fp->handle = target_fd;
+ } break;
+
--- /dev/null
+From dd665be0e243873343a28e18f9f345927b658daf Mon Sep 17 00:00:00 2001
+From: Arnd Bergmann <arnd@arndb.de>
+Date: Fri, 1 Jul 2016 18:02:22 +0100
+Subject: ARM: 8584/1: floppy: avoid gcc-6 warning
+
+From: Arnd Bergmann <arnd@arndb.de>
+
+commit dd665be0e243873343a28e18f9f345927b658daf upstream.
+
+gcc-6.0 warns about comparisons between two identical expressions,
+which is what we get in the floppy driver when writing to the FD_DOR
+register:
+
+drivers/block/floppy.c: In function 'set_dor':
+drivers/block/floppy.c:810:44: error: self-comparison always evaluates to true [-Werror=tautological-compare]
+ fd_outb(newdor, FD_DOR);
+
+It would be nice to use a static inline function instead of the
+macro, to avoid the warning, but we cannot do that because the
+FD_DOR definition is incomplete at this point.
+
+Adding a cast to (u32) is a harmless way to shut up the warning,
+just not very nice.
+
+Signed-off-by: Arnd Bergmann <arnd@arndb.de>
+Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/arm/include/asm/floppy.h | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/arch/arm/include/asm/floppy.h
++++ b/arch/arm/include/asm/floppy.h
+@@ -17,7 +17,7 @@
+
+ #define fd_outb(val,port) \
+ do { \
+- if ((port) == FD_DOR) \
++ if ((port) == (u32)FD_DOR) \
+ fd_setdor((val)); \
+ else \
+ outb((val),(port)); \
--- /dev/null
+From 55c4b906aa2aec3fa66310ec03c6842e34a04b2a Mon Sep 17 00:00:00 2001
+From: Arnd Bergmann <arnd@arndb.de>
+Date: Mon, 14 Mar 2016 15:22:25 +0100
+Subject: drm/exynos: fix error handling in exynos_drm_subdrv_open
+
+From: Arnd Bergmann <arnd@arndb.de>
+
+commit 55c4b906aa2aec3fa66310ec03c6842e34a04b2a upstream.
+
+gcc-6 warns about a pointless loop in exynos_drm_subdrv_open:
+
+drivers/gpu/drm/exynos/exynos_drm_core.c: In function 'exynos_drm_subdrv_open':
+drivers/gpu/drm/exynos/exynos_drm_core.c:104:199: error: self-comparison always evaluates to false [-Werror=tautological-compare]
+ list_for_each_entry_reverse(subdrv, &subdrv->list, list) {
+
+Here, the list_for_each_entry_reverse immediately terminates because
+the subdrv pointer is compared to itself as the loop end condition.
+
+If we were to take the current subdrv pointer as the start of the
+list (as we would do if list_for_each_entry_reverse() was not a macro),
+we would iterate backwards over the &exynos_drm_subdrv_list anchor,
+which would be even worse.
+
+Instead, we need to use list_for_each_entry_continue_reverse()
+to go back over each subdrv that was successfully opened until
+the first entry.
+
+Signed-off-by: Arnd Bergmann <arnd@arndb.de>
+Signed-off-by: Inki Dae <inki.dae@samsung.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/gpu/drm/exynos/exynos_drm_core.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/drivers/gpu/drm/exynos/exynos_drm_core.c
++++ b/drivers/gpu/drm/exynos/exynos_drm_core.c
+@@ -141,7 +141,7 @@ int exynos_drm_subdrv_open(struct drm_de
+ return 0;
+
+ err:
+- list_for_each_entry_reverse(subdrv, &subdrv->list, list) {
++ list_for_each_entry_continue_reverse(subdrv, &exynos_drm_subdrv_list, list) {
+ if (subdrv->close)
+ subdrv->close(dev, subdrv->dev, file);
+ }
--- /dev/null
+From 2dc705a9930b4806250fbf5a76e55266e59389f2 Mon Sep 17 00:00:00 2001
+From: Kees Cook <keescook@chromium.org>
+Date: Tue, 24 Jan 2017 15:18:24 -0800
+Subject: fbdev: color map copying bounds checking
+
+From: Kees Cook <keescook@chromium.org>
+
+commit 2dc705a9930b4806250fbf5a76e55266e59389f2 upstream.
+
+Copying color maps to userspace doesn't check the value of to->start,
+which will cause kernel heap buffer OOB read due to signedness wraps.
+
+CVE-2016-8405
+
+Link: http://lkml.kernel.org/r/20170105224249.GA50925@beast
+Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2")
+Signed-off-by: Kees Cook <keescook@chromium.org>
+Reported-by: Peter Pi (@heisecode) of Trend Micro
+Cc: Min Chong <mchong@google.com>
+Cc: Dan Carpenter <dan.carpenter@oracle.com>
+Cc: Tomi Valkeinen <tomi.valkeinen@ti.com>
+Cc: Bartlomiej Zolnierkiewicz <b.zolnierkie@samsung.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>
+
+---
+ drivers/video/fbdev/core/fbcmap.c | 26 ++++++++++++++------------
+ 1 file changed, 14 insertions(+), 12 deletions(-)
+
+--- a/drivers/video/fbdev/core/fbcmap.c
++++ b/drivers/video/fbdev/core/fbcmap.c
+@@ -163,17 +163,18 @@ void fb_dealloc_cmap(struct fb_cmap *cma
+
+ int fb_copy_cmap(const struct fb_cmap *from, struct fb_cmap *to)
+ {
+- int tooff = 0, fromoff = 0;
+- int size;
++ unsigned int tooff = 0, fromoff = 0;
++ size_t size;
+
+ if (to->start > from->start)
+ fromoff = to->start - from->start;
+ else
+ tooff = from->start - to->start;
+- size = to->len - tooff;
+- if (size > (int) (from->len - fromoff))
+- size = from->len - fromoff;
+- if (size <= 0)
++ if (fromoff >= from->len || tooff >= to->len)
++ return -EINVAL;
++
++ size = min_t(size_t, to->len - tooff, from->len - fromoff);
++ if (size == 0)
+ return -EINVAL;
+ size *= sizeof(u16);
+
+@@ -187,17 +188,18 @@ int fb_copy_cmap(const struct fb_cmap *f
+
+ int fb_cmap_to_user(const struct fb_cmap *from, struct fb_cmap_user *to)
+ {
+- int tooff = 0, fromoff = 0;
+- int size;
++ unsigned int tooff = 0, fromoff = 0;
++ size_t size;
+
+ if (to->start > from->start)
+ fromoff = to->start - from->start;
+ else
+ tooff = from->start - to->start;
+- size = to->len - tooff;
+- if (size > (int) (from->len - fromoff))
+- size = from->len - fromoff;
+- if (size <= 0)
++ if (fromoff >= from->len || tooff >= to->len)
++ return -EINVAL;
++
++ size = min_t(size_t, to->len - tooff, from->len - fromoff);
++ if (size == 0)
+ return -EINVAL;
+ size *= sizeof(u16);
+
--- /dev/null
+From dc1555e670c373bfa4ca2e1e2f839d5fe2b4501a Mon Sep 17 00:00:00 2001
+From: Linus Torvalds <torvalds@linux-foundation.org>
+Date: Tue, 8 Nov 2016 11:17:00 +0100
+Subject: Fix potential infoleak in older kernels
+
+From: Linus Torvalds <torvalds@linux-foundation.org>
+
+commit dc1555e670c373bfa4ca2e1e2f839d5fe2b4501a upstream.
+
+Not upstream as it is not needed there.
+
+So a patch something like this might be a safe way to fix the
+potential infoleak in older kernels.
+
+THIS IS UNTESTED. It's a very obvious patch, though, so if it compiles
+it probably works. It just initializes the output variable with 0 in
+the inline asm description, instead of doing it in the exception
+handler.
+
+It will generate slightly worse code (a few unnecessary ALU
+operations), but it doesn't have any interactions with the exception
+handler implementation.
+
+
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ arch/x86/include/asm/uaccess.h | 10 +++++-----
+ 1 file changed, 5 insertions(+), 5 deletions(-)
+
+--- a/arch/x86/include/asm/uaccess.h
++++ b/arch/x86/include/asm/uaccess.h
+@@ -329,7 +329,7 @@ do { \
+ #define __get_user_asm_u64(x, ptr, retval, errret) \
+ __get_user_asm(x, ptr, retval, "q", "", "=r", errret)
+ #define __get_user_asm_ex_u64(x, ptr) \
+- __get_user_asm_ex(x, ptr, "q", "", "=r")
++ __get_user_asm_ex(x, ptr, "q", "", "=&r")
+ #endif
+
+ #define __get_user_size(x, ptr, size, retval, errret) \
+@@ -372,13 +372,13 @@ do { \
+ __chk_user_ptr(ptr); \
+ switch (size) { \
+ case 1: \
+- __get_user_asm_ex(x, ptr, "b", "b", "=q"); \
++ __get_user_asm_ex(x, ptr, "b", "b", "=&q"); \
+ break; \
+ case 2: \
+- __get_user_asm_ex(x, ptr, "w", "w", "=r"); \
++ __get_user_asm_ex(x, ptr, "w", "w", "=&r"); \
+ break; \
+ case 4: \
+- __get_user_asm_ex(x, ptr, "l", "k", "=r"); \
++ __get_user_asm_ex(x, ptr, "l", "k", "=&r"); \
+ break; \
+ case 8: \
+ __get_user_asm_ex_u64(x, ptr); \
+@@ -396,7 +396,7 @@ do { \
+ " jmp 2b\n" \
+ ".previous\n" \
+ _ASM_EXTABLE_EX(1b, 3b) \
+- : ltype(x) : "m" (__m(addr)))
++ : ltype(x) : "m" (__m(addr)), "0" (0))
+
+ #define __put_user_nocheck(x, ptr, size) \
+ ({ \
--- /dev/null
+From cf0ea4da4c7df11f7a508b2f37518e0f117f3791 Mon Sep 17 00:00:00 2001
+From: Oliver Neukum <oneukum@suse.com>
+Date: Thu, 3 Nov 2016 12:31:41 +0100
+Subject: HID: usbhid: add ATEN CS962 to list of quirky devices
+
+From: Oliver Neukum <oneukum@suse.com>
+
+commit cf0ea4da4c7df11f7a508b2f37518e0f117f3791 upstream.
+
+Like many similar devices it needs a quirk to work.
+Issuing the request gets the device into an irrecoverable state.
+
+Signed-off-by: Oliver Neukum <oneukum@suse.com>
+Signed-off-by: Jiri Kosina <jkosina@suse.cz>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/hid/hid-ids.h | 1 +
+ drivers/hid/usbhid/hid-quirks.c | 1 +
+ 2 files changed, 2 insertions(+)
+
+--- a/drivers/hid/hid-ids.h
++++ b/drivers/hid/hid-ids.h
+@@ -168,6 +168,7 @@
+ #define USB_DEVICE_ID_ATEN_4PORTKVM 0x2205
+ #define USB_DEVICE_ID_ATEN_4PORTKVMC 0x2208
+ #define USB_DEVICE_ID_ATEN_CS682 0x2213
++#define USB_DEVICE_ID_ATEN_CS692 0x8021
+
+ #define USB_VENDOR_ID_ATMEL 0x03eb
+ #define USB_DEVICE_ID_ATMEL_MULTITOUCH 0x211c
+--- a/drivers/hid/usbhid/hid-quirks.c
++++ b/drivers/hid/usbhid/hid-quirks.c
+@@ -61,6 +61,7 @@ static const struct hid_blacklist {
+ { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_4PORTKVM, HID_QUIRK_NOGET },
+ { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_4PORTKVMC, HID_QUIRK_NOGET },
+ { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_CS682, HID_QUIRK_NOGET },
++ { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_CS692, HID_QUIRK_NOGET },
+ { USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_FIGHTERSTICK, HID_QUIRK_NOGET },
+ { USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_COMBATSTICK, HID_QUIRK_NOGET },
+ { USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_FLIGHT_SIM_ECLIPSE_YOKE, HID_QUIRK_NOGET },
--- /dev/null
+From 1c387188c60f53b338c20eee32db055dfe022a9b Mon Sep 17 00:00:00 2001
+From: Ashok Raj <ashok.raj@intel.com>
+Date: Fri, 21 Oct 2016 15:32:05 -0700
+Subject: iommu/vt-d: Fix IOMMU lookup for SR-IOV Virtual Functions
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Ashok Raj <ashok.raj@intel.com>
+
+commit 1c387188c60f53b338c20eee32db055dfe022a9b upstream.
+
+The VT-d specification (§8.3.3) says:
+ ‘Virtual Functions’ of a ‘Physical Function’ are under the scope
+ of the same remapping unit as the ‘Physical Function’.
+
+The BIOS is not required to list all the possible VFs in the scope
+tables, and arguably *shouldn't* make any attempt to do so, since there
+could be a huge number of them.
+
+This has been broken basically for ever — the VF is never going to match
+against a specific unit's scope, so it ends up being assigned to the
+INCLUDE_ALL IOMMU. Which was always actually correct by coincidence, but
+now we're looking at Root-Complex integrated devices with SR-IOV support
+it's going to start being wrong.
+
+Fix it to simply use pci_physfn() before doing the lookup for PCI devices.
+
+Cc: stable@vger.kernel.org
+Signed-off-by: Sainath Grandhi <sainath.grandhi@intel.com>
+Signed-off-by: Ashok Raj <ashok.raj@intel.com>
+Signed-off-by: David Woodhouse <dwmw2@infradead.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/iommu/dmar.c | 4 +++-
+ drivers/iommu/intel-iommu.c | 13 +++++++++++++
+ 2 files changed, 16 insertions(+), 1 deletion(-)
+
+--- a/drivers/iommu/dmar.c
++++ b/drivers/iommu/dmar.c
+@@ -317,7 +317,9 @@ static int dmar_pci_bus_notifier(struct
+ struct pci_dev *pdev = to_pci_dev(data);
+ struct dmar_pci_notify_info *info;
+
+- /* Only care about add/remove events for physical functions */
++ /* Only care about add/remove events for physical functions.
++ * For VFs we actually do the lookup based on the corresponding
++ * PF in device_to_iommu() anyway. */
+ if (pdev->is_virtfn)
+ return NOTIFY_DONE;
+ if (action != BUS_NOTIFY_ADD_DEVICE && action != BUS_NOTIFY_DEL_DEVICE)
+--- a/drivers/iommu/intel-iommu.c
++++ b/drivers/iommu/intel-iommu.c
+@@ -696,7 +696,13 @@ static struct intel_iommu *device_to_iom
+ int i;
+
+ if (dev_is_pci(dev)) {
++ struct pci_dev *pf_pdev;
++
+ pdev = to_pci_dev(dev);
++ /* VFs aren't listed in scope tables; we need to look up
++ * the PF instead to find the IOMMU. */
++ pf_pdev = pci_physfn(pdev);
++ dev = &pf_pdev->dev;
+ segment = pci_domain_nr(pdev->bus);
+ } else if (ACPI_COMPANION(dev))
+ dev = &ACPI_COMPANION(dev)->dev;
+@@ -709,6 +715,13 @@ static struct intel_iommu *device_to_iom
+ for_each_active_dev_scope(drhd->devices,
+ drhd->devices_cnt, i, tmp) {
+ if (tmp == dev) {
++ /* For a VF use its original BDF# not that of the PF
++ * which we used for the IOMMU lookup. Strictly speaking
++ * we could do this for all PCI devices; we only need to
++ * get the BDF# from the scope table for ACPI matches. */
++ if (pdev->is_virtfn)
++ goto got_pdev;
++
+ *bus = drhd->devices[i].bus;
+ *devfn = drhd->devices[i].devfn;
+ goto out;
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Lance Richardson <lrichard@redhat.com>
+Date: Fri, 23 Sep 2016 15:50:29 -0400
+Subject: [PATCH 075/760] ip6_gre: fix flowi6_proto value in ip6gre_xmit_other()
+
+From: Lance Richardson <lrichard@redhat.com>
+
+
+[ Upstream commit db32e4e49ce2b0e5fcc17803d011a401c0a637f6 ]
+
+Similar to commit 3be07244b733 ("ip6_gre: fix flowi6_proto value in
+xmit path"), set flowi6_proto to IPPROTO_GRE for output route lookup.
+
+Up until now, ip6gre_xmit_other() has set flowi6_proto to a bogus value.
+This affected output route lookup for packets sent on an ip6gretap device
+in cases where routing was dependent on the value of flowi6_proto.
+
+Since the correct proto is already set in the tunnel flowi6 template via
+commit 252f3f5a1189 ("ip6_gre: Set flowi6_proto as IPPROTO_GRE in xmit
+path."), simply delete the line setting the incorrect flowi6_proto value.
+
+Suggested-by: Jiri Benc <jbenc@redhat.com>
+Fixes: c12b395a4664 ("gre: Support GRE over IPv6")
+Reviewed-by: Shmulik Ladkani <shmulik.ladkani@gmail.com>
+Signed-off-by: Lance Richardson <lrichard@redhat.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/ipv6/ip6_gre.c | 1 -
+ 1 file changed, 1 deletion(-)
+
+--- a/net/ipv6/ip6_gre.c
++++ b/net/ipv6/ip6_gre.c
+@@ -892,7 +892,6 @@ static int ip6gre_xmit_other(struct sk_b
+ encap_limit = t->parms.encap_limit;
+
+ memcpy(&fl6, &t->fl.u.ip6, sizeof(fl6));
+- fl6.flowi6_proto = skb->protocol;
+
+ err = ip6gre_xmit2(skb, dev, 0, &fl6, encap_limit, &mtu);
+
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
+Date: Sun, 25 Sep 2016 23:08:31 +0200
+Subject: [PATCH 076/760] ipmr, ip6mr: fix scheduling while atomic and a deadlock with ipmr_get_route
+
+From: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
+
+
+[ Upstream commit 2cf750704bb6d7ed8c7d732e071dd1bc890ea5e8 ]
+
+Since the commit below the ipmr/ip6mr rtnl_unicast() code uses the portid
+instead of the previous dst_pid which was copied from in_skb's portid.
+Since the skb is new the portid is 0 at that point so the packets are sent
+to the kernel and we get scheduling while atomic or a deadlock (depending
+on where it happens) by trying to acquire rtnl two times.
+Also since this is RTM_GETROUTE, it can be triggered by a normal user.
+
+Here's the sleeping while atomic trace:
+[ 7858.212557] BUG: sleeping function called from invalid context at kernel/locking/mutex.c:620
+[ 7858.212748] in_atomic(): 1, irqs_disabled(): 0, pid: 0, name: swapper/0
+[ 7858.212881] 2 locks held by swapper/0/0:
+[ 7858.213013] #0: (((&mrt->ipmr_expire_timer))){+.-...}, at: [<ffffffff810fbbf5>] call_timer_fn+0x5/0x350
+[ 7858.213422] #1: (mfc_unres_lock){+.....}, at: [<ffffffff8161e005>] ipmr_expire_process+0x25/0x130
+[ 7858.213807] CPU: 0 PID: 0 Comm: swapper/0 Not tainted 4.8.0-rc7+ #179
+[ 7858.213934] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.7.5-20140531_083030-gandalf 04/01/2014
+[ 7858.214108] 0000000000000000 ffff88005b403c50 ffffffff813a7804 0000000000000000
+[ 7858.214412] ffffffff81a1338e ffff88005b403c78 ffffffff810a4a72 ffffffff81a1338e
+[ 7858.214716] 000000000000026c 0000000000000000 ffff88005b403ca8 ffffffff810a4b9f
+[ 7858.215251] Call Trace:
+[ 7858.215412] <IRQ> [<ffffffff813a7804>] dump_stack+0x85/0xc1
+[ 7858.215662] [<ffffffff810a4a72>] ___might_sleep+0x192/0x250
+[ 7858.215868] [<ffffffff810a4b9f>] __might_sleep+0x6f/0x100
+[ 7858.216072] [<ffffffff8165bea3>] mutex_lock_nested+0x33/0x4d0
+[ 7858.216279] [<ffffffff815a7a5f>] ? netlink_lookup+0x25f/0x460
+[ 7858.216487] [<ffffffff8157474b>] rtnetlink_rcv+0x1b/0x40
+[ 7858.216687] [<ffffffff815a9a0c>] netlink_unicast+0x19c/0x260
+[ 7858.216900] [<ffffffff81573c70>] rtnl_unicast+0x20/0x30
+[ 7858.217128] [<ffffffff8161cd39>] ipmr_destroy_unres+0xa9/0xf0
+[ 7858.217351] [<ffffffff8161e06f>] ipmr_expire_process+0x8f/0x130
+[ 7858.217581] [<ffffffff8161dfe0>] ? ipmr_net_init+0x180/0x180
+[ 7858.217785] [<ffffffff8161dfe0>] ? ipmr_net_init+0x180/0x180
+[ 7858.217990] [<ffffffff810fbc95>] call_timer_fn+0xa5/0x350
+[ 7858.218192] [<ffffffff810fbbf5>] ? call_timer_fn+0x5/0x350
+[ 7858.218415] [<ffffffff8161dfe0>] ? ipmr_net_init+0x180/0x180
+[ 7858.218656] [<ffffffff810fde10>] run_timer_softirq+0x260/0x640
+[ 7858.218865] [<ffffffff8166379b>] ? __do_softirq+0xbb/0x54f
+[ 7858.219068] [<ffffffff816637c8>] __do_softirq+0xe8/0x54f
+[ 7858.219269] [<ffffffff8107a948>] irq_exit+0xb8/0xc0
+[ 7858.219463] [<ffffffff81663452>] smp_apic_timer_interrupt+0x42/0x50
+[ 7858.219678] [<ffffffff816625bc>] apic_timer_interrupt+0x8c/0xa0
+[ 7858.219897] <EOI> [<ffffffff81055f16>] ? native_safe_halt+0x6/0x10
+[ 7858.220165] [<ffffffff810d64dd>] ? trace_hardirqs_on+0xd/0x10
+[ 7858.220373] [<ffffffff810298e3>] default_idle+0x23/0x190
+[ 7858.220574] [<ffffffff8102a20f>] arch_cpu_idle+0xf/0x20
+[ 7858.220790] [<ffffffff810c9f8c>] default_idle_call+0x4c/0x60
+[ 7858.221016] [<ffffffff810ca33b>] cpu_startup_entry+0x39b/0x4d0
+[ 7858.221257] [<ffffffff8164f995>] rest_init+0x135/0x140
+[ 7858.221469] [<ffffffff81f83014>] start_kernel+0x50e/0x51b
+[ 7858.221670] [<ffffffff81f82120>] ? early_idt_handler_array+0x120/0x120
+[ 7858.221894] [<ffffffff81f8243f>] x86_64_start_reservations+0x2a/0x2c
+[ 7858.222113] [<ffffffff81f8257c>] x86_64_start_kernel+0x13b/0x14a
+
+Fixes: 2942e9005056 ("[RTNETLINK]: Use rtnl_unicast() for rtnetlink unicasts")
+Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ include/linux/mroute.h | 2 +-
+ include/linux/mroute6.h | 2 +-
+ net/ipv4/ipmr.c | 3 ++-
+ net/ipv4/route.c | 3 ++-
+ net/ipv6/ip6mr.c | 5 +++--
+ net/ipv6/route.c | 4 +++-
+ 6 files changed, 12 insertions(+), 7 deletions(-)
+
+--- a/include/linux/mroute.h
++++ b/include/linux/mroute.h
+@@ -103,5 +103,5 @@ struct mfc_cache {
+ struct rtmsg;
+ extern int ipmr_get_route(struct net *net, struct sk_buff *skb,
+ __be32 saddr, __be32 daddr,
+- struct rtmsg *rtm, int nowait);
++ struct rtmsg *rtm, int nowait, u32 portid);
+ #endif
+--- a/include/linux/mroute6.h
++++ b/include/linux/mroute6.h
+@@ -115,7 +115,7 @@ struct mfc6_cache {
+
+ struct rtmsg;
+ extern int ip6mr_get_route(struct net *net, struct sk_buff *skb,
+- struct rtmsg *rtm, int nowait);
++ struct rtmsg *rtm, int nowait, u32 portid);
+
+ #ifdef CONFIG_IPV6_MROUTE
+ extern struct sock *mroute6_socket(struct net *net, struct sk_buff *skb);
+--- a/net/ipv4/ipmr.c
++++ b/net/ipv4/ipmr.c
+@@ -2188,7 +2188,7 @@ static int __ipmr_fill_mroute(struct mr_
+
+ int ipmr_get_route(struct net *net, struct sk_buff *skb,
+ __be32 saddr, __be32 daddr,
+- struct rtmsg *rtm, int nowait)
++ struct rtmsg *rtm, int nowait, u32 portid)
+ {
+ struct mfc_cache *cache;
+ struct mr_table *mrt;
+@@ -2233,6 +2233,7 @@ int ipmr_get_route(struct net *net, stru
+ return -ENOMEM;
+ }
+
++ NETLINK_CB(skb2).portid = portid;
+ skb_push(skb2, sizeof(struct iphdr));
+ skb_reset_network_header(skb2);
+ iph = ip_hdr(skb2);
+--- a/net/ipv4/route.c
++++ b/net/ipv4/route.c
+@@ -2373,7 +2373,8 @@ static int rt_fill_info(struct net *net,
+ IPV4_DEVCONF_ALL(net, MC_FORWARDING)) {
+ int err = ipmr_get_route(net, skb,
+ fl4->saddr, fl4->daddr,
+- r, nowait);
++ r, nowait, portid);
++
+ if (err <= 0) {
+ if (!nowait) {
+ if (err == 0)
+--- a/net/ipv6/ip6mr.c
++++ b/net/ipv6/ip6mr.c
+@@ -2276,8 +2276,8 @@ static int __ip6mr_fill_mroute(struct mr
+ return 1;
+ }
+
+-int ip6mr_get_route(struct net *net,
+- struct sk_buff *skb, struct rtmsg *rtm, int nowait)
++int ip6mr_get_route(struct net *net, struct sk_buff *skb, struct rtmsg *rtm,
++ int nowait, u32 portid)
+ {
+ int err;
+ struct mr6_table *mrt;
+@@ -2322,6 +2322,7 @@ int ip6mr_get_route(struct net *net,
+ return -ENOMEM;
+ }
+
++ NETLINK_CB(skb2).portid = portid;
+ skb_reset_transport_header(skb2);
+
+ skb_put(skb2, sizeof(struct ipv6hdr));
+--- a/net/ipv6/route.c
++++ b/net/ipv6/route.c
+@@ -2612,7 +2612,9 @@ static int rt6_fill_node(struct net *net
+ if (iif) {
+ #ifdef CONFIG_IPV6_MROUTE
+ if (ipv6_addr_is_multicast(&rt->rt6i_dst.addr)) {
+- int err = ip6mr_get_route(net, skb, rtm, nowait);
++ int err = ip6mr_get_route(net, skb, rtm, nowait,
++ portid);
++
+ if (err <= 0) {
+ if (!nowait) {
+ if (err == 0)
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Eric Dumazet <edumazet@google.com>
+Date: Thu, 20 Oct 2016 10:26:48 -0700
+Subject: [PATCH 091/760] ipv4: disable BH in set_ping_group_range()
+
+From: Eric Dumazet <edumazet@google.com>
+
+
+[ Upstream commit a681574c99be23e4d20b769bf0e543239c364af5 ]
+
+In commit 4ee3bd4a8c746 ("ipv4: disable BH when changing ip local port
+range") Cong added BH protection in set_local_port_range() but missed
+that same fix was needed in set_ping_group_range()
+
+Fixes: b8f1a55639e6 ("udp: Add function to make source port for UDP tunnels")
+Signed-off-by: Eric Dumazet <edumazet@google.com>
+Reported-by: Eric Salo <salo@google.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/ipv4/sysctl_net_ipv4.c | 4 ++--
+ 1 file changed, 2 insertions(+), 2 deletions(-)
+
+--- a/net/ipv4/sysctl_net_ipv4.c
++++ b/net/ipv4/sysctl_net_ipv4.c
+@@ -103,10 +103,10 @@ static void set_ping_group_range(struct
+ kgid_t *data = table->data;
+ struct net *net =
+ container_of(table->data, struct net, ipv4.ping_group_range.range);
+- write_seqlock(&net->ipv4.ip_local_ports.lock);
++ write_seqlock_bh(&net->ipv4.ip_local_ports.lock);
+ data[0] = low;
+ data[1] = high;
+- write_sequnlock(&net->ipv4.ip_local_ports.lock);
++ write_sequnlock_bh(&net->ipv4.ip_local_ports.lock);
+ }
+
+ /* Validate changes from /proc interface. */
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Nicolas Dichtel <nicolas.dichtel@6wind.com>
+Date: Wed, 12 Oct 2016 10:10:40 +0200
+Subject: [PATCH 086/760] ipv6: correctly add local routes when lo goes up
+
+From: Nicolas Dichtel <nicolas.dichtel@6wind.com>
+
+
+[ Upstream commit a220445f9f4382c36a53d8ef3e08165fa27f7e2c ]
+
+The goal of the patch is to fix this scenario:
+ ip link add dummy1 type dummy
+ ip link set dummy1 up
+ ip link set lo down ; ip link set lo up
+
+After that sequence, the local route to the link layer address of dummy1 is
+not there anymore.
+
+When the loopback is set down, all local routes are deleted by
+addrconf_ifdown()/rt6_ifdown(). At this time, the rt6_info entry still
+exists, because the corresponding idev has a reference on it. After the rcu
+grace period, dst_rcu_free() is called, and thus ___dst_free(), which will
+set obsolete to DST_OBSOLETE_DEAD.
+
+In this case, init_loopback() is called before dst_rcu_free(), thus
+obsolete is still sets to something <= 0. So, the function doesn't add the
+route again. To avoid that race, let's check the rt6 refcnt instead.
+
+Fixes: 25fb6ca4ed9c ("net IPv6 : Fix broken IPv6 routing table after loopback down-up")
+Fixes: a881ae1f625c ("ipv6: don't call addrconf_dst_alloc again when enable lo")
+Fixes: 33d99113b110 ("ipv6: reallocate addrconf router for ipv6 address when lo device up")
+Reported-by: Francesco Santoro <francesco.santoro@6wind.com>
+Reported-by: Samuel Gauthier <samuel.gauthier@6wind.com>
+CC: Balakumaran Kannan <Balakumaran.Kannan@ap.sony.com>
+CC: Maruthi Thotad <Maruthi.Thotad@ap.sony.com>
+CC: Sabrina Dubroca <sd@queasysnail.net>
+CC: Hannes Frederic Sowa <hannes@stressinduktion.org>
+CC: Weilong Chen <chenweilong@huawei.com>
+CC: Gao feng <gaofeng@cn.fujitsu.com>
+Signed-off-by: Nicolas Dichtel <nicolas.dichtel@6wind.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/ipv6/addrconf.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/net/ipv6/addrconf.c
++++ b/net/ipv6/addrconf.c
+@@ -2695,7 +2695,7 @@ static void init_loopback(struct net_dev
+ * lo device down, release this obsolete dst and
+ * reallocate a new router for ifa.
+ */
+- if (sp_ifa->rt->dst.obsolete > 0) {
++ if (!atomic_read(&sp_ifa->rt->rt6i_ref)) {
+ ip6_rt_put(sp_ifa->rt);
+ sp_ifa->rt = NULL;
+ } else {
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
---
- net/ipv6/tcp_ipv6.c | 22 ++++++++++++----------
- 1 file changed, 12 insertions(+), 10 deletions(-)
+ net/ipv6/tcp_ipv6.c | 24 +++++++++++++-----------
+ 1 file changed, 13 insertions(+), 11 deletions(-)
--- a/net/ipv6/tcp_ipv6.c
+++ b/net/ipv6/tcp_ipv6.c
-@@ -1049,6 +1049,15 @@ drop:
+@@ -1049,6 +1049,16 @@ drop:
return 0; /* don't send reset */
}
+{
+ /* We need to move header back to the beginning if xfrm6_policy_check()
+ * and tcp_v6_fill_cb() are going to be called again.
++ * ip6_datagram_recv_specific_ctl() also expects IP6CB to be there.
+ */
+ memmove(IP6CB(skb), &TCP_SKB_CB(skb)->header.h6,
+ sizeof(struct inet6_skb_parm));
static struct sock *tcp_v6_syn_recv_sock(struct sock *sk, struct sk_buff *skb,
struct request_sock *req,
struct dst_entry *dst)
-@@ -1180,8 +1189,10 @@ static struct sock *tcp_v6_syn_recv_sock
+@@ -1180,8 +1190,10 @@ static struct sock *tcp_v6_syn_recv_sock
sk_gfp_atomic(sk, GFP_ATOMIC));
consume_skb(ireq->pktopts);
ireq->pktopts = NULL;
}
newnp->opt = NULL;
newnp->mcast_oif = tcp_v6_iif(skb);
-@@ -1414,15 +1425,6 @@ static void tcp_v6_fill_cb(struct sk_buf
- TCP_SKB_CB(skb)->sacked = 0;
+@@ -1250,16 +1262,6 @@ out:
+ return NULL;
}
-static void tcp_v6_restore_cb(struct sk_buff *skb)
-{
- /* We need to move header back to the beginning if xfrm6_policy_check()
- * and tcp_v6_fill_cb() are going to be called again.
+- * ip6_datagram_recv_specific_ctl() also expects IP6CB to be there.
- */
- memmove(IP6CB(skb), &TCP_SKB_CB(skb)->header.h6,
- sizeof(struct inet6_skb_parm));
-}
-
- static int tcp_v6_rcv(struct sk_buff *skb)
- {
- const struct tcphdr *th;
+ /* The socket must have it's spinlock held when we get
+ * here.
+ *
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Eric Dumazet <edumazet@google.com>
+Date: Wed, 12 Oct 2016 19:01:45 +0200
+Subject: [PATCH 084/760] ipv6: tcp: restore IP6CB for pktoptions skbs
+
+From: Eric Dumazet <edumazet@google.com>
+
+
+[ Upstream commit 8ce48623f0cf3d632e32448411feddccb693d351 ]
+
+Baozeng Ding reported following KASAN splat :
+
+BUG: KASAN: use-after-free in ip6_datagram_recv_specific_ctl+0x13f1/0x15c0 at addr ffff880029c84ec8
+Read of size 1 by task poc/25548
+Call Trace:
+ [<ffffffff82cf43c9>] dump_stack+0x12e/0x185 /lib/dump_stack.c:15
+ [< inline >] print_address_description /mm/kasan/report.c:204
+ [<ffffffff817ced3b>] kasan_report_error+0x48b/0x4b0 /mm/kasan/report.c:283
+ [< inline >] kasan_report /mm/kasan/report.c:303
+ [<ffffffff817ced9e>] __asan_report_load1_noabort+0x3e/0x40 /mm/kasan/report.c:321
+ [<ffffffff85c71da1>] ip6_datagram_recv_specific_ctl+0x13f1/0x15c0 /net/ipv6/datagram.c:687
+ [<ffffffff85c734c3>] ip6_datagram_recv_ctl+0x33/0x40
+ [<ffffffff85c0b07c>] do_ipv6_getsockopt.isra.4+0xaec/0x2150
+ [<ffffffff85c0c7f6>] ipv6_getsockopt+0x116/0x230
+ [<ffffffff859b5a12>] tcp_getsockopt+0x82/0xd0 /net/ipv4/tcp.c:3035
+ [<ffffffff855fb385>] sock_common_getsockopt+0x95/0xd0 /net/core/sock.c:2647
+ [< inline >] SYSC_getsockopt /net/socket.c:1776
+ [<ffffffff855f8ba2>] SyS_getsockopt+0x142/0x230 /net/socket.c:1758
+ [<ffffffff8685cdc5>] entry_SYSCALL_64_fastpath+0x23/0xc6
+Memory state around the buggy address:
+ ffff880029c84d80: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
+ ffff880029c84e00: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
+> ffff880029c84e80: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
+ ^
+ ffff880029c84f00: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
+ ffff880029c84f80: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
+
+He also provided a syzkaller reproducer.
+
+Issue is that ip6_datagram_recv_specific_ctl() expects to find IP6CB
+data that was moved at a different place in tcp_v6_rcv()
+
+This patch moves tcp_v6_restore_cb() up and calls it from
+tcp_v6_do_rcv() when np->pktoptions is set.
+
+Fixes: 971f10eca186 ("tcp: better TCP_SKB_CB layout to reduce cache line misses")
+Signed-off-by: Eric Dumazet <edumazet@google.com>
+Reported-by: Baozeng Ding <sploving1@gmail.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/ipv6/tcp_ipv6.c | 20 +++++++++++---------
+ 1 file changed, 11 insertions(+), 9 deletions(-)
+
+--- a/net/ipv6/tcp_ipv6.c
++++ b/net/ipv6/tcp_ipv6.c
+@@ -1250,6 +1250,16 @@ out:
+ return NULL;
+ }
+
++static void tcp_v6_restore_cb(struct sk_buff *skb)
++{
++ /* We need to move header back to the beginning if xfrm6_policy_check()
++ * and tcp_v6_fill_cb() are going to be called again.
++ * ip6_datagram_recv_specific_ctl() also expects IP6CB to be there.
++ */
++ memmove(IP6CB(skb), &TCP_SKB_CB(skb)->header.h6,
++ sizeof(struct inet6_skb_parm));
++}
++
+ /* The socket must have it's spinlock held when we get
+ * here.
+ *
+@@ -1381,6 +1391,7 @@ ipv6_pktoptions:
+ np->flow_label = ip6_flowlabel(ipv6_hdr(opt_skb));
+ if (ipv6_opt_accepted(sk, opt_skb, &TCP_SKB_CB(opt_skb)->header.h6)) {
+ skb_set_owner_r(opt_skb, sk);
++ tcp_v6_restore_cb(opt_skb);
+ opt_skb = xchg(&np->pktoptions, opt_skb);
+ } else {
+ __kfree_skb(opt_skb);
+@@ -1414,15 +1425,6 @@ static void tcp_v6_fill_cb(struct sk_buf
+ TCP_SKB_CB(skb)->sacked = 0;
+ }
+
+-static void tcp_v6_restore_cb(struct sk_buff *skb)
+-{
+- /* We need to move header back to the beginning if xfrm6_policy_check()
+- * and tcp_v6_fill_cb() are going to be called again.
+- */
+- memmove(IP6CB(skb), &TCP_SKB_CB(skb)->header.h6,
+- sizeof(struct inet6_skb_parm));
+-}
+-
+ static int tcp_v6_rcv(struct sk_buff *skb)
+ {
+ const struct tcphdr *th;
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Andrew Collins <acollins@cradlepoint.com>
+Date: Mon, 3 Oct 2016 13:43:02 -0600
+Subject: [PATCH 081/760] net: Add netdev all_adj_list refcnt propagation to fix panic
+
+From: Andrew Collins <acollins@cradlepoint.com>
+
+
+[ Upstream commit 93409033ae653f1c9a949202fb537ab095b2092f ]
+
+This is a respin of a patch to fix a relatively easily reproducible kernel
+panic related to the all_adj_list handling for netdevs in recent kernels.
+
+The following sequence of commands will reproduce the issue:
+
+ip link add link eth0 name eth0.100 type vlan id 100
+ip link add link eth0 name eth0.200 type vlan id 200
+ip link add name testbr type bridge
+ip link set eth0.100 master testbr
+ip link set eth0.200 master testbr
+ip link add link testbr mac0 type macvlan
+ip link delete dev testbr
+
+This creates an upper/lower tree of (excuse the poor ASCII art):
+
+ /---eth0.100-eth0
+mac0-testbr-
+ \---eth0.200-eth0
+
+When testbr is deleted, the all_adj_lists are walked, and eth0 is deleted twice from
+the mac0 list. Unfortunately, during setup in __netdev_upper_dev_link, only one
+reference to eth0 is added, so this results in a panic.
+
+This change adds reference count propagation so things are handled properly.
+
+Matthias Schiffer reported a similar crash in batman-adv:
+
+https://github.com/freifunk-gluon/gluon/issues/680
+https://www.open-mesh.org/issues/247
+
+which this patch also seems to resolve.
+
+Signed-off-by: Andrew Collins <acollins@cradlepoint.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/core/dev.c | 68 +++++++++++++++++++++++++++++++--------------------------
+ 1 file changed, 37 insertions(+), 31 deletions(-)
+
+--- a/net/core/dev.c
++++ b/net/core/dev.c
+@@ -4893,6 +4893,7 @@ static inline bool netdev_adjacent_is_ne
+
+ static int __netdev_adjacent_dev_insert(struct net_device *dev,
+ struct net_device *adj_dev,
++ u16 ref_nr,
+ struct list_head *dev_list,
+ void *private, bool master)
+ {
+@@ -4902,7 +4903,7 @@ static int __netdev_adjacent_dev_insert(
+ adj = __netdev_find_adj(dev, adj_dev, dev_list);
+
+ if (adj) {
+- adj->ref_nr++;
++ adj->ref_nr += ref_nr;
+ return 0;
+ }
+
+@@ -4912,7 +4913,7 @@ static int __netdev_adjacent_dev_insert(
+
+ adj->dev = adj_dev;
+ adj->master = master;
+- adj->ref_nr = 1;
++ adj->ref_nr = ref_nr;
+ adj->private = private;
+ dev_hold(adj_dev);
+
+@@ -4951,6 +4952,7 @@ free_adj:
+
+ static void __netdev_adjacent_dev_remove(struct net_device *dev,
+ struct net_device *adj_dev,
++ u16 ref_nr,
+ struct list_head *dev_list)
+ {
+ struct netdev_adjacent *adj;
+@@ -4963,10 +4965,10 @@ static void __netdev_adjacent_dev_remove
+ BUG();
+ }
+
+- if (adj->ref_nr > 1) {
+- pr_debug("%s to %s ref_nr-- = %d\n", dev->name, adj_dev->name,
+- adj->ref_nr-1);
+- adj->ref_nr--;
++ if (adj->ref_nr > ref_nr) {
++ pr_debug("%s to %s ref_nr-%d = %d\n", dev->name, adj_dev->name,
++ ref_nr, adj->ref_nr-ref_nr);
++ adj->ref_nr -= ref_nr;
+ return;
+ }
+
+@@ -4985,21 +4987,22 @@ static void __netdev_adjacent_dev_remove
+
+ static int __netdev_adjacent_dev_link_lists(struct net_device *dev,
+ struct net_device *upper_dev,
++ u16 ref_nr,
+ struct list_head *up_list,
+ struct list_head *down_list,
+ void *private, bool master)
+ {
+ int ret;
+
+- ret = __netdev_adjacent_dev_insert(dev, upper_dev, up_list, private,
+- master);
++ ret = __netdev_adjacent_dev_insert(dev, upper_dev, ref_nr, up_list,
++ private, master);
+ if (ret)
+ return ret;
+
+- ret = __netdev_adjacent_dev_insert(upper_dev, dev, down_list, private,
+- false);
++ ret = __netdev_adjacent_dev_insert(upper_dev, dev, ref_nr, down_list,
++ private, false);
+ if (ret) {
+- __netdev_adjacent_dev_remove(dev, upper_dev, up_list);
++ __netdev_adjacent_dev_remove(dev, upper_dev, ref_nr, up_list);
+ return ret;
+ }
+
+@@ -5007,9 +5010,10 @@ static int __netdev_adjacent_dev_link_li
+ }
+
+ static int __netdev_adjacent_dev_link(struct net_device *dev,
+- struct net_device *upper_dev)
++ struct net_device *upper_dev,
++ u16 ref_nr)
+ {
+- return __netdev_adjacent_dev_link_lists(dev, upper_dev,
++ return __netdev_adjacent_dev_link_lists(dev, upper_dev, ref_nr,
+ &dev->all_adj_list.upper,
+ &upper_dev->all_adj_list.lower,
+ NULL, false);
+@@ -5017,17 +5021,19 @@ static int __netdev_adjacent_dev_link(st
+
+ static void __netdev_adjacent_dev_unlink_lists(struct net_device *dev,
+ struct net_device *upper_dev,
++ u16 ref_nr,
+ struct list_head *up_list,
+ struct list_head *down_list)
+ {
+- __netdev_adjacent_dev_remove(dev, upper_dev, up_list);
+- __netdev_adjacent_dev_remove(upper_dev, dev, down_list);
++ __netdev_adjacent_dev_remove(dev, upper_dev, ref_nr, up_list);
++ __netdev_adjacent_dev_remove(upper_dev, dev, ref_nr, down_list);
+ }
+
+ static void __netdev_adjacent_dev_unlink(struct net_device *dev,
+- struct net_device *upper_dev)
++ struct net_device *upper_dev,
++ u16 ref_nr)
+ {
+- __netdev_adjacent_dev_unlink_lists(dev, upper_dev,
++ __netdev_adjacent_dev_unlink_lists(dev, upper_dev, ref_nr,
+ &dev->all_adj_list.upper,
+ &upper_dev->all_adj_list.lower);
+ }
+@@ -5036,17 +5042,17 @@ static int __netdev_adjacent_dev_link_ne
+ struct net_device *upper_dev,
+ void *private, bool master)
+ {
+- int ret = __netdev_adjacent_dev_link(dev, upper_dev);
++ int ret = __netdev_adjacent_dev_link(dev, upper_dev, 1);
+
+ if (ret)
+ return ret;
+
+- ret = __netdev_adjacent_dev_link_lists(dev, upper_dev,
++ ret = __netdev_adjacent_dev_link_lists(dev, upper_dev, 1,
+ &dev->adj_list.upper,
+ &upper_dev->adj_list.lower,
+ private, master);
+ if (ret) {
+- __netdev_adjacent_dev_unlink(dev, upper_dev);
++ __netdev_adjacent_dev_unlink(dev, upper_dev, 1);
+ return ret;
+ }
+
+@@ -5056,8 +5062,8 @@ static int __netdev_adjacent_dev_link_ne
+ static void __netdev_adjacent_dev_unlink_neighbour(struct net_device *dev,
+ struct net_device *upper_dev)
+ {
+- __netdev_adjacent_dev_unlink(dev, upper_dev);
+- __netdev_adjacent_dev_unlink_lists(dev, upper_dev,
++ __netdev_adjacent_dev_unlink(dev, upper_dev, 1);
++ __netdev_adjacent_dev_unlink_lists(dev, upper_dev, 1,
+ &dev->adj_list.upper,
+ &upper_dev->adj_list.lower);
+ }
+@@ -5098,7 +5104,7 @@ static int __netdev_upper_dev_link(struc
+ list_for_each_entry(j, &upper_dev->all_adj_list.upper, list) {
+ pr_debug("Interlinking %s with %s, non-neighbour\n",
+ i->dev->name, j->dev->name);
+- ret = __netdev_adjacent_dev_link(i->dev, j->dev);
++ ret = __netdev_adjacent_dev_link(i->dev, j->dev, i->ref_nr);
+ if (ret)
+ goto rollback_mesh;
+ }
+@@ -5108,7 +5114,7 @@ static int __netdev_upper_dev_link(struc
+ list_for_each_entry(i, &upper_dev->all_adj_list.upper, list) {
+ pr_debug("linking %s's upper device %s with %s\n",
+ upper_dev->name, i->dev->name, dev->name);
+- ret = __netdev_adjacent_dev_link(dev, i->dev);
++ ret = __netdev_adjacent_dev_link(dev, i->dev, i->ref_nr);
+ if (ret)
+ goto rollback_upper_mesh;
+ }
+@@ -5117,7 +5123,7 @@ static int __netdev_upper_dev_link(struc
+ list_for_each_entry(i, &dev->all_adj_list.lower, list) {
+ pr_debug("linking %s's lower device %s with %s\n", dev->name,
+ i->dev->name, upper_dev->name);
+- ret = __netdev_adjacent_dev_link(i->dev, upper_dev);
++ ret = __netdev_adjacent_dev_link(i->dev, upper_dev, i->ref_nr);
+ if (ret)
+ goto rollback_lower_mesh;
+ }
+@@ -5130,7 +5136,7 @@ rollback_lower_mesh:
+ list_for_each_entry(i, &dev->all_adj_list.lower, list) {
+ if (i == to_i)
+ break;
+- __netdev_adjacent_dev_unlink(i->dev, upper_dev);
++ __netdev_adjacent_dev_unlink(i->dev, upper_dev, i->ref_nr);
+ }
+
+ i = NULL;
+@@ -5140,7 +5146,7 @@ rollback_upper_mesh:
+ list_for_each_entry(i, &upper_dev->all_adj_list.upper, list) {
+ if (i == to_i)
+ break;
+- __netdev_adjacent_dev_unlink(dev, i->dev);
++ __netdev_adjacent_dev_unlink(dev, i->dev, i->ref_nr);
+ }
+
+ i = j = NULL;
+@@ -5152,7 +5158,7 @@ rollback_mesh:
+ list_for_each_entry(j, &upper_dev->all_adj_list.upper, list) {
+ if (i == to_i && j == to_j)
+ break;
+- __netdev_adjacent_dev_unlink(i->dev, j->dev);
++ __netdev_adjacent_dev_unlink(i->dev, j->dev, i->ref_nr);
+ }
+ if (i == to_i)
+ break;
+@@ -5228,16 +5234,16 @@ void netdev_upper_dev_unlink(struct net_
+ */
+ list_for_each_entry(i, &dev->all_adj_list.lower, list)
+ list_for_each_entry(j, &upper_dev->all_adj_list.upper, list)
+- __netdev_adjacent_dev_unlink(i->dev, j->dev);
++ __netdev_adjacent_dev_unlink(i->dev, j->dev, i->ref_nr);
+
+ /* remove also the devices itself from lower/upper device
+ * list
+ */
+ list_for_each_entry(i, &dev->all_adj_list.lower, list)
+- __netdev_adjacent_dev_unlink(i->dev, upper_dev);
++ __netdev_adjacent_dev_unlink(i->dev, upper_dev, i->ref_nr);
+
+ list_for_each_entry(i, &upper_dev->all_adj_list.upper, list)
+- __netdev_adjacent_dev_unlink(dev, i->dev);
++ __netdev_adjacent_dev_unlink(dev, i->dev, i->ref_nr);
+
+ call_netdevice_notifiers(NETDEV_CHANGEUPPER, dev);
+ }
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Eric Dumazet <edumazet@google.com>
+Date: Sat, 15 Oct 2016 17:50:49 +0200
+Subject: [PATCH 087/760] net: pktgen: remove rcu locking in pktgen_change_name()
+
+From: Eric Dumazet <edumazet@google.com>
+
+
+[ Upstream commit 9a0b1e8ba4061778897b544afc898de2163382f7 ]
+
+After Jesper commit back in linux-3.18, we trigger a lockdep
+splat in proc_create_data() while allocating memory from
+pktgen_change_name().
+
+This patch converts t->if_lock to a mutex, since it is now only
+used from control path, and adds proper locking to pktgen_change_name()
+
+1) pktgen_thread_lock to protect the outer loop (iterating threads)
+2) t->if_lock to protect the inner loop (iterating devices)
+
+Note that before Jesper patch, pktgen_change_name() was lacking proper
+protection, but lockdep was not able to detect the problem.
+
+Fixes: 8788370a1d4b ("pktgen: RCU-ify "if_list" to remove lock in next_to_run()")
+Reported-by: John Sperbeck <jsperbeck@google.com>
+Signed-off-by: Eric Dumazet <edumazet@google.com>
+Cc: Jesper Dangaard Brouer <brouer@redhat.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/core/pktgen.c | 17 ++++++++++-------
+ 1 file changed, 10 insertions(+), 7 deletions(-)
+
+--- a/net/core/pktgen.c
++++ b/net/core/pktgen.c
+@@ -211,8 +211,8 @@
+ #define T_REMDEV (1<<3) /* Remove one dev */
+
+ /* If lock -- protects updating of if_list */
+-#define if_lock(t) spin_lock(&(t->if_lock));
+-#define if_unlock(t) spin_unlock(&(t->if_lock));
++#define if_lock(t) mutex_lock(&(t->if_lock));
++#define if_unlock(t) mutex_unlock(&(t->if_lock));
+
+ /* Used to help with determining the pkts on receive */
+ #define PKTGEN_MAGIC 0xbe9be955
+@@ -418,7 +418,7 @@ struct pktgen_net {
+ };
+
+ struct pktgen_thread {
+- spinlock_t if_lock; /* for list of devices */
++ struct mutex if_lock; /* for list of devices */
+ struct list_head if_list; /* All device here */
+ struct list_head th_list;
+ struct task_struct *tsk;
+@@ -1952,11 +1952,13 @@ static void pktgen_change_name(const str
+ {
+ struct pktgen_thread *t;
+
++ mutex_lock(&pktgen_thread_lock);
++
+ list_for_each_entry(t, &pn->pktgen_threads, th_list) {
+ struct pktgen_dev *pkt_dev;
+
+- rcu_read_lock();
+- list_for_each_entry_rcu(pkt_dev, &t->if_list, list) {
++ if_lock(t);
++ list_for_each_entry(pkt_dev, &t->if_list, list) {
+ if (pkt_dev->odev != dev)
+ continue;
+
+@@ -1971,8 +1973,9 @@ static void pktgen_change_name(const str
+ dev->name);
+ break;
+ }
+- rcu_read_unlock();
++ if_unlock(t);
+ }
++ mutex_unlock(&pktgen_thread_lock);
+ }
+
+ static int pktgen_device_event(struct notifier_block *unused,
+@@ -3656,7 +3659,7 @@ static int __net_init pktgen_create_thre
+ return -ENOMEM;
+ }
+
+- spin_lock_init(&t->if_lock);
++ mutex_init(&t->if_lock);
+ t->cpu = cpu;
+
+ INIT_LIST_HEAD(&t->if_list);
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Jiri Slaby <jslaby@suse.cz>
+Date: Fri, 21 Oct 2016 14:13:24 +0200
+Subject: [PATCH 093/760] net: sctp, forbid negative length
+
+From: Jiri Slaby <jslaby@suse.cz>
+
+
+[ Upstream commit a4b8e71b05c27bae6bad3bdecddbc6b68a3ad8cf ]
+
+Most of getsockopt handlers in net/sctp/socket.c check len against
+sizeof some structure like:
+ if (len < sizeof(int))
+ return -EINVAL;
+
+On the first look, the check seems to be correct. But since len is int
+and sizeof returns size_t, int gets promoted to unsigned size_t too. So
+the test returns false for negative lengths. Yes, (-1 < sizeof(long)) is
+false.
+
+Fix this in sctp by explicitly checking len < 0 before any getsockopt
+handler is called.
+
+Note that sctp_getsockopt_events already handled the negative case.
+Since we added the < 0 check elsewhere, this one can be removed.
+
+If not checked, this is the result:
+UBSAN: Undefined behaviour in ../mm/page_alloc.c:2722:19
+shift exponent 52 is too large for 32-bit type 'int'
+CPU: 1 PID: 24535 Comm: syz-executor Not tainted 4.8.1-0-syzkaller #1
+Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.9.1-0-gb3ef39f-prebuilt.qemu-project.org 04/01/2014
+ 0000000000000000 ffff88006d99f2a8 ffffffffb2f7bdea 0000000041b58ab3
+ ffffffffb4363c14 ffffffffb2f7bcde ffff88006d99f2d0 ffff88006d99f270
+ 0000000000000000 0000000000000000 0000000000000034 ffffffffb5096422
+Call Trace:
+ [<ffffffffb3051498>] ? __ubsan_handle_shift_out_of_bounds+0x29c/0x300
+...
+ [<ffffffffb273f0e4>] ? kmalloc_order+0x24/0x90
+ [<ffffffffb27416a4>] ? kmalloc_order_trace+0x24/0x220
+ [<ffffffffb2819a30>] ? __kmalloc+0x330/0x540
+ [<ffffffffc18c25f4>] ? sctp_getsockopt_local_addrs+0x174/0xca0 [sctp]
+ [<ffffffffc18d2bcd>] ? sctp_getsockopt+0x10d/0x1b0 [sctp]
+ [<ffffffffb37c1219>] ? sock_common_getsockopt+0xb9/0x150
+ [<ffffffffb37be2f5>] ? SyS_getsockopt+0x1a5/0x270
+
+Signed-off-by: Jiri Slaby <jslaby@suse.cz>
+Cc: Vlad Yasevich <vyasevich@gmail.com>
+Cc: Neil Horman <nhorman@tuxdriver.com>
+Cc: "David S. Miller" <davem@davemloft.net>
+Cc: linux-sctp@vger.kernel.org
+Cc: netdev@vger.kernel.org
+Acked-by: Neil Horman <nhorman@tuxdriver.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/sctp/socket.c | 5 ++++-
+ 1 file changed, 4 insertions(+), 1 deletion(-)
+
+--- a/net/sctp/socket.c
++++ b/net/sctp/socket.c
+@@ -4385,7 +4385,7 @@ static int sctp_getsockopt_disable_fragm
+ static int sctp_getsockopt_events(struct sock *sk, int len, char __user *optval,
+ int __user *optlen)
+ {
+- if (len <= 0)
++ if (len == 0)
+ return -EINVAL;
+ if (len > sizeof(struct sctp_event_subscribe))
+ len = sizeof(struct sctp_event_subscribe);
+@@ -5981,6 +5981,9 @@ static int sctp_getsockopt(struct sock *
+ if (get_user(len, optlen))
+ return -EFAULT;
+
++ if (len < 0)
++ return -EINVAL;
++
+ lock_sock(sk);
+
+ switch (optname) {
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Eric Dumazet <edumazet@google.com>
+Date: Thu, 6 Oct 2016 04:13:18 +0900
+Subject: [PATCH 083/760] netlink: do not enter direct reclaim from netlink_dump()
+
+From: Eric Dumazet <edumazet@google.com>
+
+
+[ Upstream commit d35c99ff77ecb2eb239731b799386f3b3637a31e ]
+
+Since linux-3.15, netlink_dump() can use up to 16384 bytes skb
+allocations.
+
+Due to struct skb_shared_info ~320 bytes overhead, we end up using
+order-3 (on x86) page allocations, that might trigger direct reclaim and
+add stress.
+
+The intent was really to attempt a large allocation but immediately
+fallback to a smaller one (order-1 on x86) in case of memory stress.
+
+On recent kernels (linux-4.4), we can remove __GFP_DIRECT_RECLAIM to
+meet the goal. Old kernels would need to remove __GFP_WAIT
+
+While we are at it, since we do an order-3 allocation, allow to use
+all the allocated bytes instead of 16384 to reduce syscalls during
+large dumps.
+
+iproute2 already uses 32KB recvmsg() buffer sizes.
+
+Alexei provided an initial patch downsizing to SKB_WITH_OVERHEAD(16384)
+
+Fixes: 9063e21fb026 ("netlink: autosize skb lengthes")
+Signed-off-by: Eric Dumazet <edumazet@google.com>
+Reported-by: Alexei Starovoitov <ast@kernel.org>
+Cc: Greg Thelen <gthelen@google.com>
+Reviewed-by: Greg Rose <grose@lightfleet.com>
+Acked-by: Alexei Starovoitov <ast@kernel.org>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/netlink/af_netlink.c | 9 ++++-----
+ 1 file changed, 4 insertions(+), 5 deletions(-)
+
+--- a/net/netlink/af_netlink.c
++++ b/net/netlink/af_netlink.c
+@@ -2398,7 +2398,7 @@ static int netlink_recvmsg(struct kiocb
+ /* Record the max length of recvmsg() calls for future allocations */
+ nlk->max_recvmsg_len = max(nlk->max_recvmsg_len, len);
+ nlk->max_recvmsg_len = min_t(size_t, nlk->max_recvmsg_len,
+- 16384);
++ SKB_WITH_OVERHEAD(32768));
+
+ copied = data_skb->len;
+ if (len < copied) {
+@@ -2656,9 +2656,8 @@ static int netlink_dump(struct sock *sk)
+ skb = netlink_alloc_skb(sk,
+ nlk->max_recvmsg_len,
+ nlk->portid,
+- GFP_KERNEL |
+- __GFP_NOWARN |
+- __GFP_NORETRY);
++ (GFP_KERNEL & ~__GFP_WAIT) |
++ __GFP_NOWARN | __GFP_NORETRY);
+ /* available room should be exact amount to avoid MSG_TRUNC */
+ if (skb)
+ skb_reserve(skb, skb_tailroom(skb) -
+@@ -2666,7 +2665,7 @@ static int netlink_dump(struct sock *sk)
+ }
+ if (!skb)
+ skb = netlink_alloc_skb(sk, alloc_size, nlk->portid,
+- GFP_KERNEL);
++ (GFP_KERNEL & ~__GFP_WAIT));
+ if (!skb)
+ goto errout_skb;
+ netlink_skb_set_owner_r(skb, sk);
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Anoob Soman <anoob.soman@citrix.com>
+Date: Wed, 5 Oct 2016 15:12:54 +0100
+Subject: [PATCH 082/760] packet: call fanout_release, while UNREGISTERING a netdev
+
+From: Anoob Soman <anoob.soman@citrix.com>
+
+
+[ Upstream commit 6664498280cf17a59c3e7cf1a931444c02633ed1 ]
+
+If a socket has FANOUT sockopt set, a new proto_hook is registered
+as part of fanout_add(). When processing a NETDEV_UNREGISTER event in
+af_packet, __fanout_unlink is called for all sockets, but prot_hook which was
+registered as part of fanout_add is not removed. Call fanout_release, on a
+NETDEV_UNREGISTER, which removes prot_hook and removes fanout from the
+fanout_list.
+
+This fixes BUG_ON(!list_empty(&dev->ptype_specific)) in netdev_run_todo()
+
+Signed-off-by: Anoob Soman <anoob.soman@citrix.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/packet/af_packet.c | 1 +
+ 1 file changed, 1 insertion(+)
+
+--- a/net/packet/af_packet.c
++++ b/net/packet/af_packet.c
+@@ -3552,6 +3552,7 @@ static int packet_notifier(struct notifi
+ }
+ if (msg == NETDEV_UNREGISTER) {
+ packet_cached_dev_reset(po);
++ fanout_release(sk);
+ po->ifindex = -1;
+ if (po->prot_hook.dev)
+ dev_put(po->prot_hook.dev);
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Willem de Bruijn <willemb@google.com>
+Date: Wed, 26 Oct 2016 11:23:07 -0400
+Subject: [PATCH 097/760] packet: on direct_xmit, limit tso and csum to supported devices
+
+From: Willem de Bruijn <willemb@google.com>
+
+
+[ Upstream commit 104ba78c98808ae837d1f63aae58c183db5505df ]
+
+When transmitting on a packet socket with PACKET_VNET_HDR and
+PACKET_QDISC_BYPASS, validate device support for features requested
+in vnet_hdr.
+
+Drop TSO packets sent to devices that do not support TSO or have the
+feature disabled. Note that the latter currently do process those
+packets correctly, regardless of not advertising the feature.
+
+Because of SKB_GSO_DODGY, it is not sufficient to test device features
+with netif_needs_gso. Full validate_xmit_skb is needed.
+
+Switch to software checksum for non-TSO packets that request checksum
+offload if that device feature is unsupported or disabled. Note that
+similar to the TSO case, device drivers may perform checksum offload
+correctly even when not advertising it.
+
+When switching to software checksum, packets hit skb_checksum_help,
+which has two BUG_ON checksum not in linear segment. Packet sockets
+always allocate at least up to csum_start + csum_off + 2 as linear.
+
+Tested by running github.com/wdebruij/kerneltools/psock_txring_vnet.c
+
+ ethtool -K eth0 tso off tx on
+ psock_txring_vnet -d $dst -s $src -i eth0 -l 2000 -n 1 -q -v
+ psock_txring_vnet -d $dst -s $src -i eth0 -l 2000 -n 1 -q -v -N
+
+ ethtool -K eth0 tx off
+ psock_txring_vnet -d $dst -s $src -i eth0 -l 1000 -n 1 -q -v -G
+ psock_txring_vnet -d $dst -s $src -i eth0 -l 1000 -n 1 -q -v -G -N
+
+v2:
+ - add EXPORT_SYMBOL_GPL(validate_xmit_skb_list)
+
+Fixes: d346a3fae3ff ("packet: introduce PACKET_QDISC_BYPASS socket option")
+Signed-off-by: Willem de Bruijn <willemb@google.com>
+Acked-by: Eric Dumazet <edumazet@google.com>
+Acked-by: Daniel Borkmann <daniel@iogearbox.net>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/core/dev.c | 1 +
+ net/packet/af_packet.c | 9 ++++-----
+ 2 files changed, 5 insertions(+), 5 deletions(-)
+
+--- a/net/core/dev.c
++++ b/net/core/dev.c
+@@ -2741,6 +2741,7 @@ struct sk_buff *validate_xmit_skb_list(s
+ }
+ return head;
+ }
++EXPORT_SYMBOL_GPL(validate_xmit_skb_list);
+
+ static void qdisc_pkt_len_init(struct sk_buff *skb)
+ {
+--- a/net/packet/af_packet.c
++++ b/net/packet/af_packet.c
+@@ -240,7 +240,7 @@ static void __fanout_link(struct sock *s
+ static int packet_direct_xmit(struct sk_buff *skb)
+ {
+ struct net_device *dev = skb->dev;
+- netdev_features_t features;
++ struct sk_buff *orig_skb = skb;
+ struct netdev_queue *txq;
+ int ret = NETDEV_TX_BUSY;
+
+@@ -248,9 +248,8 @@ static int packet_direct_xmit(struct sk_
+ !netif_carrier_ok(dev)))
+ goto drop;
+
+- features = netif_skb_features(skb);
+- if (skb_needs_linearize(skb, features) &&
+- __skb_linearize(skb))
++ skb = validate_xmit_skb_list(skb, dev);
++ if (skb != orig_skb)
+ goto drop;
+
+ txq = skb_get_tx_queue(dev, skb);
+@@ -270,7 +269,7 @@ static int packet_direct_xmit(struct sk_
+ return ret;
+ drop:
+ atomic_long_inc(&dev->tx_dropped);
+- kfree_skb(skb);
++ kfree_skb_list(skb);
+ return NET_XMIT_DROP;
+ }
+
--- /dev/null
+From 0733424c9ba9f42242409d1ece780777272f7ea1 Mon Sep 17 00:00:00 2001
+From: David Hsu <davidhsu@google.com>
+Date: Tue, 9 Aug 2016 14:57:46 -0700
+Subject: pwm: Unexport children before chip removal
+
+From: David Hsu <davidhsu@google.com>
+
+commit 0733424c9ba9f42242409d1ece780777272f7ea1 upstream.
+
+Exported pwm channels aren't removed before the pwmchip and are
+leaked. This results in invalid sysfs files. This fix removes
+all exported pwm channels before chip removal.
+
+Signed-off-by: David Hsu <davidhsu@google.com>
+Fixes: 76abbdde2d95 ("pwm: Add sysfs interface")
+Signed-off-by: Thierry Reding <thierry.reding@gmail.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/pwm/core.c | 2 ++
+ drivers/pwm/sysfs.c | 18 ++++++++++++++++++
+ include/linux/pwm.h | 5 +++++
+ 3 files changed, 25 insertions(+)
+
+--- a/drivers/pwm/core.c
++++ b/drivers/pwm/core.c
+@@ -293,6 +293,8 @@ int pwmchip_remove(struct pwm_chip *chip
+ unsigned int i;
+ int ret = 0;
+
++ pwmchip_sysfs_unexport_children(chip);
++
+ mutex_lock(&pwm_lock);
+
+ for (i = 0; i < chip->npwm; i++) {
+--- a/drivers/pwm/sysfs.c
++++ b/drivers/pwm/sysfs.c
+@@ -340,6 +340,24 @@ void pwmchip_sysfs_unexport(struct pwm_c
+ }
+ }
+
++void pwmchip_sysfs_unexport_children(struct pwm_chip *chip)
++{
++ struct device *parent;
++ unsigned int i;
++
++ parent = class_find_device(&pwm_class, NULL, chip,
++ pwmchip_sysfs_match);
++ if (!parent)
++ return;
++
++ for (i = 0; i < chip->npwm; i++) {
++ struct pwm_device *pwm = &chip->pwms[i];
++
++ if (test_bit(PWMF_EXPORTED, &pwm->flags))
++ pwm_unexport_child(parent, pwm);
++ }
++}
++
+ static int __init pwm_sysfs_init(void)
+ {
+ return class_register(&pwm_class);
+--- a/include/linux/pwm.h
++++ b/include/linux/pwm.h
+@@ -299,6 +299,7 @@ static inline void pwm_add_table(struct
+ #ifdef CONFIG_PWM_SYSFS
+ void pwmchip_sysfs_export(struct pwm_chip *chip);
+ void pwmchip_sysfs_unexport(struct pwm_chip *chip);
++void pwmchip_sysfs_unexport_children(struct pwm_chip *chip);
+ #else
+ static inline void pwmchip_sysfs_export(struct pwm_chip *chip)
+ {
+@@ -307,6 +308,10 @@ static inline void pwmchip_sysfs_export(
+ static inline void pwmchip_sysfs_unexport(struct pwm_chip *chip)
+ {
+ }
++
++static inline void pwmchip_sysfs_unexport_children(struct pwm_chip *chip)
++{
++}
+ #endif /* CONFIG_PWM_SYSFS */
+
+ #endif /* __LINUX_PWM_H */
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Marcelo Ricardo Leitner <marcelo.leitner@gmail.com>
+Date: Tue, 25 Oct 2016 14:27:39 -0200
+Subject: [PATCH 096/760] sctp: validate chunk len before actually using it
+
+From: Marcelo Ricardo Leitner <marcelo.leitner@gmail.com>
+
+
+[ Upstream commit bf911e985d6bbaa328c20c3e05f4eb03de11fdd6 ]
+
+Andrey Konovalov reported that KASAN detected that SCTP was using a slab
+beyond the boundaries. It was caused because when handling out of the
+blue packets in function sctp_sf_ootb() it was checking the chunk len
+only after already processing the first chunk, validating only for the
+2nd and subsequent ones.
+
+The fix is to just move the check upwards so it's also validated for the
+1st chunk.
+
+Reported-by: Andrey Konovalov <andreyknvl@google.com>
+Tested-by: Andrey Konovalov <andreyknvl@google.com>
+Signed-off-by: Marcelo Ricardo Leitner <marcelo.leitner@gmail.com>
+Reviewed-by: Xin Long <lucien.xin@gmail.com>
+Acked-by: Neil Horman <nhorman@tuxdriver.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/sctp/sm_statefuns.c | 12 ++++++------
+ 1 file changed, 6 insertions(+), 6 deletions(-)
+
+--- a/net/sctp/sm_statefuns.c
++++ b/net/sctp/sm_statefuns.c
+@@ -3426,6 +3426,12 @@ sctp_disposition_t sctp_sf_ootb(struct n
+ return sctp_sf_violation_chunklen(net, ep, asoc, type, arg,
+ commands);
+
++ /* Report violation if chunk len overflows */
++ ch_end = ((__u8 *)ch) + WORD_ROUND(ntohs(ch->length));
++ if (ch_end > skb_tail_pointer(skb))
++ return sctp_sf_violation_chunklen(net, ep, asoc, type, arg,
++ commands);
++
+ /* Now that we know we at least have a chunk header,
+ * do things that are type appropriate.
+ */
+@@ -3457,12 +3463,6 @@ sctp_disposition_t sctp_sf_ootb(struct n
+ }
+ }
+
+- /* Report violation if chunk len overflows */
+- ch_end = ((__u8 *)ch) + WORD_ROUND(ntohs(ch->length));
+- if (ch_end > skb_tail_pointer(skb))
+- return sctp_sf_violation_chunklen(net, ep, asoc, type, arg,
+- commands);
+-
+ ch = (sctp_chunkhdr_t *) ch_end;
+ } while (ch_end < skb_tail_pointer(skb));
+
--- /dev/null
+From 0c461cb727d146c9ef2d3e86214f498b78b7d125 Mon Sep 17 00:00:00 2001
+From: Stephen Smalley <sds@tycho.nsa.gov>
+Date: Tue, 31 Jan 2017 11:54:04 -0500
+Subject: selinux: fix off-by-one in setprocattr
+
+From: Stephen Smalley <sds@tycho.nsa.gov>
+
+commit 0c461cb727d146c9ef2d3e86214f498b78b7d125 upstream.
+
+SELinux tries to support setting/clearing of /proc/pid/attr attributes
+from the shell by ignoring terminating newlines and treating an
+attribute value that begins with a NUL or newline as an attempt to
+clear the attribute. However, the test for clearing attributes has
+always been wrong; it has an off-by-one error, and this could further
+lead to reading past the end of the allocated buffer since commit
+bb646cdb12e75d82258c2f2e7746d5952d3e321a ("proc_pid_attr_write():
+switch to memdup_user()"). Fix the off-by-one error.
+
+Even with this fix, setting and clearing /proc/pid/attr attributes
+from the shell is not straightforward since the interface does not
+support multiple write() calls (so shells that write the value and
+newline separately will set and then immediately clear the attribute,
+requiring use of echo -n to set the attribute), whereas trying to use
+echo -n "" to clear the attribute causes the shell to skip the
+write() call altogether since POSIX says that a zero-length write
+causes no side effects. Thus, one must use echo -n to set and echo
+without -n to clear, as in the following example:
+$ echo -n unconfined_u:object_r:user_home_t:s0 > /proc/$$/attr/fscreate
+$ cat /proc/$$/attr/fscreate
+unconfined_u:object_r:user_home_t:s0
+$ echo "" > /proc/$$/attr/fscreate
+$ cat /proc/$$/attr/fscreate
+
+Note the use of /proc/$$ rather than /proc/self, as otherwise
+the cat command will read its own attribute value, not that of the shell.
+
+There are no users of this facility to my knowledge; possibly we
+should just get rid of it.
+
+UPDATE: Upon further investigation it appears that a local process
+with the process:setfscreate permission can cause a kernel panic as a
+result of this bug. This patch fixes CVE-2017-2618.
+
+Signed-off-by: Stephen Smalley <sds@tycho.nsa.gov>
+[PM: added the update about CVE-2017-2618 to the commit description]
+Signed-off-by: Paul Moore <paul@paul-moore.com>
+Signed-off-by: James Morris <james.l.morris@oracle.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ security/selinux/hooks.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/security/selinux/hooks.c
++++ b/security/selinux/hooks.c
+@@ -5594,7 +5594,7 @@ static int selinux_setprocattr(struct ta
+ return error;
+
+ /* Obtain a SID for the context, if one was specified. */
+- if (size && str[1] && str[1] != '\n') {
++ if (size && str[0] && str[0] != '\n') {
+ if (str[size-1] == '\n') {
+ str[size-1] = 0;
+ size--;
ping-fix-a-null-pointer-dereference.patch
l2tp-do-not-use-udp_ioctl.patch
ip6_gre-fix-ip6gre_err-invalid-reads.patch
+ipv6-tcp-restore-ip6cb-for-pktoptions-skbs.patch
ipv6-tcp-add-a-missing-tcp_v6_restore_cb.patch
tcp-avoid-infinite-loop-in-tcp_splice_read.patch
+iommu-vt-d-fix-iommu-lookup-for-sr-iov-virtual-functions.patch
+usb-chipidea-move-the-lock-initialization-to-core-file.patch
+tcp-fix-overflow-in-__tcp_retransmit_skb.patch
+android-binder-add-strong-ref-checks.patch
+android-binder-clear-binder-and-cookie-when-setting-handle-in-flat-binder-struct.patch
+alsa-usb-audio-add-quirk-for-syntek-stk1160.patch
+fix-potential-infoleak-in-older-kernels.patch
+tty-vt-fix-bogus-division-in-csi_j.patch
+arm-8584-1-floppy-avoid-gcc-6-warning.patch
+drm-exynos-fix-error-handling-in-exynos_drm_subdrv_open.patch
+smc91x-avoid-self-comparison-warning.patch
+ubi-fastmap-scrub-peb-when-bitflips-are-detected-in-a-free-peb-ec-header.patch
+pwm-unexport-children-before-chip-removal.patch
+hid-usbhid-add-aten-cs962-to-list-of-quirky-devices.patch
+selinux-fix-off-by-one-in-setprocattr.patch
+fbdev-color-map-copying-bounds-checking.patch
+tcp-fix-wrong-checksum-calculation-on-mtu-probing.patch
+tcp-fix-a-compile-error-in-dbgundo.patch
+ip6_gre-fix-flowi6_proto-value-in-ip6gre_xmit_other.patch
+ipmr-ip6mr-fix-scheduling-while-atomic-and-a-deadlock-with-ipmr_get_route.patch
+net-add-netdev-all_adj_list-refcnt-propagation-to-fix-panic.patch
+packet-call-fanout_release-while-unregistering-a-netdev.patch
+ipv6-correctly-add-local-routes-when-lo-goes-up.patch
+net-pktgen-remove-rcu-locking-in-pktgen_change_name.patch
+ipv4-disable-bh-in-set_ping_group_range.patch
+net-sctp-forbid-negative-length.patch
+sctp-validate-chunk-len-before-actually-using-it.patch
+packet-on-direct_xmit-limit-tso-and-csum-to-supported-devices.patch
+netlink-do-not-enter-direct-reclaim-from-netlink_dump.patch
--- /dev/null
+From e3ebd894f084255fde19116955ba7054858ff5d6 Mon Sep 17 00:00:00 2001
+From: Arnd Bergmann <arnd@arndb.de>
+Date: Mon, 14 Mar 2016 23:45:12 +0100
+Subject: smc91x: avoid self-comparison warning
+
+From: Arnd Bergmann <arnd@arndb.de>
+
+commit e3ebd894f084255fde19116955ba7054858ff5d6 upstream.
+
+The smc91x driver defines a macro that compares its argument to
+itself, apparently to get a true result while using its argument
+to avoid a warning about unused local variables.
+
+Unfortunately, this triggers a warning with gcc-6, as the comparison
+is obviously useless:
+
+drivers/net/ethernet/smsc/smc91x.c: In function 'smc_hardware_send_pkt':
+drivers/net/ethernet/smsc/smc91x.c:563:14: error: self-comparison always evaluates to true [-Werror=tautological-compare]
+ if (!smc_special_trylock(&lp->lock, flags)) {
+
+This replaces the macro with another one that behaves similarly,
+with a cast to (void) to ensure the argument is used, and using
+a literal 'true' as its value.
+
+Signed-off-by: Arnd Bergmann <arnd@arndb.de>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/net/ethernet/smsc/smc91x.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/drivers/net/ethernet/smsc/smc91x.c
++++ b/drivers/net/ethernet/smsc/smc91x.c
+@@ -535,7 +535,7 @@ static inline void smc_rcv(struct net_d
+ #define smc_special_lock(lock, flags) spin_lock_irqsave(lock, flags)
+ #define smc_special_unlock(lock, flags) spin_unlock_irqrestore(lock, flags)
+ #else
+-#define smc_special_trylock(lock, flags) (flags == flags)
++#define smc_special_trylock(lock, flags) ((void)flags, true)
+ #define smc_special_lock(lock, flags) do { flags = 0; } while (0)
+ #define smc_special_unlock(lock, flags) do { flags = 0; } while (0)
+ #endif
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Eric Dumazet <edumazet@google.com>
+Date: Thu, 22 Sep 2016 17:54:00 -0700
+Subject: [PATCH 074/760] tcp: fix a compile error in DBGUNDO()
+
+From: Eric Dumazet <edumazet@google.com>
+
+
+[ Upstream commit 019b1c9fe32a2a32c1153e31375f87ec3e591273 ]
+
+If DBGUNDO() is enabled (FASTRETRANS_DEBUG > 1), a compile
+error will happen, since inet6_sk(sk)->daddr became sk->sk_v6_daddr
+
+Fixes: efe4208f47f9 ("ipv6: make lookups simpler and faster")
+Signed-off-by: Eric Dumazet <edumazet@google.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/ipv4/tcp_input.c | 3 +--
+ 1 file changed, 1 insertion(+), 2 deletions(-)
+
+--- a/net/ipv4/tcp_input.c
++++ b/net/ipv4/tcp_input.c
+@@ -2360,10 +2360,9 @@ static void DBGUNDO(struct sock *sk, con
+ }
+ #if IS_ENABLED(CONFIG_IPV6)
+ else if (sk->sk_family == AF_INET6) {
+- struct ipv6_pinfo *np = inet6_sk(sk);
+ pr_debug("Undo %s %pI6/%u c%u l%u ss%u/%u p%u\n",
+ msg,
+- &np->daddr, ntohs(inet->inet_dport),
++ &sk->sk_v6_daddr, ntohs(inet->inet_dport),
+ tp->snd_cwnd, tcp_left_out(tp),
+ tp->snd_ssthresh, tp->prior_ssthresh,
+ tp->packets_out);
--- /dev/null
+From ffb4d6c8508657824bcef68a36b2a0f9d8c09d10 Mon Sep 17 00:00:00 2001
+From: Eric Dumazet <edumazet@google.com>
+Date: Thu, 15 Sep 2016 08:12:33 -0700
+Subject: tcp: fix overflow in __tcp_retransmit_skb()
+
+From: Eric Dumazet <edumazet@google.com>
+
+commit ffb4d6c8508657824bcef68a36b2a0f9d8c09d10 upstream.
+
+If a TCP socket gets a large write queue, an overflow can happen
+in a test in __tcp_retransmit_skb() preventing all retransmits.
+
+The flow then stalls and resets after timeouts.
+
+Tested:
+
+sysctl -w net.core.wmem_max=1000000000
+netperf -H dest -- -s 1000000000
+
+Signed-off-by: Eric Dumazet <edumazet@google.com>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ net/ipv4/tcp_output.c | 3 ++-
+ 1 file changed, 2 insertions(+), 1 deletion(-)
+
+--- a/net/ipv4/tcp_output.c
++++ b/net/ipv4/tcp_output.c
+@@ -2481,7 +2481,8 @@ int __tcp_retransmit_skb(struct sock *sk
+ * copying overhead: fragmentation, tunneling, mangling etc.
+ */
+ if (atomic_read(&sk->sk_wmem_alloc) >
+- min(sk->sk_wmem_queued + (sk->sk_wmem_queued >> 2), sk->sk_sndbuf))
++ min_t(u32, sk->sk_wmem_queued + (sk->sk_wmem_queued >> 2),
++ sk->sk_sndbuf))
+ return -EAGAIN;
+
+ if (skb_still_in_host_queue(sk, skb))
--- /dev/null
+From foo@baz Mon Feb 20 16:34:36 CET 2017
+From: Douglas Caetano dos Santos <douglascs@taghos.com.br>
+Date: Thu, 22 Sep 2016 15:52:04 -0300
+Subject: [PATCH 073/760] tcp: fix wrong checksum calculation on MTU probing
+
+From: Douglas Caetano dos Santos <douglascs@taghos.com.br>
+
+
+[ Upstream commit 2fe664f1fcf7c4da6891f95708a7a56d3c024354 ]
+
+With TCP MTU probing enabled and offload TX checksumming disabled,
+tcp_mtu_probe() calculated the wrong checksum when a fragment being copied
+into the probe's SKB had an odd length. This was caused by the direct use
+of skb_copy_and_csum_bits() to calculate the checksum, as it pads the
+fragment being copied, if needed. When this fragment was not the last, a
+subsequent call used the previous checksum without considering this
+padding.
+
+The effect was a stale connection in one way, as even retransmissions
+wouldn't solve the problem, because the checksum was never recalculated for
+the full SKB length.
+
+Signed-off-by: Douglas Caetano dos Santos <douglascs@taghos.com.br>
+Signed-off-by: David S. Miller <davem@davemloft.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ net/ipv4/tcp_output.c | 12 +++++++-----
+ 1 file changed, 7 insertions(+), 5 deletions(-)
+
+--- a/net/ipv4/tcp_output.c
++++ b/net/ipv4/tcp_output.c
+@@ -1869,12 +1869,14 @@ static int tcp_mtu_probe(struct sock *sk
+ len = 0;
+ tcp_for_write_queue_from_safe(skb, next, sk) {
+ copy = min_t(int, skb->len, probe_size - len);
+- if (nskb->ip_summed)
++ if (nskb->ip_summed) {
+ skb_copy_bits(skb, 0, skb_put(nskb, copy), copy);
+- else
+- nskb->csum = skb_copy_and_csum_bits(skb, 0,
+- skb_put(nskb, copy),
+- copy, nskb->csum);
++ } else {
++ __wsum csum = skb_copy_and_csum_bits(skb, 0,
++ skb_put(nskb, copy),
++ copy, 0);
++ nskb->csum = csum_block_add(nskb->csum, csum, len);
++ }
+
+ if (skb->len <= copy) {
+ /* We've eaten all the data from this skb.
--- /dev/null
+From 42acfc6615f47e465731c263bee0c799edb098f2 Mon Sep 17 00:00:00 2001
+From: Jiri Slaby <jslaby@suse.cz>
+Date: Mon, 3 Oct 2016 11:00:17 +0200
+Subject: tty: vt, fix bogus division in csi_J
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+From: Jiri Slaby <jslaby@suse.cz>
+
+commit 42acfc6615f47e465731c263bee0c799edb098f2 upstream.
+
+In csi_J(3), the third parameter of scr_memsetw (vc_screenbuf_size) is
+divided by 2 inappropriatelly. But scr_memsetw expects size, not
+count, because it divides the size by 2 on its own before doing actual
+memset-by-words.
+
+So remove the bogus division.
+
+Signed-off-by: Jiri Slaby <jslaby@suse.cz>
+Cc: Petr Písař <ppisar@redhat.com>
+Fixes: f8df13e0a9 (tty: Clean console safely)
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/tty/vt/vt.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/drivers/tty/vt/vt.c
++++ b/drivers/tty/vt/vt.c
+@@ -1169,7 +1169,7 @@ static void csi_J(struct vc_data *vc, in
+ break;
+ case 3: /* erase scroll-back buffer (and whole display) */
+ scr_memsetw(vc->vc_screenbuf, vc->vc_video_erase_char,
+- vc->vc_screenbuf_size >> 1);
++ vc->vc_screenbuf_size);
+ set_origin(vc);
+ if (CON_IS_VISIBLE(vc))
+ update_screen(vc);
--- /dev/null
+From ecbfa8eabae9cd73522d1d3d15869703c263d859 Mon Sep 17 00:00:00 2001
+From: Boris Brezillon <boris.brezillon@free-electrons.com>
+Date: Fri, 16 Sep 2016 16:59:12 +0200
+Subject: UBI: fastmap: scrub PEB when bitflips are detected in a free PEB EC header
+
+From: Boris Brezillon <boris.brezillon@free-electrons.com>
+
+commit ecbfa8eabae9cd73522d1d3d15869703c263d859 upstream.
+
+scan_pool() does not mark the PEB for scrubing when bitflips are
+detected in the EC header of a free PEB (VID header region left to
+0xff).
+Make sure we scrub the PEB in this case.
+
+Signed-off-by: Boris Brezillon <boris.brezillon@free-electrons.com>
+Fixes: dbb7d2a88d2a ("UBI: Add fastmap core")
+Signed-off-by: Richard Weinberger <richard@nod.at>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/mtd/ubi/fastmap.c | 7 ++++---
+ 1 file changed, 4 insertions(+), 3 deletions(-)
+
+--- a/drivers/mtd/ubi/fastmap.c
++++ b/drivers/mtd/ubi/fastmap.c
+@@ -446,10 +446,11 @@ static int scan_pool(struct ubi_device *
+ unsigned long long ec = be64_to_cpu(ech->ec);
+ unmap_peb(ai, pnum);
+ dbg_bld("Adding PEB to free: %i", pnum);
++
+ if (err == UBI_IO_FF_BITFLIPS)
+- add_aeb(ai, free, pnum, ec, 1);
+- else
+- add_aeb(ai, free, pnum, ec, 0);
++ scrub = 1;
++
++ add_aeb(ai, free, pnum, ec, scrub);
+ continue;
+ } else if (err == 0 || err == UBI_IO_BITFLIPS) {
+ dbg_bld("Found non empty PEB:%i in pool", pnum);
--- /dev/null
+From a5d906bb261cde5f881a949d3b0fbaa285dcc574 Mon Sep 17 00:00:00 2001
+From: Peter Chen <peter.chen@nxp.com>
+Date: Tue, 15 Nov 2016 18:05:33 +0800
+Subject: usb: chipidea: move the lock initialization to core file
+
+From: Peter Chen <peter.chen@nxp.com>
+
+commit a5d906bb261cde5f881a949d3b0fbaa285dcc574 upstream.
+
+This can fix below dump when the lock is accessed at host
+mode due to it is not initialized.
+
+[ 46.119638] INFO: trying to register non-static key.
+[ 46.124643] the code is fine but needs lockdep annotation.
+[ 46.130144] turning off the locking correctness validator.
+[ 46.135659] CPU: 0 PID: 690 Comm: cat Not tainted 4.9.0-rc3-00079-g4b75f1d #1210
+[ 46.143075] Hardware name: Freescale i.MX6 SoloX (Device Tree)
+[ 46.148923] Backtrace:
+[ 46.151448] [<c010c460>] (dump_backtrace) from [<c010c658>] (show_stack+0x18/0x1c)
+[ 46.159038] r7:edf52000
+[ 46.161412] r6:60000193
+[ 46.163967] r5:00000000
+[ 46.165035] r4:c0e25c2c
+
+[ 46.169109] [<c010c640>] (show_stack) from [<c03f58a4>] (dump_stack+0xb4/0xe8)
+[ 46.176362] [<c03f57f0>] (dump_stack) from [<c016d690>] (register_lock_class+0x4fc/0x56c)
+[ 46.184554] r10:c0e25d24
+[ 46.187014] r9:edf53e70
+[ 46.189569] r8:c1642444
+[ 46.190637] r7:ee9da024
+[ 46.193191] r6:00000000
+[ 46.194258] r5:00000000
+[ 46.196812] r4:00000000
+[ 46.199185] r3:00000001
+
+[ 46.203259] [<c016d194>] (register_lock_class) from [<c0171294>] (__lock_acquire+0x80/0x10f0)
+[ 46.211797] r10:c0e25d24
+[ 46.214257] r9:edf53e70
+[ 46.216813] r8:ee9da024
+[ 46.217880] r7:c1642444
+[ 46.220435] r6:edcd1800
+[ 46.221502] r5:60000193
+[ 46.224057] r4:00000000
+
+[ 46.227953] [<c0171214>] (__lock_acquire) from [<c01726c0>] (lock_acquire+0x74/0x94)
+[ 46.235710] r10:00000001
+[ 46.238169] r9:edf53e70
+[ 46.240723] r8:edf53f80
+[ 46.241790] r7:00000001
+[ 46.244344] r6:00000001
+[ 46.245412] r5:60000193
+[ 46.247966] r4:00000000
+
+[ 46.251866] [<c017264c>] (lock_acquire) from [<c096c8fc>] (_raw_spin_lock_irqsave+0x40/0x54)
+[ 46.260319] r7:ee1c6a00
+[ 46.262691] r6:c062a570
+[ 46.265247] r5:20000113
+[ 46.266314] r4:ee9da014
+
+[ 46.270393] [<c096c8bc>] (_raw_spin_lock_irqsave) from [<c062a570>] (ci_port_test_show+0x2c/0x70)
+[ 46.279280] r6:eebd2000
+[ 46.281652] r5:ee9da010
+[ 46.284207] r4:ee9da014
+
+[ 46.286810] [<c062a544>] (ci_port_test_show) from [<c0248d04>] (seq_read+0x1ac/0x4f8)
+[ 46.294655] r9:edf53e70
+[ 46.297028] r8:edf53f80
+[ 46.299583] r7:ee1c6a00
+[ 46.300650] r6:00000001
+[ 46.303205] r5:00000000
+[ 46.304273] r4:eebd2000
+[ 46.306850] [<c0248b58>] (seq_read) from [<c039e864>] (full_proxy_read+0x54/0x6c)
+[ 46.314348] r10:00000000
+[ 46.316808] r9:c0a6ad30
+[ 46.319363] r8:edf53f80
+[ 46.320430] r7:00020000
+[ 46.322986] r6:b6de3000
+[ 46.324053] r5:ee1c6a00
+[ 46.326607] r4:c0248b58
+
+[ 46.330505] [<c039e810>] (full_proxy_read) from [<c021ec98>] (__vfs_read+0x34/0x118)
+[ 46.338262] r9:edf52000
+[ 46.340635] r8:c0107fc4
+[ 46.343190] r7:00020000
+[ 46.344257] r6:edf53f80
+[ 46.346812] r5:c039e810
+[ 46.347879] r4:ee1c6a00
+[ 46.350447] [<c021ec64>] (__vfs_read) from [<c021fbd0>] (vfs_read+0x8c/0x11c)
+[ 46.357597] r9:edf52000
+[ 46.359969] r8:c0107fc4
+[ 46.362524] r7:edf53f80
+[ 46.363592] r6:b6de3000
+[ 46.366147] r5:ee1c6a00
+[ 46.367214] r4:00020000
+[ 46.369782] [<c021fb44>] (vfs_read) from [<c0220a4c>] (SyS_read+0x4c/0xa8)
+[ 46.376672] r8:c0107fc4
+[ 46.379045] r7:00020000
+[ 46.381600] r6:b6de3000
+[ 46.382667] r5:ee1c6a00
+[ 46.385222] r4:ee1c6a00
+
+[ 46.387817] [<c0220a00>] (SyS_read) from [<c0107e20>] (ret_fast_syscall+0x0/0x1c)
+[ 46.395314] r7:00000003
+[ 46.397687] r6:b6de3000
+[ 46.400243] r5:00020000
+[ 46.401310] r4:00020000
+
+Fixes: 26c696c678c4 ("USB: Chipidea: rename struct
+ ci13xxx variables from udc to ci")
+Signed-off-by: Peter Chen <peter.chen@nxp.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+---
+ drivers/usb/chipidea/core.c | 1 +
+ drivers/usb/chipidea/udc.c | 2 --
+ 2 files changed, 1 insertion(+), 2 deletions(-)
+
+--- a/drivers/usb/chipidea/core.c
++++ b/drivers/usb/chipidea/core.c
+@@ -594,6 +594,7 @@ static int ci_hdrc_probe(struct platform
+ return -ENOMEM;
+ }
+
++ spin_lock_init(&ci->lock);
+ ci->dev = dev;
+ ci->platdata = dev_get_platdata(dev);
+ ci->imx28_write_fix = !!(ci->platdata->flags &
+--- a/drivers/usb/chipidea/udc.c
++++ b/drivers/usb/chipidea/udc.c
+@@ -1798,8 +1798,6 @@ static int udc_start(struct ci_hdrc *ci)
+ struct device *dev = ci->dev;
+ int retval = 0;
+
+- spin_lock_init(&ci->lock);
+-
+ ci->gadget.ops = &usb_gadget_ops;
+ ci->gadget.speed = USB_SPEED_UNKNOWN;
+ ci->gadget.max_speed = USB_SPEED_HIGH;