summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to '4.9.16/1015_linux-4.9.16.patch')
-rw-r--r--4.9.16/1015_linux-4.9.16.patch1623
1 files changed, 1623 insertions, 0 deletions
diff --git a/4.9.16/1015_linux-4.9.16.patch b/4.9.16/1015_linux-4.9.16.patch
new file mode 100644
index 0000000..7ac2f77
--- /dev/null
+++ b/4.9.16/1015_linux-4.9.16.patch
@@ -0,0 +1,1623 @@
+diff --git a/Makefile b/Makefile
+index 03df4fc..4e0f962 100644
+--- a/Makefile
++++ b/Makefile
+@@ -1,6 +1,6 @@
+ VERSION = 4
+ PATCHLEVEL = 9
+-SUBLEVEL = 15
++SUBLEVEL = 16
+ EXTRAVERSION =
+ NAME = Roaring Lionus
+
+diff --git a/arch/mips/configs/ip22_defconfig b/arch/mips/configs/ip22_defconfig
+index 5d83ff7..ec8e968 100644
+--- a/arch/mips/configs/ip22_defconfig
++++ b/arch/mips/configs/ip22_defconfig
+@@ -67,8 +67,8 @@ CONFIG_NETFILTER_NETLINK_QUEUE=m
+ CONFIG_NF_CONNTRACK=m
+ CONFIG_NF_CONNTRACK_SECMARK=y
+ CONFIG_NF_CONNTRACK_EVENTS=y
+-CONFIG_NF_CT_PROTO_DCCP=m
+-CONFIG_NF_CT_PROTO_UDPLITE=m
++CONFIG_NF_CT_PROTO_DCCP=y
++CONFIG_NF_CT_PROTO_UDPLITE=y
+ CONFIG_NF_CONNTRACK_AMANDA=m
+ CONFIG_NF_CONNTRACK_FTP=m
+ CONFIG_NF_CONNTRACK_H323=m
+diff --git a/arch/mips/configs/ip27_defconfig b/arch/mips/configs/ip27_defconfig
+index 2b74aee..e582069 100644
+--- a/arch/mips/configs/ip27_defconfig
++++ b/arch/mips/configs/ip27_defconfig
+@@ -133,7 +133,7 @@ CONFIG_LIBFC=m
+ CONFIG_SCSI_QLOGIC_1280=y
+ CONFIG_SCSI_PMCRAID=m
+ CONFIG_SCSI_BFA_FC=m
+-CONFIG_SCSI_DH=m
++CONFIG_SCSI_DH=y
+ CONFIG_SCSI_DH_RDAC=m
+ CONFIG_SCSI_DH_HP_SW=m
+ CONFIG_SCSI_DH_EMC=m
+@@ -205,7 +205,6 @@ CONFIG_MLX4_EN=m
+ # CONFIG_MLX4_DEBUG is not set
+ CONFIG_TEHUTI=m
+ CONFIG_BNX2X=m
+-CONFIG_QLGE=m
+ CONFIG_SFC=m
+ CONFIG_BE2NET=m
+ CONFIG_LIBERTAS_THINFIRM=m
+diff --git a/arch/mips/configs/lemote2f_defconfig b/arch/mips/configs/lemote2f_defconfig
+index 5da76e0..0cdb431 100644
+--- a/arch/mips/configs/lemote2f_defconfig
++++ b/arch/mips/configs/lemote2f_defconfig
+@@ -39,7 +39,7 @@ CONFIG_HIBERNATION=y
+ CONFIG_PM_STD_PARTITION="/dev/hda3"
+ CONFIG_CPU_FREQ=y
+ CONFIG_CPU_FREQ_DEBUG=y
+-CONFIG_CPU_FREQ_STAT=m
++CONFIG_CPU_FREQ_STAT=y
+ CONFIG_CPU_FREQ_STAT_DETAILS=y
+ CONFIG_CPU_FREQ_DEFAULT_GOV_ONDEMAND=y
+ CONFIG_CPU_FREQ_GOV_POWERSAVE=m
+diff --git a/arch/mips/configs/malta_defconfig b/arch/mips/configs/malta_defconfig
+index 58d43f3..078ecac 100644
+--- a/arch/mips/configs/malta_defconfig
++++ b/arch/mips/configs/malta_defconfig
+@@ -59,8 +59,8 @@ CONFIG_NETFILTER=y
+ CONFIG_NF_CONNTRACK=m
+ CONFIG_NF_CONNTRACK_SECMARK=y
+ CONFIG_NF_CONNTRACK_EVENTS=y
+-CONFIG_NF_CT_PROTO_DCCP=m
+-CONFIG_NF_CT_PROTO_UDPLITE=m
++CONFIG_NF_CT_PROTO_DCCP=y
++CONFIG_NF_CT_PROTO_UDPLITE=y
+ CONFIG_NF_CONNTRACK_AMANDA=m
+ CONFIG_NF_CONNTRACK_FTP=m
+ CONFIG_NF_CONNTRACK_H323=m
+diff --git a/arch/mips/configs/malta_kvm_defconfig b/arch/mips/configs/malta_kvm_defconfig
+index c8f7e28..e233f87 100644
+--- a/arch/mips/configs/malta_kvm_defconfig
++++ b/arch/mips/configs/malta_kvm_defconfig
+@@ -60,8 +60,8 @@ CONFIG_NETFILTER=y
+ CONFIG_NF_CONNTRACK=m
+ CONFIG_NF_CONNTRACK_SECMARK=y
+ CONFIG_NF_CONNTRACK_EVENTS=y
+-CONFIG_NF_CT_PROTO_DCCP=m
+-CONFIG_NF_CT_PROTO_UDPLITE=m
++CONFIG_NF_CT_PROTO_DCCP=y
++CONFIG_NF_CT_PROTO_UDPLITE=y
+ CONFIG_NF_CONNTRACK_AMANDA=m
+ CONFIG_NF_CONNTRACK_FTP=m
+ CONFIG_NF_CONNTRACK_H323=m
+diff --git a/arch/mips/configs/malta_kvm_guest_defconfig b/arch/mips/configs/malta_kvm_guest_defconfig
+index d2f54e5..fbe085c 100644
+--- a/arch/mips/configs/malta_kvm_guest_defconfig
++++ b/arch/mips/configs/malta_kvm_guest_defconfig
+@@ -59,8 +59,8 @@ CONFIG_NETFILTER=y
+ CONFIG_NF_CONNTRACK=m
+ CONFIG_NF_CONNTRACK_SECMARK=y
+ CONFIG_NF_CONNTRACK_EVENTS=y
+-CONFIG_NF_CT_PROTO_DCCP=m
+-CONFIG_NF_CT_PROTO_UDPLITE=m
++CONFIG_NF_CT_PROTO_DCCP=y
++CONFIG_NF_CT_PROTO_UDPLITE=y
+ CONFIG_NF_CONNTRACK_AMANDA=m
+ CONFIG_NF_CONNTRACK_FTP=m
+ CONFIG_NF_CONNTRACK_H323=m
+diff --git a/arch/mips/configs/maltaup_xpa_defconfig b/arch/mips/configs/maltaup_xpa_defconfig
+index 3d0d9cb..2942610 100644
+--- a/arch/mips/configs/maltaup_xpa_defconfig
++++ b/arch/mips/configs/maltaup_xpa_defconfig
+@@ -61,8 +61,8 @@ CONFIG_NETFILTER=y
+ CONFIG_NF_CONNTRACK=m
+ CONFIG_NF_CONNTRACK_SECMARK=y
+ CONFIG_NF_CONNTRACK_EVENTS=y
+-CONFIG_NF_CT_PROTO_DCCP=m
+-CONFIG_NF_CT_PROTO_UDPLITE=m
++CONFIG_NF_CT_PROTO_DCCP=y
++CONFIG_NF_CT_PROTO_UDPLITE=y
+ CONFIG_NF_CONNTRACK_AMANDA=m
+ CONFIG_NF_CONNTRACK_FTP=m
+ CONFIG_NF_CONNTRACK_H323=m
+diff --git a/arch/mips/configs/nlm_xlp_defconfig b/arch/mips/configs/nlm_xlp_defconfig
+index b496c25..07d0182 100644
+--- a/arch/mips/configs/nlm_xlp_defconfig
++++ b/arch/mips/configs/nlm_xlp_defconfig
+@@ -110,7 +110,7 @@ CONFIG_NETFILTER=y
+ CONFIG_NF_CONNTRACK=m
+ CONFIG_NF_CONNTRACK_SECMARK=y
+ CONFIG_NF_CONNTRACK_EVENTS=y
+-CONFIG_NF_CT_PROTO_UDPLITE=m
++CONFIG_NF_CT_PROTO_UDPLITE=y
+ CONFIG_NF_CONNTRACK_AMANDA=m
+ CONFIG_NF_CONNTRACK_FTP=m
+ CONFIG_NF_CONNTRACK_H323=m
+diff --git a/arch/mips/configs/nlm_xlr_defconfig b/arch/mips/configs/nlm_xlr_defconfig
+index 8e99ad8..f59969a 100644
+--- a/arch/mips/configs/nlm_xlr_defconfig
++++ b/arch/mips/configs/nlm_xlr_defconfig
+@@ -90,7 +90,7 @@ CONFIG_NETFILTER=y
+ CONFIG_NF_CONNTRACK=m
+ CONFIG_NF_CONNTRACK_SECMARK=y
+ CONFIG_NF_CONNTRACK_EVENTS=y
+-CONFIG_NF_CT_PROTO_UDPLITE=m
++CONFIG_NF_CT_PROTO_UDPLITE=y
+ CONFIG_NF_CONNTRACK_AMANDA=m
+ CONFIG_NF_CONNTRACK_FTP=m
+ CONFIG_NF_CONNTRACK_H323=m
+diff --git a/arch/mips/include/asm/mach-ip27/spaces.h b/arch/mips/include/asm/mach-ip27/spaces.h
+index 4775a11..24d5e31 100644
+--- a/arch/mips/include/asm/mach-ip27/spaces.h
++++ b/arch/mips/include/asm/mach-ip27/spaces.h
+@@ -12,14 +12,16 @@
+
+ /*
+ * IP27 uses the R10000's uncached attribute feature. Attribute 3 selects
+- * uncached memory addressing.
++ * uncached memory addressing. Hide the definitions on 32-bit compilation
++ * of the compat-vdso code.
+ */
+-
++#ifdef CONFIG_64BIT
+ #define HSPEC_BASE 0x9000000000000000
+ #define IO_BASE 0x9200000000000000
+ #define MSPEC_BASE 0x9400000000000000
+ #define UNCAC_BASE 0x9600000000000000
+ #define CAC_BASE 0xa800000000000000
++#endif
+
+ #define TO_MSPEC(x) (MSPEC_BASE | ((x) & TO_PHYS_MASK))
+ #define TO_HSPEC(x) (HSPEC_BASE | ((x) & TO_PHYS_MASK))
+diff --git a/arch/mips/ralink/prom.c b/arch/mips/ralink/prom.c
+index 5a73c5e..23198c9 100644
+--- a/arch/mips/ralink/prom.c
++++ b/arch/mips/ralink/prom.c
+@@ -30,8 +30,10 @@ const char *get_system_type(void)
+ return soc_info.sys_type;
+ }
+
+-static __init void prom_init_cmdline(int argc, char **argv)
++static __init void prom_init_cmdline(void)
+ {
++ int argc;
++ char **argv;
+ int i;
+
+ pr_debug("prom: fw_arg0=%08x fw_arg1=%08x fw_arg2=%08x fw_arg3=%08x\n",
+@@ -60,14 +62,11 @@ static __init void prom_init_cmdline(int argc, char **argv)
+
+ void __init prom_init(void)
+ {
+- int argc;
+- char **argv;
+-
+ prom_soc_init(&soc_info);
+
+ pr_info("SoC Type: %s\n", get_system_type());
+
+- prom_init_cmdline(argc, argv);
++ prom_init_cmdline();
+ }
+
+ void __init prom_free_prom_memory(void)
+diff --git a/arch/mips/ralink/rt288x.c b/arch/mips/ralink/rt288x.c
+index 285796e..2b76e36 100644
+--- a/arch/mips/ralink/rt288x.c
++++ b/arch/mips/ralink/rt288x.c
+@@ -40,16 +40,6 @@ static struct rt2880_pmx_group rt2880_pinmux_data_act[] = {
+ { 0 }
+ };
+
+-static void rt288x_wdt_reset(void)
+-{
+- u32 t;
+-
+- /* enable WDT reset output on pin SRAM_CS_N */
+- t = rt_sysc_r32(SYSC_REG_CLKCFG);
+- t |= CLKCFG_SRAM_CS_N_WDT;
+- rt_sysc_w32(t, SYSC_REG_CLKCFG);
+-}
+-
+ void __init ralink_clk_init(void)
+ {
+ unsigned long cpu_rate, wmac_rate = 40000000;
+diff --git a/arch/mips/ralink/rt305x.c b/arch/mips/ralink/rt305x.c
+index c8a28c4b..e778e0b 100644
+--- a/arch/mips/ralink/rt305x.c
++++ b/arch/mips/ralink/rt305x.c
+@@ -89,17 +89,6 @@ static struct rt2880_pmx_group rt5350_pinmux_data[] = {
+ { 0 }
+ };
+
+-static void rt305x_wdt_reset(void)
+-{
+- u32 t;
+-
+- /* enable WDT reset output on pin SRAM_CS_N */
+- t = rt_sysc_r32(SYSC_REG_SYSTEM_CONFIG);
+- t |= RT305X_SYSCFG_SRAM_CS0_MODE_WDT <<
+- RT305X_SYSCFG_SRAM_CS0_MODE_SHIFT;
+- rt_sysc_w32(t, SYSC_REG_SYSTEM_CONFIG);
+-}
+-
+ static unsigned long rt5350_get_mem_size(void)
+ {
+ void __iomem *sysc = (void __iomem *) KSEG1ADDR(RT305X_SYSC_BASE);
+diff --git a/arch/mips/ralink/rt3883.c b/arch/mips/ralink/rt3883.c
+index 4cef916..3e0aa09 100644
+--- a/arch/mips/ralink/rt3883.c
++++ b/arch/mips/ralink/rt3883.c
+@@ -63,16 +63,6 @@ static struct rt2880_pmx_group rt3883_pinmux_data[] = {
+ { 0 }
+ };
+
+-static void rt3883_wdt_reset(void)
+-{
+- u32 t;
+-
+- /* enable WDT reset output on GPIO 2 */
+- t = rt_sysc_r32(RT3883_SYSC_REG_SYSCFG1);
+- t |= RT3883_SYSCFG1_GPIO2_AS_WDT_OUT;
+- rt_sysc_w32(t, RT3883_SYSC_REG_SYSCFG1);
+-}
+-
+ void __init ralink_clk_init(void)
+ {
+ unsigned long cpu_rate, sys_rate;
+diff --git a/arch/mips/ralink/timer.c b/arch/mips/ralink/timer.c
+index 8077ff3..d4469b2 100644
+--- a/arch/mips/ralink/timer.c
++++ b/arch/mips/ralink/timer.c
+@@ -71,11 +71,6 @@ static int rt_timer_request(struct rt_timer *rt)
+ return err;
+ }
+
+-static void rt_timer_free(struct rt_timer *rt)
+-{
+- free_irq(rt->irq, rt);
+-}
+-
+ static int rt_timer_config(struct rt_timer *rt, unsigned long divisor)
+ {
+ if (rt->timer_freq < divisor)
+@@ -101,15 +96,6 @@ static int rt_timer_enable(struct rt_timer *rt)
+ return 0;
+ }
+
+-static void rt_timer_disable(struct rt_timer *rt)
+-{
+- u32 t;
+-
+- t = rt_timer_r32(rt, TIMER_REG_TMR0CTL);
+- t &= ~TMR0CTL_ENABLE;
+- rt_timer_w32(rt, TIMER_REG_TMR0CTL, t);
+-}
+-
+ static int rt_timer_probe(struct platform_device *pdev)
+ {
+ struct resource *res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+diff --git a/arch/mips/sgi-ip22/Platform b/arch/mips/sgi-ip22/Platform
+index b7a4b7e..e8f6b3a 100644
+--- a/arch/mips/sgi-ip22/Platform
++++ b/arch/mips/sgi-ip22/Platform
+@@ -25,7 +25,7 @@ endif
+ # Simplified: what IP22 does at 128MB+ in ksegN, IP28 does at 512MB+ in xkphys
+ #
+ ifdef CONFIG_SGI_IP28
+- ifeq ($(call cc-option-yn,-mr10k-cache-barrier=store), n)
++ ifeq ($(call cc-option-yn,-march=r10000 -mr10k-cache-barrier=store), n)
+ $(error gcc doesn't support needed option -mr10k-cache-barrier=store)
+ endif
+ endif
+diff --git a/arch/powerpc/lib/sstep.c b/arch/powerpc/lib/sstep.c
+index 3362299..6ca3b90 100644
+--- a/arch/powerpc/lib/sstep.c
++++ b/arch/powerpc/lib/sstep.c
+@@ -1807,8 +1807,6 @@ int __kprobes emulate_step(struct pt_regs *regs, unsigned int instr)
+ goto instr_done;
+
+ case LARX:
+- if (regs->msr & MSR_LE)
+- return 0;
+ if (op.ea & (size - 1))
+ break; /* can't handle misaligned */
+ err = -EFAULT;
+@@ -1832,8 +1830,6 @@ int __kprobes emulate_step(struct pt_regs *regs, unsigned int instr)
+ goto ldst_done;
+
+ case STCX:
+- if (regs->msr & MSR_LE)
+- return 0;
+ if (op.ea & (size - 1))
+ break; /* can't handle misaligned */
+ err = -EFAULT;
+@@ -1859,8 +1855,6 @@ int __kprobes emulate_step(struct pt_regs *regs, unsigned int instr)
+ goto ldst_done;
+
+ case LOAD:
+- if (regs->msr & MSR_LE)
+- return 0;
+ err = read_mem(&regs->gpr[op.reg], op.ea, size, regs);
+ if (!err) {
+ if (op.type & SIGNEXT)
+@@ -1872,8 +1866,6 @@ int __kprobes emulate_step(struct pt_regs *regs, unsigned int instr)
+
+ #ifdef CONFIG_PPC_FPU
+ case LOAD_FP:
+- if (regs->msr & MSR_LE)
+- return 0;
+ if (size == 4)
+ err = do_fp_load(op.reg, do_lfs, op.ea, size, regs);
+ else
+@@ -1882,15 +1874,11 @@ int __kprobes emulate_step(struct pt_regs *regs, unsigned int instr)
+ #endif
+ #ifdef CONFIG_ALTIVEC
+ case LOAD_VMX:
+- if (regs->msr & MSR_LE)
+- return 0;
+ err = do_vec_load(op.reg, do_lvx, op.ea & ~0xfUL, regs);
+ goto ldst_done;
+ #endif
+ #ifdef CONFIG_VSX
+ case LOAD_VSX:
+- if (regs->msr & MSR_LE)
+- return 0;
+ err = do_vsx_load(op.reg, do_lxvd2x, op.ea, regs);
+ goto ldst_done;
+ #endif
+@@ -1913,8 +1901,6 @@ int __kprobes emulate_step(struct pt_regs *regs, unsigned int instr)
+ goto instr_done;
+
+ case STORE:
+- if (regs->msr & MSR_LE)
+- return 0;
+ if ((op.type & UPDATE) && size == sizeof(long) &&
+ op.reg == 1 && op.update_reg == 1 &&
+ !(regs->msr & MSR_PR) &&
+@@ -1927,8 +1913,6 @@ int __kprobes emulate_step(struct pt_regs *regs, unsigned int instr)
+
+ #ifdef CONFIG_PPC_FPU
+ case STORE_FP:
+- if (regs->msr & MSR_LE)
+- return 0;
+ if (size == 4)
+ err = do_fp_store(op.reg, do_stfs, op.ea, size, regs);
+ else
+@@ -1937,15 +1921,11 @@ int __kprobes emulate_step(struct pt_regs *regs, unsigned int instr)
+ #endif
+ #ifdef CONFIG_ALTIVEC
+ case STORE_VMX:
+- if (regs->msr & MSR_LE)
+- return 0;
+ err = do_vec_store(op.reg, do_stvx, op.ea & ~0xfUL, regs);
+ goto ldst_done;
+ #endif
+ #ifdef CONFIG_VSX
+ case STORE_VSX:
+- if (regs->msr & MSR_LE)
+- return 0;
+ err = do_vsx_store(op.reg, do_stxvd2x, op.ea, regs);
+ goto ldst_done;
+ #endif
+diff --git a/arch/powerpc/sysdev/xics/icp-opal.c b/arch/powerpc/sysdev/xics/icp-opal.c
+index c96c0cb..32c46b4 100644
+--- a/arch/powerpc/sysdev/xics/icp-opal.c
++++ b/arch/powerpc/sysdev/xics/icp-opal.c
+@@ -91,6 +91,16 @@ static unsigned int icp_opal_get_irq(void)
+
+ static void icp_opal_set_cpu_priority(unsigned char cppr)
+ {
++ /*
++ * Here be dragons. The caller has asked to allow only IPI's and not
++ * external interrupts. But OPAL XIVE doesn't support that. So instead
++ * of allowing no interrupts allow all. That's still not right, but
++ * currently the only caller who does this is xics_migrate_irqs_away()
++ * and it works in that case.
++ */
++ if (cppr >= DEFAULT_PRIORITY)
++ cppr = LOWEST_PRIORITY;
++
+ xics_set_base_cppr(cppr);
+ opal_int_set_cppr(cppr);
+ iosync();
+diff --git a/arch/powerpc/sysdev/xics/xics-common.c b/arch/powerpc/sysdev/xics/xics-common.c
+index 69d858e..23efe4e 100644
+--- a/arch/powerpc/sysdev/xics/xics-common.c
++++ b/arch/powerpc/sysdev/xics/xics-common.c
+@@ -20,6 +20,7 @@
+ #include <linux/of.h>
+ #include <linux/slab.h>
+ #include <linux/spinlock.h>
++#include <linux/delay.h>
+
+ #include <asm/prom.h>
+ #include <asm/io.h>
+@@ -198,9 +199,6 @@ void xics_migrate_irqs_away(void)
+ /* Remove ourselves from the global interrupt queue */
+ xics_set_cpu_giq(xics_default_distrib_server, 0);
+
+- /* Allow IPIs again... */
+- icp_ops->set_priority(DEFAULT_PRIORITY);
+-
+ for_each_irq_desc(virq, desc) {
+ struct irq_chip *chip;
+ long server;
+@@ -255,6 +253,19 @@ void xics_migrate_irqs_away(void)
+ unlock:
+ raw_spin_unlock_irqrestore(&desc->lock, flags);
+ }
++
++ /* Allow "sufficient" time to drop any inflight IRQ's */
++ mdelay(5);
++
++ /*
++ * Allow IPIs again. This is done at the very end, after migrating all
++ * interrupts, the expectation is that we'll only get woken up by an IPI
++ * interrupt beyond this point, but leave externals masked just to be
++ * safe. If we're using icp-opal this may actually allow all
++ * interrupts anyway, but that should be OK.
++ */
++ icp_ops->set_priority(DEFAULT_PRIORITY);
++
+ }
+ #endif /* CONFIG_HOTPLUG_CPU */
+
+diff --git a/arch/s390/mm/pgtable.c b/arch/s390/mm/pgtable.c
+index d56ef26..7678f79 100644
+--- a/arch/s390/mm/pgtable.c
++++ b/arch/s390/mm/pgtable.c
+@@ -606,12 +606,29 @@ void ptep_zap_key(struct mm_struct *mm, unsigned long addr, pte_t *ptep)
+ bool test_and_clear_guest_dirty(struct mm_struct *mm, unsigned long addr)
+ {
+ spinlock_t *ptl;
++ pgd_t *pgd;
++ pud_t *pud;
++ pmd_t *pmd;
+ pgste_t pgste;
+ pte_t *ptep;
+ pte_t pte;
+ bool dirty;
+
+- ptep = get_locked_pte(mm, addr, &ptl);
++ pgd = pgd_offset(mm, addr);
++ pud = pud_alloc(mm, pgd, addr);
++ if (!pud)
++ return false;
++ pmd = pmd_alloc(mm, pud, addr);
++ if (!pmd)
++ return false;
++ /* We can't run guests backed by huge pages, but userspace can
++ * still set them up and then try to migrate them without any
++ * migration support.
++ */
++ if (pmd_large(*pmd))
++ return true;
++
++ ptep = pte_alloc_map_lock(mm, pmd, addr, &ptl);
+ if (unlikely(!ptep))
+ return false;
+
+diff --git a/crypto/Makefile b/crypto/Makefile
+index bd6a029..9e52b3c 100644
+--- a/crypto/Makefile
++++ b/crypto/Makefile
+@@ -71,6 +71,7 @@ obj-$(CONFIG_CRYPTO_SHA256) += sha256_generic.o
+ obj-$(CONFIG_CRYPTO_SHA512) += sha512_generic.o
+ obj-$(CONFIG_CRYPTO_SHA3) += sha3_generic.o
+ obj-$(CONFIG_CRYPTO_WP512) += wp512.o
++CFLAGS_wp512.o := $(call cc-option,-fno-schedule-insns) # https://gcc.gnu.org/bugzilla/show_bug.cgi?id=79149
+ obj-$(CONFIG_CRYPTO_TGR192) += tgr192.o
+ obj-$(CONFIG_CRYPTO_GF128MUL) += gf128mul.o
+ obj-$(CONFIG_CRYPTO_ECB) += ecb.o
+@@ -94,6 +95,7 @@ obj-$(CONFIG_CRYPTO_BLOWFISH_COMMON) += blowfish_common.o
+ obj-$(CONFIG_CRYPTO_TWOFISH) += twofish_generic.o
+ obj-$(CONFIG_CRYPTO_TWOFISH_COMMON) += twofish_common.o
+ obj-$(CONFIG_CRYPTO_SERPENT) += serpent_generic.o
++CFLAGS_serpent_generic.o := $(call cc-option,-fsched-pressure) # https://gcc.gnu.org/bugzilla/show_bug.cgi?id=79149
+ obj-$(CONFIG_CRYPTO_AES) += aes_generic.o
+ obj-$(CONFIG_CRYPTO_CAMELLIA) += camellia_generic.o
+ obj-$(CONFIG_CRYPTO_CAST_COMMON) += cast_common.o
+diff --git a/drivers/firmware/efi/arm-runtime.c b/drivers/firmware/efi/arm-runtime.c
+index 7c75a8d..6bdf39e 100644
+--- a/drivers/firmware/efi/arm-runtime.c
++++ b/drivers/firmware/efi/arm-runtime.c
+@@ -65,6 +65,7 @@ static bool __init efi_virtmap_init(void)
+ bool systab_found;
+
+ efi_mm.pgd = pgd_alloc(&efi_mm);
++ mm_init_cpumask(&efi_mm);
+ init_new_context(NULL, &efi_mm);
+
+ systab_found = false;
+diff --git a/drivers/i2c/i2c-mux.c b/drivers/i2c/i2c-mux.c
+index 83768e8..2178266 100644
+--- a/drivers/i2c/i2c-mux.c
++++ b/drivers/i2c/i2c-mux.c
+@@ -429,6 +429,7 @@ void i2c_mux_del_adapters(struct i2c_mux_core *muxc)
+ while (muxc->num_adapters) {
+ struct i2c_adapter *adap = muxc->adapter[--muxc->num_adapters];
+ struct i2c_mux_priv *priv = adap->algo_data;
++ struct device_node *np = adap->dev.of_node;
+
+ muxc->adapter[muxc->num_adapters] = NULL;
+
+@@ -438,6 +439,7 @@ void i2c_mux_del_adapters(struct i2c_mux_core *muxc)
+
+ sysfs_remove_link(&priv->adap.dev.kobj, "mux_device");
+ i2c_del_adapter(adap);
++ of_node_put(np);
+ kfree(priv);
+ }
+ }
+diff --git a/drivers/infiniband/hw/mlx5/main.c b/drivers/infiniband/hw/mlx5/main.c
+index 4cab29e..11bfa27 100644
+--- a/drivers/infiniband/hw/mlx5/main.c
++++ b/drivers/infiniband/hw/mlx5/main.c
+@@ -3141,9 +3141,11 @@ static void *mlx5_ib_add(struct mlx5_core_dev *mdev)
+ if (err)
+ goto err_rsrc;
+
+- err = mlx5_ib_alloc_q_counters(dev);
+- if (err)
+- goto err_odp;
++ if (MLX5_CAP_GEN(dev->mdev, max_qp_cnt)) {
++ err = mlx5_ib_alloc_q_counters(dev);
++ if (err)
++ goto err_odp;
++ }
+
+ err = ib_register_device(&dev->ib_dev, NULL);
+ if (err)
+@@ -3171,7 +3173,8 @@ static void *mlx5_ib_add(struct mlx5_core_dev *mdev)
+ ib_unregister_device(&dev->ib_dev);
+
+ err_q_cnt:
+- mlx5_ib_dealloc_q_counters(dev);
++ if (MLX5_CAP_GEN(dev->mdev, max_qp_cnt))
++ mlx5_ib_dealloc_q_counters(dev);
+
+ err_odp:
+ mlx5_ib_odp_remove_one(dev);
+@@ -3201,7 +3204,8 @@ static void mlx5_ib_remove(struct mlx5_core_dev *mdev, void *context)
+
+ mlx5_remove_roce_notifier(dev);
+ ib_unregister_device(&dev->ib_dev);
+- mlx5_ib_dealloc_q_counters(dev);
++ if (MLX5_CAP_GEN(dev->mdev, max_qp_cnt))
++ mlx5_ib_dealloc_q_counters(dev);
+ destroy_umrc_res(dev);
+ mlx5_ib_odp_remove_one(dev);
+ destroy_dev_resources(&dev->devr);
+diff --git a/drivers/md/dm.c b/drivers/md/dm.c
+index ef7bf1d..628ba00 100644
+--- a/drivers/md/dm.c
++++ b/drivers/md/dm.c
+@@ -972,10 +972,61 @@ void dm_accept_partial_bio(struct bio *bio, unsigned n_sectors)
+ }
+ EXPORT_SYMBOL_GPL(dm_accept_partial_bio);
+
++/*
++ * Flush current->bio_list when the target map method blocks.
++ * This fixes deadlocks in snapshot and possibly in other targets.
++ */
++struct dm_offload {
++ struct blk_plug plug;
++ struct blk_plug_cb cb;
++};
++
++static void flush_current_bio_list(struct blk_plug_cb *cb, bool from_schedule)
++{
++ struct dm_offload *o = container_of(cb, struct dm_offload, cb);
++ struct bio_list list;
++ struct bio *bio;
++
++ INIT_LIST_HEAD(&o->cb.list);
++
++ if (unlikely(!current->bio_list))
++ return;
++
++ list = *current->bio_list;
++ bio_list_init(current->bio_list);
++
++ while ((bio = bio_list_pop(&list))) {
++ struct bio_set *bs = bio->bi_pool;
++ if (unlikely(!bs) || bs == fs_bio_set) {
++ bio_list_add(current->bio_list, bio);
++ continue;
++ }
++
++ spin_lock(&bs->rescue_lock);
++ bio_list_add(&bs->rescue_list, bio);
++ queue_work(bs->rescue_workqueue, &bs->rescue_work);
++ spin_unlock(&bs->rescue_lock);
++ }
++}
++
++static void dm_offload_start(struct dm_offload *o)
++{
++ blk_start_plug(&o->plug);
++ o->cb.callback = flush_current_bio_list;
++ list_add(&o->cb.list, &current->plug->cb_list);
++}
++
++static void dm_offload_end(struct dm_offload *o)
++{
++ list_del(&o->cb.list);
++ blk_finish_plug(&o->plug);
++}
++
+ static void __map_bio(struct dm_target_io *tio)
+ {
+ int r;
+ sector_t sector;
++ struct dm_offload o;
+ struct bio *clone = &tio->clone;
+ struct dm_target *ti = tio->ti;
+
+@@ -988,7 +1039,11 @@ static void __map_bio(struct dm_target_io *tio)
+ */
+ atomic_inc(&tio->io->io_count);
+ sector = clone->bi_iter.bi_sector;
++
++ dm_offload_start(&o);
+ r = ti->type->map(ti, clone);
++ dm_offload_end(&o);
++
+ if (r == DM_MAPIO_REMAPPED) {
+ /* the bio has been remapped so dispatch it */
+
+diff --git a/drivers/media/rc/rc-main.c b/drivers/media/rc/rc-main.c
+index d9c1f2f..aba7735 100644
+--- a/drivers/media/rc/rc-main.c
++++ b/drivers/media/rc/rc-main.c
+@@ -1411,6 +1411,7 @@ int rc_register_device(struct rc_dev *dev)
+ int attr = 0;
+ int minor;
+ int rc;
++ u64 rc_type;
+
+ if (!dev || !dev->map_name)
+ return -EINVAL;
+@@ -1496,14 +1497,18 @@ int rc_register_device(struct rc_dev *dev)
+ goto out_input;
+ }
+
++ rc_type = BIT_ULL(rc_map->rc_type);
++
+ if (dev->change_protocol) {
+- u64 rc_type = (1ll << rc_map->rc_type);
+ rc = dev->change_protocol(dev, &rc_type);
+ if (rc < 0)
+ goto out_raw;
+ dev->enabled_protocols = rc_type;
+ }
+
++ if (dev->driver_type == RC_DRIVER_IR_RAW)
++ ir_raw_load_modules(&rc_type);
++
+ /* Allow the RC sysfs nodes to be accessible */
+ atomic_set(&dev->initialized, 1);
+
+diff --git a/drivers/media/usb/dvb-usb/dw2102.c b/drivers/media/usb/dvb-usb/dw2102.c
+index 2c720cb..c3e6734 100644
+--- a/drivers/media/usb/dvb-usb/dw2102.c
++++ b/drivers/media/usb/dvb-usb/dw2102.c
+@@ -68,6 +68,7 @@
+ struct dw2102_state {
+ u8 initialized;
+ u8 last_lock;
++ u8 data[MAX_XFER_SIZE + 4];
+ struct i2c_client *i2c_client_demod;
+ struct i2c_client *i2c_client_tuner;
+
+@@ -662,62 +663,72 @@ static int su3000_i2c_transfer(struct i2c_adapter *adap, struct i2c_msg msg[],
+ int num)
+ {
+ struct dvb_usb_device *d = i2c_get_adapdata(adap);
+- u8 obuf[0x40], ibuf[0x40];
++ struct dw2102_state *state;
+
+ if (!d)
+ return -ENODEV;
++
++ state = d->priv;
++
+ if (mutex_lock_interruptible(&d->i2c_mutex) < 0)
+ return -EAGAIN;
++ if (mutex_lock_interruptible(&d->data_mutex) < 0) {
++ mutex_unlock(&d->i2c_mutex);
++ return -EAGAIN;
++ }
+
+ switch (num) {
+ case 1:
+ switch (msg[0].addr) {
+ case SU3000_STREAM_CTRL:
+- obuf[0] = msg[0].buf[0] + 0x36;
+- obuf[1] = 3;
+- obuf[2] = 0;
+- if (dvb_usb_generic_rw(d, obuf, 3, ibuf, 0, 0) < 0)
++ state->data[0] = msg[0].buf[0] + 0x36;
++ state->data[1] = 3;
++ state->data[2] = 0;
++ if (dvb_usb_generic_rw(d, state->data, 3,
++ state->data, 0, 0) < 0)
+ err("i2c transfer failed.");
+ break;
+ case DW2102_RC_QUERY:
+- obuf[0] = 0x10;
+- if (dvb_usb_generic_rw(d, obuf, 1, ibuf, 2, 0) < 0)
++ state->data[0] = 0x10;
++ if (dvb_usb_generic_rw(d, state->data, 1,
++ state->data, 2, 0) < 0)
+ err("i2c transfer failed.");
+- msg[0].buf[1] = ibuf[0];
+- msg[0].buf[0] = ibuf[1];
++ msg[0].buf[1] = state->data[0];
++ msg[0].buf[0] = state->data[1];
+ break;
+ default:
+ /* always i2c write*/
+- obuf[0] = 0x08;
+- obuf[1] = msg[0].addr;
+- obuf[2] = msg[0].len;
++ state->data[0] = 0x08;
++ state->data[1] = msg[0].addr;
++ state->data[2] = msg[0].len;
+
+- memcpy(&obuf[3], msg[0].buf, msg[0].len);
++ memcpy(&state->data[3], msg[0].buf, msg[0].len);
+
+- if (dvb_usb_generic_rw(d, obuf, msg[0].len + 3,
+- ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, msg[0].len + 3,
++ state->data, 1, 0) < 0)
+ err("i2c transfer failed.");
+
+ }
+ break;
+ case 2:
+ /* always i2c read */
+- obuf[0] = 0x09;
+- obuf[1] = msg[0].len;
+- obuf[2] = msg[1].len;
+- obuf[3] = msg[0].addr;
+- memcpy(&obuf[4], msg[0].buf, msg[0].len);
+-
+- if (dvb_usb_generic_rw(d, obuf, msg[0].len + 4,
+- ibuf, msg[1].len + 1, 0) < 0)
++ state->data[0] = 0x09;
++ state->data[1] = msg[0].len;
++ state->data[2] = msg[1].len;
++ state->data[3] = msg[0].addr;
++ memcpy(&state->data[4], msg[0].buf, msg[0].len);
++
++ if (dvb_usb_generic_rw(d, state->data, msg[0].len + 4,
++ state->data, msg[1].len + 1, 0) < 0)
+ err("i2c transfer failed.");
+
+- memcpy(msg[1].buf, &ibuf[1], msg[1].len);
++ memcpy(msg[1].buf, &state->data[1], msg[1].len);
+ break;
+ default:
+ warn("more than 2 i2c messages at a time is not handled yet.");
+ break;
+ }
++ mutex_unlock(&d->data_mutex);
+ mutex_unlock(&d->i2c_mutex);
+ return num;
+ }
+@@ -845,17 +856,23 @@ static int su3000_streaming_ctrl(struct dvb_usb_adapter *adap, int onoff)
+ static int su3000_power_ctrl(struct dvb_usb_device *d, int i)
+ {
+ struct dw2102_state *state = (struct dw2102_state *)d->priv;
+- u8 obuf[] = {0xde, 0};
++ int ret = 0;
+
+ info("%s: %d, initialized %d", __func__, i, state->initialized);
+
+ if (i && !state->initialized) {
++ mutex_lock(&d->data_mutex);
++
++ state->data[0] = 0xde;
++ state->data[1] = 0;
++
+ state->initialized = 1;
+ /* reset board */
+- return dvb_usb_generic_rw(d, obuf, 2, NULL, 0, 0);
++ ret = dvb_usb_generic_rw(d, state->data, 2, NULL, 0, 0);
++ mutex_unlock(&d->data_mutex);
+ }
+
+- return 0;
++ return ret;
+ }
+
+ static int su3000_read_mac_address(struct dvb_usb_device *d, u8 mac[6])
+@@ -1310,49 +1327,57 @@ static int prof_7500_frontend_attach(struct dvb_usb_adapter *d)
+ return 0;
+ }
+
+-static int su3000_frontend_attach(struct dvb_usb_adapter *d)
++static int su3000_frontend_attach(struct dvb_usb_adapter *adap)
+ {
+- u8 obuf[3] = { 0xe, 0x80, 0 };
+- u8 ibuf[] = { 0 };
++ struct dvb_usb_device *d = adap->dev;
++ struct dw2102_state *state = d->priv;
++
++ mutex_lock(&d->data_mutex);
++
++ state->data[0] = 0xe;
++ state->data[1] = 0x80;
++ state->data[2] = 0;
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+
+- obuf[0] = 0xe;
+- obuf[1] = 0x02;
+- obuf[2] = 1;
++ state->data[0] = 0xe;
++ state->data[1] = 0x02;
++ state->data[2] = 1;
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+ msleep(300);
+
+- obuf[0] = 0xe;
+- obuf[1] = 0x83;
+- obuf[2] = 0;
++ state->data[0] = 0xe;
++ state->data[1] = 0x83;
++ state->data[2] = 0;
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+
+- obuf[0] = 0xe;
+- obuf[1] = 0x83;
+- obuf[2] = 1;
++ state->data[0] = 0xe;
++ state->data[1] = 0x83;
++ state->data[2] = 1;
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+
+- obuf[0] = 0x51;
++ state->data[0] = 0x51;
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 1, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 1, state->data, 1, 0) < 0)
+ err("command 0x51 transfer failed.");
+
+- d->fe_adap[0].fe = dvb_attach(ds3000_attach, &su3000_ds3000_config,
+- &d->dev->i2c_adap);
+- if (d->fe_adap[0].fe == NULL)
++ mutex_unlock(&d->data_mutex);
++
++ adap->fe_adap[0].fe = dvb_attach(ds3000_attach, &su3000_ds3000_config,
++ &d->i2c_adap);
++ if (adap->fe_adap[0].fe == NULL)
+ return -EIO;
+
+- if (dvb_attach(ts2020_attach, d->fe_adap[0].fe,
++ if (dvb_attach(ts2020_attach, adap->fe_adap[0].fe,
+ &dw2104_ts2020_config,
+- &d->dev->i2c_adap)) {
++ &d->i2c_adap)) {
+ info("Attached DS3000/TS2020!");
+ return 0;
+ }
+@@ -1361,47 +1386,55 @@ static int su3000_frontend_attach(struct dvb_usb_adapter *d)
+ return -EIO;
+ }
+
+-static int t220_frontend_attach(struct dvb_usb_adapter *d)
++static int t220_frontend_attach(struct dvb_usb_adapter *adap)
+ {
+- u8 obuf[3] = { 0xe, 0x87, 0 };
+- u8 ibuf[] = { 0 };
++ struct dvb_usb_device *d = adap->dev;
++ struct dw2102_state *state = d->priv;
++
++ mutex_lock(&d->data_mutex);
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0)
++ state->data[0] = 0xe;
++ state->data[1] = 0x87;
++ state->data[2] = 0x0;
++
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+
+- obuf[0] = 0xe;
+- obuf[1] = 0x86;
+- obuf[2] = 1;
++ state->data[0] = 0xe;
++ state->data[1] = 0x86;
++ state->data[2] = 1;
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+
+- obuf[0] = 0xe;
+- obuf[1] = 0x80;
+- obuf[2] = 0;
++ state->data[0] = 0xe;
++ state->data[1] = 0x80;
++ state->data[2] = 0;
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+
+ msleep(50);
+
+- obuf[0] = 0xe;
+- obuf[1] = 0x80;
+- obuf[2] = 1;
++ state->data[0] = 0xe;
++ state->data[1] = 0x80;
++ state->data[2] = 1;
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+
+- obuf[0] = 0x51;
++ state->data[0] = 0x51;
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 1, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 1, state->data, 1, 0) < 0)
+ err("command 0x51 transfer failed.");
+
+- d->fe_adap[0].fe = dvb_attach(cxd2820r_attach, &cxd2820r_config,
+- &d->dev->i2c_adap, NULL);
+- if (d->fe_adap[0].fe != NULL) {
+- if (dvb_attach(tda18271_attach, d->fe_adap[0].fe, 0x60,
+- &d->dev->i2c_adap, &tda18271_config)) {
++ mutex_unlock(&d->data_mutex);
++
++ adap->fe_adap[0].fe = dvb_attach(cxd2820r_attach, &cxd2820r_config,
++ &d->i2c_adap, NULL);
++ if (adap->fe_adap[0].fe != NULL) {
++ if (dvb_attach(tda18271_attach, adap->fe_adap[0].fe, 0x60,
++ &d->i2c_adap, &tda18271_config)) {
+ info("Attached TDA18271HD/CXD2820R!");
+ return 0;
+ }
+@@ -1411,23 +1444,30 @@ static int t220_frontend_attach(struct dvb_usb_adapter *d)
+ return -EIO;
+ }
+
+-static int m88rs2000_frontend_attach(struct dvb_usb_adapter *d)
++static int m88rs2000_frontend_attach(struct dvb_usb_adapter *adap)
+ {
+- u8 obuf[] = { 0x51 };
+- u8 ibuf[] = { 0 };
++ struct dvb_usb_device *d = adap->dev;
++ struct dw2102_state *state = d->priv;
++
++ mutex_lock(&d->data_mutex);
+
+- if (dvb_usb_generic_rw(d->dev, obuf, 1, ibuf, 1, 0) < 0)
++ state->data[0] = 0x51;
++
++ if (dvb_usb_generic_rw(d, state->data, 1, state->data, 1, 0) < 0)
+ err("command 0x51 transfer failed.");
+
+- d->fe_adap[0].fe = dvb_attach(m88rs2000_attach, &s421_m88rs2000_config,
+- &d->dev->i2c_adap);
++ mutex_unlock(&d->data_mutex);
+
+- if (d->fe_adap[0].fe == NULL)
++ adap->fe_adap[0].fe = dvb_attach(m88rs2000_attach,
++ &s421_m88rs2000_config,
++ &d->i2c_adap);
++
++ if (adap->fe_adap[0].fe == NULL)
+ return -EIO;
+
+- if (dvb_attach(ts2020_attach, d->fe_adap[0].fe,
++ if (dvb_attach(ts2020_attach, adap->fe_adap[0].fe,
+ &dw2104_ts2020_config,
+- &d->dev->i2c_adap)) {
++ &d->i2c_adap)) {
+ info("Attached RS2000/TS2020!");
+ return 0;
+ }
+@@ -1440,44 +1480,50 @@ static int tt_s2_4600_frontend_attach(struct dvb_usb_adapter *adap)
+ {
+ struct dvb_usb_device *d = adap->dev;
+ struct dw2102_state *state = d->priv;
+- u8 obuf[3] = { 0xe, 0x80, 0 };
+- u8 ibuf[] = { 0 };
+ struct i2c_adapter *i2c_adapter;
+ struct i2c_client *client;
+ struct i2c_board_info board_info;
+ struct m88ds3103_platform_data m88ds3103_pdata = {};
+ struct ts2020_config ts2020_config = {};
+
+- if (dvb_usb_generic_rw(d, obuf, 3, ibuf, 1, 0) < 0)
++ mutex_lock(&d->data_mutex);
++
++ state->data[0] = 0xe;
++ state->data[1] = 0x80;
++ state->data[2] = 0x0;
++
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+
+- obuf[0] = 0xe;
+- obuf[1] = 0x02;
+- obuf[2] = 1;
++ state->data[0] = 0xe;
++ state->data[1] = 0x02;
++ state->data[2] = 1;
+
+- if (dvb_usb_generic_rw(d, obuf, 3, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+ msleep(300);
+
+- obuf[0] = 0xe;
+- obuf[1] = 0x83;
+- obuf[2] = 0;
++ state->data[0] = 0xe;
++ state->data[1] = 0x83;
++ state->data[2] = 0;
+
+- if (dvb_usb_generic_rw(d, obuf, 3, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+
+- obuf[0] = 0xe;
+- obuf[1] = 0x83;
+- obuf[2] = 1;
++ state->data[0] = 0xe;
++ state->data[1] = 0x83;
++ state->data[2] = 1;
+
+- if (dvb_usb_generic_rw(d, obuf, 3, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 3, state->data, 1, 0) < 0)
+ err("command 0x0e transfer failed.");
+
+- obuf[0] = 0x51;
++ state->data[0] = 0x51;
+
+- if (dvb_usb_generic_rw(d, obuf, 1, ibuf, 1, 0) < 0)
++ if (dvb_usb_generic_rw(d, state->data, 1, state->data, 1, 0) < 0)
+ err("command 0x51 transfer failed.");
+
++ mutex_unlock(&d->data_mutex);
++
+ /* attach demod */
+ m88ds3103_pdata.clk = 27000000;
+ m88ds3103_pdata.i2c_wr_max = 33;
+diff --git a/drivers/mtd/maps/pmcmsp-flash.c b/drivers/mtd/maps/pmcmsp-flash.c
+index f9fa3fa..2051f28 100644
+--- a/drivers/mtd/maps/pmcmsp-flash.c
++++ b/drivers/mtd/maps/pmcmsp-flash.c
+@@ -139,15 +139,13 @@ static int __init init_msp_flash(void)
+ }
+
+ msp_maps[i].bankwidth = 1;
+- msp_maps[i].name = kmalloc(7, GFP_KERNEL);
++ msp_maps[i].name = kstrndup(flash_name, 7, GFP_KERNEL);
+ if (!msp_maps[i].name) {
+ iounmap(msp_maps[i].virt);
+ kfree(msp_parts[i]);
+ goto cleanup_loop;
+ }
+
+- msp_maps[i].name = strncpy(msp_maps[i].name, flash_name, 7);
+-
+ for (j = 0; j < pcnt; j++) {
+ part_name[5] = '0' + i;
+ part_name[7] = '0' + j;
+diff --git a/drivers/net/ethernet/broadcom/bcm63xx_enet.c b/drivers/net/ethernet/broadcom/bcm63xx_enet.c
+index 5370909..08d91ef 100644
+--- a/drivers/net/ethernet/broadcom/bcm63xx_enet.c
++++ b/drivers/net/ethernet/broadcom/bcm63xx_enet.c
+@@ -913,6 +913,8 @@ static int bcm_enet_open(struct net_device *dev)
+ priv->old_link = 0;
+ priv->old_duplex = -1;
+ priv->old_pause = -1;
++ } else {
++ phydev = NULL;
+ }
+
+ /* mask all interrupts and request them */
+@@ -1083,7 +1085,7 @@ static int bcm_enet_open(struct net_device *dev)
+ enet_dmac_writel(priv, priv->dma_chan_int_mask,
+ ENETDMAC_IRMASK, priv->tx_chan);
+
+- if (priv->has_phy)
++ if (phydev)
+ phy_start(phydev);
+ else
+ bcm_enet_adjust_link(dev);
+@@ -1126,7 +1128,7 @@ static int bcm_enet_open(struct net_device *dev)
+ free_irq(dev->irq, dev);
+
+ out_phy_disconnect:
+- if (priv->has_phy)
++ if (phydev)
+ phy_disconnect(phydev);
+
+ return ret;
+diff --git a/drivers/net/ethernet/ti/cpmac.c b/drivers/net/ethernet/ti/cpmac.c
+index 28097be..5127b7e 100644
+--- a/drivers/net/ethernet/ti/cpmac.c
++++ b/drivers/net/ethernet/ti/cpmac.c
+@@ -1211,7 +1211,7 @@ int cpmac_init(void)
+ goto fail_alloc;
+ }
+
+-#warning FIXME: unhardcode gpio&reset bits
++ /* FIXME: unhardcode gpio&reset bits */
+ ar7_gpio_disable(26);
+ ar7_gpio_disable(27);
+ ar7_device_reset(AR7_RESET_BIT_CPMAC_LO);
+diff --git a/drivers/pci/quirks.c b/drivers/pci/quirks.c
+index 3a035e07..087a218 100644
+--- a/drivers/pci/quirks.c
++++ b/drivers/pci/quirks.c
+@@ -2173,6 +2173,7 @@ DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_LSI_LOGIC, 0x005d, quirk_blacklist_vpd);
+ DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_LSI_LOGIC, 0x005f, quirk_blacklist_vpd);
+ DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_ATTANSIC, PCI_ANY_ID,
+ quirk_blacklist_vpd);
++DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_QLOGIC, 0x2261, quirk_blacklist_vpd);
+
+ /*
+ * For Broadcom 5706, 5708, 5709 rev. A nics, any read beyond the
+diff --git a/drivers/tty/serial/samsung.c b/drivers/tty/serial/samsung.c
+index f44615f..3e2ef4f 100644
+--- a/drivers/tty/serial/samsung.c
++++ b/drivers/tty/serial/samsung.c
+@@ -1036,8 +1036,10 @@ static int s3c64xx_serial_startup(struct uart_port *port)
+ if (ourport->dma) {
+ ret = s3c24xx_serial_request_dma(ourport);
+ if (ret < 0) {
+- dev_warn(port->dev, "DMA request failed\n");
+- return ret;
++ dev_warn(port->dev,
++ "DMA request failed, DMA will not be used\n");
++ devm_kfree(port->dev, ourport->dma);
++ ourport->dma = NULL;
+ }
+ }
+
+diff --git a/drivers/usb/dwc3/dwc3-omap.c b/drivers/usb/dwc3/dwc3-omap.c
+index 29e80cc..5dd1832 100644
+--- a/drivers/usb/dwc3/dwc3-omap.c
++++ b/drivers/usb/dwc3/dwc3-omap.c
+@@ -249,6 +249,7 @@ static void dwc3_omap_set_mailbox(struct dwc3_omap *omap,
+ val = dwc3_omap_read_utmi_ctrl(omap);
+ val |= USBOTGSS_UTMI_OTG_CTRL_IDDIG;
+ dwc3_omap_write_utmi_ctrl(omap, val);
++ break;
+
+ case OMAP_DWC3_VBUS_OFF:
+ val = dwc3_omap_read_utmi_ctrl(omap);
+diff --git a/drivers/usb/dwc3/gadget.h b/drivers/usb/dwc3/gadget.h
+index e4a1d97..39459b7 100644
+--- a/drivers/usb/dwc3/gadget.h
++++ b/drivers/usb/dwc3/gadget.h
+@@ -28,23 +28,23 @@ struct dwc3;
+ #define gadget_to_dwc(g) (container_of(g, struct dwc3, gadget))
+
+ /* DEPCFG parameter 1 */
+-#define DWC3_DEPCFG_INT_NUM(n) ((n) << 0)
++#define DWC3_DEPCFG_INT_NUM(n) (((n) & 0x1f) << 0)
+ #define DWC3_DEPCFG_XFER_COMPLETE_EN (1 << 8)
+ #define DWC3_DEPCFG_XFER_IN_PROGRESS_EN (1 << 9)
+ #define DWC3_DEPCFG_XFER_NOT_READY_EN (1 << 10)
+ #define DWC3_DEPCFG_FIFO_ERROR_EN (1 << 11)
+ #define DWC3_DEPCFG_STREAM_EVENT_EN (1 << 13)
+-#define DWC3_DEPCFG_BINTERVAL_M1(n) ((n) << 16)
++#define DWC3_DEPCFG_BINTERVAL_M1(n) (((n) & 0xff) << 16)
+ #define DWC3_DEPCFG_STREAM_CAPABLE (1 << 24)
+-#define DWC3_DEPCFG_EP_NUMBER(n) ((n) << 25)
++#define DWC3_DEPCFG_EP_NUMBER(n) (((n) & 0x1f) << 25)
+ #define DWC3_DEPCFG_BULK_BASED (1 << 30)
+ #define DWC3_DEPCFG_FIFO_BASED (1 << 31)
+
+ /* DEPCFG parameter 0 */
+-#define DWC3_DEPCFG_EP_TYPE(n) ((n) << 1)
+-#define DWC3_DEPCFG_MAX_PACKET_SIZE(n) ((n) << 3)
+-#define DWC3_DEPCFG_FIFO_NUMBER(n) ((n) << 17)
+-#define DWC3_DEPCFG_BURST_SIZE(n) ((n) << 22)
++#define DWC3_DEPCFG_EP_TYPE(n) (((n) & 0x3) << 1)
++#define DWC3_DEPCFG_MAX_PACKET_SIZE(n) (((n) & 0x7ff) << 3)
++#define DWC3_DEPCFG_FIFO_NUMBER(n) (((n) & 0x1f) << 17)
++#define DWC3_DEPCFG_BURST_SIZE(n) (((n) & 0xf) << 22)
+ #define DWC3_DEPCFG_DATA_SEQ_NUM(n) ((n) << 26)
+ /* This applies for core versions earlier than 1.94a */
+ #define DWC3_DEPCFG_IGN_SEQ_NUM (1 << 31)
+diff --git a/drivers/usb/gadget/function/f_fs.c b/drivers/usb/gadget/function/f_fs.c
+index 8d412d8..89081b8 100644
+--- a/drivers/usb/gadget/function/f_fs.c
++++ b/drivers/usb/gadget/function/f_fs.c
+@@ -1833,11 +1833,14 @@ static int ffs_func_eps_enable(struct ffs_function *func)
+ spin_lock_irqsave(&func->ffs->eps_lock, flags);
+ do {
+ struct usb_endpoint_descriptor *ds;
++ struct usb_ss_ep_comp_descriptor *comp_desc = NULL;
++ int needs_comp_desc = false;
+ int desc_idx;
+
+- if (ffs->gadget->speed == USB_SPEED_SUPER)
++ if (ffs->gadget->speed == USB_SPEED_SUPER) {
+ desc_idx = 2;
+- else if (ffs->gadget->speed == USB_SPEED_HIGH)
++ needs_comp_desc = true;
++ } else if (ffs->gadget->speed == USB_SPEED_HIGH)
+ desc_idx = 1;
+ else
+ desc_idx = 0;
+@@ -1854,6 +1857,14 @@ static int ffs_func_eps_enable(struct ffs_function *func)
+
+ ep->ep->driver_data = ep;
+ ep->ep->desc = ds;
++
++ comp_desc = (struct usb_ss_ep_comp_descriptor *)(ds +
++ USB_DT_ENDPOINT_SIZE);
++ ep->ep->maxburst = comp_desc->bMaxBurst + 1;
++
++ if (needs_comp_desc)
++ ep->ep->comp_desc = comp_desc;
++
+ ret = usb_ep_enable(ep->ep);
+ if (likely(!ret)) {
+ epfile->ep = ep;
+diff --git a/drivers/usb/gadget/function/f_uvc.c b/drivers/usb/gadget/function/f_uvc.c
+index 27ed51b..29b41b5 100644
+--- a/drivers/usb/gadget/function/f_uvc.c
++++ b/drivers/usb/gadget/function/f_uvc.c
+@@ -258,13 +258,6 @@ uvc_function_setup(struct usb_function *f, const struct usb_ctrlrequest *ctrl)
+ memcpy(&uvc_event->req, ctrl, sizeof(uvc_event->req));
+ v4l2_event_queue(&uvc->vdev, &v4l2_event);
+
+- /* Pass additional setup data to userspace */
+- if (uvc->event_setup_out && uvc->event_length) {
+- uvc->control_req->length = uvc->event_length;
+- return usb_ep_queue(uvc->func.config->cdev->gadget->ep0,
+- uvc->control_req, GFP_ATOMIC);
+- }
+-
+ return 0;
+ }
+
+diff --git a/drivers/usb/gadget/udc/dummy_hcd.c b/drivers/usb/gadget/udc/dummy_hcd.c
+index a81d9ab..4fa5de2 100644
+--- a/drivers/usb/gadget/udc/dummy_hcd.c
++++ b/drivers/usb/gadget/udc/dummy_hcd.c
+@@ -1031,6 +1031,8 @@ static int dummy_udc_probe(struct platform_device *pdev)
+ int rc;
+
+ dum = *((void **)dev_get_platdata(&pdev->dev));
++ /* Clear usb_gadget region for new registration to udc-core */
++ memzero_explicit(&dum->gadget, sizeof(struct usb_gadget));
+ dum->gadget.name = gadget_name;
+ dum->gadget.ops = &dummy_ops;
+ dum->gadget.max_speed = USB_SPEED_SUPER;
+diff --git a/drivers/usb/host/ohci-at91.c b/drivers/usb/host/ohci-at91.c
+index b38a228..af0566d 100644
+--- a/drivers/usb/host/ohci-at91.c
++++ b/drivers/usb/host/ohci-at91.c
+@@ -361,7 +361,7 @@ static int ohci_at91_hub_control(struct usb_hcd *hcd, u16 typeReq, u16 wValue,
+
+ case USB_PORT_FEAT_SUSPEND:
+ dev_dbg(hcd->self.controller, "SetPortFeat: SUSPEND\n");
+- if (valid_port(wIndex)) {
++ if (valid_port(wIndex) && ohci_at91->sfr_regmap) {
+ ohci_at91_port_suspend(ohci_at91->sfr_regmap,
+ 1);
+ return 0;
+@@ -404,7 +404,7 @@ static int ohci_at91_hub_control(struct usb_hcd *hcd, u16 typeReq, u16 wValue,
+
+ case USB_PORT_FEAT_SUSPEND:
+ dev_dbg(hcd->self.controller, "ClearPortFeature: SUSPEND\n");
+- if (valid_port(wIndex)) {
++ if (valid_port(wIndex) && ohci_at91->sfr_regmap) {
+ ohci_at91_port_suspend(ohci_at91->sfr_regmap,
+ 0);
+ return 0;
+diff --git a/drivers/usb/host/xhci-dbg.c b/drivers/usb/host/xhci-dbg.c
+index 74c42f7..3425154 100644
+--- a/drivers/usb/host/xhci-dbg.c
++++ b/drivers/usb/host/xhci-dbg.c
+@@ -111,7 +111,7 @@ static void xhci_print_cap_regs(struct xhci_hcd *xhci)
+ xhci_dbg(xhci, "RTSOFF 0x%x:\n", temp & RTSOFF_MASK);
+
+ /* xhci 1.1 controllers have the HCCPARAMS2 register */
+- if (hci_version > 100) {
++ if (hci_version > 0x100) {
+ temp = readl(&xhci->cap_regs->hcc_params2);
+ xhci_dbg(xhci, "HCC PARAMS2 0x%x:\n", (unsigned int) temp);
+ xhci_dbg(xhci, " HC %s Force save context capability",
+diff --git a/drivers/usb/host/xhci-plat.c b/drivers/usb/host/xhci-plat.c
+index abe3606..5895e84 100644
+--- a/drivers/usb/host/xhci-plat.c
++++ b/drivers/usb/host/xhci-plat.c
+@@ -274,6 +274,8 @@ static int xhci_plat_remove(struct platform_device *dev)
+ struct xhci_hcd *xhci = hcd_to_xhci(hcd);
+ struct clk *clk = xhci->clk;
+
++ xhci->xhc_state |= XHCI_STATE_REMOVING;
++
+ usb_remove_hcd(xhci->shared_hcd);
+ usb_phy_shutdown(hcd->usb_phy);
+
+diff --git a/drivers/usb/misc/iowarrior.c b/drivers/usb/misc/iowarrior.c
+index 095778f..37c63cb 100644
+--- a/drivers/usb/misc/iowarrior.c
++++ b/drivers/usb/misc/iowarrior.c
+@@ -781,12 +781,6 @@ static int iowarrior_probe(struct usb_interface *interface,
+ iface_desc = interface->cur_altsetting;
+ dev->product_id = le16_to_cpu(udev->descriptor.idProduct);
+
+- if (iface_desc->desc.bNumEndpoints < 1) {
+- dev_err(&interface->dev, "Invalid number of endpoints\n");
+- retval = -EINVAL;
+- goto error;
+- }
+-
+ /* set up the endpoint information */
+ for (i = 0; i < iface_desc->desc.bNumEndpoints; ++i) {
+ endpoint = &iface_desc->endpoint[i].desc;
+@@ -797,6 +791,21 @@ static int iowarrior_probe(struct usb_interface *interface,
+ /* this one will match for the IOWarrior56 only */
+ dev->int_out_endpoint = endpoint;
+ }
++
++ if (!dev->int_in_endpoint) {
++ dev_err(&interface->dev, "no interrupt-in endpoint found\n");
++ retval = -ENODEV;
++ goto error;
++ }
++
++ if (dev->product_id == USB_DEVICE_ID_CODEMERCS_IOW56) {
++ if (!dev->int_out_endpoint) {
++ dev_err(&interface->dev, "no interrupt-out endpoint found\n");
++ retval = -ENODEV;
++ goto error;
++ }
++ }
++
+ /* we have to check the report_size often, so remember it in the endianness suitable for our machine */
+ dev->report_size = usb_endpoint_maxp(dev->int_in_endpoint);
+ if ((dev->interface->cur_altsetting->desc.bInterfaceNumber == 0) &&
+diff --git a/drivers/usb/serial/digi_acceleport.c b/drivers/usb/serial/digi_acceleport.c
+index 6a1df9e..30bf0f5 100644
+--- a/drivers/usb/serial/digi_acceleport.c
++++ b/drivers/usb/serial/digi_acceleport.c
+@@ -1482,16 +1482,20 @@ static int digi_read_oob_callback(struct urb *urb)
+ struct usb_serial *serial = port->serial;
+ struct tty_struct *tty;
+ struct digi_port *priv = usb_get_serial_port_data(port);
++ unsigned char *buf = urb->transfer_buffer;
+ int opcode, line, status, val;
+ int i;
+ unsigned int rts;
+
++ if (urb->actual_length < 4)
++ return -1;
++
+ /* handle each oob command */
+- for (i = 0; i < urb->actual_length - 3;) {
+- opcode = ((unsigned char *)urb->transfer_buffer)[i++];
+- line = ((unsigned char *)urb->transfer_buffer)[i++];
+- status = ((unsigned char *)urb->transfer_buffer)[i++];
+- val = ((unsigned char *)urb->transfer_buffer)[i++];
++ for (i = 0; i < urb->actual_length - 3; i += 4) {
++ opcode = buf[i];
++ line = buf[i + 1];
++ status = buf[i + 2];
++ val = buf[i + 3];
+
+ dev_dbg(&port->dev, "digi_read_oob_callback: opcode=%d, line=%d, status=%d, val=%d\n",
+ opcode, line, status, val);
+diff --git a/drivers/usb/serial/io_ti.c b/drivers/usb/serial/io_ti.c
+index c02808a..f1a8fdc 100644
+--- a/drivers/usb/serial/io_ti.c
++++ b/drivers/usb/serial/io_ti.c
+@@ -1674,6 +1674,12 @@ static void edge_interrupt_callback(struct urb *urb)
+ function = TIUMP_GET_FUNC_FROM_CODE(data[0]);
+ dev_dbg(dev, "%s - port_number %d, function %d, info 0x%x\n", __func__,
+ port_number, function, data[1]);
++
++ if (port_number >= edge_serial->serial->num_ports) {
++ dev_err(dev, "bad port number %d\n", port_number);
++ goto exit;
++ }
++
+ port = edge_serial->serial->port[port_number];
+ edge_port = usb_get_serial_port_data(port);
+ if (!edge_port) {
+@@ -1755,7 +1761,7 @@ static void edge_bulk_in_callback(struct urb *urb)
+
+ port_number = edge_port->port->port_number;
+
+- if (edge_port->lsr_event) {
++ if (urb->actual_length > 0 && edge_port->lsr_event) {
+ edge_port->lsr_event = 0;
+ dev_dbg(dev, "%s ===== Port %u LSR Status = %02x, Data = %02x ======\n",
+ __func__, port_number, edge_port->lsr_mask, *data);
+diff --git a/drivers/usb/serial/omninet.c b/drivers/usb/serial/omninet.c
+index a180b17..76564b3 100644
+--- a/drivers/usb/serial/omninet.c
++++ b/drivers/usb/serial/omninet.c
+@@ -142,12 +142,6 @@ static int omninet_port_remove(struct usb_serial_port *port)
+
+ static int omninet_open(struct tty_struct *tty, struct usb_serial_port *port)
+ {
+- struct usb_serial *serial = port->serial;
+- struct usb_serial_port *wport;
+-
+- wport = serial->port[1];
+- tty_port_tty_set(&wport->port, tty);
+-
+ return usb_serial_generic_open(tty, port);
+ }
+
+diff --git a/drivers/usb/serial/safe_serial.c b/drivers/usb/serial/safe_serial.c
+index 93c6c9b..8a069aa 100644
+--- a/drivers/usb/serial/safe_serial.c
++++ b/drivers/usb/serial/safe_serial.c
+@@ -200,6 +200,11 @@ static void safe_process_read_urb(struct urb *urb)
+ if (!safe)
+ goto out;
+
++ if (length < 2) {
++ dev_err(&port->dev, "malformed packet\n");
++ return;
++ }
++
+ fcs = fcs_compute10(data, length, CRC10_INITFCS);
+ if (fcs) {
+ dev_err(&port->dev, "%s - bad CRC %x\n", __func__, fcs);
+diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c
+index 1d4f5fa..dc9d64a 100644
+--- a/fs/ext4/inode.c
++++ b/fs/ext4/inode.c
+@@ -3824,6 +3824,10 @@ static int ext4_block_truncate_page(handle_t *handle,
+ unsigned blocksize;
+ struct inode *inode = mapping->host;
+
++ /* If we are processing an encrypted inode during orphan list handling */
++ if (ext4_encrypted_inode(inode) && !fscrypt_has_encryption_key(inode))
++ return 0;
++
+ blocksize = inode->i_sb->s_blocksize;
+ length = blocksize - (offset & (blocksize - 1));
+
+diff --git a/include/linux/user_namespace.h b/include/linux/user_namespace.h
+index eb209d4..dc79773 100644
+--- a/include/linux/user_namespace.h
++++ b/include/linux/user_namespace.h
+@@ -65,7 +65,7 @@ struct ucounts {
+ struct hlist_node node;
+ struct user_namespace *ns;
+ kuid_t uid;
+- atomic_t count;
++ int count;
+ atomic_t ucount[UCOUNT_COUNTS];
+ };
+
+diff --git a/include/trace/events/syscalls.h b/include/trace/events/syscalls.h
+index 14e49c7..b35533b 100644
+--- a/include/trace/events/syscalls.h
++++ b/include/trace/events/syscalls.h
+@@ -1,5 +1,6 @@
+ #undef TRACE_SYSTEM
+ #define TRACE_SYSTEM raw_syscalls
++#undef TRACE_INCLUDE_FILE
+ #define TRACE_INCLUDE_FILE syscalls
+
+ #if !defined(_TRACE_EVENTS_SYSCALLS_H) || defined(TRACE_HEADER_MULTI_READ)
+diff --git a/kernel/ucount.c b/kernel/ucount.c
+index 4bbd38e..f4ac185 100644
+--- a/kernel/ucount.c
++++ b/kernel/ucount.c
+@@ -139,7 +139,7 @@ static struct ucounts *get_ucounts(struct user_namespace *ns, kuid_t uid)
+
+ new->ns = ns;
+ new->uid = uid;
+- atomic_set(&new->count, 0);
++ new->count = 0;
+
+ spin_lock_irq(&ucounts_lock);
+ ucounts = find_ucounts(ns, uid, hashent);
+@@ -150,8 +150,10 @@ static struct ucounts *get_ucounts(struct user_namespace *ns, kuid_t uid)
+ ucounts = new;
+ }
+ }
+- if (!atomic_add_unless(&ucounts->count, 1, INT_MAX))
++ if (ucounts->count == INT_MAX)
+ ucounts = NULL;
++ else
++ ucounts->count += 1;
+ spin_unlock_irq(&ucounts_lock);
+ return ucounts;
+ }
+@@ -160,13 +162,15 @@ static void put_ucounts(struct ucounts *ucounts)
+ {
+ unsigned long flags;
+
+- if (atomic_dec_and_test(&ucounts->count)) {
+- spin_lock_irqsave(&ucounts_lock, flags);
++ spin_lock_irqsave(&ucounts_lock, flags);
++ ucounts->count -= 1;
++ if (!ucounts->count)
+ hlist_del_init(&ucounts->node);
+- spin_unlock_irqrestore(&ucounts_lock, flags);
++ else
++ ucounts = NULL;
++ spin_unlock_irqrestore(&ucounts_lock, flags);
+
+- kfree(ucounts);
+- }
++ kfree(ucounts);
+ }
+
+ static inline bool atomic_inc_below(atomic_t *v, int u)
+diff --git a/virt/kvm/arm/vgic/vgic-mmio.c b/virt/kvm/arm/vgic/vgic-mmio.c
+index ebe1b9f..85814d1 100644
+--- a/virt/kvm/arm/vgic/vgic-mmio.c
++++ b/virt/kvm/arm/vgic/vgic-mmio.c
+@@ -187,21 +187,37 @@ unsigned long vgic_mmio_read_active(struct kvm_vcpu *vcpu,
+ static void vgic_mmio_change_active(struct kvm_vcpu *vcpu, struct vgic_irq *irq,
+ bool new_active_state)
+ {
++ struct kvm_vcpu *requester_vcpu;
+ spin_lock(&irq->irq_lock);
++
++ /*
++ * The vcpu parameter here can mean multiple things depending on how
++ * this function is called; when handling a trap from the kernel it
++ * depends on the GIC version, and these functions are also called as
++ * part of save/restore from userspace.
++ *
++ * Therefore, we have to figure out the requester in a reliable way.
++ *
++ * When accessing VGIC state from user space, the requester_vcpu is
++ * NULL, which is fine, because we guarantee that no VCPUs are running
++ * when accessing VGIC state from user space so irq->vcpu->cpu is
++ * always -1.
++ */
++ requester_vcpu = kvm_arm_get_running_vcpu();
++
+ /*
+ * If this virtual IRQ was written into a list register, we
+ * have to make sure the CPU that runs the VCPU thread has
+- * synced back LR state to the struct vgic_irq. We can only
+- * know this for sure, when either this irq is not assigned to
+- * anyone's AP list anymore, or the VCPU thread is not
+- * running on any CPUs.
++ * synced back the LR state to the struct vgic_irq.
+ *
+- * In the opposite case, we know the VCPU thread may be on its
+- * way back from the guest and still has to sync back this
+- * IRQ, so we release and re-acquire the spin_lock to let the
+- * other thread sync back the IRQ.
++ * As long as the conditions below are true, we know the VCPU thread
++ * may be on its way back from the guest (we kicked the VCPU thread in
++ * vgic_change_active_prepare) and still has to sync back this IRQ,
++ * so we release and re-acquire the spin_lock to let the other thread
++ * sync back the IRQ.
+ */
+ while (irq->vcpu && /* IRQ may have state in an LR somewhere */
++ irq->vcpu != requester_vcpu && /* Current thread is not the VCPU thread */
+ irq->vcpu->cpu != -1) /* VCPU thread is running */
+ cond_resched_lock(&irq->irq_lock);
+