summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAnthony G. Basile <blueness@gentoo.org>2016-11-09 20:16:01 -0500
committerAnthony G. Basile <blueness@gentoo.org>2016-11-09 20:16:01 -0500
commit1a79343c48a4931d4ccad75512471f4dbf962f7e (patch)
tree2c85c88376c23fe28b47aca6b8b33d6f308f7b5e /4.8.6/1005_linux-4.8.6.patch
parentgrsecurity-3.1-4.7.10-201611011946 (diff)
downloadhardened-patchset-1a79343c48a4931d4ccad75512471f4dbf962f7e.tar.gz
hardened-patchset-1a79343c48a4931d4ccad75512471f4dbf962f7e.tar.bz2
hardened-patchset-1a79343c48a4931d4ccad75512471f4dbf962f7e.zip
grsecurity-3.1-4.8.6-20161109180020161109
Diffstat (limited to '4.8.6/1005_linux-4.8.6.patch')
-rw-r--r--4.8.6/1005_linux-4.8.6.patch5137
1 files changed, 5137 insertions, 0 deletions
diff --git a/4.8.6/1005_linux-4.8.6.patch b/4.8.6/1005_linux-4.8.6.patch
new file mode 100644
index 0000000..641ba27
--- /dev/null
+++ b/4.8.6/1005_linux-4.8.6.patch
@@ -0,0 +1,5137 @@
+diff --git a/Makefile b/Makefile
+index daa3a01..b249529 100644
+--- a/Makefile
++++ b/Makefile
+@@ -1,6 +1,6 @@
+ VERSION = 4
+ PATCHLEVEL = 8
+-SUBLEVEL = 5
++SUBLEVEL = 6
+ EXTRAVERSION =
+ NAME = Psychotic Stoned Sheep
+
+diff --git a/arch/arm/boot/dts/arm-realview-eb.dtsi b/arch/arm/boot/dts/arm-realview-eb.dtsi
+index 1c6a040..e2e9599 100644
+--- a/arch/arm/boot/dts/arm-realview-eb.dtsi
++++ b/arch/arm/boot/dts/arm-realview-eb.dtsi
+@@ -51,14 +51,6 @@
+ regulator-boot-on;
+ };
+
+- veth: fixedregulator@0 {
+- compatible = "regulator-fixed";
+- regulator-name = "veth";
+- regulator-min-microvolt = <3300000>;
+- regulator-max-microvolt = <3300000>;
+- regulator-boot-on;
+- };
+-
+ xtal24mhz: xtal24mhz@24M {
+ #clock-cells = <0>;
+ compatible = "fixed-clock";
+@@ -134,16 +126,15 @@
+ bank-width = <4>;
+ };
+
+- /* SMSC 9118 ethernet with PHY and EEPROM */
++ /* SMSC LAN91C111 ethernet with PHY and EEPROM */
+ ethernet: ethernet@4e000000 {
+- compatible = "smsc,lan9118", "smsc,lan9115";
++ compatible = "smsc,lan91c111";
+ reg = <0x4e000000 0x10000>;
+- phy-mode = "mii";
+- reg-io-width = <4>;
+- smsc,irq-active-high;
+- smsc,irq-push-pull;
+- vdd33a-supply = <&veth>;
+- vddvario-supply = <&veth>;
++ /*
++ * This means the adapter can be accessed with 8, 16 or
++ * 32 bit reads/writes.
++ */
++ reg-io-width = <7>;
+ };
+
+ usb: usb@4f000000 {
+diff --git a/arch/arm/boot/dts/bcm958625hr.dts b/arch/arm/boot/dts/bcm958625hr.dts
+index 03b8bbe..652418a 100644
+--- a/arch/arm/boot/dts/bcm958625hr.dts
++++ b/arch/arm/boot/dts/bcm958625hr.dts
+@@ -47,7 +47,8 @@
+ };
+
+ memory {
+- reg = <0x60000000 0x20000000>;
++ device_type = "memory";
++ reg = <0x60000000 0x80000000>;
+ };
+ };
+
+diff --git a/arch/arm/boot/dts/omap3-overo-common-lcd35.dtsi b/arch/arm/boot/dts/omap3-overo-common-lcd35.dtsi
+index ca86da6..854117d 100644
+--- a/arch/arm/boot/dts/omap3-overo-common-lcd35.dtsi
++++ b/arch/arm/boot/dts/omap3-overo-common-lcd35.dtsi
+@@ -119,7 +119,7 @@
+ pinctrl-names = "default";
+ pinctrl-0 = <&mcspi1_pins>;
+
+- lcd0: display {
++ lcd0: display@1 {
+ compatible = "lgphilips,lb035q02";
+ label = "lcd35";
+
+diff --git a/arch/arm/boot/dts/sun9i-a80.dtsi b/arch/arm/boot/dts/sun9i-a80.dtsi
+index f68b324..3f528a3 100644
+--- a/arch/arm/boot/dts/sun9i-a80.dtsi
++++ b/arch/arm/boot/dts/sun9i-a80.dtsi
+@@ -899,8 +899,7 @@
+ resets = <&apbs_rst 0>;
+ gpio-controller;
+ interrupt-controller;
+- #address-cells = <1>;
+- #size-cells = <0>;
++ #interrupt-cells = <3>;
+ #gpio-cells = <3>;
+
+ r_ir_pins: r_ir {
+diff --git a/arch/arm/crypto/ghash-ce-glue.c b/arch/arm/crypto/ghash-ce-glue.c
+index 1568cb5..b88364a 100644
+--- a/arch/arm/crypto/ghash-ce-glue.c
++++ b/arch/arm/crypto/ghash-ce-glue.c
+@@ -220,6 +220,27 @@ static int ghash_async_digest(struct ahash_request *req)
+ }
+ }
+
++static int ghash_async_import(struct ahash_request *req, const void *in)
++{
++ struct ahash_request *cryptd_req = ahash_request_ctx(req);
++ struct crypto_ahash *tfm = crypto_ahash_reqtfm(req);
++ struct ghash_async_ctx *ctx = crypto_ahash_ctx(tfm);
++ struct shash_desc *desc = cryptd_shash_desc(cryptd_req);
++
++ desc->tfm = cryptd_ahash_child(ctx->cryptd_tfm);
++ desc->flags = req->base.flags;
++
++ return crypto_shash_import(desc, in);
++}
++
++static int ghash_async_export(struct ahash_request *req, void *out)
++{
++ struct ahash_request *cryptd_req = ahash_request_ctx(req);
++ struct shash_desc *desc = cryptd_shash_desc(cryptd_req);
++
++ return crypto_shash_export(desc, out);
++}
++
+ static int ghash_async_setkey(struct crypto_ahash *tfm, const u8 *key,
+ unsigned int keylen)
+ {
+@@ -268,7 +289,10 @@ static struct ahash_alg ghash_async_alg = {
+ .final = ghash_async_final,
+ .setkey = ghash_async_setkey,
+ .digest = ghash_async_digest,
++ .import = ghash_async_import,
++ .export = ghash_async_export,
+ .halg.digestsize = GHASH_DIGEST_SIZE,
++ .halg.statesize = sizeof(struct ghash_desc_ctx),
+ .halg.base = {
+ .cra_name = "ghash",
+ .cra_driver_name = "ghash-ce",
+diff --git a/arch/arm/mach-pxa/corgi_pm.c b/arch/arm/mach-pxa/corgi_pm.c
+index d920681..c71c483 100644
+--- a/arch/arm/mach-pxa/corgi_pm.c
++++ b/arch/arm/mach-pxa/corgi_pm.c
+@@ -131,16 +131,11 @@ static int corgi_should_wakeup(unsigned int resume_on_alarm)
+ return is_resume;
+ }
+
+-static unsigned long corgi_charger_wakeup(void)
++static bool corgi_charger_wakeup(void)
+ {
+- unsigned long ret;
+-
+- ret = (!gpio_get_value(CORGI_GPIO_AC_IN) << GPIO_bit(CORGI_GPIO_AC_IN))
+- | (!gpio_get_value(CORGI_GPIO_KEY_INT)
+- << GPIO_bit(CORGI_GPIO_KEY_INT))
+- | (!gpio_get_value(CORGI_GPIO_WAKEUP)
+- << GPIO_bit(CORGI_GPIO_WAKEUP));
+- return ret;
++ return !gpio_get_value(CORGI_GPIO_AC_IN) ||
++ !gpio_get_value(CORGI_GPIO_KEY_INT) ||
++ !gpio_get_value(CORGI_GPIO_WAKEUP);
+ }
+
+ unsigned long corgipm_read_devdata(int type)
+diff --git a/arch/arm/mach-pxa/pxa_cplds_irqs.c b/arch/arm/mach-pxa/pxa_cplds_irqs.c
+index 2385052..e362f86 100644
+--- a/arch/arm/mach-pxa/pxa_cplds_irqs.c
++++ b/arch/arm/mach-pxa/pxa_cplds_irqs.c
+@@ -41,30 +41,35 @@ static irqreturn_t cplds_irq_handler(int in_irq, void *d)
+ unsigned long pending;
+ unsigned int bit;
+
+- pending = readl(fpga->base + FPGA_IRQ_SET_CLR) & fpga->irq_mask;
+- for_each_set_bit(bit, &pending, CPLDS_NB_IRQ)
+- generic_handle_irq(irq_find_mapping(fpga->irqdomain, bit));
++ do {
++ pending = readl(fpga->base + FPGA_IRQ_SET_CLR) & fpga->irq_mask;
++ for_each_set_bit(bit, &pending, CPLDS_NB_IRQ) {
++ generic_handle_irq(irq_find_mapping(fpga->irqdomain,
++ bit));
++ }
++ } while (pending);
+
+ return IRQ_HANDLED;
+ }
+
+-static void cplds_irq_mask_ack(struct irq_data *d)
++static void cplds_irq_mask(struct irq_data *d)
+ {
+ struct cplds *fpga = irq_data_get_irq_chip_data(d);
+ unsigned int cplds_irq = irqd_to_hwirq(d);
+- unsigned int set, bit = BIT(cplds_irq);
++ unsigned int bit = BIT(cplds_irq);
+
+ fpga->irq_mask &= ~bit;
+ writel(fpga->irq_mask, fpga->base + FPGA_IRQ_MASK_EN);
+- set = readl(fpga->base + FPGA_IRQ_SET_CLR);
+- writel(set & ~bit, fpga->base + FPGA_IRQ_SET_CLR);
+ }
+
+ static void cplds_irq_unmask(struct irq_data *d)
+ {
+ struct cplds *fpga = irq_data_get_irq_chip_data(d);
+ unsigned int cplds_irq = irqd_to_hwirq(d);
+- unsigned int bit = BIT(cplds_irq);
++ unsigned int set, bit = BIT(cplds_irq);
++
++ set = readl(fpga->base + FPGA_IRQ_SET_CLR);
++ writel(set & ~bit, fpga->base + FPGA_IRQ_SET_CLR);
+
+ fpga->irq_mask |= bit;
+ writel(fpga->irq_mask, fpga->base + FPGA_IRQ_MASK_EN);
+@@ -72,7 +77,8 @@ static void cplds_irq_unmask(struct irq_data *d)
+
+ static struct irq_chip cplds_irq_chip = {
+ .name = "pxa_cplds",
+- .irq_mask_ack = cplds_irq_mask_ack,
++ .irq_ack = cplds_irq_mask,
++ .irq_mask = cplds_irq_mask,
+ .irq_unmask = cplds_irq_unmask,
+ .flags = IRQCHIP_MASK_ON_SUSPEND | IRQCHIP_SKIP_SET_WAKE,
+ };
+diff --git a/arch/arm/mach-pxa/sharpsl_pm.c b/arch/arm/mach-pxa/sharpsl_pm.c
+index b80eab9..249b7bd 100644
+--- a/arch/arm/mach-pxa/sharpsl_pm.c
++++ b/arch/arm/mach-pxa/sharpsl_pm.c
+@@ -744,7 +744,7 @@ static int sharpsl_off_charge_battery(void)
+ time = RCNR;
+ while (1) {
+ /* Check if any wakeup event had occurred */
+- if (sharpsl_pm.machinfo->charger_wakeup() != 0)
++ if (sharpsl_pm.machinfo->charger_wakeup())
+ return 0;
+ /* Check for timeout */
+ if ((RCNR - time) > SHARPSL_WAIT_CO_TIME)
+diff --git a/arch/arm/mach-pxa/sharpsl_pm.h b/arch/arm/mach-pxa/sharpsl_pm.h
+index 905be67..fa75b6d 100644
+--- a/arch/arm/mach-pxa/sharpsl_pm.h
++++ b/arch/arm/mach-pxa/sharpsl_pm.h
+@@ -34,7 +34,7 @@ struct sharpsl_charger_machinfo {
+ #define SHARPSL_STATUS_LOCK 5
+ #define SHARPSL_STATUS_CHRGFULL 6
+ #define SHARPSL_STATUS_FATAL 7
+- unsigned long (*charger_wakeup)(void);
++ bool (*charger_wakeup)(void);
+ int (*should_wakeup)(unsigned int resume_on_alarm);
+ void (*backlight_limit)(int);
+ int (*backlight_get_status) (void);
+diff --git a/arch/arm/mach-pxa/spitz_pm.c b/arch/arm/mach-pxa/spitz_pm.c
+index ea9f903..4e64a14 100644
+--- a/arch/arm/mach-pxa/spitz_pm.c
++++ b/arch/arm/mach-pxa/spitz_pm.c
+@@ -165,13 +165,10 @@ static int spitz_should_wakeup(unsigned int resume_on_alarm)
+ return is_resume;
+ }
+
+-static unsigned long spitz_charger_wakeup(void)
++static bool spitz_charger_wakeup(void)
+ {
+- unsigned long ret;
+- ret = ((!gpio_get_value(SPITZ_GPIO_KEY_INT)
+- << GPIO_bit(SPITZ_GPIO_KEY_INT))
+- | gpio_get_value(SPITZ_GPIO_SYNC));
+- return ret;
++ return !gpio_get_value(SPITZ_GPIO_KEY_INT) ||
++ gpio_get_value(SPITZ_GPIO_SYNC);
+ }
+
+ unsigned long spitzpm_read_devdata(int type)
+diff --git a/arch/powerpc/include/asm/book3s/64/pgtable.h b/arch/powerpc/include/asm/book3s/64/pgtable.h
+index 263bf39..9bd84ba 100644
+--- a/arch/powerpc/include/asm/book3s/64/pgtable.h
++++ b/arch/powerpc/include/asm/book3s/64/pgtable.h
+@@ -6,6 +6,8 @@
+ */
+ #define _PAGE_BIT_SWAP_TYPE 0
+
++#define _PAGE_RO 0
++
+ #define _PAGE_EXEC 0x00001 /* execute permission */
+ #define _PAGE_WRITE 0x00002 /* write access allowed */
+ #define _PAGE_READ 0x00004 /* read access allowed */
+diff --git a/arch/powerpc/kernel/nvram_64.c b/arch/powerpc/kernel/nvram_64.c
+index 64174bf..05a0a91 100644
+--- a/arch/powerpc/kernel/nvram_64.c
++++ b/arch/powerpc/kernel/nvram_64.c
+@@ -956,7 +956,7 @@ int __init nvram_remove_partition(const char *name, int sig,
+
+ /* Make partition a free partition */
+ part->header.signature = NVRAM_SIG_FREE;
+- strncpy(part->header.name, "wwwwwwwwwwww", 12);
++ memset(part->header.name, 'w', 12);
+ part->header.checksum = nvram_checksum(&part->header);
+ rc = nvram_write_header(part);
+ if (rc <= 0) {
+@@ -974,8 +974,8 @@ int __init nvram_remove_partition(const char *name, int sig,
+ }
+ if (prev) {
+ prev->header.length += part->header.length;
+- prev->header.checksum = nvram_checksum(&part->header);
+- rc = nvram_write_header(part);
++ prev->header.checksum = nvram_checksum(&prev->header);
++ rc = nvram_write_header(prev);
+ if (rc <= 0) {
+ printk(KERN_ERR "nvram_remove_partition: nvram_write failed (%d)\n", rc);
+ return rc;
+diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
+index 9ee2623..ad37aa1 100644
+--- a/arch/powerpc/kernel/process.c
++++ b/arch/powerpc/kernel/process.c
+@@ -88,7 +88,13 @@ static void check_if_tm_restore_required(struct task_struct *tsk)
+ set_thread_flag(TIF_RESTORE_TM);
+ }
+ }
++
++static inline bool msr_tm_active(unsigned long msr)
++{
++ return MSR_TM_ACTIVE(msr);
++}
+ #else
++static inline bool msr_tm_active(unsigned long msr) { return false; }
+ static inline void check_if_tm_restore_required(struct task_struct *tsk) { }
+ #endif /* CONFIG_PPC_TRANSACTIONAL_MEM */
+
+@@ -208,7 +214,7 @@ void enable_kernel_fp(void)
+ EXPORT_SYMBOL(enable_kernel_fp);
+
+ static int restore_fp(struct task_struct *tsk) {
+- if (tsk->thread.load_fp) {
++ if (tsk->thread.load_fp || msr_tm_active(tsk->thread.regs->msr)) {
+ load_fp_state(&current->thread.fp_state);
+ current->thread.load_fp++;
+ return 1;
+@@ -278,7 +284,8 @@ EXPORT_SYMBOL_GPL(flush_altivec_to_thread);
+
+ static int restore_altivec(struct task_struct *tsk)
+ {
+- if (cpu_has_feature(CPU_FTR_ALTIVEC) && tsk->thread.load_vec) {
++ if (cpu_has_feature(CPU_FTR_ALTIVEC) &&
++ (tsk->thread.load_vec || msr_tm_active(tsk->thread.regs->msr))) {
+ load_vr_state(&tsk->thread.vr_state);
+ tsk->thread.used_vr = 1;
+ tsk->thread.load_vec++;
+@@ -438,6 +445,7 @@ void giveup_all(struct task_struct *tsk)
+ return;
+
+ msr_check_and_set(msr_all_available);
++ check_if_tm_restore_required(tsk);
+
+ #ifdef CONFIG_PPC_FPU
+ if (usermsr & MSR_FP)
+@@ -464,7 +472,8 @@ void restore_math(struct pt_regs *regs)
+ {
+ unsigned long msr;
+
+- if (!current->thread.load_fp && !loadvec(current->thread))
++ if (!msr_tm_active(regs->msr) &&
++ !current->thread.load_fp && !loadvec(current->thread))
+ return;
+
+ msr = regs->msr;
+@@ -983,6 +992,13 @@ void restore_tm_state(struct pt_regs *regs)
+ msr_diff = current->thread.ckpt_regs.msr & ~regs->msr;
+ msr_diff &= MSR_FP | MSR_VEC | MSR_VSX;
+
++ /* Ensure that restore_math() will restore */
++ if (msr_diff & MSR_FP)
++ current->thread.load_fp = 1;
++#ifdef CONFIG_ALIVEC
++ if (cpu_has_feature(CPU_FTR_ALTIVEC) && msr_diff & MSR_VEC)
++ current->thread.load_vec = 1;
++#endif
+ restore_math(regs);
+
+ regs->msr |= msr_diff;
+diff --git a/arch/powerpc/mm/hugetlbpage.c b/arch/powerpc/mm/hugetlbpage.c
+index 7372ee1..a5d3ecd 100644
+--- a/arch/powerpc/mm/hugetlbpage.c
++++ b/arch/powerpc/mm/hugetlbpage.c
+@@ -1019,8 +1019,15 @@ int gup_hugepte(pte_t *ptep, unsigned long sz, unsigned long addr,
+
+ pte = READ_ONCE(*ptep);
+ mask = _PAGE_PRESENT | _PAGE_READ;
++
++ /*
++ * On some CPUs like the 8xx, _PAGE_RW hence _PAGE_WRITE is defined
++ * as 0 and _PAGE_RO has to be set when a page is not writable
++ */
+ if (write)
+ mask |= _PAGE_WRITE;
++ else
++ mask |= _PAGE_RO;
+
+ if ((pte_val(pte) & mask) != mask)
+ return 0;
+diff --git a/arch/x86/kernel/early-quirks.c b/arch/x86/kernel/early-quirks.c
+index de7501e..8b8852b 100644
+--- a/arch/x86/kernel/early-quirks.c
++++ b/arch/x86/kernel/early-quirks.c
+@@ -317,16 +317,11 @@ static phys_addr_t __init i85x_stolen_base(int num, int slot, int func,
+ static phys_addr_t __init i865_stolen_base(int num, int slot, int func,
+ size_t stolen_size)
+ {
+- u16 toud;
++ u16 toud = 0;
+
+- /*
+- * FIXME is the graphics stolen memory region
+- * always at TOUD? Ie. is it always the last
+- * one to be allocated by the BIOS?
+- */
+ toud = read_pci_config_16(0, 0, 0, I865_TOUD);
+
+- return (phys_addr_t)toud << 16;
++ return (phys_addr_t)(toud << 16) + i845_tseg_size();
+ }
+
+ static phys_addr_t __init gen3_stolen_base(int num, int slot, int func,
+diff --git a/crypto/gcm.c b/crypto/gcm.c
+index 70a892e8..f624ac9 100644
+--- a/crypto/gcm.c
++++ b/crypto/gcm.c
+@@ -117,7 +117,7 @@ static int crypto_gcm_setkey(struct crypto_aead *aead, const u8 *key,
+ struct crypto_skcipher *ctr = ctx->ctr;
+ struct {
+ be128 hash;
+- u8 iv[8];
++ u8 iv[16];
+
+ struct crypto_gcm_setkey_result result;
+
+diff --git a/drivers/char/hw_random/omap-rng.c b/drivers/char/hw_random/omap-rng.c
+index 01d4be2..f5c26a5 100644
+--- a/drivers/char/hw_random/omap-rng.c
++++ b/drivers/char/hw_random/omap-rng.c
+@@ -385,7 +385,7 @@ static int omap_rng_probe(struct platform_device *pdev)
+
+ pm_runtime_enable(&pdev->dev);
+ ret = pm_runtime_get_sync(&pdev->dev);
+- if (ret) {
++ if (ret < 0) {
+ dev_err(&pdev->dev, "Failed to runtime_get device: %d\n", ret);
+ pm_runtime_put_noidle(&pdev->dev);
+ goto err_ioremap;
+@@ -443,7 +443,7 @@ static int __maybe_unused omap_rng_resume(struct device *dev)
+ int ret;
+
+ ret = pm_runtime_get_sync(dev);
+- if (ret) {
++ if (ret < 0) {
+ dev_err(dev, "Failed to runtime_get device: %d\n", ret);
+ pm_runtime_put_noidle(dev);
+ return ret;
+diff --git a/drivers/clk/bcm/clk-bcm2835.c b/drivers/clk/bcm/clk-bcm2835.c
+index 7a79708..0fc71cb 100644
+--- a/drivers/clk/bcm/clk-bcm2835.c
++++ b/drivers/clk/bcm/clk-bcm2835.c
+@@ -1006,16 +1006,28 @@ static int bcm2835_clock_set_rate(struct clk_hw *hw,
+ return 0;
+ }
+
++static bool
++bcm2835_clk_is_pllc(struct clk_hw *hw)
++{
++ if (!hw)
++ return false;
++
++ return strncmp(clk_hw_get_name(hw), "pllc", 4) == 0;
++}
++
+ static int bcm2835_clock_determine_rate(struct clk_hw *hw,
+ struct clk_rate_request *req)
+ {
+ struct bcm2835_clock *clock = bcm2835_clock_from_hw(hw);
+ struct clk_hw *parent, *best_parent = NULL;
++ bool current_parent_is_pllc;
+ unsigned long rate, best_rate = 0;
+ unsigned long prate, best_prate = 0;
+ size_t i;
+ u32 div;
+
++ current_parent_is_pllc = bcm2835_clk_is_pllc(clk_hw_get_parent(hw));
++
+ /*
+ * Select parent clock that results in the closest but lower rate
+ */
+@@ -1023,6 +1035,17 @@ static int bcm2835_clock_determine_rate(struct clk_hw *hw,
+ parent = clk_hw_get_parent_by_index(hw, i);
+ if (!parent)
+ continue;
++
++ /*
++ * Don't choose a PLLC-derived clock as our parent
++ * unless it had been manually set that way. PLLC's
++ * frequency gets adjusted by the firmware due to
++ * over-temp or under-voltage conditions, without
++ * prior notification to our clock consumer.
++ */
++ if (bcm2835_clk_is_pllc(parent) && !current_parent_is_pllc)
++ continue;
++
+ prate = clk_hw_get_rate(parent);
+ div = bcm2835_clock_choose_div(hw, req->rate, prate, true);
+ rate = bcm2835_clock_rate_from_divisor(clock, prate, div);
+diff --git a/drivers/clk/clk-divider.c b/drivers/clk/clk-divider.c
+index a0f55bc..96386ff 100644
+--- a/drivers/clk/clk-divider.c
++++ b/drivers/clk/clk-divider.c
+@@ -352,7 +352,7 @@ static long clk_divider_round_rate(struct clk_hw *hw, unsigned long rate,
+
+ /* if read only, just return current value */
+ if (divider->flags & CLK_DIVIDER_READ_ONLY) {
+- bestdiv = readl(divider->reg) >> divider->shift;
++ bestdiv = clk_readl(divider->reg) >> divider->shift;
+ bestdiv &= div_mask(divider->width);
+ bestdiv = _get_div(divider->table, bestdiv, divider->flags,
+ divider->width);
+diff --git a/drivers/clk/clk-qoriq.c b/drivers/clk/clk-qoriq.c
+index 58566a17..20b1055 100644
+--- a/drivers/clk/clk-qoriq.c
++++ b/drivers/clk/clk-qoriq.c
+@@ -766,7 +766,11 @@ static struct clk * __init create_one_cmux(struct clockgen *cg, int idx)
+ if (!hwc)
+ return NULL;
+
+- hwc->reg = cg->regs + 0x20 * idx;
++ if (cg->info.flags & CG_VER3)
++ hwc->reg = cg->regs + 0x70000 + 0x20 * idx;
++ else
++ hwc->reg = cg->regs + 0x20 * idx;
++
+ hwc->info = cg->info.cmux_groups[cg->info.cmux_to_group[idx]];
+
+ /*
+diff --git a/drivers/clk/clk.c b/drivers/clk/clk.c
+index 820a939..2877a4d 100644
+--- a/drivers/clk/clk.c
++++ b/drivers/clk/clk.c
+@@ -1908,10 +1908,6 @@ int clk_set_phase(struct clk *clk, int degrees)
+
+ clk_prepare_lock();
+
+- /* bail early if nothing to do */
+- if (degrees == clk->core->phase)
+- goto out;
+-
+ trace_clk_set_phase(clk->core, degrees);
+
+ if (clk->core->ops->set_phase)
+@@ -1922,7 +1918,6 @@ int clk_set_phase(struct clk *clk, int degrees)
+ if (!ret)
+ clk->core->phase = degrees;
+
+-out:
+ clk_prepare_unlock();
+
+ return ret;
+@@ -3186,7 +3181,7 @@ struct clk *__of_clk_get_from_provider(struct of_phandle_args *clkspec,
+ {
+ struct of_clk_provider *provider;
+ struct clk *clk = ERR_PTR(-EPROBE_DEFER);
+- struct clk_hw *hw = ERR_PTR(-EPROBE_DEFER);
++ struct clk_hw *hw;
+
+ if (!clkspec)
+ return ERR_PTR(-EINVAL);
+@@ -3194,12 +3189,13 @@ struct clk *__of_clk_get_from_provider(struct of_phandle_args *clkspec,
+ /* Check if we have such a provider in our array */
+ mutex_lock(&of_clk_mutex);
+ list_for_each_entry(provider, &of_clk_providers, link) {
+- if (provider->node == clkspec->np)
++ if (provider->node == clkspec->np) {
+ hw = __of_clk_get_hw_from_provider(provider, clkspec);
+- if (!IS_ERR(hw)) {
+ clk = __clk_create_clk(hw, dev_id, con_id);
++ }
+
+- if (!IS_ERR(clk) && !__clk_get(clk)) {
++ if (!IS_ERR(clk)) {
++ if (!__clk_get(clk)) {
+ __clk_free_clk(clk);
+ clk = ERR_PTR(-ENOENT);
+ }
+diff --git a/drivers/clk/imx/clk-imx35.c b/drivers/clk/imx/clk-imx35.c
+index b0978d3..d302ed3 100644
+--- a/drivers/clk/imx/clk-imx35.c
++++ b/drivers/clk/imx/clk-imx35.c
+@@ -115,7 +115,7 @@ static void __init _mx35_clocks_init(void)
+ }
+
+ clk[ckih] = imx_clk_fixed("ckih", 24000000);
+- clk[ckil] = imx_clk_fixed("ckih", 32768);
++ clk[ckil] = imx_clk_fixed("ckil", 32768);
+ clk[mpll] = imx_clk_pllv1(IMX_PLLV1_IMX35, "mpll", "ckih", base + MX35_CCM_MPCTL);
+ clk[ppll] = imx_clk_pllv1(IMX_PLLV1_IMX35, "ppll", "ckih", base + MX35_CCM_PPCTL);
+
+diff --git a/drivers/clk/qcom/Kconfig b/drivers/clk/qcom/Kconfig
+index 95e3b3e..98909b1 100644
+--- a/drivers/clk/qcom/Kconfig
++++ b/drivers/clk/qcom/Kconfig
+@@ -117,6 +117,7 @@ config MSM_MMCC_8974
+
+ config MSM_GCC_8996
+ tristate "MSM8996 Global Clock Controller"
++ select QCOM_GDSC
+ depends on COMMON_CLK_QCOM
+ help
+ Support for the global clock controller on msm8996 devices.
+@@ -126,6 +127,7 @@ config MSM_GCC_8996
+ config MSM_MMCC_8996
+ tristate "MSM8996 Multimedia Clock Controller"
+ select MSM_GCC_8996
++ select QCOM_GDSC
+ depends on COMMON_CLK_QCOM
+ help
+ Support for the multimedia clock controller on msm8996 devices.
+diff --git a/drivers/clk/qcom/gcc-msm8996.c b/drivers/clk/qcom/gcc-msm8996.c
+index bbf732b..9f643cc 100644
+--- a/drivers/clk/qcom/gcc-msm8996.c
++++ b/drivers/clk/qcom/gcc-msm8996.c
+@@ -2592,9 +2592,9 @@ static struct clk_branch gcc_pcie_2_aux_clk = {
+ };
+
+ static struct clk_branch gcc_pcie_2_pipe_clk = {
+- .halt_reg = 0x6e108,
++ .halt_reg = 0x6e018,
+ .clkr = {
+- .enable_reg = 0x6e108,
++ .enable_reg = 0x6e018,
+ .enable_mask = BIT(0),
+ .hw.init = &(struct clk_init_data){
+ .name = "gcc_pcie_2_pipe_clk",
+diff --git a/drivers/crypto/ccp/ccp-dmaengine.c b/drivers/crypto/ccp/ccp-dmaengine.c
+index 94f77b0..32f645e 100644
+--- a/drivers/crypto/ccp/ccp-dmaengine.c
++++ b/drivers/crypto/ccp/ccp-dmaengine.c
+@@ -650,7 +650,7 @@ int ccp_dmaengine_register(struct ccp_device *ccp)
+ dma_desc_cache_name = devm_kasprintf(ccp->dev, GFP_KERNEL,
+ "%s-dmaengine-desc-cache",
+ ccp->name);
+- if (!dma_cmd_cache_name)
++ if (!dma_desc_cache_name)
+ return -ENOMEM;
+ ccp->dma_desc_cache = kmem_cache_create(dma_desc_cache_name,
+ sizeof(struct ccp_dma_desc),
+diff --git a/drivers/crypto/marvell/cesa.c b/drivers/crypto/marvell/cesa.c
+index d64af86..37dadb2 100644
+--- a/drivers/crypto/marvell/cesa.c
++++ b/drivers/crypto/marvell/cesa.c
+@@ -166,6 +166,7 @@ static irqreturn_t mv_cesa_int(int irq, void *priv)
+ if (!req)
+ break;
+
++ ctx = crypto_tfm_ctx(req->tfm);
+ mv_cesa_complete_req(ctx, req, 0);
+ }
+ }
+diff --git a/drivers/crypto/marvell/hash.c b/drivers/crypto/marvell/hash.c
+index 82e0f4e6..b111e14 100644
+--- a/drivers/crypto/marvell/hash.c
++++ b/drivers/crypto/marvell/hash.c
+@@ -805,13 +805,14 @@ static int mv_cesa_md5_init(struct ahash_request *req)
+ struct mv_cesa_op_ctx tmpl = { };
+
+ mv_cesa_set_op_cfg(&tmpl, CESA_SA_DESC_CFG_MACM_MD5);
++
++ mv_cesa_ahash_init(req, &tmpl, true);
++
+ creq->state[0] = MD5_H0;
+ creq->state[1] = MD5_H1;
+ creq->state[2] = MD5_H2;
+ creq->state[3] = MD5_H3;
+
+- mv_cesa_ahash_init(req, &tmpl, true);
+-
+ return 0;
+ }
+
+@@ -873,14 +874,15 @@ static int mv_cesa_sha1_init(struct ahash_request *req)
+ struct mv_cesa_op_ctx tmpl = { };
+
+ mv_cesa_set_op_cfg(&tmpl, CESA_SA_DESC_CFG_MACM_SHA1);
++
++ mv_cesa_ahash_init(req, &tmpl, false);
++
+ creq->state[0] = SHA1_H0;
+ creq->state[1] = SHA1_H1;
+ creq->state[2] = SHA1_H2;
+ creq->state[3] = SHA1_H3;
+ creq->state[4] = SHA1_H4;
+
+- mv_cesa_ahash_init(req, &tmpl, false);
+-
+ return 0;
+ }
+
+@@ -942,6 +944,9 @@ static int mv_cesa_sha256_init(struct ahash_request *req)
+ struct mv_cesa_op_ctx tmpl = { };
+
+ mv_cesa_set_op_cfg(&tmpl, CESA_SA_DESC_CFG_MACM_SHA256);
++
++ mv_cesa_ahash_init(req, &tmpl, false);
++
+ creq->state[0] = SHA256_H0;
+ creq->state[1] = SHA256_H1;
+ creq->state[2] = SHA256_H2;
+@@ -951,8 +956,6 @@ static int mv_cesa_sha256_init(struct ahash_request *req)
+ creq->state[6] = SHA256_H6;
+ creq->state[7] = SHA256_H7;
+
+- mv_cesa_ahash_init(req, &tmpl, false);
+-
+ return 0;
+ }
+
+diff --git a/drivers/dma/ipu/ipu_irq.c b/drivers/dma/ipu/ipu_irq.c
+index 2bf37e6..dd184b5 100644
+--- a/drivers/dma/ipu/ipu_irq.c
++++ b/drivers/dma/ipu/ipu_irq.c
+@@ -286,22 +286,21 @@ static void ipu_irq_handler(struct irq_desc *desc)
+ raw_spin_unlock(&bank_lock);
+ while ((line = ffs(status))) {
+ struct ipu_irq_map *map;
+- unsigned int irq = NO_IRQ;
++ unsigned int irq;
+
+ line--;
+ status &= ~(1UL << line);
+
+ raw_spin_lock(&bank_lock);
+ map = src2map(32 * i + line);
+- if (map)
+- irq = map->irq;
+- raw_spin_unlock(&bank_lock);
+-
+ if (!map) {
++ raw_spin_unlock(&bank_lock);
+ pr_err("IPU: Interrupt on unmapped source %u bank %d\n",
+ line, i);
+ continue;
+ }
++ irq = map->irq;
++ raw_spin_unlock(&bank_lock);
+ generic_handle_irq(irq);
+ }
+ }
+diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ctx.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ctx.c
+index 17e1362..4e71a68 100644
+--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ctx.c
++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ctx.c
+@@ -43,6 +43,9 @@ static int amdgpu_ctx_init(struct amdgpu_device *adev, struct amdgpu_ctx *ctx)
+ ctx->rings[i].sequence = 1;
+ ctx->rings[i].fences = &ctx->fences[amdgpu_sched_jobs * i];
+ }
++
++ ctx->reset_counter = atomic_read(&adev->gpu_reset_counter);
++
+ /* create context entity for each ring */
+ for (i = 0; i < adev->num_rings; i++) {
+ struct amdgpu_ring *ring = adev->rings[i];
+diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_dpm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_dpm.c
+index fe36caf..14f57d9 100644
+--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_dpm.c
++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_dpm.c
+@@ -113,24 +113,26 @@ void amdgpu_dpm_print_ps_status(struct amdgpu_device *adev,
+ printk("\n");
+ }
+
++
+ u32 amdgpu_dpm_get_vblank_time(struct amdgpu_device *adev)
+ {
+ struct drm_device *dev = adev->ddev;
+ struct drm_crtc *crtc;
+ struct amdgpu_crtc *amdgpu_crtc;
+- u32 line_time_us, vblank_lines;
++ u32 vblank_in_pixels;
+ u32 vblank_time_us = 0xffffffff; /* if the displays are off, vblank time is max */
+
+ if (adev->mode_info.num_crtc && adev->mode_info.mode_config_initialized) {
+ list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
+ amdgpu_crtc = to_amdgpu_crtc(crtc);
+ if (crtc->enabled && amdgpu_crtc->enabled && amdgpu_crtc->hw_mode.clock) {
+- line_time_us = (amdgpu_crtc->hw_mode.crtc_htotal * 1000) /
+- amdgpu_crtc->hw_mode.clock;
+- vblank_lines = amdgpu_crtc->hw_mode.crtc_vblank_end -
++ vblank_in_pixels =
++ amdgpu_crtc->hw_mode.crtc_htotal *
++ (amdgpu_crtc->hw_mode.crtc_vblank_end -
+ amdgpu_crtc->hw_mode.crtc_vdisplay +
+- (amdgpu_crtc->v_border * 2);
+- vblank_time_us = vblank_lines * line_time_us;
++ (amdgpu_crtc->v_border * 2));
++
++ vblank_time_us = vblank_in_pixels * 1000 / amdgpu_crtc->hw_mode.clock;
+ break;
+ }
+ }
+diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c
+index d942654..e24a8af 100644
+--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c
++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c
+@@ -292,7 +292,7 @@ static int amdgpu_info_ioctl(struct drm_device *dev, void *data, struct drm_file
+ type = AMD_IP_BLOCK_TYPE_UVD;
+ ring_mask = adev->uvd.ring.ready ? 1 : 0;
+ ib_start_alignment = AMDGPU_GPU_PAGE_SIZE;
+- ib_size_alignment = 8;
++ ib_size_alignment = 16;
+ break;
+ case AMDGPU_HW_IP_VCE:
+ type = AMD_IP_BLOCK_TYPE_VCE;
+diff --git a/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c b/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c
+index c1b04e9..172bed9 100644
+--- a/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c
++++ b/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c
+@@ -425,16 +425,6 @@ static void dce_v10_0_hpd_init(struct amdgpu_device *adev)
+ list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
+ struct amdgpu_connector *amdgpu_connector = to_amdgpu_connector(connector);
+
+- if (connector->connector_type == DRM_MODE_CONNECTOR_eDP ||
+- connector->connector_type == DRM_MODE_CONNECTOR_LVDS) {
+- /* don't try to enable hpd on eDP or LVDS avoid breaking the
+- * aux dp channel on imac and help (but not completely fix)
+- * https://bugzilla.redhat.com/show_bug.cgi?id=726143
+- * also avoid interrupt storms during dpms.
+- */
+- continue;
+- }
+-
+ switch (amdgpu_connector->hpd.hpd) {
+ case AMDGPU_HPD_1:
+ idx = 0;
+@@ -458,6 +448,19 @@ static void dce_v10_0_hpd_init(struct amdgpu_device *adev)
+ continue;
+ }
+
++ if (connector->connector_type == DRM_MODE_CONNECTOR_eDP ||
++ connector->connector_type == DRM_MODE_CONNECTOR_LVDS) {
++ /* don't try to enable hpd on eDP or LVDS avoid breaking the
++ * aux dp channel on imac and help (but not completely fix)
++ * https://bugzilla.redhat.com/show_bug.cgi?id=726143
++ * also avoid interrupt storms during dpms.
++ */
++ tmp = RREG32(mmDC_HPD_INT_CONTROL + hpd_offsets[idx]);
++ tmp = REG_SET_FIELD(tmp, DC_HPD_INT_CONTROL, DC_HPD_INT_EN, 0);
++ WREG32(mmDC_HPD_INT_CONTROL + hpd_offsets[idx], tmp);
++ continue;
++ }
++
+ tmp = RREG32(mmDC_HPD_CONTROL + hpd_offsets[idx]);
+ tmp = REG_SET_FIELD(tmp, DC_HPD_CONTROL, DC_HPD_EN, 1);
+ WREG32(mmDC_HPD_CONTROL + hpd_offsets[idx], tmp);
+diff --git a/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c b/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c
+index d4bf133..67c7c05 100644
+--- a/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c
++++ b/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c
+@@ -443,16 +443,6 @@ static void dce_v11_0_hpd_init(struct amdgpu_device *adev)
+ list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
+ struct amdgpu_connector *amdgpu_connector = to_amdgpu_connector(connector);
+
+- if (connector->connector_type == DRM_MODE_CONNECTOR_eDP ||
+- connector->connector_type == DRM_MODE_CONNECTOR_LVDS) {
+- /* don't try to enable hpd on eDP or LVDS avoid breaking the
+- * aux dp channel on imac and help (but not completely fix)
+- * https://bugzilla.redhat.com/show_bug.cgi?id=726143
+- * also avoid interrupt storms during dpms.
+- */
+- continue;
+- }
+-
+ switch (amdgpu_connector->hpd.hpd) {
+ case AMDGPU_HPD_1:
+ idx = 0;
+@@ -476,6 +466,19 @@ static void dce_v11_0_hpd_init(struct amdgpu_device *adev)
+ continue;
+ }
+
++ if (connector->connector_type == DRM_MODE_CONNECTOR_eDP ||
++ connector->connector_type == DRM_MODE_CONNECTOR_LVDS) {
++ /* don't try to enable hpd on eDP or LVDS avoid breaking the
++ * aux dp channel on imac and help (but not completely fix)
++ * https://bugzilla.redhat.com/show_bug.cgi?id=726143
++ * also avoid interrupt storms during dpms.
++ */
++ tmp = RREG32(mmDC_HPD_INT_CONTROL + hpd_offsets[idx]);
++ tmp = REG_SET_FIELD(tmp, DC_HPD_INT_CONTROL, DC_HPD_INT_EN, 0);
++ WREG32(mmDC_HPD_INT_CONTROL + hpd_offsets[idx], tmp);
++ continue;
++ }
++
+ tmp = RREG32(mmDC_HPD_CONTROL + hpd_offsets[idx]);
+ tmp = REG_SET_FIELD(tmp, DC_HPD_CONTROL, DC_HPD_EN, 1);
+ WREG32(mmDC_HPD_CONTROL + hpd_offsets[idx], tmp);
+@@ -3109,6 +3112,7 @@ static int dce_v11_0_sw_fini(void *handle)
+
+ dce_v11_0_afmt_fini(adev);
+
++ drm_mode_config_cleanup(adev->ddev);
+ adev->mode_info.mode_config_initialized = false;
+
+ return 0;
+diff --git a/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c b/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c
+index 4fdfab1..ea07c50 100644
+--- a/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c
++++ b/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c
+@@ -395,15 +395,6 @@ static void dce_v8_0_hpd_init(struct amdgpu_device *adev)
+ list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
+ struct amdgpu_connector *amdgpu_connector = to_amdgpu_connector(connector);
+
+- if (connector->connector_type == DRM_MODE_CONNECTOR_eDP ||
+- connector->connector_type == DRM_MODE_CONNECTOR_LVDS) {
+- /* don't try to enable hpd on eDP or LVDS avoid breaking the
+- * aux dp channel on imac and help (but not completely fix)
+- * https://bugzilla.redhat.com/show_bug.cgi?id=726143
+- * also avoid interrupt storms during dpms.
+- */
+- continue;
+- }
+ switch (amdgpu_connector->hpd.hpd) {
+ case AMDGPU_HPD_1:
+ WREG32(mmDC_HPD1_CONTROL, tmp);
+@@ -426,6 +417,45 @@ static void dce_v8_0_hpd_init(struct amdgpu_device *adev)
+ default:
+ break;
+ }
++
++ if (connector->connector_type == DRM_MODE_CONNECTOR_eDP ||
++ connector->connector_type == DRM_MODE_CONNECTOR_LVDS) {
++ /* don't try to enable hpd on eDP or LVDS avoid breaking the
++ * aux dp channel on imac and help (but not completely fix)
++ * https://bugzilla.redhat.com/show_bug.cgi?id=726143
++ * also avoid interrupt storms during dpms.
++ */
++ u32 dc_hpd_int_cntl_reg, dc_hpd_int_cntl;
++
++ switch (amdgpu_connector->hpd.hpd) {
++ case AMDGPU_HPD_1:
++ dc_hpd_int_cntl_reg = mmDC_HPD1_INT_CONTROL;
++ break;
++ case AMDGPU_HPD_2:
++ dc_hpd_int_cntl_reg = mmDC_HPD2_INT_CONTROL;
++ break;
++ case AMDGPU_HPD_3:
++ dc_hpd_int_cntl_reg = mmDC_HPD3_INT_CONTROL;
++ break;
++ case AMDGPU_HPD_4:
++ dc_hpd_int_cntl_reg = mmDC_HPD4_INT_CONTROL;
++ break;
++ case AMDGPU_HPD_5:
++ dc_hpd_int_cntl_reg = mmDC_HPD5_INT_CONTROL;
++ break;
++ case AMDGPU_HPD_6:
++ dc_hpd_int_cntl_reg = mmDC_HPD6_INT_CONTROL;
++ break;
++ default:
++ continue;
++ }
++
++ dc_hpd_int_cntl = RREG32(dc_hpd_int_cntl_reg);
++ dc_hpd_int_cntl &= ~DC_HPD1_INT_CONTROL__DC_HPD1_INT_EN_MASK;
++ WREG32(dc_hpd_int_cntl_reg, dc_hpd_int_cntl);
++ continue;
++ }
++
+ dce_v8_0_hpd_set_polarity(adev, amdgpu_connector->hpd.hpd);
+ amdgpu_irq_get(adev, &adev->hpd_irq, amdgpu_connector->hpd.hpd);
+ }
+diff --git a/drivers/gpu/drm/amd/powerplay/eventmgr/eventactionchains.c b/drivers/gpu/drm/amd/powerplay/eventmgr/eventactionchains.c
+index 635fc4b..92b1178 100644
+--- a/drivers/gpu/drm/amd/powerplay/eventmgr/eventactionchains.c
++++ b/drivers/gpu/drm/amd/powerplay/eventmgr/eventactionchains.c
+@@ -262,6 +262,8 @@ static const pem_event_action * const display_config_change_event[] = {
+ unblock_adjust_power_state_tasks,
+ set_cpu_power_state,
+ notify_hw_power_source_tasks,
++ get_2d_performance_state_tasks,
++ set_performance_state_tasks,
+ /* updateDALConfigurationTasks,
+ variBrightDisplayConfigurationChangeTasks, */
+ adjust_power_state_tasks,
+diff --git a/drivers/gpu/drm/amd/powerplay/eventmgr/psm.c b/drivers/gpu/drm/amd/powerplay/eventmgr/psm.c
+index a46225c..d6bee72 100644
+--- a/drivers/gpu/drm/amd/powerplay/eventmgr/psm.c
++++ b/drivers/gpu/drm/amd/powerplay/eventmgr/psm.c
+@@ -100,11 +100,12 @@ int psm_adjust_power_state_dynamic(struct pp_eventmgr *eventmgr, bool skip)
+ if (requested == NULL)
+ return 0;
+
++ phm_apply_state_adjust_rules(hwmgr, requested, pcurrent);
++
+ if (pcurrent == NULL || (0 != phm_check_states_equal(hwmgr, &pcurrent->hardware, &requested->hardware, &equal)))
+ equal = false;
+
+ if (!equal || phm_check_smc_update_required_for_display_configuration(hwmgr)) {
+- phm_apply_state_adjust_rules(hwmgr, requested, pcurrent);
+ phm_set_power_state(hwmgr, &pcurrent->hardware, &requested->hardware);
+ hwmgr->current_ps = requested;
+ }
+diff --git a/drivers/gpu/drm/drm_prime.c b/drivers/gpu/drm/drm_prime.c
+index 780589b..9c4387d 100644
+--- a/drivers/gpu/drm/drm_prime.c
++++ b/drivers/gpu/drm/drm_prime.c
+@@ -335,14 +335,17 @@ static const struct dma_buf_ops drm_gem_prime_dmabuf_ops = {
+ * using the PRIME helpers.
+ */
+ struct dma_buf *drm_gem_prime_export(struct drm_device *dev,
+- struct drm_gem_object *obj, int flags)
++ struct drm_gem_object *obj,
++ int flags)
+ {
+- DEFINE_DMA_BUF_EXPORT_INFO(exp_info);
+-
+- exp_info.ops = &drm_gem_prime_dmabuf_ops;
+- exp_info.size = obj->size;
+- exp_info.flags = flags;
+- exp_info.priv = obj;
++ struct dma_buf_export_info exp_info = {
++ .exp_name = KBUILD_MODNAME, /* white lie for debug */
++ .owner = dev->driver->fops->owner,
++ .ops = &drm_gem_prime_dmabuf_ops,
++ .size = obj->size,
++ .flags = flags,
++ .priv = obj,
++ };
+
+ if (dev->driver->gem_prime_res_obj)
+ exp_info.resv = dev->driver->gem_prime_res_obj(obj);
+diff --git a/drivers/gpu/drm/fsl-dcu/fsl_dcu_drm_drv.c b/drivers/gpu/drm/fsl-dcu/fsl_dcu_drm_drv.c
+index 7882387..5fc8ebd 100644
+--- a/drivers/gpu/drm/fsl-dcu/fsl_dcu_drm_drv.c
++++ b/drivers/gpu/drm/fsl-dcu/fsl_dcu_drm_drv.c
+@@ -330,6 +330,7 @@ static int fsl_dcu_drm_probe(struct platform_device *pdev)
+ const char *pix_clk_in_name;
+ const struct of_device_id *id;
+ int ret;
++ u8 div_ratio_shift = 0;
+
+ fsl_dev = devm_kzalloc(dev, sizeof(*fsl_dev), GFP_KERNEL);
+ if (!fsl_dev)
+@@ -382,11 +383,14 @@ static int fsl_dcu_drm_probe(struct platform_device *pdev)
+ pix_clk_in = fsl_dev->clk;
+ }
+
++ if (of_property_read_bool(dev->of_node, "big-endian"))
++ div_ratio_shift = 24;
++
+ pix_clk_in_name = __clk_get_name(pix_clk_in);
+ snprintf(pix_clk_name, sizeof(pix_clk_name), "%s_pix", pix_clk_in_name);
+ fsl_dev->pix_clk = clk_register_divider(dev, pix_clk_name,
+ pix_clk_in_name, 0, base + DCU_DIV_RATIO,
+- 0, 8, CLK_DIVIDER_ROUND_CLOSEST, NULL);
++ div_ratio_shift, 8, CLK_DIVIDER_ROUND_CLOSEST, NULL);
+ if (IS_ERR(fsl_dev->pix_clk)) {
+ dev_err(dev, "failed to register pix clk\n");
+ ret = PTR_ERR(fsl_dev->pix_clk);
+diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h
+index f68c789..84a0010 100644
+--- a/drivers/gpu/drm/i915/i915_drv.h
++++ b/drivers/gpu/drm/i915/i915_drv.h
+@@ -631,6 +631,8 @@ struct drm_i915_display_funcs {
+ struct intel_crtc_state *crtc_state);
+ void (*crtc_enable)(struct drm_crtc *crtc);
+ void (*crtc_disable)(struct drm_crtc *crtc);
++ void (*update_crtcs)(struct drm_atomic_state *state,
++ unsigned int *crtc_vblank_mask);
+ void (*audio_codec_enable)(struct drm_connector *connector,
+ struct intel_encoder *encoder,
+ const struct drm_display_mode *adjusted_mode);
+@@ -1965,11 +1967,11 @@ struct drm_i915_private {
+ struct vlv_s0ix_state vlv_s0ix_state;
+
+ enum {
+- I915_SKL_SAGV_UNKNOWN = 0,
+- I915_SKL_SAGV_DISABLED,
+- I915_SKL_SAGV_ENABLED,
+- I915_SKL_SAGV_NOT_CONTROLLED
+- } skl_sagv_status;
++ I915_SAGV_UNKNOWN = 0,
++ I915_SAGV_DISABLED,
++ I915_SAGV_ENABLED,
++ I915_SAGV_NOT_CONTROLLED
++ } sagv_status;
+
+ struct {
+ /*
+@@ -2280,21 +2282,19 @@ struct drm_i915_gem_object {
+ /** Record of address bit 17 of each page at last unbind. */
+ unsigned long *bit_17;
+
+- union {
+- /** for phy allocated objects */
+- struct drm_dma_handle *phys_handle;
+-
+- struct i915_gem_userptr {
+- uintptr_t ptr;
+- unsigned read_only :1;
+- unsigned workers :4;
++ struct i915_gem_userptr {
++ uintptr_t ptr;
++ unsigned read_only :1;
++ unsigned workers :4;
+ #define I915_GEM_USERPTR_MAX_WORKERS 15
+
+- struct i915_mm_struct *mm;
+- struct i915_mmu_object *mmu_object;
+- struct work_struct *work;
+- } userptr;
+- };
++ struct i915_mm_struct *mm;
++ struct i915_mmu_object *mmu_object;
++ struct work_struct *work;
++ } userptr;
++
++ /** for phys allocated objects */
++ struct drm_dma_handle *phys_handle;
+ };
+ #define to_intel_bo(x) container_of(x, struct drm_i915_gem_object, base)
+
+diff --git a/drivers/gpu/drm/i915/i915_gem_stolen.c b/drivers/gpu/drm/i915/i915_gem_stolen.c
+index 66be299a1..2bb69f3 100644
+--- a/drivers/gpu/drm/i915/i915_gem_stolen.c
++++ b/drivers/gpu/drm/i915/i915_gem_stolen.c
+@@ -115,17 +115,28 @@ static unsigned long i915_stolen_to_physical(struct drm_device *dev)
+
+ base = bsm & INTEL_BSM_MASK;
+ } else if (IS_I865G(dev)) {
++ u32 tseg_size = 0;
+ u16 toud = 0;
++ u8 tmp;
++
++ pci_bus_read_config_byte(dev->pdev->bus, PCI_DEVFN(0, 0),
++ I845_ESMRAMC, &tmp);
++
++ if (tmp & TSEG_ENABLE) {
++ switch (tmp & I845_TSEG_SIZE_MASK) {
++ case I845_TSEG_SIZE_512K:
++ tseg_size = KB(512);
++ break;
++ case I845_TSEG_SIZE_1M:
++ tseg_size = MB(1);
++ break;
++ }
++ }
+
+- /*
+- * FIXME is the graphics stolen memory region
+- * always at TOUD? Ie. is it always the last
+- * one to be allocated by the BIOS?
+- */
+ pci_bus_read_config_word(dev->pdev->bus, PCI_DEVFN(0, 0),
+ I865_TOUD, &toud);
+
+- base = toud << 16;
++ base = (toud << 16) + tseg_size;
+ } else if (IS_I85X(dev)) {
+ u32 tseg_size = 0;
+ u32 tom;
+diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c
+index 175595f..e9a64fb 100644
+--- a/drivers/gpu/drm/i915/intel_display.c
++++ b/drivers/gpu/drm/i915/intel_display.c
+@@ -2980,6 +2980,7 @@ static void skylake_update_primary_plane(struct drm_plane *plane,
+ struct intel_crtc *intel_crtc = to_intel_crtc(crtc_state->base.crtc);
+ struct drm_framebuffer *fb = plane_state->base.fb;
+ struct drm_i915_gem_object *obj = intel_fb_obj(fb);
++ const struct skl_wm_values *wm = &dev_priv->wm.skl_results;
+ int pipe = intel_crtc->pipe;
+ u32 plane_ctl, stride_div, stride;
+ u32 tile_height, plane_offset, plane_size;
+@@ -3031,6 +3032,9 @@ static void skylake_update_primary_plane(struct drm_plane *plane,
+ intel_crtc->adjusted_x = x_offset;
+ intel_crtc->adjusted_y = y_offset;
+
++ if (wm->dirty_pipes & drm_crtc_mask(&intel_crtc->base))
++ skl_write_plane_wm(intel_crtc, wm, 0);
++
+ I915_WRITE(PLANE_CTL(pipe, 0), plane_ctl);
+ I915_WRITE(PLANE_OFFSET(pipe, 0), plane_offset);
+ I915_WRITE(PLANE_SIZE(pipe, 0), plane_size);
+@@ -3061,7 +3065,15 @@ static void skylake_disable_primary_plane(struct drm_plane *primary,
+ {
+ struct drm_device *dev = crtc->dev;
+ struct drm_i915_private *dev_priv = to_i915(dev);
+- int pipe = to_intel_crtc(crtc)->pipe;
++ struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
++ int pipe = intel_crtc->pipe;
++
++ /*
++ * We only populate skl_results on watermark updates, and if the
++ * plane's visiblity isn't actually changing neither is its watermarks.
++ */
++ if (!to_intel_plane_state(crtc->primary->state)->visible)
++ skl_write_plane_wm(intel_crtc, &dev_priv->wm.skl_results, 0);
+
+ I915_WRITE(PLANE_CTL(pipe, 0), 0);
+ I915_WRITE(PLANE_SURF(pipe, 0), 0);
+@@ -8995,6 +9007,24 @@ static void ironlake_compute_dpll(struct intel_crtc *intel_crtc,
+ if (intel_crtc_has_dp_encoder(crtc_state))
+ dpll |= DPLL_SDVO_HIGH_SPEED;
+
++ /*
++ * The high speed IO clock is only really required for
++ * SDVO/HDMI/DP, but we also enable it for CRT to make it
++ * possible to share the DPLL between CRT and HDMI. Enabling
++ * the clock needlessly does no real harm, except use up a
++ * bit of power potentially.
++ *
++ * We'll limit this to IVB with 3 pipes, since it has only two
++ * DPLLs and so DPLL sharing is the only way to get three pipes
++ * driving PCH ports at the same time. On SNB we could do this,
++ * and potentially avoid enabling the second DPLL, but it's not
++ * clear if it''s a win or loss power wise. No point in doing
++ * this on ILK at all since it has a fixed DPLL<->pipe mapping.
++ */
++ if (INTEL_INFO(dev_priv)->num_pipes == 3 &&
++ intel_crtc_has_type(crtc_state, INTEL_OUTPUT_ANALOG))
++ dpll |= DPLL_SDVO_HIGH_SPEED;
++
+ /* compute bitmask from p1 value */
+ dpll |= (1 << (crtc_state->dpll.p1 - 1)) << DPLL_FPA01_P1_POST_DIV_SHIFT;
+ /* also FPA1 */
+@@ -10306,9 +10336,13 @@ static void i9xx_update_cursor(struct drm_crtc *crtc, u32 base,
+ struct drm_device *dev = crtc->dev;
+ struct drm_i915_private *dev_priv = to_i915(dev);
+ struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
++ const struct skl_wm_values *wm = &dev_priv->wm.skl_results;
+ int pipe = intel_crtc->pipe;
+ uint32_t cntl = 0;
+
++ if (INTEL_GEN(dev_priv) >= 9 && wm->dirty_pipes & drm_crtc_mask(crtc))
++ skl_write_cursor_wm(intel_crtc, wm);
++
+ if (plane_state && plane_state->visible) {
+ cntl = MCURSOR_GAMMA_ENABLE;
+ switch (plane_state->base.crtc_w) {
+@@ -12956,16 +12990,23 @@ static void verify_wm_state(struct drm_crtc *crtc,
+ hw_entry->start, hw_entry->end);
+ }
+
+- /* cursor */
+- hw_entry = &hw_ddb.plane[pipe][PLANE_CURSOR];
+- sw_entry = &sw_ddb->plane[pipe][PLANE_CURSOR];
+-
+- if (!skl_ddb_entry_equal(hw_entry, sw_entry)) {
+- DRM_ERROR("mismatch in DDB state pipe %c cursor "
+- "(expected (%u,%u), found (%u,%u))\n",
+- pipe_name(pipe),
+- sw_entry->start, sw_entry->end,
+- hw_entry->start, hw_entry->end);
++ /*
++ * cursor
++ * If the cursor plane isn't active, we may not have updated it's ddb
++ * allocation. In that case since the ddb allocation will be updated
++ * once the plane becomes visible, we can skip this check
++ */
++ if (intel_crtc->cursor_addr) {
++ hw_entry = &hw_ddb.plane[pipe][PLANE_CURSOR];
++ sw_entry = &sw_ddb->plane[pipe][PLANE_CURSOR];
++
++ if (!skl_ddb_entry_equal(hw_entry, sw_entry)) {
++ DRM_ERROR("mismatch in DDB state pipe %c cursor "
++ "(expected (%u,%u), found (%u,%u))\n",
++ pipe_name(pipe),
++ sw_entry->start, sw_entry->end,
++ hw_entry->start, hw_entry->end);
++ }
+ }
+ }
+
+@@ -13671,6 +13712,111 @@ static bool needs_vblank_wait(struct intel_crtc_state *crtc_state)
+ return false;
+ }
+
++static void intel_update_crtc(struct drm_crtc *crtc,
++ struct drm_atomic_state *state,
++ struct drm_crtc_state *old_crtc_state,
++ unsigned int *crtc_vblank_mask)
++{
++ struct drm_device *dev = crtc->dev;
++ struct drm_i915_private *dev_priv = to_i915(dev);
++ struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
++ struct intel_crtc_state *pipe_config = to_intel_crtc_state(crtc->state);
++ bool modeset = needs_modeset(crtc->state);
++
++ if (modeset) {
++ update_scanline_offset(intel_crtc);
++ dev_priv->display.crtc_enable(crtc);
++ } else {
++ intel_pre_plane_update(to_intel_crtc_state(old_crtc_state));
++ }
++
++ if (drm_atomic_get_existing_plane_state(state, crtc->primary)) {
++ intel_fbc_enable(
++ intel_crtc, pipe_config,
++ to_intel_plane_state(crtc->primary->state));
++ }
++
++ drm_atomic_helper_commit_planes_on_crtc(old_crtc_state);
++
++ if (needs_vblank_wait(pipe_config))
++ *crtc_vblank_mask |= drm_crtc_mask(crtc);
++}
++
++static void intel_update_crtcs(struct drm_atomic_state *state,
++ unsigned int *crtc_vblank_mask)
++{
++ struct drm_crtc *crtc;
++ struct drm_crtc_state *old_crtc_state;
++ int i;
++
++ for_each_crtc_in_state(state, crtc, old_crtc_state, i) {
++ if (!crtc->state->active)
++ continue;
++
++ intel_update_crtc(crtc, state, old_crtc_state,
++ crtc_vblank_mask);
++ }
++}
++
++static void skl_update_crtcs(struct drm_atomic_state *state,
++ unsigned int *crtc_vblank_mask)
++{
++ struct drm_device *dev = state->dev;
++ struct drm_i915_private *dev_priv = to_i915(dev);
++ struct intel_atomic_state *intel_state = to_intel_atomic_state(state);
++ struct drm_crtc *crtc;
++ struct drm_crtc_state *old_crtc_state;
++ struct skl_ddb_allocation *new_ddb = &intel_state->wm_results.ddb;
++ struct skl_ddb_allocation *cur_ddb = &dev_priv->wm.skl_hw.ddb;
++ unsigned int updated = 0;
++ bool progress;
++ enum pipe pipe;
++
++ /*
++ * Whenever the number of active pipes changes, we need to make sure we
++ * update the pipes in the right order so that their ddb allocations
++ * never overlap with eachother inbetween CRTC updates. Otherwise we'll
++ * cause pipe underruns and other bad stuff.
++ */
++ do {
++ int i;
++ progress = false;
++
++ for_each_crtc_in_state(state, crtc, old_crtc_state, i) {
++ bool vbl_wait = false;
++ unsigned int cmask = drm_crtc_mask(crtc);
++ pipe = to_intel_crtc(crtc)->pipe;
++
++ if (updated & cmask || !crtc->state->active)
++ continue;
++ if (skl_ddb_allocation_overlaps(state, cur_ddb, new_ddb,
++ pipe))
++ continue;
++
++ updated |= cmask;
++
++ /*
++ * If this is an already active pipe, it's DDB changed,
++ * and this isn't the last pipe that needs updating
++ * then we need to wait for a vblank to pass for the
++ * new ddb allocation to take effect.
++ */
++ if (!skl_ddb_allocation_equals(cur_ddb, new_ddb, pipe) &&
++ !crtc->state->active_changed &&
++ intel_state->wm_results.dirty_pipes != updated)
++ vbl_wait = true;
++
++ intel_update_crtc(crtc, state, old_crtc_state,
++ crtc_vblank_mask);
++
++ if (vbl_wait)
++ intel_wait_for_vblank(dev, pipe);
++
++ progress = true;
++ }
++ } while (progress);
++}
++
+ static void intel_atomic_commit_tail(struct drm_atomic_state *state)
+ {
+ struct drm_device *dev = state->dev;
+@@ -13763,23 +13909,15 @@ static void intel_atomic_commit_tail(struct drm_atomic_state *state)
+ * SKL workaround: bspec recommends we disable the SAGV when we
+ * have more then one pipe enabled
+ */
+- if (IS_SKYLAKE(dev_priv) && !skl_can_enable_sagv(state))
+- skl_disable_sagv(dev_priv);
++ if (!intel_can_enable_sagv(state))
++ intel_disable_sagv(dev_priv);
+
+ intel_modeset_verify_disabled(dev);
+ }
+
+- /* Now enable the clocks, plane, pipe, and connectors that we set up. */
++ /* Complete the events for pipes that have now been disabled */
+ for_each_crtc_in_state(state, crtc, old_crtc_state, i) {
+- struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
+ bool modeset = needs_modeset(crtc->state);
+- struct intel_crtc_state *pipe_config =
+- to_intel_crtc_state(crtc->state);
+-
+- if (modeset && crtc->state->active) {
+- update_scanline_offset(to_intel_crtc(crtc));
+- dev_priv->display.crtc_enable(crtc);
+- }
+
+ /* Complete events for now disable pipes here. */
+ if (modeset && !crtc->state->active && crtc->state->event) {
+@@ -13789,21 +13927,11 @@ static void intel_atomic_commit_tail(struct drm_atomic_state *state)
+
+ crtc->state->event = NULL;
+ }
+-
+- if (!modeset)
+- intel_pre_plane_update(to_intel_crtc_state(old_crtc_state));
+-
+- if (crtc->state->active &&
+- drm_atomic_get_existing_plane_state(state, crtc->primary))
+- intel_fbc_enable(intel_crtc, pipe_config, to_intel_plane_state(crtc->primary->state));
+-
+- if (crtc->state->active)
+- drm_atomic_helper_commit_planes_on_crtc(old_crtc_state);
+-
+- if (pipe_config->base.active && needs_vblank_wait(pipe_config))
+- crtc_vblank_mask |= 1 << i;
+ }
+
++ /* Now enable the clocks, plane, pipe, and connectors that we set up. */
++ dev_priv->display.update_crtcs(state, &crtc_vblank_mask);
++
+ /* FIXME: We should call drm_atomic_helper_commit_hw_done() here
+ * already, but still need the state for the delayed optimization. To
+ * fix this:
+@@ -13839,9 +13967,8 @@ static void intel_atomic_commit_tail(struct drm_atomic_state *state)
+ intel_modeset_verify_crtc(crtc, old_crtc_state, crtc->state);
+ }
+
+- if (IS_SKYLAKE(dev_priv) && intel_state->modeset &&
+- skl_can_enable_sagv(state))
+- skl_enable_sagv(dev_priv);
++ if (intel_state->modeset && intel_can_enable_sagv(state))
++ intel_enable_sagv(dev_priv);
+
+ drm_atomic_helper_commit_hw_done(state);
+
+@@ -14221,10 +14348,12 @@ static void intel_begin_crtc_commit(struct drm_crtc *crtc,
+ struct drm_crtc_state *old_crtc_state)
+ {
+ struct drm_device *dev = crtc->dev;
++ struct drm_i915_private *dev_priv = to_i915(dev);
+ struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
+ struct intel_crtc_state *old_intel_state =
+ to_intel_crtc_state(old_crtc_state);
+ bool modeset = needs_modeset(crtc->state);
++ enum pipe pipe = intel_crtc->pipe;
+
+ /* Perform vblank evasion around commit operation */
+ intel_pipe_update_start(intel_crtc);
+@@ -14239,8 +14368,12 @@ static void intel_begin_crtc_commit(struct drm_crtc *crtc,
+
+ if (to_intel_crtc_state(crtc->state)->update_pipe)
+ intel_update_pipe_config(intel_crtc, old_intel_state);
+- else if (INTEL_INFO(dev)->gen >= 9)
++ else if (INTEL_GEN(dev_priv) >= 9) {
+ skl_detach_scalers(intel_crtc);
++
++ I915_WRITE(PIPE_WM_LINETIME(pipe),
++ dev_priv->wm.skl_hw.wm_linetime[pipe]);
++ }
+ }
+
+ static void intel_finish_crtc_commit(struct drm_crtc *crtc,
+@@ -15347,6 +15480,11 @@ void intel_init_display_hooks(struct drm_i915_private *dev_priv)
+ skl_modeset_calc_cdclk;
+ }
+
++ if (dev_priv->info.gen >= 9)
++ dev_priv->display.update_crtcs = skl_update_crtcs;
++ else
++ dev_priv->display.update_crtcs = intel_update_crtcs;
++
+ switch (INTEL_INFO(dev_priv)->gen) {
+ case 2:
+ dev_priv->display.queue_flip = intel_gen2_queue_flip;
+diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c
+index 21b04c3..1ca155f 100644
+--- a/drivers/gpu/drm/i915/intel_dp.c
++++ b/drivers/gpu/drm/i915/intel_dp.c
+@@ -4148,7 +4148,7 @@ static bool bxt_digital_port_connected(struct drm_i915_private *dev_priv,
+ *
+ * Return %true if @port is connected, %false otherwise.
+ */
+-bool intel_digital_port_connected(struct drm_i915_private *dev_priv,
++static bool intel_digital_port_connected(struct drm_i915_private *dev_priv,
+ struct intel_digital_port *port)
+ {
+ if (HAS_PCH_IBX(dev_priv))
+@@ -4207,7 +4207,7 @@ intel_dp_unset_edid(struct intel_dp *intel_dp)
+ intel_dp->has_audio = false;
+ }
+
+-static void
++static enum drm_connector_status
+ intel_dp_long_pulse(struct intel_connector *intel_connector)
+ {
+ struct drm_connector *connector = &intel_connector->base;
+@@ -4232,7 +4232,7 @@ intel_dp_long_pulse(struct intel_connector *intel_connector)
+ else
+ status = connector_status_disconnected;
+
+- if (status != connector_status_connected) {
++ if (status == connector_status_disconnected) {
+ intel_dp->compliance_test_active = 0;
+ intel_dp->compliance_test_type = 0;
+ intel_dp->compliance_test_data = 0;
+@@ -4284,8 +4284,8 @@ intel_dp_long_pulse(struct intel_connector *intel_connector)
+ intel_dp->aux.i2c_defer_count = 0;
+
+ intel_dp_set_edid(intel_dp);
+-
+- status = connector_status_connected;
++ if (is_edp(intel_dp) || intel_connector->detect_edid)
++ status = connector_status_connected;
+ intel_dp->detect_done = true;
+
+ /* Try to read the source of the interrupt */
+@@ -4303,12 +4303,11 @@ intel_dp_long_pulse(struct intel_connector *intel_connector)
+ }
+
+ out:
+- if ((status != connector_status_connected) &&
+- (intel_dp->is_mst == false))
++ if (status != connector_status_connected && !intel_dp->is_mst)
+ intel_dp_unset_edid(intel_dp);
+
+ intel_display_power_put(to_i915(dev), power_domain);
+- return;
++ return status;
+ }
+
+ static enum drm_connector_status
+@@ -4317,7 +4316,7 @@ intel_dp_detect(struct drm_connector *connector, bool force)
+ struct intel_dp *intel_dp = intel_attached_dp(connector);
+ struct intel_digital_port *intel_dig_port = dp_to_dig_port(intel_dp);
+ struct intel_encoder *intel_encoder = &intel_dig_port->base;
+- struct intel_connector *intel_connector = to_intel_connector(connector);
++ enum drm_connector_status status = connector->status;
+
+ DRM_DEBUG_KMS("[CONNECTOR:%d:%s]\n",
+ connector->base.id, connector->name);
+@@ -4332,14 +4331,11 @@ intel_dp_detect(struct drm_connector *connector, bool force)
+
+ /* If full detect is not performed yet, do a full detect */
+ if (!intel_dp->detect_done)
+- intel_dp_long_pulse(intel_dp->attached_connector);
++ status = intel_dp_long_pulse(intel_dp->attached_connector);
+
+ intel_dp->detect_done = false;
+
+- if (is_edp(intel_dp) || intel_connector->detect_edid)
+- return connector_status_connected;
+- else
+- return connector_status_disconnected;
++ return status;
+ }
+
+ static void
+@@ -4696,36 +4692,34 @@ intel_dp_hpd_pulse(struct intel_digital_port *intel_dig_port, bool long_hpd)
+ port_name(intel_dig_port->port),
+ long_hpd ? "long" : "short");
+
++ if (long_hpd) {
++ intel_dp->detect_done = false;
++ return IRQ_NONE;
++ }
++
+ power_domain = intel_display_port_aux_power_domain(intel_encoder);
+ intel_display_power_get(dev_priv, power_domain);
+
+- if (long_hpd) {
+- intel_dp_long_pulse(intel_dp->attached_connector);
+- if (intel_dp->is_mst)
+- ret = IRQ_HANDLED;
+- goto put_power;
+-
+- } else {
+- if (intel_dp->is_mst) {
+- if (intel_dp_check_mst_status(intel_dp) == -EINVAL) {
+- /*
+- * If we were in MST mode, and device is not
+- * there, get out of MST mode
+- */
+- DRM_DEBUG_KMS("MST device may have disappeared %d vs %d\n",
+- intel_dp->is_mst, intel_dp->mst_mgr.mst_state);
+- intel_dp->is_mst = false;
+- drm_dp_mst_topology_mgr_set_mst(&intel_dp->mst_mgr,
+- intel_dp->is_mst);
+- goto put_power;
+- }
++ if (intel_dp->is_mst) {
++ if (intel_dp_check_mst_status(intel_dp) == -EINVAL) {
++ /*
++ * If we were in MST mode, and device is not
++ * there, get out of MST mode
++ */
++ DRM_DEBUG_KMS("MST device may have disappeared %d vs %d\n",
++ intel_dp->is_mst, intel_dp->mst_mgr.mst_state);
++ intel_dp->is_mst = false;
++ drm_dp_mst_topology_mgr_set_mst(&intel_dp->mst_mgr,
++ intel_dp->is_mst);
++ intel_dp->detect_done = false;
++ goto put_power;
+ }
++ }
+
+- if (!intel_dp->is_mst) {
+- if (!intel_dp_short_pulse(intel_dp)) {
+- intel_dp_long_pulse(intel_dp->attached_connector);
+- goto put_power;
+- }
++ if (!intel_dp->is_mst) {
++ if (!intel_dp_short_pulse(intel_dp)) {
++ intel_dp->detect_done = false;
++ goto put_power;
+ }
+ }
+
+diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h
+index ff399b9..9a58800 100644
+--- a/drivers/gpu/drm/i915/intel_drv.h
++++ b/drivers/gpu/drm/i915/intel_drv.h
+@@ -236,6 +236,7 @@ struct intel_panel {
+ bool enabled;
+ bool combination_mode; /* gen 2/4 only */
+ bool active_low_pwm;
++ bool alternate_pwm_increment; /* lpt+ */
+
+ /* PWM chip */
+ bool util_pin_active_low; /* bxt+ */
+@@ -1387,8 +1388,6 @@ void intel_edp_drrs_disable(struct intel_dp *intel_dp);
+ void intel_edp_drrs_invalidate(struct drm_device *dev,
+ unsigned frontbuffer_bits);
+ void intel_edp_drrs_flush(struct drm_device *dev, unsigned frontbuffer_bits);
+-bool intel_digital_port_connected(struct drm_i915_private *dev_priv,
+- struct intel_digital_port *port);
+
+ void
+ intel_dp_program_link_training_pattern(struct intel_dp *intel_dp,
+@@ -1716,9 +1715,21 @@ void ilk_wm_get_hw_state(struct drm_device *dev);
+ void skl_wm_get_hw_state(struct drm_device *dev);
+ void skl_ddb_get_hw_state(struct drm_i915_private *dev_priv,
+ struct skl_ddb_allocation *ddb /* out */);
+-bool skl_can_enable_sagv(struct drm_atomic_state *state);
+-int skl_enable_sagv(struct drm_i915_private *dev_priv);
+-int skl_disable_sagv(struct drm_i915_private *dev_priv);
++bool intel_can_enable_sagv(struct drm_atomic_state *state);
++int intel_enable_sagv(struct drm_i915_private *dev_priv);
++int intel_disable_sagv(struct drm_i915_private *dev_priv);
++bool skl_ddb_allocation_equals(const struct skl_ddb_allocation *old,
++ const struct skl_ddb_allocation *new,
++ enum pipe pipe);
++bool skl_ddb_allocation_overlaps(struct drm_atomic_state *state,
++ const struct skl_ddb_allocation *old,
++ const struct skl_ddb_allocation *new,
++ enum pipe pipe);
++void skl_write_cursor_wm(struct intel_crtc *intel_crtc,
++ const struct skl_wm_values *wm);
++void skl_write_plane_wm(struct intel_crtc *intel_crtc,
++ const struct skl_wm_values *wm,
++ int plane);
+ uint32_t ilk_pipe_pixel_rate(const struct intel_crtc_state *pipe_config);
+ bool ilk_disable_lp_wm(struct drm_device *dev);
+ int sanitize_rc6_option(struct drm_i915_private *dev_priv, int enable_rc6);
+diff --git a/drivers/gpu/drm/i915/intel_hdmi.c b/drivers/gpu/drm/i915/intel_hdmi.c
+index 4df9f38..c3aa9e6 100644
+--- a/drivers/gpu/drm/i915/intel_hdmi.c
++++ b/drivers/gpu/drm/i915/intel_hdmi.c
+@@ -1422,24 +1422,22 @@ intel_hdmi_dp_dual_mode_detect(struct drm_connector *connector, bool has_edid)
+ }
+
+ static bool
+-intel_hdmi_set_edid(struct drm_connector *connector, bool force)
++intel_hdmi_set_edid(struct drm_connector *connector)
+ {
+ struct drm_i915_private *dev_priv = to_i915(connector->dev);
+ struct intel_hdmi *intel_hdmi = intel_attached_hdmi(connector);
+- struct edid *edid = NULL;
++ struct edid *edid;
+ bool connected = false;
+
+- if (force) {
+- intel_display_power_get(dev_priv, POWER_DOMAIN_GMBUS);
++ intel_display_power_get(dev_priv, POWER_DOMAIN_GMBUS);
+
+- edid = drm_get_edid(connector,
+- intel_gmbus_get_adapter(dev_priv,
+- intel_hdmi->ddc_bus));
++ edid = drm_get_edid(connector,
++ intel_gmbus_get_adapter(dev_priv,
++ intel_hdmi->ddc_bus));
+
+- intel_hdmi_dp_dual_mode_detect(connector, edid != NULL);
++ intel_hdmi_dp_dual_mode_detect(connector, edid != NULL);
+
+- intel_display_power_put(dev_priv, POWER_DOMAIN_GMBUS);
+- }
++ intel_display_power_put(dev_priv, POWER_DOMAIN_GMBUS);
+
+ to_intel_connector(connector)->detect_edid = edid;
+ if (edid && edid->input & DRM_EDID_INPUT_DIGITAL) {
+@@ -1465,37 +1463,16 @@ static enum drm_connector_status
+ intel_hdmi_detect(struct drm_connector *connector, bool force)
+ {
+ enum drm_connector_status status;
+- struct intel_hdmi *intel_hdmi = intel_attached_hdmi(connector);
+ struct drm_i915_private *dev_priv = to_i915(connector->dev);
+- bool live_status = false;
+- unsigned int try;
+
+ DRM_DEBUG_KMS("[CONNECTOR:%d:%s]\n",
+ connector->base.id, connector->name);
+
+ intel_display_power_get(dev_priv, POWER_DOMAIN_GMBUS);
+
+- for (try = 0; !live_status && try < 9; try++) {
+- if (try)
+- msleep(10);
+- live_status = intel_digital_port_connected(dev_priv,
+- hdmi_to_dig_port(intel_hdmi));
+- }
+-
+- if (!live_status) {
+- DRM_DEBUG_KMS("HDMI live status down\n");
+- /*
+- * Live status register is not reliable on all intel platforms.
+- * So consider live_status only for certain platforms, for
+- * others, read EDID to determine presence of sink.
+- */
+- if (INTEL_INFO(dev_priv)->gen < 7 || IS_IVYBRIDGE(dev_priv))
+- live_status = true;
+- }
+-
+ intel_hdmi_unset_edid(connector);
+
+- if (intel_hdmi_set_edid(connector, live_status)) {
++ if (intel_hdmi_set_edid(connector)) {
+ struct intel_hdmi *intel_hdmi = intel_attached_hdmi(connector);
+
+ hdmi_to_dig_port(intel_hdmi)->base.type = INTEL_OUTPUT_HDMI;
+@@ -1521,7 +1498,7 @@ intel_hdmi_force(struct drm_connector *connector)
+ if (connector->status != connector_status_connected)
+ return;
+
+- intel_hdmi_set_edid(connector, true);
++ intel_hdmi_set_edid(connector);
+ hdmi_to_dig_port(intel_hdmi)->base.type = INTEL_OUTPUT_HDMI;
+ }
+
+diff --git a/drivers/gpu/drm/i915/intel_panel.c b/drivers/gpu/drm/i915/intel_panel.c
+index 96c65d7..9a2393a 100644
+--- a/drivers/gpu/drm/i915/intel_panel.c
++++ b/drivers/gpu/drm/i915/intel_panel.c
+@@ -841,7 +841,7 @@ static void lpt_enable_backlight(struct intel_connector *connector)
+ {
+ struct drm_i915_private *dev_priv = to_i915(connector->base.dev);
+ struct intel_panel *panel = &connector->panel;
+- u32 pch_ctl1, pch_ctl2;
++ u32 pch_ctl1, pch_ctl2, schicken;
+
+ pch_ctl1 = I915_READ(BLC_PWM_PCH_CTL1);
+ if (pch_ctl1 & BLM_PCH_PWM_ENABLE) {
+@@ -850,6 +850,22 @@ static void lpt_enable_backlight(struct intel_connector *connector)
+ I915_WRITE(BLC_PWM_PCH_CTL1, pch_ctl1);
+ }
+
++ if (HAS_PCH_LPT(dev_priv)) {
++ schicken = I915_READ(SOUTH_CHICKEN2);
++ if (panel->backlight.alternate_pwm_increment)
++ schicken |= LPT_PWM_GRANULARITY;
++ else
++ schicken &= ~LPT_PWM_GRANULARITY;
++ I915_WRITE(SOUTH_CHICKEN2, schicken);
++ } else {
++ schicken = I915_READ(SOUTH_CHICKEN1);
++ if (panel->backlight.alternate_pwm_increment)
++ schicken |= SPT_PWM_GRANULARITY;
++ else
++ schicken &= ~SPT_PWM_GRANULARITY;
++ I915_WRITE(SOUTH_CHICKEN1, schicken);
++ }
++
+ pch_ctl2 = panel->backlight.max << 16;
+ I915_WRITE(BLC_PWM_PCH_CTL2, pch_ctl2);
+
+@@ -1242,10 +1258,10 @@ static u32 bxt_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz)
+ */
+ static u32 spt_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz)
+ {
+- struct drm_i915_private *dev_priv = to_i915(connector->base.dev);
++ struct intel_panel *panel = &connector->panel;
+ u32 mul;
+
+- if (I915_READ(SOUTH_CHICKEN1) & SPT_PWM_GRANULARITY)
++ if (panel->backlight.alternate_pwm_increment)
+ mul = 128;
+ else
+ mul = 16;
+@@ -1261,9 +1277,10 @@ static u32 spt_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz)
+ static u32 lpt_hz_to_pwm(struct intel_connector *connector, u32 pwm_freq_hz)
+ {
+ struct drm_i915_private *dev_priv = to_i915(connector->base.dev);
++ struct intel_panel *panel = &connector->panel;
+ u32 mul, clock;
+
+- if (I915_READ(SOUTH_CHICKEN2) & LPT_PWM_GRANULARITY)
++ if (panel->backlight.alternate_pwm_increment)
+ mul = 16;
+ else
+ mul = 128;
+@@ -1414,6 +1431,13 @@ static int lpt_setup_backlight(struct intel_connector *connector, enum pipe unus
+ struct drm_i915_private *dev_priv = to_i915(connector->base.dev);
+ struct intel_panel *panel = &connector->panel;
+ u32 pch_ctl1, pch_ctl2, val;
++ bool alt;
++
++ if (HAS_PCH_LPT(dev_priv))
++ alt = I915_READ(SOUTH_CHICKEN2) & LPT_PWM_GRANULARITY;
++ else
++ alt = I915_READ(SOUTH_CHICKEN1) & SPT_PWM_GRANULARITY;
++ panel->backlight.alternate_pwm_increment = alt;
+
+ pch_ctl1 = I915_READ(BLC_PWM_PCH_CTL1);
+ panel->backlight.active_low_pwm = pch_ctl1 & BLM_PCH_POLARITY;
+diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c
+index 2d24813..e59a28c 100644
+--- a/drivers/gpu/drm/i915/intel_pm.c
++++ b/drivers/gpu/drm/i915/intel_pm.c
+@@ -2119,32 +2119,34 @@ static void intel_read_wm_latency(struct drm_device *dev, uint16_t wm[8])
+ GEN9_MEM_LATENCY_LEVEL_MASK;
+
+ /*
++ * If a level n (n > 1) has a 0us latency, all levels m (m >= n)
++ * need to be disabled. We make sure to sanitize the values out
++ * of the punit to satisfy this requirement.
++ */
++ for (level = 1; level <= max_level; level++) {
++ if (wm[level] == 0) {
++ for (i = level + 1; i <= max_level; i++)
++ wm[i] = 0;
++ break;
++ }
++ }
++
++ /*
+ * WaWmMemoryReadLatency:skl
+ *
+ * punit doesn't take into account the read latency so we need
+- * to add 2us to the various latency levels we retrieve from
+- * the punit.
+- * - W0 is a bit special in that it's the only level that
+- * can't be disabled if we want to have display working, so
+- * we always add 2us there.
+- * - For levels >=1, punit returns 0us latency when they are
+- * disabled, so we respect that and don't add 2us then
+- *
+- * Additionally, if a level n (n > 1) has a 0us latency, all
+- * levels m (m >= n) need to be disabled. We make sure to
+- * sanitize the values out of the punit to satisfy this
+- * requirement.
++ * to add 2us to the various latency levels we retrieve from the
++ * punit when level 0 response data us 0us.
+ */
+- wm[0] += 2;
+- for (level = 1; level <= max_level; level++)
+- if (wm[level] != 0)
++ if (wm[0] == 0) {
++ wm[0] += 2;
++ for (level = 1; level <= max_level; level++) {
++ if (wm[level] == 0)
++ break;
+ wm[level] += 2;
+- else {
+- for (i = level + 1; i <= max_level; i++)
+- wm[i] = 0;
+-
+- break;
+ }
++ }
++
+ } else if (IS_HASWELL(dev) || IS_BROADWELL(dev)) {
+ uint64_t sskpd = I915_READ64(MCH_SSKPD);
+
+@@ -2876,6 +2878,19 @@ skl_wm_plane_id(const struct intel_plane *plane)
+ }
+ }
+
++static bool
++intel_has_sagv(struct drm_i915_private *dev_priv)
++{
++ if (IS_KABYLAKE(dev_priv))
++ return true;
++
++ if (IS_SKYLAKE(dev_priv) &&
++ dev_priv->sagv_status != I915_SAGV_NOT_CONTROLLED)
++ return true;
++
++ return false;
++}
++
+ /*
+ * SAGV dynamically adjusts the system agent voltage and clock frequencies
+ * depending on power and performance requirements. The display engine access
+@@ -2888,12 +2903,14 @@ skl_wm_plane_id(const struct intel_plane *plane)
+ * - We're not using an interlaced display configuration
+ */
+ int
+-skl_enable_sagv(struct drm_i915_private *dev_priv)
++intel_enable_sagv(struct drm_i915_private *dev_priv)
+ {
+ int ret;
+
+- if (dev_priv->skl_sagv_status == I915_SKL_SAGV_NOT_CONTROLLED ||
+- dev_priv->skl_sagv_status == I915_SKL_SAGV_ENABLED)
++ if (!intel_has_sagv(dev_priv))
++ return 0;
++
++ if (dev_priv->sagv_status == I915_SAGV_ENABLED)
+ return 0;
+
+ DRM_DEBUG_KMS("Enabling the SAGV\n");
+@@ -2909,21 +2926,21 @@ skl_enable_sagv(struct drm_i915_private *dev_priv)
+ * Some skl systems, pre-release machines in particular,
+ * don't actually have an SAGV.
+ */
+- if (ret == -ENXIO) {
++ if (IS_SKYLAKE(dev_priv) && ret == -ENXIO) {
+ DRM_DEBUG_DRIVER("No SAGV found on system, ignoring\n");
+- dev_priv->skl_sagv_status = I915_SKL_SAGV_NOT_CONTROLLED;
++ dev_priv->sagv_status = I915_SAGV_NOT_CONTROLLED;
+ return 0;
+ } else if (ret < 0) {
+ DRM_ERROR("Failed to enable the SAGV\n");
+ return ret;
+ }
+
+- dev_priv->skl_sagv_status = I915_SKL_SAGV_ENABLED;
++ dev_priv->sagv_status = I915_SAGV_ENABLED;
+ return 0;
+ }
+
+ static int
+-skl_do_sagv_disable(struct drm_i915_private *dev_priv)
++intel_do_sagv_disable(struct drm_i915_private *dev_priv)
+ {
+ int ret;
+ uint32_t temp = GEN9_SAGV_DISABLE;
+@@ -2937,19 +2954,21 @@ skl_do_sagv_disable(struct drm_i915_private *dev_priv)
+ }
+
+ int
+-skl_disable_sagv(struct drm_i915_private *dev_priv)
++intel_disable_sagv(struct drm_i915_private *dev_priv)
+ {
+ int ret, result;
+
+- if (dev_priv->skl_sagv_status == I915_SKL_SAGV_NOT_CONTROLLED ||
+- dev_priv->skl_sagv_status == I915_SKL_SAGV_DISABLED)
++ if (!intel_has_sagv(dev_priv))
++ return 0;
++
++ if (dev_priv->sagv_status == I915_SAGV_DISABLED)
+ return 0;
+
+ DRM_DEBUG_KMS("Disabling the SAGV\n");
+ mutex_lock(&dev_priv->rps.hw_lock);
+
+ /* bspec says to keep retrying for at least 1 ms */
+- ret = wait_for(result = skl_do_sagv_disable(dev_priv), 1);
++ ret = wait_for(result = intel_do_sagv_disable(dev_priv), 1);
+ mutex_unlock(&dev_priv->rps.hw_lock);
+
+ if (ret == -ETIMEDOUT) {
+@@ -2961,20 +2980,20 @@ skl_disable_sagv(struct drm_i915_private *dev_priv)
+ * Some skl systems, pre-release machines in particular,
+ * don't actually have an SAGV.
+ */
+- if (result == -ENXIO) {
++ if (IS_SKYLAKE(dev_priv) && result == -ENXIO) {
+ DRM_DEBUG_DRIVER("No SAGV found on system, ignoring\n");
+- dev_priv->skl_sagv_status = I915_SKL_SAGV_NOT_CONTROLLED;
++ dev_priv->sagv_status = I915_SAGV_NOT_CONTROLLED;
+ return 0;
+ } else if (result < 0) {
+ DRM_ERROR("Failed to disable the SAGV\n");
+ return result;
+ }
+
+- dev_priv->skl_sagv_status = I915_SKL_SAGV_DISABLED;
++ dev_priv->sagv_status = I915_SAGV_DISABLED;
+ return 0;
+ }
+
+-bool skl_can_enable_sagv(struct drm_atomic_state *state)
++bool intel_can_enable_sagv(struct drm_atomic_state *state)
+ {
+ struct drm_device *dev = state->dev;
+ struct drm_i915_private *dev_priv = to_i915(dev);
+@@ -2983,6 +3002,9 @@ bool skl_can_enable_sagv(struct drm_atomic_state *state)
+ enum pipe pipe;
+ int level, plane;
+
++ if (!intel_has_sagv(dev_priv))
++ return false;
++
+ /*
+ * SKL workaround: bspec recommends we disable the SAGV when we have
+ * more then one pipe enabled
+@@ -3473,29 +3495,14 @@ static uint32_t skl_wm_method1(uint32_t pixel_rate, uint8_t cpp, uint32_t latenc
+ }
+
+ static uint32_t skl_wm_method2(uint32_t pixel_rate, uint32_t pipe_htotal,
+- uint32_t horiz_pixels, uint8_t cpp,
+- uint64_t tiling, uint32_t latency)
++ uint32_t latency, uint32_t plane_blocks_per_line)
+ {
+ uint32_t ret;
+- uint32_t plane_bytes_per_line, plane_blocks_per_line;
+ uint32_t wm_intermediate_val;
+
+ if (latency == 0)
+ return UINT_MAX;
+
+- plane_bytes_per_line = horiz_pixels * cpp;
+-
+- if (tiling == I915_FORMAT_MOD_Y_TILED ||
+- tiling == I915_FORMAT_MOD_Yf_TILED) {
+- plane_bytes_per_line *= 4;
+- plane_blocks_per_line = DIV_ROUND_UP(plane_bytes_per_line, 512);
+- plane_blocks_per_line /= 4;
+- } else if (tiling == DRM_FORMAT_MOD_NONE) {
+- plane_blocks_per_line = DIV_ROUND_UP(plane_bytes_per_line, 512) + 1;
+- } else {
+- plane_blocks_per_line = DIV_ROUND_UP(plane_bytes_per_line, 512);
+- }
+-
+ wm_intermediate_val = latency * pixel_rate;
+ ret = DIV_ROUND_UP(wm_intermediate_val, pipe_htotal * 1000) *
+ plane_blocks_per_line;
+@@ -3546,6 +3553,7 @@ static int skl_compute_plane_wm(const struct drm_i915_private *dev_priv,
+ uint8_t cpp;
+ uint32_t width = 0, height = 0;
+ uint32_t plane_pixel_rate;
++ uint32_t y_tile_minimum, y_min_scanlines;
+
+ if (latency == 0 || !cstate->base.active || !intel_pstate->visible) {
+ *enabled = false;
+@@ -3561,38 +3569,51 @@ static int skl_compute_plane_wm(const struct drm_i915_private *dev_priv,
+ cpp = drm_format_plane_cpp(fb->pixel_format, 0);
+ plane_pixel_rate = skl_adjusted_plane_pixel_rate(cstate, intel_pstate);
+
++ if (intel_rotation_90_or_270(pstate->rotation)) {
++ int cpp = (fb->pixel_format == DRM_FORMAT_NV12) ?
++ drm_format_plane_cpp(fb->pixel_format, 1) :
++ drm_format_plane_cpp(fb->pixel_format, 0);
++
++ switch (cpp) {
++ case 1:
++ y_min_scanlines = 16;
++ break;
++ case 2:
++ y_min_scanlines = 8;
++ break;
++ default:
++ WARN(1, "Unsupported pixel depth for rotation");
++ case 4:
++ y_min_scanlines = 4;
++ break;
++ }
++ } else {
++ y_min_scanlines = 4;
++ }
++
++ plane_bytes_per_line = width * cpp;
++ if (fb->modifier[0] == I915_FORMAT_MOD_Y_TILED ||
++ fb->modifier[0] == I915_FORMAT_MOD_Yf_TILED) {
++ plane_blocks_per_line =
++ DIV_ROUND_UP(plane_bytes_per_line * y_min_scanlines, 512);
++ plane_blocks_per_line /= y_min_scanlines;
++ } else if (fb->modifier[0] == DRM_FORMAT_MOD_NONE) {
++ plane_blocks_per_line = DIV_ROUND_UP(plane_bytes_per_line, 512)
++ + 1;
++ } else {
++ plane_blocks_per_line = DIV_ROUND_UP(plane_bytes_per_line, 512);
++ }
++
+ method1 = skl_wm_method1(plane_pixel_rate, cpp, latency);
+ method2 = skl_wm_method2(plane_pixel_rate,
+ cstate->base.adjusted_mode.crtc_htotal,
+- width,
+- cpp,
+- fb->modifier[0],
+- latency);
++ latency,
++ plane_blocks_per_line);
+
+- plane_bytes_per_line = width * cpp;
+- plane_blocks_per_line = DIV_ROUND_UP(plane_bytes_per_line, 512);
++ y_tile_minimum = plane_blocks_per_line * y_min_scanlines;
+
+ if (fb->modifier[0] == I915_FORMAT_MOD_Y_TILED ||
+ fb->modifier[0] == I915_FORMAT_MOD_Yf_TILED) {
+- uint32_t min_scanlines = 4;
+- uint32_t y_tile_minimum;
+- if (intel_rotation_90_or_270(pstate->rotation)) {
+- int cpp = (fb->pixel_format == DRM_FORMAT_NV12) ?
+- drm_format_plane_cpp(fb->pixel_format, 1) :
+- drm_format_plane_cpp(fb->pixel_format, 0);
+-
+- switch (cpp) {
+- case 1:
+- min_scanlines = 16;
+- break;
+- case 2:
+- min_scanlines = 8;
+- break;
+- case 8:
+- WARN(1, "Unsupported pixel depth for rotation");
+- }
+- }
+- y_tile_minimum = plane_blocks_per_line * min_scanlines;
+ selected_result = max(method2, y_tile_minimum);
+ } else {
+ if ((ddb_allocation / plane_blocks_per_line) >= 1)
+@@ -3606,10 +3627,12 @@ static int skl_compute_plane_wm(const struct drm_i915_private *dev_priv,
+
+ if (level >= 1 && level <= 7) {
+ if (fb->modifier[0] == I915_FORMAT_MOD_Y_TILED ||
+- fb->modifier[0] == I915_FORMAT_MOD_Yf_TILED)
+- res_lines += 4;
+- else
++ fb->modifier[0] == I915_FORMAT_MOD_Yf_TILED) {
++ res_blocks += y_tile_minimum;
++ res_lines += y_min_scanlines;
++ } else {
+ res_blocks++;
++ }
+ }
+
+ if (res_blocks >= ddb_allocation || res_lines > 31) {
+@@ -3828,183 +3851,82 @@ static void skl_ddb_entry_write(struct drm_i915_private *dev_priv,
+ I915_WRITE(reg, 0);
+ }
+
+-static void skl_write_wm_values(struct drm_i915_private *dev_priv,
+- const struct skl_wm_values *new)
++void skl_write_plane_wm(struct intel_crtc *intel_crtc,
++ const struct skl_wm_values *wm,
++ int plane)
+ {
+- struct drm_device *dev = &dev_priv->drm;
+- struct intel_crtc *crtc;
+-
+- for_each_intel_crtc(dev, crtc) {
+- int i, level, max_level = ilk_wm_max_level(dev);
+- enum pipe pipe = crtc->pipe;
+-
+- if ((new->dirty_pipes & drm_crtc_mask(&crtc->base)) == 0)
+- continue;
+- if (!crtc->active)
+- continue;
+-
+- I915_WRITE(PIPE_WM_LINETIME(pipe), new->wm_linetime[pipe]);
+-
+- for (level = 0; level <= max_level; level++) {
+- for (i = 0; i < intel_num_planes(crtc); i++)
+- I915_WRITE(PLANE_WM(pipe, i, level),
+- new->plane[pipe][i][level]);
+- I915_WRITE(CUR_WM(pipe, level),
+- new->plane[pipe][PLANE_CURSOR][level]);
+- }
+- for (i = 0; i < intel_num_planes(crtc); i++)
+- I915_WRITE(PLANE_WM_TRANS(pipe, i),
+- new->plane_trans[pipe][i]);
+- I915_WRITE(CUR_WM_TRANS(pipe),
+- new->plane_trans[pipe][PLANE_CURSOR]);
+-
+- for (i = 0; i < intel_num_planes(crtc); i++) {
+- skl_ddb_entry_write(dev_priv,
+- PLANE_BUF_CFG(pipe, i),
+- &new->ddb.plane[pipe][i]);
+- skl_ddb_entry_write(dev_priv,
+- PLANE_NV12_BUF_CFG(pipe, i),
+- &new->ddb.y_plane[pipe][i]);
+- }
++ struct drm_crtc *crtc = &intel_crtc->base;
++ struct drm_device *dev = crtc->dev;
++ struct drm_i915_private *dev_priv = to_i915(dev);
++ int level, max_level = ilk_wm_max_level(dev);
++ enum pipe pipe = intel_crtc->pipe;
+
+- skl_ddb_entry_write(dev_priv, CUR_BUF_CFG(pipe),
+- &new->ddb.plane[pipe][PLANE_CURSOR]);
++ for (level = 0; level <= max_level; level++) {
++ I915_WRITE(PLANE_WM(pipe, plane, level),
++ wm->plane[pipe][plane][level]);
+ }
+-}
++ I915_WRITE(PLANE_WM_TRANS(pipe, plane), wm->plane_trans[pipe][plane]);
+
+-/*
+- * When setting up a new DDB allocation arrangement, we need to correctly
+- * sequence the times at which the new allocations for the pipes are taken into
+- * account or we'll have pipes fetching from space previously allocated to
+- * another pipe.
+- *
+- * Roughly the sequence looks like:
+- * 1. re-allocate the pipe(s) with the allocation being reduced and not
+- * overlapping with a previous light-up pipe (another way to put it is:
+- * pipes with their new allocation strickly included into their old ones).
+- * 2. re-allocate the other pipes that get their allocation reduced
+- * 3. allocate the pipes having their allocation increased
+- *
+- * Steps 1. and 2. are here to take care of the following case:
+- * - Initially DDB looks like this:
+- * | B | C |
+- * - enable pipe A.
+- * - pipe B has a reduced DDB allocation that overlaps with the old pipe C
+- * allocation
+- * | A | B | C |
+- *
+- * We need to sequence the re-allocation: C, B, A (and not B, C, A).
+- */
++ skl_ddb_entry_write(dev_priv, PLANE_BUF_CFG(pipe, plane),
++ &wm->ddb.plane[pipe][plane]);
++ skl_ddb_entry_write(dev_priv, PLANE_NV12_BUF_CFG(pipe, plane),
++ &wm->ddb.y_plane[pipe][plane]);
++}
+
+-static void
+-skl_wm_flush_pipe(struct drm_i915_private *dev_priv, enum pipe pipe, int pass)
++void skl_write_cursor_wm(struct intel_crtc *intel_crtc,
++ const struct skl_wm_values *wm)
+ {
+- int plane;
+-
+- DRM_DEBUG_KMS("flush pipe %c (pass %d)\n", pipe_name(pipe), pass);
++ struct drm_crtc *crtc = &intel_crtc->base;
++ struct drm_device *dev = crtc->dev;
++ struct drm_i915_private *dev_priv = to_i915(dev);
++ int level, max_level = ilk_wm_max_level(dev);
++ enum pipe pipe = intel_crtc->pipe;
+
+- for_each_plane(dev_priv, pipe, plane) {
+- I915_WRITE(PLANE_SURF(pipe, plane),
+- I915_READ(PLANE_SURF(pipe, plane)));
++ for (level = 0; level <= max_level; level++) {
++ I915_WRITE(CUR_WM(pipe, level),
++ wm->plane[pipe][PLANE_CURSOR][level]);
+ }
+- I915_WRITE(CURBASE(pipe), I915_READ(CURBASE(pipe)));
++ I915_WRITE(CUR_WM_TRANS(pipe), wm->plane_trans[pipe][PLANE_CURSOR]);
++
++ skl_ddb_entry_write(dev_priv, CUR_BUF_CFG(pipe),
++ &wm->ddb.plane[pipe][PLANE_CURSOR]);
+ }
+
+-static bool
+-skl_ddb_allocation_included(const struct skl_ddb_allocation *old,
+- const struct skl_ddb_allocation *new,
+- enum pipe pipe)
++bool skl_ddb_allocation_equals(const struct skl_ddb_allocation *old,
++ const struct skl_ddb_allocation *new,
++ enum pipe pipe)
+ {
+- uint16_t old_size, new_size;
+-
+- old_size = skl_ddb_entry_size(&old->pipe[pipe]);
+- new_size = skl_ddb_entry_size(&new->pipe[pipe]);
+-
+- return old_size != new_size &&
+- new->pipe[pipe].start >= old->pipe[pipe].start &&
+- new->pipe[pipe].end <= old->pipe[pipe].end;
++ return new->pipe[pipe].start == old->pipe[pipe].start &&
++ new->pipe[pipe].end == old->pipe[pipe].end;
+ }
+
+-static void skl_flush_wm_values(struct drm_i915_private *dev_priv,
+- struct skl_wm_values *new_values)
++static inline bool skl_ddb_entries_overlap(const struct skl_ddb_entry *a,
++ const struct skl_ddb_entry *b)
+ {
+- struct drm_device *dev = &dev_priv->drm;
+- struct skl_ddb_allocation *cur_ddb, *new_ddb;
+- bool reallocated[I915_MAX_PIPES] = {};
+- struct intel_crtc *crtc;
+- enum pipe pipe;
+-
+- new_ddb = &new_values->ddb;
+- cur_ddb = &dev_priv->wm.skl_hw.ddb;
+-
+- /*
+- * First pass: flush the pipes with the new allocation contained into
+- * the old space.
+- *
+- * We'll wait for the vblank on those pipes to ensure we can safely
+- * re-allocate the freed space without this pipe fetching from it.
+- */
+- for_each_intel_crtc(dev, crtc) {
+- if (!crtc->active)
+- continue;
+-
+- pipe = crtc->pipe;
+-
+- if (!skl_ddb_allocation_included(cur_ddb, new_ddb, pipe))
+- continue;
+-
+- skl_wm_flush_pipe(dev_priv, pipe, 1);
+- intel_wait_for_vblank(dev, pipe);
+-
+- reallocated[pipe] = true;
+- }
+-
++ return a->start < b->end && b->start < a->end;
++}
+
+- /*
+- * Second pass: flush the pipes that are having their allocation
+- * reduced, but overlapping with a previous allocation.
+- *
+- * Here as well we need to wait for the vblank to make sure the freed
+- * space is not used anymore.
+- */
+- for_each_intel_crtc(dev, crtc) {
+- if (!crtc->active)
+- continue;
++bool skl_ddb_allocation_overlaps(struct drm_atomic_state *state,
++ const struct skl_ddb_allocation *old,
++ const struct skl_ddb_allocation *new,
++ enum pipe pipe)
++{
++ struct drm_device *dev = state->dev;
++ struct intel_crtc *intel_crtc;
++ enum pipe otherp;
+
+- pipe = crtc->pipe;
++ for_each_intel_crtc(dev, intel_crtc) {
++ otherp = intel_crtc->pipe;
+
+- if (reallocated[pipe])
++ if (otherp == pipe)
+ continue;
+
+- if (skl_ddb_entry_size(&new_ddb->pipe[pipe]) <
+- skl_ddb_entry_size(&cur_ddb->pipe[pipe])) {
+- skl_wm_flush_pipe(dev_priv, pipe, 2);
+- intel_wait_for_vblank(dev, pipe);
+- reallocated[pipe] = true;
+- }
++ if (skl_ddb_entries_overlap(&new->pipe[pipe],
++ &old->pipe[otherp]))
++ return true;
+ }
+
+- /*
+- * Third pass: flush the pipes that got more space allocated.
+- *
+- * We don't need to actively wait for the update here, next vblank
+- * will just get more DDB space with the correct WM values.
+- */
+- for_each_intel_crtc(dev, crtc) {
+- if (!crtc->active)
+- continue;
+-
+- pipe = crtc->pipe;
+-
+- /*
+- * At this point, only the pipes more space than before are
+- * left to re-allocate.
+- */
+- if (reallocated[pipe])
+- continue;
+-
+- skl_wm_flush_pipe(dev_priv, pipe, 3);
+- }
++ return false;
+ }
+
+ static int skl_update_pipe_wm(struct drm_crtc_state *cstate,
+@@ -4041,6 +3963,41 @@ pipes_modified(struct drm_atomic_state *state)
+ return ret;
+ }
+
++int
++skl_ddb_add_affected_planes(struct intel_crtc_state *cstate)
++{
++ struct drm_atomic_state *state = cstate->base.state;
++ struct drm_device *dev = state->dev;
++ struct drm_crtc *crtc = cstate->base.crtc;
++ struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
++ struct drm_i915_private *dev_priv = to_i915(dev);
++ struct intel_atomic_state *intel_state = to_intel_atomic_state(state);
++ struct skl_ddb_allocation *new_ddb = &intel_state->wm_results.ddb;
++ struct skl_ddb_allocation *cur_ddb = &dev_priv->wm.skl_hw.ddb;
++ struct drm_plane_state *plane_state;
++ struct drm_plane *plane;
++ enum pipe pipe = intel_crtc->pipe;
++ int id;
++
++ WARN_ON(!drm_atomic_get_existing_crtc_state(state, crtc));
++
++ drm_for_each_plane_mask(plane, dev, crtc->state->plane_mask) {
++ id = skl_wm_plane_id(to_intel_plane(plane));
++
++ if (skl_ddb_entry_equal(&cur_ddb->plane[pipe][id],
++ &new_ddb->plane[pipe][id]) &&
++ skl_ddb_entry_equal(&cur_ddb->y_plane[pipe][id],
++ &new_ddb->y_plane[pipe][id]))
++ continue;
++
++ plane_state = drm_atomic_get_plane_state(state, plane);
++ if (IS_ERR(plane_state))
++ return PTR_ERR(plane_state);
++ }
++
++ return 0;
++}
++
+ static int
+ skl_compute_ddb(struct drm_atomic_state *state)
+ {
+@@ -4105,6 +4062,10 @@ skl_compute_ddb(struct drm_atomic_state *state)
+ if (ret)
+ return ret;
+
++ ret = skl_ddb_add_affected_planes(cstate);
++ if (ret)
++ return ret;
++
+ ret = drm_atomic_add_affected_planes(state, &intel_crtc->base);
+ if (ret)
+ return ret;
+@@ -4206,7 +4167,7 @@ static void skl_update_wm(struct drm_crtc *crtc)
+ struct skl_wm_values *hw_vals = &dev_priv->wm.skl_hw;
+ struct intel_crtc_state *cstate = to_intel_crtc_state(crtc->state);
+ struct skl_pipe_wm *pipe_wm = &cstate->wm.skl.optimal;
+- int pipe;
++ enum pipe pipe = intel_crtc->pipe;
+
+ if ((results->dirty_pipes & drm_crtc_mask(crtc)) == 0)
+ return;
+@@ -4215,15 +4176,22 @@ static void skl_update_wm(struct drm_crtc *crtc)
+
+ mutex_lock(&dev_priv->wm.wm_mutex);
+
+- skl_write_wm_values(dev_priv, results);
+- skl_flush_wm_values(dev_priv, results);
+-
+ /*
+- * Store the new configuration (but only for the pipes that have
+- * changed; the other values weren't recomputed).
++ * If this pipe isn't active already, we're going to be enabling it
++ * very soon. Since it's safe to update a pipe's ddb allocation while
++ * the pipe's shut off, just do so here. Already active pipes will have
++ * their watermarks updated once we update their planes.
+ */
+- for_each_pipe_masked(dev_priv, pipe, results->dirty_pipes)
+- skl_copy_wm_for_pipe(hw_vals, results, pipe);
++ if (crtc->state->active_changed) {
++ int plane;
++
++ for (plane = 0; plane < intel_num_planes(intel_crtc); plane++)
++ skl_write_plane_wm(intel_crtc, results, plane);
++
++ skl_write_cursor_wm(intel_crtc, results);
++ }
++
++ skl_copy_wm_for_pipe(hw_vals, results, pipe);
+
+ mutex_unlock(&dev_priv->wm.wm_mutex);
+ }
+diff --git a/drivers/gpu/drm/i915/intel_sprite.c b/drivers/gpu/drm/i915/intel_sprite.c
+index 7c08e4f..4178849 100644
+--- a/drivers/gpu/drm/i915/intel_sprite.c
++++ b/drivers/gpu/drm/i915/intel_sprite.c
+@@ -203,6 +203,9 @@ skl_update_plane(struct drm_plane *drm_plane,
+ struct intel_plane *intel_plane = to_intel_plane(drm_plane);
+ struct drm_framebuffer *fb = plane_state->base.fb;
+ struct drm_i915_gem_object *obj = intel_fb_obj(fb);
++ const struct skl_wm_values *wm = &dev_priv->wm.skl_results;
++ struct drm_crtc *crtc = crtc_state->base.crtc;
++ struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
+ const int pipe = intel_plane->pipe;
+ const int plane = intel_plane->plane + 1;
+ u32 plane_ctl, stride_div, stride;
+@@ -238,6 +241,9 @@ skl_update_plane(struct drm_plane *drm_plane,
+ crtc_w--;
+ crtc_h--;
+
++ if (wm->dirty_pipes & drm_crtc_mask(crtc))
++ skl_write_plane_wm(intel_crtc, wm, plane);
++
+ if (key->flags) {
+ I915_WRITE(PLANE_KEYVAL(pipe, plane), key->min_value);
+ I915_WRITE(PLANE_KEYMAX(pipe, plane), key->max_value);
+@@ -308,6 +314,14 @@ skl_disable_plane(struct drm_plane *dplane, struct drm_crtc *crtc)
+ const int pipe = intel_plane->pipe;
+ const int plane = intel_plane->plane + 1;
+
++ /*
++ * We only populate skl_results on watermark updates, and if the
++ * plane's visiblity isn't actually changing neither is its watermarks.
++ */
++ if (!to_intel_plane_state(dplane->state)->visible)
++ skl_write_plane_wm(to_intel_crtc(crtc),
++ &dev_priv->wm.skl_results, plane);
++
+ I915_WRITE(PLANE_CTL(pipe, plane), 0);
+
+ I915_WRITE(PLANE_SURF(pipe, plane), 0);
+diff --git a/drivers/gpu/drm/i915/intel_uncore.c b/drivers/gpu/drm/i915/intel_uncore.c
+index ff80a81..ec28b15 100644
+--- a/drivers/gpu/drm/i915/intel_uncore.c
++++ b/drivers/gpu/drm/i915/intel_uncore.c
+@@ -796,10 +796,9 @@ __unclaimed_reg_debug(struct drm_i915_private *dev_priv,
+ const bool read,
+ const bool before)
+ {
+- if (WARN(check_for_unclaimed_mmio(dev_priv),
+- "Unclaimed register detected %s %s register 0x%x\n",
+- before ? "before" : "after",
+- read ? "reading" : "writing to",
++ if (WARN(check_for_unclaimed_mmio(dev_priv) && !before,
++ "Unclaimed %s register 0x%x\n",
++ read ? "read from" : "write to",
+ i915_mmio_reg_offset(reg)))
+ i915.mmio_debug--; /* Only report the first N failures */
+ }
+diff --git a/drivers/gpu/drm/radeon/r600_dpm.c b/drivers/gpu/drm/radeon/r600_dpm.c
+index 6a4b020..5a26eb4 100644
+--- a/drivers/gpu/drm/radeon/r600_dpm.c
++++ b/drivers/gpu/drm/radeon/r600_dpm.c
+@@ -156,19 +156,20 @@ u32 r600_dpm_get_vblank_time(struct radeon_device *rdev)
+ struct drm_device *dev = rdev->ddev;
+ struct drm_crtc *crtc;
+ struct radeon_crtc *radeon_crtc;
+- u32 line_time_us, vblank_lines;
++ u32 vblank_in_pixels;
+ u32 vblank_time_us = 0xffffffff; /* if the displays are off, vblank time is max */
+
+ if (rdev->num_crtc && rdev->mode_info.mode_config_initialized) {
+ list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
+ radeon_crtc = to_radeon_crtc(crtc);
+ if (crtc->enabled && radeon_crtc->enabled && radeon_crtc->hw_mode.clock) {
+- line_time_us = (radeon_crtc->hw_mode.crtc_htotal * 1000) /
+- radeon_crtc->hw_mode.clock;
+- vblank_lines = radeon_crtc->hw_mode.crtc_vblank_end -
+- radeon_crtc->hw_mode.crtc_vdisplay +
+- (radeon_crtc->v_border * 2);
+- vblank_time_us = vblank_lines * line_time_us;
++ vblank_in_pixels =
++ radeon_crtc->hw_mode.crtc_htotal *
++ (radeon_crtc->hw_mode.crtc_vblank_end -
++ radeon_crtc->hw_mode.crtc_vdisplay +
++ (radeon_crtc->v_border * 2));
++
++ vblank_time_us = vblank_in_pixels * 1000 / radeon_crtc->hw_mode.clock;
+ break;
+ }
+ }
+diff --git a/drivers/gpu/drm/radeon/radeon_device.c b/drivers/gpu/drm/radeon/radeon_device.c
+index a00dd2f..554ca71 100644
+--- a/drivers/gpu/drm/radeon/radeon_device.c
++++ b/drivers/gpu/drm/radeon/radeon_device.c
+@@ -661,8 +661,9 @@ bool radeon_card_posted(struct radeon_device *rdev)
+ {
+ uint32_t reg;
+
+- /* for pass through, always force asic_init */
+- if (radeon_device_is_virtual())
++ /* for pass through, always force asic_init for CI */
++ if (rdev->family >= CHIP_BONAIRE &&
++ radeon_device_is_virtual())
+ return false;
+
+ /* required for EFI mode on macbook2,1 which uses an r5xx asic */
+diff --git a/drivers/gpu/drm/radeon/si_dpm.c b/drivers/gpu/drm/radeon/si_dpm.c
+index 1f78ec2..89bdf20 100644
+--- a/drivers/gpu/drm/radeon/si_dpm.c
++++ b/drivers/gpu/drm/radeon/si_dpm.c
+@@ -4112,7 +4112,7 @@ static int si_populate_smc_voltage_tables(struct radeon_device *rdev,
+ &rdev->pm.dpm.dyn_state.phase_shedding_limits_table)) {
+ si_populate_smc_voltage_table(rdev, &si_pi->vddc_phase_shed_table, table);
+
+- table->phaseMaskTable.lowMask[SISLANDS_SMC_VOLTAGEMASK_VDDC] =
++ table->phaseMaskTable.lowMask[SISLANDS_SMC_VOLTAGEMASK_VDDC_PHASE_SHEDDING] =
+ cpu_to_be32(si_pi->vddc_phase_shed_table.mask_low);
+
+ si_write_smc_soft_register(rdev, SI_SMC_SOFT_REGISTER_phase_shedding_delay,
+diff --git a/drivers/gpu/drm/radeon/sislands_smc.h b/drivers/gpu/drm/radeon/sislands_smc.h
+index 3c77983..966e3a5 100644
+--- a/drivers/gpu/drm/radeon/sislands_smc.h
++++ b/drivers/gpu/drm/radeon/sislands_smc.h
+@@ -194,6 +194,7 @@ typedef struct SISLANDS_SMC_SWSTATE SISLANDS_SMC_SWSTATE;
+ #define SISLANDS_SMC_VOLTAGEMASK_VDDC 0
+ #define SISLANDS_SMC_VOLTAGEMASK_MVDD 1
+ #define SISLANDS_SMC_VOLTAGEMASK_VDDCI 2
++#define SISLANDS_SMC_VOLTAGEMASK_VDDC_PHASE_SHEDDING 3
+ #define SISLANDS_SMC_VOLTAGEMASK_MAX 4
+
+ struct SISLANDS_SMC_VOLTAGEMASKTABLE
+diff --git a/drivers/gpu/drm/vc4/vc4_drv.h b/drivers/gpu/drm/vc4/vc4_drv.h
+index 428e249..f696b75 100644
+--- a/drivers/gpu/drm/vc4/vc4_drv.h
++++ b/drivers/gpu/drm/vc4/vc4_drv.h
+@@ -122,9 +122,16 @@ to_vc4_dev(struct drm_device *dev)
+ struct vc4_bo {
+ struct drm_gem_cma_object base;
+
+- /* seqno of the last job to render to this BO. */
++ /* seqno of the last job to render using this BO. */
+ uint64_t seqno;
+
++ /* seqno of the last job to use the RCL to write to this BO.
++ *
++ * Note that this doesn't include binner overflow memory
++ * writes.
++ */
++ uint64_t write_seqno;
++
+ /* List entry for the BO's position in either
+ * vc4_exec_info->unref_list or vc4_dev->bo_cache.time_list
+ */
+@@ -216,6 +223,9 @@ struct vc4_exec_info {
+ /* Sequence number for this bin/render job. */
+ uint64_t seqno;
+
++ /* Latest write_seqno of any BO that binning depends on. */
++ uint64_t bin_dep_seqno;
++
+ /* Last current addresses the hardware was processing when the
+ * hangcheck timer checked on us.
+ */
+@@ -230,6 +240,13 @@ struct vc4_exec_info {
+ struct drm_gem_cma_object **bo;
+ uint32_t bo_count;
+
++ /* List of BOs that are being written by the RCL. Other than
++ * the binner temporary storage, this is all the BOs written
++ * by the job.
++ */
++ struct drm_gem_cma_object *rcl_write_bo[4];
++ uint32_t rcl_write_bo_count;
++
+ /* Pointers for our position in vc4->job_list */
+ struct list_head head;
+
+diff --git a/drivers/gpu/drm/vc4/vc4_gem.c b/drivers/gpu/drm/vc4/vc4_gem.c
+index b262c5c..ae1609e 100644
+--- a/drivers/gpu/drm/vc4/vc4_gem.c
++++ b/drivers/gpu/drm/vc4/vc4_gem.c
+@@ -471,6 +471,11 @@ vc4_update_bo_seqnos(struct vc4_exec_info *exec, uint64_t seqno)
+ list_for_each_entry(bo, &exec->unref_list, unref_head) {
+ bo->seqno = seqno;
+ }
++
++ for (i = 0; i < exec->rcl_write_bo_count; i++) {
++ bo = to_vc4_bo(&exec->rcl_write_bo[i]->base);
++ bo->write_seqno = seqno;
++ }
+ }
+
+ /* Queues a struct vc4_exec_info for execution. If no job is
+@@ -673,6 +678,14 @@ vc4_get_bcl(struct drm_device *dev, struct vc4_exec_info *exec)
+ goto fail;
+
+ ret = vc4_validate_shader_recs(dev, exec);
++ if (ret)
++ goto fail;
++
++ /* Block waiting on any previous rendering into the CS's VBO,
++ * IB, or textures, so that pixels are actually written by the
++ * time we try to read them.
++ */
++ ret = vc4_wait_for_seqno(dev, exec->bin_dep_seqno, ~0ull, true);
+
+ fail:
+ drm_free_large(temp);
+diff --git a/drivers/gpu/drm/vc4/vc4_render_cl.c b/drivers/gpu/drm/vc4/vc4_render_cl.c
+index 0f12418..08886a3 100644
+--- a/drivers/gpu/drm/vc4/vc4_render_cl.c
++++ b/drivers/gpu/drm/vc4/vc4_render_cl.c
+@@ -45,6 +45,8 @@ struct vc4_rcl_setup {
+
+ struct drm_gem_cma_object *rcl;
+ u32 next_offset;
++
++ u32 next_write_bo_index;
+ };
+
+ static inline void rcl_u8(struct vc4_rcl_setup *setup, u8 val)
+@@ -407,6 +409,8 @@ static int vc4_rcl_msaa_surface_setup(struct vc4_exec_info *exec,
+ if (!*obj)
+ return -EINVAL;
+
++ exec->rcl_write_bo[exec->rcl_write_bo_count++] = *obj;
++
+ if (surf->offset & 0xf) {
+ DRM_ERROR("MSAA write must be 16b aligned.\n");
+ return -EINVAL;
+@@ -417,7 +421,8 @@ static int vc4_rcl_msaa_surface_setup(struct vc4_exec_info *exec,
+
+ static int vc4_rcl_surface_setup(struct vc4_exec_info *exec,
+ struct drm_gem_cma_object **obj,
+- struct drm_vc4_submit_rcl_surface *surf)
++ struct drm_vc4_submit_rcl_surface *surf,
++ bool is_write)
+ {
+ uint8_t tiling = VC4_GET_FIELD(surf->bits,
+ VC4_LOADSTORE_TILE_BUFFER_TILING);
+@@ -440,6 +445,9 @@ static int vc4_rcl_surface_setup(struct vc4_exec_info *exec,
+ if (!*obj)
+ return -EINVAL;
+
++ if (is_write)
++ exec->rcl_write_bo[exec->rcl_write_bo_count++] = *obj;
++
+ if (surf->flags & VC4_SUBMIT_RCL_SURFACE_READ_IS_FULL_RES) {
+ if (surf == &exec->args->zs_write) {
+ DRM_ERROR("general zs write may not be a full-res.\n");
+@@ -542,6 +550,8 @@ vc4_rcl_render_config_surface_setup(struct vc4_exec_info *exec,
+ if (!*obj)
+ return -EINVAL;
+
++ exec->rcl_write_bo[exec->rcl_write_bo_count++] = *obj;
++
+ if (tiling > VC4_TILING_FORMAT_LT) {
+ DRM_ERROR("Bad tiling format\n");
+ return -EINVAL;
+@@ -599,15 +609,18 @@ int vc4_get_rcl(struct drm_device *dev, struct vc4_exec_info *exec)
+ if (ret)
+ return ret;
+
+- ret = vc4_rcl_surface_setup(exec, &setup.color_read, &args->color_read);
++ ret = vc4_rcl_surface_setup(exec, &setup.color_read, &args->color_read,
++ false);
+ if (ret)
+ return ret;
+
+- ret = vc4_rcl_surface_setup(exec, &setup.zs_read, &args->zs_read);
++ ret = vc4_rcl_surface_setup(exec, &setup.zs_read, &args->zs_read,
++ false);
+ if (ret)
+ return ret;
+
+- ret = vc4_rcl_surface_setup(exec, &setup.zs_write, &args->zs_write);
++ ret = vc4_rcl_surface_setup(exec, &setup.zs_write, &args->zs_write,
++ true);
+ if (ret)
+ return ret;
+
+diff --git a/drivers/gpu/drm/vc4/vc4_validate.c b/drivers/gpu/drm/vc4/vc4_validate.c
+index 9ce1d0a..26503e3 100644
+--- a/drivers/gpu/drm/vc4/vc4_validate.c
++++ b/drivers/gpu/drm/vc4/vc4_validate.c
+@@ -267,6 +267,9 @@ validate_indexed_prim_list(VALIDATE_ARGS)
+ if (!ib)
+ return -EINVAL;
+
++ exec->bin_dep_seqno = max(exec->bin_dep_seqno,
++ to_vc4_bo(&ib->base)->write_seqno);
++
+ if (offset > ib->base.size ||
+ (ib->base.size - offset) / index_size < length) {
+ DRM_ERROR("IB access overflow (%d + %d*%d > %zd)\n",
+@@ -555,8 +558,7 @@ static bool
+ reloc_tex(struct vc4_exec_info *exec,
+ void *uniform_data_u,
+ struct vc4_texture_sample_info *sample,
+- uint32_t texture_handle_index)
+-
++ uint32_t texture_handle_index, bool is_cs)
+ {
+ struct drm_gem_cma_object *tex;
+ uint32_t p0 = *(uint32_t *)(uniform_data_u + sample->p_offset[0]);
+@@ -714,6 +716,11 @@ reloc_tex(struct vc4_exec_info *exec,
+
+ *validated_p0 = tex->paddr + p0;
+
++ if (is_cs) {
++ exec->bin_dep_seqno = max(exec->bin_dep_seqno,
++ to_vc4_bo(&tex->base)->write_seqno);
++ }
++
+ return true;
+ fail:
+ DRM_INFO("Texture p0 at %d: 0x%08x\n", sample->p_offset[0], p0);
+@@ -835,7 +842,8 @@ validate_gl_shader_rec(struct drm_device *dev,
+ if (!reloc_tex(exec,
+ uniform_data_u,
+ &validated_shader->texture_samples[tex],
+- texture_handles_u[tex])) {
++ texture_handles_u[tex],
++ i == 2)) {
+ return -EINVAL;
+ }
+ }
+@@ -867,6 +875,9 @@ validate_gl_shader_rec(struct drm_device *dev,
+ uint32_t stride = *(uint8_t *)(pkt_u + o + 5);
+ uint32_t max_index;
+
++ exec->bin_dep_seqno = max(exec->bin_dep_seqno,
++ to_vc4_bo(&vbo->base)->write_seqno);
++
+ if (state->addr & 0x8)
+ stride |= (*(uint32_t *)(pkt_u + 100 + i * 4)) & ~0xff;
+
+diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c b/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c
+index dc5beff..8a15c4a 100644
+--- a/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c
++++ b/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c
+@@ -34,6 +34,24 @@
+
+ #define VMW_RES_HT_ORDER 12
+
++ /**
++ * enum vmw_resource_relocation_type - Relocation type for resources
++ *
++ * @vmw_res_rel_normal: Traditional relocation. The resource id in the
++ * command stream is replaced with the actual id after validation.
++ * @vmw_res_rel_nop: NOP relocation. The command is unconditionally replaced
++ * with a NOP.
++ * @vmw_res_rel_cond_nop: Conditional NOP relocation. If the resource id
++ * after validation is -1, the command is replaced with a NOP. Otherwise no
++ * action.
++ */
++enum vmw_resource_relocation_type {
++ vmw_res_rel_normal,
++ vmw_res_rel_nop,
++ vmw_res_rel_cond_nop,
++ vmw_res_rel_max
++};
++
+ /**
+ * struct vmw_resource_relocation - Relocation info for resources
+ *
+@@ -41,11 +59,13 @@
+ * @res: Non-ref-counted pointer to the resource.
+ * @offset: Offset of 4 byte entries into the command buffer where the
+ * id that needs fixup is located.
++ * @rel_type: Type of relocation.
+ */
+ struct vmw_resource_relocation {
+ struct list_head head;
+ const struct vmw_resource *res;
+- unsigned long offset;
++ u32 offset:29;
++ enum vmw_resource_relocation_type rel_type:3;
+ };
+
+ /**
+@@ -410,10 +430,13 @@ static int vmw_resource_context_res_add(struct vmw_private *dev_priv,
+ * @res: The resource.
+ * @offset: Offset into the command buffer currently being parsed where the
+ * id that needs fixup is located. Granularity is 4 bytes.
++ * @rel_type: Relocation type.
+ */
+ static int vmw_resource_relocation_add(struct list_head *list,
+ const struct vmw_resource *res,
+- unsigned long offset)
++ unsigned long offset,
++ enum vmw_resource_relocation_type
++ rel_type)
+ {
+ struct vmw_resource_relocation *rel;
+
+@@ -425,6 +448,7 @@ static int vmw_resource_relocation_add(struct list_head *list,
+
+ rel->res = res;
+ rel->offset = offset;
++ rel->rel_type = rel_type;
+ list_add_tail(&rel->head, list);
+
+ return 0;
+@@ -459,11 +483,23 @@ static void vmw_resource_relocations_apply(uint32_t *cb,
+ {
+ struct vmw_resource_relocation *rel;
+
++ /* Validate the struct vmw_resource_relocation member size */
++ BUILD_BUG_ON(SVGA_CB_MAX_SIZE >= (1 << 29));
++ BUILD_BUG_ON(vmw_res_rel_max >= (1 << 3));
++
+ list_for_each_entry(rel, list, head) {
+- if (likely(rel->res != NULL))
++ switch (rel->rel_type) {
++ case vmw_res_rel_normal:
+ cb[rel->offset] = rel->res->id;
+- else
++ break;
++ case vmw_res_rel_nop:
+ cb[rel->offset] = SVGA_3D_CMD_NOP;
++ break;
++ default:
++ if (rel->res->id == -1)
++ cb[rel->offset] = SVGA_3D_CMD_NOP;
++ break;
++ }
+ }
+ }
+
+@@ -655,7 +691,8 @@ static int vmw_cmd_res_reloc_add(struct vmw_private *dev_priv,
+ *p_val = NULL;
+ ret = vmw_resource_relocation_add(&sw_context->res_relocations,
+ res,
+- id_loc - sw_context->buf_start);
++ id_loc - sw_context->buf_start,
++ vmw_res_rel_normal);
+ if (unlikely(ret != 0))
+ return ret;
+
+@@ -721,7 +758,8 @@ vmw_cmd_res_check(struct vmw_private *dev_priv,
+
+ return vmw_resource_relocation_add
+ (&sw_context->res_relocations, res,
+- id_loc - sw_context->buf_start);
++ id_loc - sw_context->buf_start,
++ vmw_res_rel_normal);
+ }
+
+ ret = vmw_user_resource_lookup_handle(dev_priv,
+@@ -2144,7 +2182,8 @@ static int vmw_cmd_shader_define(struct vmw_private *dev_priv,
+
+ return vmw_resource_relocation_add(&sw_context->res_relocations,
+ NULL, &cmd->header.id -
+- sw_context->buf_start);
++ sw_context->buf_start,
++ vmw_res_rel_nop);
+
+ return 0;
+ }
+@@ -2189,7 +2228,8 @@ static int vmw_cmd_shader_destroy(struct vmw_private *dev_priv,
+
+ return vmw_resource_relocation_add(&sw_context->res_relocations,
+ NULL, &cmd->header.id -
+- sw_context->buf_start);
++ sw_context->buf_start,
++ vmw_res_rel_nop);
+
+ return 0;
+ }
+@@ -2848,8 +2888,7 @@ static int vmw_cmd_dx_cid_check(struct vmw_private *dev_priv,
+ * @header: Pointer to the command header in the command stream.
+ *
+ * Check that the view exists, and if it was not created using this
+- * command batch, make sure it's validated (present in the device) so that
+- * the remove command will not confuse the device.
++ * command batch, conditionally make this command a NOP.
+ */
+ static int vmw_cmd_dx_view_remove(struct vmw_private *dev_priv,
+ struct vmw_sw_context *sw_context,
+@@ -2877,10 +2916,15 @@ static int vmw_cmd_dx_view_remove(struct vmw_private *dev_priv,
+ return ret;
+
+ /*
+- * Add view to the validate list iff it was not created using this
+- * command batch.
++ * If the view wasn't created during this command batch, it might
++ * have been removed due to a context swapout, so add a
++ * relocation to conditionally make this command a NOP to avoid
++ * device errors.
+ */
+- return vmw_view_res_val_add(sw_context, view);
++ return vmw_resource_relocation_add(&sw_context->res_relocations,
++ view,
++ &cmd->header.id - sw_context->buf_start,
++ vmw_res_rel_cond_nop);
+ }
+
+ /**
+@@ -3848,14 +3892,14 @@ static void *vmw_execbuf_cmdbuf(struct vmw_private *dev_priv,
+ int ret;
+
+ *header = NULL;
+- if (!dev_priv->cman || kernel_commands)
+- return kernel_commands;
+-
+ if (command_size > SVGA_CB_MAX_SIZE) {
+ DRM_ERROR("Command buffer is too large.\n");
+ return ERR_PTR(-EINVAL);
+ }
+
++ if (!dev_priv->cman || kernel_commands)
++ return kernel_commands;
++
+ /* If possible, add a little space for fencing. */
+ cmdbuf_size = command_size + 512;
+ cmdbuf_size = min_t(size_t, cmdbuf_size, SVGA_CB_MAX_SIZE);
+diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h
+index 4ed9a4f..e92b09d 100644
+--- a/drivers/hid/hid-ids.h
++++ b/drivers/hid/hid-ids.h
+@@ -64,6 +64,9 @@
+ #define USB_VENDOR_ID_AKAI 0x2011
+ #define USB_DEVICE_ID_AKAI_MPKMINI2 0x0715
+
++#define USB_VENDOR_ID_AKAI_09E8 0x09E8
++#define USB_DEVICE_ID_AKAI_09E8_MIDIMIX 0x0031
++
+ #define USB_VENDOR_ID_ALCOR 0x058f
+ #define USB_DEVICE_ID_ALCOR_USBRS232 0x9720
+
+diff --git a/drivers/hid/usbhid/hid-quirks.c b/drivers/hid/usbhid/hid-quirks.c
+index b4b8c6a..bb40008 100644
+--- a/drivers/hid/usbhid/hid-quirks.c
++++ b/drivers/hid/usbhid/hid-quirks.c
+@@ -56,6 +56,7 @@ static const struct hid_blacklist {
+
+ { USB_VENDOR_ID_AIREN, USB_DEVICE_ID_AIREN_SLIMPLUS, HID_QUIRK_NOGET },
+ { USB_VENDOR_ID_AKAI, USB_DEVICE_ID_AKAI_MPKMINI2, HID_QUIRK_NO_INIT_REPORTS },
++ { USB_VENDOR_ID_AKAI_09E8, USB_DEVICE_ID_AKAI_09E8_MIDIMIX, HID_QUIRK_NO_INIT_REPORTS },
+ { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_UC100KM, HID_QUIRK_NOGET },
+ { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_CS124U, HID_QUIRK_NOGET },
+ { USB_VENDOR_ID_ATEN, USB_DEVICE_ID_ATEN_2PORTKVM, HID_QUIRK_NOGET },
+diff --git a/drivers/hwtracing/coresight/coresight-tmc.c b/drivers/hwtracing/coresight/coresight-tmc.c
+index 9e02ac9..3978cbb 100644
+--- a/drivers/hwtracing/coresight/coresight-tmc.c
++++ b/drivers/hwtracing/coresight/coresight-tmc.c
+@@ -388,9 +388,6 @@ static int tmc_probe(struct amba_device *adev, const struct amba_id *id)
+ err_misc_register:
+ coresight_unregister(drvdata->csdev);
+ err_devm_kzalloc:
+- if (drvdata->config_type == TMC_CONFIG_TYPE_ETR)
+- dma_free_coherent(dev, drvdata->size,
+- drvdata->vaddr, drvdata->paddr);
+ return ret;
+ }
+
+diff --git a/drivers/iio/dac/ad5755.c b/drivers/iio/dac/ad5755.c
+index 0fde593..5f79682 100644
+--- a/drivers/iio/dac/ad5755.c
++++ b/drivers/iio/dac/ad5755.c
+@@ -655,7 +655,7 @@ static struct ad5755_platform_data *ad5755_parse_dt(struct device *dev)
+
+ devnr = 0;
+ for_each_child_of_node(np, pp) {
+- if (devnr > AD5755_NUM_CHANNELS) {
++ if (devnr >= AD5755_NUM_CHANNELS) {
+ dev_err(dev,
+ "There is to many channels defined in DT\n");
+ goto error_out;
+diff --git a/drivers/iio/light/us5182d.c b/drivers/iio/light/us5182d.c
+index 20c40f7..18cf2e2 100644
+--- a/drivers/iio/light/us5182d.c
++++ b/drivers/iio/light/us5182d.c
+@@ -894,7 +894,7 @@ static int us5182d_probe(struct i2c_client *client,
+ goto out_err;
+
+ if (data->default_continuous) {
+- pm_runtime_set_active(&client->dev);
++ ret = pm_runtime_set_active(&client->dev);
+ if (ret < 0)
+ goto out_err;
+ }
+diff --git a/drivers/infiniband/hw/hfi1/qp.c b/drivers/infiniband/hw/hfi1/qp.c
+index 4e4d831..c17c9dd 100644
+--- a/drivers/infiniband/hw/hfi1/qp.c
++++ b/drivers/infiniband/hw/hfi1/qp.c
+@@ -808,6 +808,13 @@ void *qp_priv_alloc(struct rvt_dev_info *rdi, struct rvt_qp *qp,
+ kfree(priv);
+ return ERR_PTR(-ENOMEM);
+ }
++ iowait_init(
++ &priv->s_iowait,
++ 1,
++ _hfi1_do_send,
++ iowait_sleep,
++ iowait_wakeup,
++ iowait_sdma_drained);
+ setup_timer(&priv->s_rnr_timer, hfi1_rc_rnr_retry, (unsigned long)qp);
+ qp->s_timer.function = hfi1_rc_timeout;
+ return priv;
+@@ -873,13 +880,6 @@ void notify_qp_reset(struct rvt_qp *qp)
+ {
+ struct hfi1_qp_priv *priv = qp->priv;
+
+- iowait_init(
+- &priv->s_iowait,
+- 1,
+- _hfi1_do_send,
+- iowait_sleep,
+- iowait_wakeup,
+- iowait_sdma_drained);
+ priv->r_adefered = 0;
+ clear_ahg(qp);
+ }
+diff --git a/drivers/infiniband/hw/mlx5/main.c b/drivers/infiniband/hw/mlx5/main.c
+index e19537c..bff8707a 100644
+--- a/drivers/infiniband/hw/mlx5/main.c
++++ b/drivers/infiniband/hw/mlx5/main.c
+@@ -1843,6 +1843,7 @@ static struct mlx5_ib_flow_handler *create_leftovers_rule(struct mlx5_ib_dev *de
+ &leftovers_specs[LEFTOVERS_UC].flow_attr,
+ dst);
+ if (IS_ERR(handler_ucast)) {
++ mlx5_del_flow_rule(handler->rule);
+ kfree(handler);
+ handler = handler_ucast;
+ } else {
+diff --git a/drivers/infiniband/hw/qib/qib.h b/drivers/infiniband/hw/qib/qib.h
+index bbf0a16..54bb655f 100644
+--- a/drivers/infiniband/hw/qib/qib.h
++++ b/drivers/infiniband/hw/qib/qib.h
+@@ -1131,7 +1131,6 @@ extern spinlock_t qib_devs_lock;
+ extern struct qib_devdata *qib_lookup(int unit);
+ extern u32 qib_cpulist_count;
+ extern unsigned long *qib_cpulist;
+-extern u16 qpt_mask;
+ extern unsigned qib_cc_table_size;
+
+ int qib_init(struct qib_devdata *, int);
+diff --git a/drivers/infiniband/hw/qib/qib_qp.c b/drivers/infiniband/hw/qib/qib_qp.c
+index f9b8cd2..99d31ef 100644
+--- a/drivers/infiniband/hw/qib/qib_qp.c
++++ b/drivers/infiniband/hw/qib/qib_qp.c
+@@ -41,14 +41,6 @@
+
+ #include "qib.h"
+
+-/*
+- * mask field which was present in now deleted qib_qpn_table
+- * is not present in rvt_qpn_table. Defining the same field
+- * as qpt_mask here instead of adding the mask field to
+- * rvt_qpn_table.
+- */
+-u16 qpt_mask;
+-
+ static inline unsigned mk_qpn(struct rvt_qpn_table *qpt,
+ struct rvt_qpn_map *map, unsigned off)
+ {
+@@ -57,7 +49,7 @@ static inline unsigned mk_qpn(struct rvt_qpn_table *qpt,
+
+ static inline unsigned find_next_offset(struct rvt_qpn_table *qpt,
+ struct rvt_qpn_map *map, unsigned off,
+- unsigned n)
++ unsigned n, u16 qpt_mask)
+ {
+ if (qpt_mask) {
+ off++;
+@@ -179,6 +171,7 @@ int qib_alloc_qpn(struct rvt_dev_info *rdi, struct rvt_qpn_table *qpt,
+ struct qib_ibdev *verbs_dev = container_of(rdi, struct qib_ibdev, rdi);
+ struct qib_devdata *dd = container_of(verbs_dev, struct qib_devdata,
+ verbs_dev);
++ u16 qpt_mask = dd->qpn_mask;
+
+ if (type == IB_QPT_SMI || type == IB_QPT_GSI) {
+ unsigned n;
+@@ -215,7 +208,7 @@ int qib_alloc_qpn(struct rvt_dev_info *rdi, struct rvt_qpn_table *qpt,
+ goto bail;
+ }
+ offset = find_next_offset(qpt, map, offset,
+- dd->n_krcv_queues);
++ dd->n_krcv_queues, qpt_mask);
+ qpn = mk_qpn(qpt, map, offset);
+ /*
+ * This test differs from alloc_pidmap().
+diff --git a/drivers/infiniband/hw/qib/qib_verbs.c b/drivers/infiniband/hw/qib/qib_verbs.c
+index fd1dfbc..b2b845f 100644
+--- a/drivers/infiniband/hw/qib/qib_verbs.c
++++ b/drivers/infiniband/hw/qib/qib_verbs.c
+@@ -1606,8 +1606,6 @@ int qib_register_ib_device(struct qib_devdata *dd)
+ /* Only need to initialize non-zero fields. */
+ setup_timer(&dev->mem_timer, mem_timer, (unsigned long)dev);
+
+- qpt_mask = dd->qpn_mask;
+-
+ INIT_LIST_HEAD(&dev->piowait);
+ INIT_LIST_HEAD(&dev->dmawait);
+ INIT_LIST_HEAD(&dev->txwait);
+diff --git a/drivers/infiniband/sw/rdmavt/qp.c b/drivers/infiniband/sw/rdmavt/qp.c
+index 870b4f2..5911c53 100644
+--- a/drivers/infiniband/sw/rdmavt/qp.c
++++ b/drivers/infiniband/sw/rdmavt/qp.c
+@@ -501,12 +501,9 @@ static void rvt_remove_qp(struct rvt_dev_info *rdi, struct rvt_qp *qp)
+ */
+ static void rvt_reset_qp(struct rvt_dev_info *rdi, struct rvt_qp *qp,
+ enum ib_qp_type type)
+- __releases(&qp->s_lock)
+- __releases(&qp->s_hlock)
+- __releases(&qp->r_lock)
+- __acquires(&qp->r_lock)
+- __acquires(&qp->s_hlock)
+- __acquires(&qp->s_lock)
++ __must_hold(&qp->r_lock)
++ __must_hold(&qp->s_hlock)
++ __must_hold(&qp->s_lock)
+ {
+ if (qp->state != IB_QPS_RESET) {
+ qp->state = IB_QPS_RESET;
+diff --git a/drivers/net/ethernet/intel/i40e/i40e_client.c b/drivers/net/ethernet/intel/i40e/i40e_client.c
+index 618f184..c65e17f 100644
+--- a/drivers/net/ethernet/intel/i40e/i40e_client.c
++++ b/drivers/net/ethernet/intel/i40e/i40e_client.c
+@@ -1009,7 +1009,6 @@ int i40e_unregister_client(struct i40e_client *client)
+ if (!i40e_client_is_registered(client)) {
+ pr_info("i40e: Client %s has not been registered\n",
+ client->name);
+- mutex_unlock(&i40e_client_mutex);
+ ret = -ENODEV;
+ goto out;
+ }
+diff --git a/drivers/net/ethernet/intel/i40e/i40e_main.c b/drivers/net/ethernet/intel/i40e/i40e_main.c
+index dad15b6..c74d164 100644
+--- a/drivers/net/ethernet/intel/i40e/i40e_main.c
++++ b/drivers/net/ethernet/intel/i40e/i40e_main.c
+@@ -7990,45 +7990,34 @@ static int i40e_setup_misc_vector(struct i40e_pf *pf)
+ static int i40e_config_rss_aq(struct i40e_vsi *vsi, const u8 *seed,
+ u8 *lut, u16 lut_size)
+ {
+- struct i40e_aqc_get_set_rss_key_data rss_key;
+ struct i40e_pf *pf = vsi->back;
+ struct i40e_hw *hw = &pf->hw;
+- bool pf_lut = false;
+- u8 *rss_lut;
+- int ret, i;
+-
+- memcpy(&rss_key, seed, sizeof(rss_key));
+-
+- rss_lut = kzalloc(pf->rss_table_size, GFP_KERNEL);
+- if (!rss_lut)
+- return -ENOMEM;
+-
+- /* Populate the LUT with max no. of queues in round robin fashion */
+- for (i = 0; i < vsi->rss_table_size; i++)
+- rss_lut[i] = i % vsi->rss_size;
++ int ret = 0;
+
+- ret = i40e_aq_set_rss_key(hw, vsi->id, &rss_key);
+- if (ret) {
+- dev_info(&pf->pdev->dev,
+- "Cannot set RSS key, err %s aq_err %s\n",
+- i40e_stat_str(&pf->hw, ret),
+- i40e_aq_str(&pf->hw, pf->hw.aq.asq_last_status));
+- goto config_rss_aq_out;
++ if (seed) {
++ struct i40e_aqc_get_set_rss_key_data *seed_dw =
++ (struct i40e_aqc_get_set_rss_key_data *)seed;
++ ret = i40e_aq_set_rss_key(hw, vsi->id, seed_dw);
++ if (ret) {
++ dev_info(&pf->pdev->dev,
++ "Cannot set RSS key, err %s aq_err %s\n",
++ i40e_stat_str(hw, ret),
++ i40e_aq_str(hw, hw->aq.asq_last_status));
++ return ret;
++ }
+ }
++ if (lut) {
++ bool pf_lut = vsi->type == I40E_VSI_MAIN ? true : false;
+
+- if (vsi->type == I40E_VSI_MAIN)
+- pf_lut = true;
+-
+- ret = i40e_aq_set_rss_lut(hw, vsi->id, pf_lut, rss_lut,
+- vsi->rss_table_size);
+- if (ret)
+- dev_info(&pf->pdev->dev,
+- "Cannot set RSS lut, err %s aq_err %s\n",
+- i40e_stat_str(&pf->hw, ret),
+- i40e_aq_str(&pf->hw, pf->hw.aq.asq_last_status));
+-
+-config_rss_aq_out:
+- kfree(rss_lut);
++ ret = i40e_aq_set_rss_lut(hw, vsi->id, pf_lut, lut, lut_size);
++ if (ret) {
++ dev_info(&pf->pdev->dev,
++ "Cannot set RSS lut, err %s aq_err %s\n",
++ i40e_stat_str(hw, ret),
++ i40e_aq_str(hw, hw->aq.asq_last_status));
++ return ret;
++ }
++ }
+ return ret;
+ }
+
+diff --git a/drivers/net/wireless/ath/ath10k/htt_rx.c b/drivers/net/wireless/ath/ath10k/htt_rx.c
+index 24c8d65..09ca634 100644
+--- a/drivers/net/wireless/ath/ath10k/htt_rx.c
++++ b/drivers/net/wireless/ath/ath10k/htt_rx.c
+@@ -2394,6 +2394,8 @@ static void ath10k_htt_txrx_compl_task(unsigned long ptr)
+ skb_queue_splice_init(&htt->rx_in_ord_compl_q, &rx_ind_q);
+ spin_unlock_irqrestore(&htt->rx_in_ord_compl_q.lock, flags);
+
++ ath10k_mac_tx_push_pending(ar);
++
+ spin_lock_irqsave(&htt->tx_fetch_ind_q.lock, flags);
+ skb_queue_splice_init(&htt->tx_fetch_ind_q, &tx_ind_q);
+ spin_unlock_irqrestore(&htt->tx_fetch_ind_q.lock, flags);
+diff --git a/drivers/net/wireless/ath/ath10k/mac.c b/drivers/net/wireless/ath/ath10k/mac.c
+index 0bbd0a0..146365b 100644
+--- a/drivers/net/wireless/ath/ath10k/mac.c
++++ b/drivers/net/wireless/ath/ath10k/mac.c
+@@ -3777,7 +3777,9 @@ int ath10k_mac_tx_push_txq(struct ieee80211_hw *hw,
+ enum ath10k_hw_txrx_mode txmode;
+ enum ath10k_mac_tx_path txpath;
+ struct sk_buff *skb;
++ struct ieee80211_hdr *hdr;
+ size_t skb_len;
++ bool is_mgmt, is_presp;
+ int ret;
+
+ spin_lock_bh(&ar->htt.tx_lock);
+@@ -3801,6 +3803,22 @@ int ath10k_mac_tx_push_txq(struct ieee80211_hw *hw,
+ skb_len = skb->len;
+ txmode = ath10k_mac_tx_h_get_txmode(ar, vif, sta, skb);
+ txpath = ath10k_mac_tx_h_get_txpath(ar, skb, txmode);
++ is_mgmt = (txpath == ATH10K_MAC_TX_HTT_MGMT);
++
++ if (is_mgmt) {
++ hdr = (struct ieee80211_hdr *)skb->data;
++ is_presp = ieee80211_is_probe_resp(hdr->frame_control);
++
++ spin_lock_bh(&ar->htt.tx_lock);
++ ret = ath10k_htt_tx_mgmt_inc_pending(htt, is_mgmt, is_presp);
++
++ if (ret) {
++ ath10k_htt_tx_dec_pending(htt);
++ spin_unlock_bh(&ar->htt.tx_lock);
++ return ret;
++ }
++ spin_unlock_bh(&ar->htt.tx_lock);
++ }
+
+ ret = ath10k_mac_tx(ar, vif, sta, txmode, txpath, skb);
+ if (unlikely(ret)) {
+@@ -3808,6 +3826,8 @@ int ath10k_mac_tx_push_txq(struct ieee80211_hw *hw,
+
+ spin_lock_bh(&ar->htt.tx_lock);
+ ath10k_htt_tx_dec_pending(htt);
++ if (is_mgmt)
++ ath10k_htt_tx_mgmt_dec_pending(htt);
+ spin_unlock_bh(&ar->htt.tx_lock);
+
+ return ret;
+@@ -6538,7 +6558,7 @@ static int ath10k_get_survey(struct ieee80211_hw *hw, int idx,
+ goto exit;
+ }
+
+- ath10k_mac_update_bss_chan_survey(ar, survey->channel);
++ ath10k_mac_update_bss_chan_survey(ar, &sband->channels[idx]);
+
+ spin_lock_bh(&ar->data_lock);
+ memcpy(survey, ar_survey, sizeof(*survey));
+diff --git a/drivers/net/wireless/ath/ath10k/txrx.c b/drivers/net/wireless/ath/ath10k/txrx.c
+index b29a86a..28ff5cb 100644
+--- a/drivers/net/wireless/ath/ath10k/txrx.c
++++ b/drivers/net/wireless/ath/ath10k/txrx.c
+@@ -119,8 +119,6 @@ int ath10k_txrx_tx_unref(struct ath10k_htt *htt,
+ ieee80211_tx_status(htt->ar->hw, msdu);
+ /* we do not own the msdu anymore */
+
+- ath10k_mac_tx_push_pending(ar);
+-
+ return 0;
+ }
+
+diff --git a/drivers/net/wireless/ath/ath10k/wmi.h b/drivers/net/wireless/ath/ath10k/wmi.h
+index 3ef4688..f67cc19 100644
+--- a/drivers/net/wireless/ath/ath10k/wmi.h
++++ b/drivers/net/wireless/ath/ath10k/wmi.h
+@@ -180,6 +180,7 @@ enum wmi_service {
+ WMI_SERVICE_MESH_NON_11S,
+ WMI_SERVICE_PEER_STATS,
+ WMI_SERVICE_RESTRT_CHNL_SUPPORT,
++ WMI_SERVICE_PERIODIC_CHAN_STAT_SUPPORT,
+ WMI_SERVICE_TX_MODE_PUSH_ONLY,
+ WMI_SERVICE_TX_MODE_PUSH_PULL,
+ WMI_SERVICE_TX_MODE_DYNAMIC,
+@@ -305,6 +306,7 @@ enum wmi_10_4_service {
+ WMI_10_4_SERVICE_RESTRT_CHNL_SUPPORT,
+ WMI_10_4_SERVICE_PEER_STATS,
+ WMI_10_4_SERVICE_MESH_11S,
++ WMI_10_4_SERVICE_PERIODIC_CHAN_STAT_SUPPORT,
+ WMI_10_4_SERVICE_TX_MODE_PUSH_ONLY,
+ WMI_10_4_SERVICE_TX_MODE_PUSH_PULL,
+ WMI_10_4_SERVICE_TX_MODE_DYNAMIC,
+@@ -402,6 +404,7 @@ static inline char *wmi_service_name(int service_id)
+ SVCSTR(WMI_SERVICE_MESH_NON_11S);
+ SVCSTR(WMI_SERVICE_PEER_STATS);
+ SVCSTR(WMI_SERVICE_RESTRT_CHNL_SUPPORT);
++ SVCSTR(WMI_SERVICE_PERIODIC_CHAN_STAT_SUPPORT);
+ SVCSTR(WMI_SERVICE_TX_MODE_PUSH_ONLY);
+ SVCSTR(WMI_SERVICE_TX_MODE_PUSH_PULL);
+ SVCSTR(WMI_SERVICE_TX_MODE_DYNAMIC);
+@@ -652,6 +655,8 @@ static inline void wmi_10_4_svc_map(const __le32 *in, unsigned long *out,
+ WMI_SERVICE_PEER_STATS, len);
+ SVCMAP(WMI_10_4_SERVICE_MESH_11S,
+ WMI_SERVICE_MESH_11S, len);
++ SVCMAP(WMI_10_4_SERVICE_PERIODIC_CHAN_STAT_SUPPORT,
++ WMI_SERVICE_PERIODIC_CHAN_STAT_SUPPORT, len);
+ SVCMAP(WMI_10_4_SERVICE_TX_MODE_PUSH_ONLY,
+ WMI_SERVICE_TX_MODE_PUSH_ONLY, len);
+ SVCMAP(WMI_10_4_SERVICE_TX_MODE_PUSH_PULL,
+diff --git a/drivers/net/wireless/intel/iwlwifi/iwl-nvm-parse.c b/drivers/net/wireless/intel/iwlwifi/iwl-nvm-parse.c
+index 43f8f7d..adba3b0 100644
+--- a/drivers/net/wireless/intel/iwlwifi/iwl-nvm-parse.c
++++ b/drivers/net/wireless/intel/iwlwifi/iwl-nvm-parse.c
+@@ -564,11 +564,16 @@ static void iwl_set_hw_address_from_csr(struct iwl_trans *trans,
+ __le32 mac_addr0 = cpu_to_le32(iwl_read32(trans, CSR_MAC_ADDR0_STRAP));
+ __le32 mac_addr1 = cpu_to_le32(iwl_read32(trans, CSR_MAC_ADDR1_STRAP));
+
+- /* If OEM did not fuse address - get it from OTP */
+- if (!mac_addr0 && !mac_addr1) {
+- mac_addr0 = cpu_to_le32(iwl_read32(trans, CSR_MAC_ADDR0_OTP));
+- mac_addr1 = cpu_to_le32(iwl_read32(trans, CSR_MAC_ADDR1_OTP));
+- }
++ iwl_flip_hw_address(mac_addr0, mac_addr1, data->hw_addr);
++ /*
++ * If the OEM fused a valid address, use it instead of the one in the
++ * OTP
++ */
++ if (is_valid_ether_addr(data->hw_addr))
++ return;
++
++ mac_addr0 = cpu_to_le32(iwl_read32(trans, CSR_MAC_ADDR0_OTP));
++ mac_addr1 = cpu_to_le32(iwl_read32(trans, CSR_MAC_ADDR1_OTP));
+
+ iwl_flip_hw_address(mac_addr0, mac_addr1, data->hw_addr);
+ }
+diff --git a/drivers/net/wireless/intel/iwlwifi/mvm/fw.c b/drivers/net/wireless/intel/iwlwifi/mvm/fw.c
+index 7e0cdbf..794c574 100644
+--- a/drivers/net/wireless/intel/iwlwifi/mvm/fw.c
++++ b/drivers/net/wireless/intel/iwlwifi/mvm/fw.c
+@@ -1214,9 +1214,12 @@ int iwl_mvm_up(struct iwl_mvm *mvm)
+ }
+
+ /* TODO: read the budget from BIOS / Platform NVM */
+- if (iwl_mvm_is_ctdp_supported(mvm) && mvm->cooling_dev.cur_state > 0)
++ if (iwl_mvm_is_ctdp_supported(mvm) && mvm->cooling_dev.cur_state > 0) {
+ ret = iwl_mvm_ctdp_command(mvm, CTDP_CMD_OPERATION_START,
+ mvm->cooling_dev.cur_state);
++ if (ret)
++ goto error;
++ }
+ #else
+ /* Initialize tx backoffs to the minimal possible */
+ iwl_mvm_tt_tx_backoff(mvm, 0);
+diff --git a/drivers/net/wireless/intel/iwlwifi/mvm/mac-ctxt.c b/drivers/net/wireless/intel/iwlwifi/mvm/mac-ctxt.c
+index 69c42ce..d742d27 100644
+--- a/drivers/net/wireless/intel/iwlwifi/mvm/mac-ctxt.c
++++ b/drivers/net/wireless/intel/iwlwifi/mvm/mac-ctxt.c
+@@ -539,6 +539,11 @@ void iwl_mvm_mac_ctxt_release(struct iwl_mvm *mvm, struct ieee80211_vif *vif)
+ iwl_mvm_disable_txq(mvm, IWL_MVM_OFFCHANNEL_QUEUE,
+ IWL_MVM_OFFCHANNEL_QUEUE,
+ IWL_MAX_TID_COUNT, 0);
++ else
++ iwl_mvm_disable_txq(mvm,
++ IWL_MVM_DQA_P2P_DEVICE_QUEUE,
++ vif->hw_queue[0], IWL_MAX_TID_COUNT,
++ 0);
+
+ break;
+ case NL80211_IFTYPE_AP:
+diff --git a/drivers/net/wireless/intel/iwlwifi/mvm/rxmq.c b/drivers/net/wireless/intel/iwlwifi/mvm/rxmq.c
+index df6c32c..afb7eb6 100644
+--- a/drivers/net/wireless/intel/iwlwifi/mvm/rxmq.c
++++ b/drivers/net/wireless/intel/iwlwifi/mvm/rxmq.c
+@@ -598,9 +598,10 @@ static bool iwl_mvm_reorder(struct iwl_mvm *mvm,
+
+ mvm_sta = iwl_mvm_sta_from_mac80211(sta);
+
+- /* not a data packet */
+- if (!ieee80211_is_data_qos(hdr->frame_control) ||
+- is_multicast_ether_addr(hdr->addr1))
++ /* not a data packet or a bar */
++ if (!ieee80211_is_back_req(hdr->frame_control) &&
++ (!ieee80211_is_data_qos(hdr->frame_control) ||
++ is_multicast_ether_addr(hdr->addr1)))
+ return false;
+
+ if (unlikely(!ieee80211_is_data_present(hdr->frame_control)))
+@@ -624,6 +625,11 @@ static bool iwl_mvm_reorder(struct iwl_mvm *mvm,
+
+ spin_lock_bh(&buffer->lock);
+
++ if (ieee80211_is_back_req(hdr->frame_control)) {
++ iwl_mvm_release_frames(mvm, sta, napi, buffer, nssn);
++ goto drop;
++ }
++
+ /*
+ * If there was a significant jump in the nssn - adjust.
+ * If the SN is smaller than the NSSN it might need to first go into
+diff --git a/drivers/net/wireless/intel/iwlwifi/mvm/sta.c b/drivers/net/wireless/intel/iwlwifi/mvm/sta.c
+index 3130b9c..e933c12 100644
+--- a/drivers/net/wireless/intel/iwlwifi/mvm/sta.c
++++ b/drivers/net/wireless/intel/iwlwifi/mvm/sta.c
+@@ -576,9 +576,7 @@ static int iwl_mvm_scd_queue_redirect(struct iwl_mvm *mvm, int queue, int tid,
+ ret);
+
+ /* Make sure the SCD wrptr is correctly set before reconfiguring */
+- iwl_trans_txq_enable(mvm->trans, queue, iwl_mvm_ac_to_tx_fifo[ac],
+- cmd.sta_id, tid, LINK_QUAL_AGG_FRAME_LIMIT_DEF,
+- ssn, wdg_timeout);
++ iwl_trans_txq_enable_cfg(mvm->trans, queue, ssn, NULL, wdg_timeout);
+
+ /* TODO: Work-around SCD bug when moving back by multiples of 0x40 */
+
+@@ -1270,9 +1268,31 @@ int iwl_mvm_rm_sta(struct iwl_mvm *mvm,
+ ret = iwl_mvm_drain_sta(mvm, mvm_sta, false);
+
+ /* If DQA is supported - the queues can be disabled now */
+- if (iwl_mvm_is_dqa_supported(mvm))
++ if (iwl_mvm_is_dqa_supported(mvm)) {
++ u8 reserved_txq = mvm_sta->reserved_queue;
++ enum iwl_mvm_queue_status *status;
++
+ iwl_mvm_disable_sta_queues(mvm, vif, mvm_sta);
+
++ /*
++ * If no traffic has gone through the reserved TXQ - it
++ * is still marked as IWL_MVM_QUEUE_RESERVED, and
++ * should be manually marked as free again
++ */
++ spin_lock_bh(&mvm->queue_info_lock);
++ status = &mvm->queue_info[reserved_txq].status;
++ if (WARN((*status != IWL_MVM_QUEUE_RESERVED) &&
++ (*status != IWL_MVM_QUEUE_FREE),
++ "sta_id %d reserved txq %d status %d",
++ mvm_sta->sta_id, reserved_txq, *status)) {
++ spin_unlock_bh(&mvm->queue_info_lock);
++ return -EINVAL;
++ }
++
++ *status = IWL_MVM_QUEUE_FREE;
++ spin_unlock_bh(&mvm->queue_info_lock);
++ }
++
+ if (vif->type == NL80211_IFTYPE_STATION &&
+ mvmvif->ap_sta_id == mvm_sta->sta_id) {
+ /* if associated - we can't remove the AP STA now */
+diff --git a/drivers/net/wireless/intel/iwlwifi/mvm/tx.c b/drivers/net/wireless/intel/iwlwifi/mvm/tx.c
+index b3a87a3..a0c1e3d 100644
+--- a/drivers/net/wireless/intel/iwlwifi/mvm/tx.c
++++ b/drivers/net/wireless/intel/iwlwifi/mvm/tx.c
+@@ -903,9 +903,13 @@ static int iwl_mvm_tx_mpdu(struct iwl_mvm *mvm, struct sk_buff *skb,
+ tid = IWL_MAX_TID_COUNT;
+ }
+
+- if (iwl_mvm_is_dqa_supported(mvm))
++ if (iwl_mvm_is_dqa_supported(mvm)) {
+ txq_id = mvmsta->tid_data[tid].txq_id;
+
++ if (ieee80211_is_mgmt(fc))
++ tx_cmd->tid_tspec = IWL_TID_NON_QOS;
++ }
++
+ /* Copy MAC header from skb into command buffer */
+ memcpy(tx_cmd->hdr, hdr, hdrlen);
+
+diff --git a/drivers/net/wireless/marvell/mwifiex/join.c b/drivers/net/wireless/marvell/mwifiex/join.c
+index 1c7b006..b89596c 100644
+--- a/drivers/net/wireless/marvell/mwifiex/join.c
++++ b/drivers/net/wireless/marvell/mwifiex/join.c
+@@ -669,9 +669,8 @@ int mwifiex_ret_802_11_associate(struct mwifiex_private *priv,
+ priv->assoc_rsp_size = min(le16_to_cpu(resp->size) - S_DS_GEN,
+ sizeof(priv->assoc_rsp_buf));
+
+- memcpy(priv->assoc_rsp_buf, &resp->params, priv->assoc_rsp_size);
+-
+ assoc_rsp->a_id = cpu_to_le16(aid);
++ memcpy(priv->assoc_rsp_buf, &resp->params, priv->assoc_rsp_size);
+
+ if (status_code) {
+ priv->adapter->dbg.num_cmd_assoc_failure++;
+diff --git a/drivers/net/wireless/marvell/mwifiex/sta_event.c b/drivers/net/wireless/marvell/mwifiex/sta_event.c
+index a422f33..7e394d4 100644
+--- a/drivers/net/wireless/marvell/mwifiex/sta_event.c
++++ b/drivers/net/wireless/marvell/mwifiex/sta_event.c
+@@ -708,7 +708,11 @@ int mwifiex_process_sta_event(struct mwifiex_private *priv)
+
+ case EVENT_EXT_SCAN_REPORT:
+ mwifiex_dbg(adapter, EVENT, "event: EXT_SCAN Report\n");
+- if (adapter->ext_scan && !priv->scan_aborting)
++ /* We intend to skip this event during suspend, but handle
++ * it in interface disabled case
++ */
++ if (adapter->ext_scan && (!priv->scan_aborting ||
++ !netif_running(priv->netdev)))
+ ret = mwifiex_handle_event_ext_scan_report(priv,
+ adapter->event_skb->data);
+
+diff --git a/drivers/net/wireless/ralink/rt2x00/rt2x00usb.c b/drivers/net/wireless/ralink/rt2x00/rt2x00usb.c
+index 7cf26c6..6005e14 100644
+--- a/drivers/net/wireless/ralink/rt2x00/rt2x00usb.c
++++ b/drivers/net/wireless/ralink/rt2x00/rt2x00usb.c
+@@ -831,8 +831,10 @@ int rt2x00usb_probe(struct usb_interface *usb_intf,
+ rt2x00dev->anchor = devm_kmalloc(&usb_dev->dev,
+ sizeof(struct usb_anchor),
+ GFP_KERNEL);
+- if (!rt2x00dev->anchor)
++ if (!rt2x00dev->anchor) {
++ retval = -ENOMEM;
+ goto exit_free_reg;
++ }
+
+ init_usb_anchor(rt2x00dev->anchor);
+ return 0;
+diff --git a/drivers/nvdimm/bus.c b/drivers/nvdimm/bus.c
+index 935866f..a8b6949 100644
+--- a/drivers/nvdimm/bus.c
++++ b/drivers/nvdimm/bus.c
+@@ -217,6 +217,8 @@ long nvdimm_clear_poison(struct device *dev, phys_addr_t phys,
+ return rc;
+ if (cmd_rc < 0)
+ return cmd_rc;
++
++ nvdimm_clear_from_poison_list(nvdimm_bus, phys, len);
+ return clear_err.cleared;
+ }
+ EXPORT_SYMBOL_GPL(nvdimm_clear_poison);
+diff --git a/drivers/nvdimm/core.c b/drivers/nvdimm/core.c
+index 4d7bbd2..7ceba08 100644
+--- a/drivers/nvdimm/core.c
++++ b/drivers/nvdimm/core.c
+@@ -547,11 +547,12 @@ void nvdimm_badblocks_populate(struct nd_region *nd_region,
+ }
+ EXPORT_SYMBOL_GPL(nvdimm_badblocks_populate);
+
+-static int add_poison(struct nvdimm_bus *nvdimm_bus, u64 addr, u64 length)
++static int add_poison(struct nvdimm_bus *nvdimm_bus, u64 addr, u64 length,
++ gfp_t flags)
+ {
+ struct nd_poison *pl;
+
+- pl = kzalloc(sizeof(*pl), GFP_KERNEL);
++ pl = kzalloc(sizeof(*pl), flags);
+ if (!pl)
+ return -ENOMEM;
+
+@@ -567,7 +568,7 @@ static int bus_add_poison(struct nvdimm_bus *nvdimm_bus, u64 addr, u64 length)
+ struct nd_poison *pl;
+
+ if (list_empty(&nvdimm_bus->poison_list))
+- return add_poison(nvdimm_bus, addr, length);
++ return add_poison(nvdimm_bus, addr, length, GFP_KERNEL);
+
+ /*
+ * There is a chance this is a duplicate, check for those first.
+@@ -587,7 +588,7 @@ static int bus_add_poison(struct nvdimm_bus *nvdimm_bus, u64 addr, u64 length)
+ * as any overlapping ranges will get resolved when the list is consumed
+ * and converted to badblocks
+ */
+- return add_poison(nvdimm_bus, addr, length);
++ return add_poison(nvdimm_bus, addr, length, GFP_KERNEL);
+ }
+
+ int nvdimm_bus_add_poison(struct nvdimm_bus *nvdimm_bus, u64 addr, u64 length)
+@@ -602,6 +603,70 @@ int nvdimm_bus_add_poison(struct nvdimm_bus *nvdimm_bus, u64 addr, u64 length)
+ }
+ EXPORT_SYMBOL_GPL(nvdimm_bus_add_poison);
+
++void nvdimm_clear_from_poison_list(struct nvdimm_bus *nvdimm_bus,
++ phys_addr_t start, unsigned int len)
++{
++ struct list_head *poison_list = &nvdimm_bus->poison_list;
++ u64 clr_end = start + len - 1;
++ struct nd_poison *pl, *next;
++
++ nvdimm_bus_lock(&nvdimm_bus->dev);
++ WARN_ON_ONCE(list_empty(poison_list));
++
++ /*
++ * [start, clr_end] is the poison interval being cleared.
++ * [pl->start, pl_end] is the poison_list entry we're comparing
++ * the above interval against. The poison list entry may need
++ * to be modified (update either start or length), deleted, or
++ * split into two based on the overlap characteristics
++ */
++
++ list_for_each_entry_safe(pl, next, poison_list, list) {
++ u64 pl_end = pl->start + pl->length - 1;
++
++ /* Skip intervals with no intersection */
++ if (pl_end < start)
++ continue;
++ if (pl->start > clr_end)
++ continue;
++ /* Delete completely overlapped poison entries */
++ if ((pl->start >= start) && (pl_end <= clr_end)) {
++ list_del(&pl->list);
++ kfree(pl);
++ continue;
++ }
++ /* Adjust start point of partially cleared entries */
++ if ((start <= pl->start) && (clr_end > pl->start)) {
++ pl->length -= clr_end - pl->start + 1;
++ pl->start = clr_end + 1;
++ continue;
++ }
++ /* Adjust pl->length for partial clearing at the tail end */
++ if ((pl->start < start) && (pl_end <= clr_end)) {
++ /* pl->start remains the same */
++ pl->length = start - pl->start;
++ continue;
++ }
++ /*
++ * If clearing in the middle of an entry, we split it into
++ * two by modifying the current entry to represent one half of
++ * the split, and adding a new entry for the second half.
++ */
++ if ((pl->start < start) && (pl_end > clr_end)) {
++ u64 new_start = clr_end + 1;
++ u64 new_len = pl_end - new_start + 1;
++
++ /* Add new entry covering the right half */
++ add_poison(nvdimm_bus, new_start, new_len, GFP_NOIO);
++ /* Adjust this entry to cover the left half */
++ pl->length = start - pl->start;
++ continue;
++ }
++ }
++ nvdimm_bus_unlock(&nvdimm_bus->dev);
++}
++EXPORT_SYMBOL_GPL(nvdimm_clear_from_poison_list);
++
+ #ifdef CONFIG_BLK_DEV_INTEGRITY
+ int nd_integrity_init(struct gendisk *disk, unsigned long meta_size)
+ {
+diff --git a/drivers/pci/host/pci-aardvark.c b/drivers/pci/host/pci-aardvark.c
+index ef9893f..4f5e567 100644
+--- a/drivers/pci/host/pci-aardvark.c
++++ b/drivers/pci/host/pci-aardvark.c
+@@ -848,7 +848,7 @@ static int advk_pcie_parse_request_of_pci_ranges(struct advk_pcie *pcie)
+ int err, res_valid = 0;
+ struct device *dev = &pcie->pdev->dev;
+ struct device_node *np = dev->of_node;
+- struct resource_entry *win;
++ struct resource_entry *win, *tmp;
+ resource_size_t iobase;
+
+ INIT_LIST_HEAD(&pcie->resources);
+@@ -862,7 +862,7 @@ static int advk_pcie_parse_request_of_pci_ranges(struct advk_pcie *pcie)
+ if (err)
+ goto out_release_res;
+
+- resource_list_for_each_entry(win, &pcie->resources) {
++ resource_list_for_each_entry_safe(win, tmp, &pcie->resources) {
+ struct resource *res = win->res;
+
+ switch (resource_type(res)) {
+@@ -874,9 +874,11 @@ static int advk_pcie_parse_request_of_pci_ranges(struct advk_pcie *pcie)
+ lower_32_bits(res->start),
+ OB_PCIE_IO);
+ err = pci_remap_iospace(res, iobase);
+- if (err)
++ if (err) {
+ dev_warn(dev, "error %d: failed to map resource %pR\n",
+ err, res);
++ resource_list_destroy_entry(win);
++ }
+ break;
+ case IORESOURCE_MEM:
+ advk_pcie_set_ob_win(pcie, 0,
+diff --git a/drivers/pci/host/pci-host-common.c b/drivers/pci/host/pci-host-common.c
+index 9d9d34e..61eb4d4 100644
+--- a/drivers/pci/host/pci-host-common.c
++++ b/drivers/pci/host/pci-host-common.c
+@@ -29,7 +29,7 @@ static int gen_pci_parse_request_of_pci_ranges(struct device *dev,
+ int err, res_valid = 0;
+ struct device_node *np = dev->of_node;
+ resource_size_t iobase;
+- struct resource_entry *win;
++ struct resource_entry *win, *tmp;
+
+ err = of_pci_get_host_bridge_resources(np, 0, 0xff, resources, &iobase);
+ if (err)
+@@ -39,15 +39,17 @@ static int gen_pci_parse_request_of_pci_ranges(struct device *dev,
+ if (err)
+ return err;
+
+- resource_list_for_each_entry(win, resources) {
++ resource_list_for_each_entry_safe(win, tmp, resources) {
+ struct resource *res = win->res;
+
+ switch (resource_type(res)) {
+ case IORESOURCE_IO:
+ err = pci_remap_iospace(res, iobase);
+- if (err)
++ if (err) {
+ dev_warn(dev, "error %d: failed to map resource %pR\n",
+ err, res);
++ resource_list_destroy_entry(win);
++ }
+ break;
+ case IORESOURCE_MEM:
+ res_valid |= !(res->flags & IORESOURCE_PREFETCH);
+diff --git a/drivers/pci/host/pci-tegra.c b/drivers/pci/host/pci-tegra.c
+index 84d650d..7ec1e80 100644
+--- a/drivers/pci/host/pci-tegra.c
++++ b/drivers/pci/host/pci-tegra.c
+@@ -621,7 +621,11 @@ static int tegra_pcie_setup(int nr, struct pci_sys_data *sys)
+ if (err < 0)
+ return err;
+
+- pci_add_resource_offset(&sys->resources, &pcie->pio, sys->io_offset);
++ err = pci_remap_iospace(&pcie->pio, pcie->io.start);
++ if (!err)
++ pci_add_resource_offset(&sys->resources, &pcie->pio,
++ sys->io_offset);
++
+ pci_add_resource_offset(&sys->resources, &pcie->mem, sys->mem_offset);
+ pci_add_resource_offset(&sys->resources, &pcie->prefetch,
+ sys->mem_offset);
+@@ -631,7 +635,6 @@ static int tegra_pcie_setup(int nr, struct pci_sys_data *sys)
+ if (err < 0)
+ return err;
+
+- pci_remap_iospace(&pcie->pio, pcie->io.start);
+ return 1;
+ }
+
+diff --git a/drivers/pci/host/pci-versatile.c b/drivers/pci/host/pci-versatile.c
+index f2344057..b7dc070 100644
+--- a/drivers/pci/host/pci-versatile.c
++++ b/drivers/pci/host/pci-versatile.c
+@@ -74,7 +74,7 @@ static int versatile_pci_parse_request_of_pci_ranges(struct device *dev,
+ int err, mem = 1, res_valid = 0;
+ struct device_node *np = dev->of_node;
+ resource_size_t iobase;
+- struct resource_entry *win;
++ struct resource_entry *win, *tmp;
+
+ err = of_pci_get_host_bridge_resources(np, 0, 0xff, res, &iobase);
+ if (err)
+@@ -84,15 +84,17 @@ static int versatile_pci_parse_request_of_pci_ranges(struct device *dev,
+ if (err)
+ goto out_release_res;
+
+- resource_list_for_each_entry(win, res) {
++ resource_list_for_each_entry_safe(win, tmp, res) {
+ struct resource *res = win->res;
+
+ switch (resource_type(res)) {
+ case IORESOURCE_IO:
+ err = pci_remap_iospace(res, iobase);
+- if (err)
++ if (err) {
+ dev_warn(dev, "error %d: failed to map resource %pR\n",
+ err, res);
++ resource_list_destroy_entry(win);
++ }
+ break;
+ case IORESOURCE_MEM:
+ res_valid |= !(res->flags & IORESOURCE_PREFETCH);
+diff --git a/drivers/pci/host/pcie-designware.c b/drivers/pci/host/pcie-designware.c
+index 12afce1..2a500f2 100644
+--- a/drivers/pci/host/pcie-designware.c
++++ b/drivers/pci/host/pcie-designware.c
+@@ -436,7 +436,7 @@ int dw_pcie_host_init(struct pcie_port *pp)
+ struct resource *cfg_res;
+ int i, ret;
+ LIST_HEAD(res);
+- struct resource_entry *win;
++ struct resource_entry *win, *tmp;
+
+ cfg_res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "config");
+ if (cfg_res) {
+@@ -457,17 +457,20 @@ int dw_pcie_host_init(struct pcie_port *pp)
+ goto error;
+
+ /* Get the I/O and memory ranges from DT */
+- resource_list_for_each_entry(win, &res) {
++ resource_list_for_each_entry_safe(win, tmp, &res) {
+ switch (resource_type(win->res)) {
+ case IORESOURCE_IO:
+- pp->io = win->res;
+- pp->io->name = "I/O";
+- pp->io_size = resource_size(pp->io);
+- pp->io_bus_addr = pp->io->start - win->offset;
+- ret = pci_remap_iospace(pp->io, pp->io_base);
+- if (ret)
++ ret = pci_remap_iospace(win->res, pp->io_base);
++ if (ret) {
+ dev_warn(pp->dev, "error %d: failed to map resource %pR\n",
+- ret, pp->io);
++ ret, win->res);
++ resource_list_destroy_entry(win);
++ } else {
++ pp->io = win->res;
++ pp->io->name = "I/O";
++ pp->io_size = resource_size(pp->io);
++ pp->io_bus_addr = pp->io->start - win->offset;
++ }
+ break;
+ case IORESOURCE_MEM:
+ pp->mem = win->res;
+diff --git a/drivers/pci/host/pcie-rcar.c b/drivers/pci/host/pcie-rcar.c
+index 65db7a2..5f7fcc9 100644
+--- a/drivers/pci/host/pcie-rcar.c
++++ b/drivers/pci/host/pcie-rcar.c
+@@ -945,7 +945,7 @@ static int rcar_pcie_parse_request_of_pci_ranges(struct rcar_pcie *pci)
+ struct device *dev = pci->dev;
+ struct device_node *np = dev->of_node;
+ resource_size_t iobase;
+- struct resource_entry *win;
++ struct resource_entry *win, *tmp;
+
+ err = of_pci_get_host_bridge_resources(np, 0, 0xff, &pci->resources, &iobase);
+ if (err)
+@@ -955,14 +955,17 @@ static int rcar_pcie_parse_request_of_pci_ranges(struct rcar_pcie *pci)
+ if (err)
+ goto out_release_res;
+
+- resource_list_for_each_entry(win, &pci->resources) {
++ resource_list_for_each_entry_safe(win, tmp, &pci->resources) {
+ struct resource *res = win->res;
+
+ if (resource_type(res) == IORESOURCE_IO) {
+ err = pci_remap_iospace(res, iobase);
+- if (err)
++ if (err) {
+ dev_warn(dev, "error %d: failed to map resource %pR\n",
+ err, res);
++
++ resource_list_destroy_entry(win);
++ }
+ }
+ }
+
+diff --git a/drivers/pinctrl/qcom/pinctrl-msm.c b/drivers/pinctrl/qcom/pinctrl-msm.c
+index 51c42d7..775c883 100644
+--- a/drivers/pinctrl/qcom/pinctrl-msm.c
++++ b/drivers/pinctrl/qcom/pinctrl-msm.c
+@@ -156,7 +156,7 @@ static int msm_pinmux_set_mux(struct pinctrl_dev *pctldev,
+ spin_lock_irqsave(&pctrl->lock, flags);
+
+ val = readl(pctrl->regs + g->ctl_reg);
+- val &= mask;
++ val &= ~mask;
+ val |= i << g->mux_bit;
+ writel(val, pctrl->regs + g->ctl_reg);
+
+diff --git a/drivers/power/bq24257_charger.c b/drivers/power/bq24257_charger.c
+index 1fea2c7..6fc31bd 100644
+--- a/drivers/power/bq24257_charger.c
++++ b/drivers/power/bq24257_charger.c
+@@ -1068,6 +1068,12 @@ static int bq24257_probe(struct i2c_client *client,
+ return ret;
+ }
+
++ ret = bq24257_power_supply_init(bq);
++ if (ret < 0) {
++ dev_err(dev, "Failed to register power supply\n");
++ return ret;
++ }
++
+ ret = devm_request_threaded_irq(dev, client->irq, NULL,
+ bq24257_irq_handler_thread,
+ IRQF_TRIGGER_FALLING |
+@@ -1078,12 +1084,6 @@ static int bq24257_probe(struct i2c_client *client,
+ return ret;
+ }
+
+- ret = bq24257_power_supply_init(bq);
+- if (ret < 0) {
+- dev_err(dev, "Failed to register power supply\n");
+- return ret;
+- }
+-
+ ret = sysfs_create_group(&bq->charger->dev.kobj, &bq24257_attr_group);
+ if (ret < 0) {
+ dev_err(dev, "Can't create sysfs entries\n");
+diff --git a/drivers/s390/char/con3270.c b/drivers/s390/char/con3270.c
+index 6b1577c..285b400 100644
+--- a/drivers/s390/char/con3270.c
++++ b/drivers/s390/char/con3270.c
+@@ -124,7 +124,12 @@ con3270_create_status(struct con3270 *cp)
+ static void
+ con3270_update_string(struct con3270 *cp, struct string *s, int nr)
+ {
+- if (s->len >= cp->view.cols - 5)
++ if (s->len < 4) {
++ /* This indicates a bug, but printing a warning would
++ * cause a deadlock. */
++ return;
++ }
++ if (s->string[s->len - 4] != TO_RA)
+ return;
+ raw3270_buffer_address(cp->view.dev, s->string + s->len - 3,
+ cp->view.cols * (nr + 1));
+@@ -460,11 +465,11 @@ con3270_cline_end(struct con3270 *cp)
+ cp->cline->len + 4 : cp->view.cols;
+ s = con3270_alloc_string(cp, size);
+ memcpy(s->string, cp->cline->string, cp->cline->len);
+- if (s->len < cp->view.cols - 5) {
++ if (cp->cline->len < cp->view.cols - 5) {
+ s->string[s->len - 4] = TO_RA;
+ s->string[s->len - 1] = 0;
+ } else {
+- while (--size > cp->cline->len)
++ while (--size >= cp->cline->len)
+ s->string[size] = cp->view.ascebc[' '];
+ }
+ /* Replace cline with allocated line s and reset cline. */
+diff --git a/drivers/s390/cio/chsc.c b/drivers/s390/cio/chsc.c
+index 940e725..1167469 100644
+--- a/drivers/s390/cio/chsc.c
++++ b/drivers/s390/cio/chsc.c
+@@ -95,12 +95,13 @@ struct chsc_ssd_area {
+ int chsc_get_ssd_info(struct subchannel_id schid, struct chsc_ssd_info *ssd)
+ {
+ struct chsc_ssd_area *ssd_area;
++ unsigned long flags;
+ int ccode;
+ int ret;
+ int i;
+ int mask;
+
+- spin_lock_irq(&chsc_page_lock);
++ spin_lock_irqsave(&chsc_page_lock, flags);
+ memset(chsc_page, 0, PAGE_SIZE);
+ ssd_area = chsc_page;
+ ssd_area->request.length = 0x0010;
+@@ -144,7 +145,7 @@ int chsc_get_ssd_info(struct subchannel_id schid, struct chsc_ssd_info *ssd)
+ ssd->fla[i] = ssd_area->fla[i];
+ }
+ out:
+- spin_unlock_irq(&chsc_page_lock);
++ spin_unlock_irqrestore(&chsc_page_lock, flags);
+ return ret;
+ }
+
+@@ -832,9 +833,10 @@ int __chsc_do_secm(struct channel_subsystem *css, int enable)
+ u32 fmt : 4;
+ u32 : 16;
+ } __attribute__ ((packed)) *secm_area;
++ unsigned long flags;
+ int ret, ccode;
+
+- spin_lock_irq(&chsc_page_lock);
++ spin_lock_irqsave(&chsc_page_lock, flags);
+ memset(chsc_page, 0, PAGE_SIZE);
+ secm_area = chsc_page;
+ secm_area->request.length = 0x0050;
+@@ -864,7 +866,7 @@ int __chsc_do_secm(struct channel_subsystem *css, int enable)
+ CIO_CRW_EVENT(2, "chsc: secm failed (rc=%04x)\n",
+ secm_area->response.code);
+ out:
+- spin_unlock_irq(&chsc_page_lock);
++ spin_unlock_irqrestore(&chsc_page_lock, flags);
+ return ret;
+ }
+
+@@ -992,6 +994,7 @@ chsc_initialize_cmg_chars(struct channel_path *chp, u8 cmcv,
+
+ int chsc_get_channel_measurement_chars(struct channel_path *chp)
+ {
++ unsigned long flags;
+ int ccode, ret;
+
+ struct {
+@@ -1021,7 +1024,7 @@ int chsc_get_channel_measurement_chars(struct channel_path *chp)
+ if (!css_chsc_characteristics.scmc || !css_chsc_characteristics.secm)
+ return -EINVAL;
+
+- spin_lock_irq(&chsc_page_lock);
++ spin_lock_irqsave(&chsc_page_lock, flags);
+ memset(chsc_page, 0, PAGE_SIZE);
+ scmc_area = chsc_page;
+ scmc_area->request.length = 0x0010;
+@@ -1053,7 +1056,7 @@ int chsc_get_channel_measurement_chars(struct channel_path *chp)
+ chsc_initialize_cmg_chars(chp, scmc_area->cmcv,
+ (struct cmg_chars *) &scmc_area->data);
+ out:
+- spin_unlock_irq(&chsc_page_lock);
++ spin_unlock_irqrestore(&chsc_page_lock, flags);
+ return ret;
+ }
+
+@@ -1134,6 +1137,7 @@ struct css_chsc_char css_chsc_characteristics;
+ int __init
+ chsc_determine_css_characteristics(void)
+ {
++ unsigned long flags;
+ int result;
+ struct {
+ struct chsc_header request;
+@@ -1146,7 +1150,7 @@ chsc_determine_css_characteristics(void)
+ u32 chsc_char[508];
+ } __attribute__ ((packed)) *scsc_area;
+
+- spin_lock_irq(&chsc_page_lock);
++ spin_lock_irqsave(&chsc_page_lock, flags);
+ memset(chsc_page, 0, PAGE_SIZE);
+ scsc_area = chsc_page;
+ scsc_area->request.length = 0x0010;
+@@ -1168,7 +1172,7 @@ chsc_determine_css_characteristics(void)
+ CIO_CRW_EVENT(2, "chsc: scsc failed (rc=%04x)\n",
+ scsc_area->response.code);
+ exit:
+- spin_unlock_irq(&chsc_page_lock);
++ spin_unlock_irqrestore(&chsc_page_lock, flags);
+ return result;
+ }
+
+diff --git a/drivers/scsi/cxlflash/main.c b/drivers/scsi/cxlflash/main.c
+index 661bb94..228b99e 100644
+--- a/drivers/scsi/cxlflash/main.c
++++ b/drivers/scsi/cxlflash/main.c
+@@ -823,17 +823,6 @@ static void notify_shutdown(struct cxlflash_cfg *cfg, bool wait)
+ }
+
+ /**
+- * cxlflash_shutdown() - shutdown handler
+- * @pdev: PCI device associated with the host.
+- */
+-static void cxlflash_shutdown(struct pci_dev *pdev)
+-{
+- struct cxlflash_cfg *cfg = pci_get_drvdata(pdev);
+-
+- notify_shutdown(cfg, false);
+-}
+-
+-/**
+ * cxlflash_remove() - PCI entry point to tear down host
+ * @pdev: PCI device associated with the host.
+ *
+@@ -844,6 +833,11 @@ static void cxlflash_remove(struct pci_dev *pdev)
+ struct cxlflash_cfg *cfg = pci_get_drvdata(pdev);
+ ulong lock_flags;
+
++ if (!pci_is_enabled(pdev)) {
++ pr_debug("%s: Device is disabled\n", __func__);
++ return;
++ }
++
+ /* If a Task Management Function is active, wait for it to complete
+ * before continuing with remove.
+ */
+@@ -2685,7 +2679,7 @@ static struct pci_driver cxlflash_driver = {
+ .id_table = cxlflash_pci_table,
+ .probe = cxlflash_probe,
+ .remove = cxlflash_remove,
+- .shutdown = cxlflash_shutdown,
++ .shutdown = cxlflash_remove,
+ .err_handler = &cxlflash_err_handler,
+ };
+
+diff --git a/drivers/scsi/mpt3sas/mpt3sas_scsih.c b/drivers/scsi/mpt3sas/mpt3sas_scsih.c
+index cd91a68..4cb7990 100644
+--- a/drivers/scsi/mpt3sas/mpt3sas_scsih.c
++++ b/drivers/scsi/mpt3sas/mpt3sas_scsih.c
+@@ -4701,7 +4701,7 @@ _scsih_io_done(struct MPT3SAS_ADAPTER *ioc, u16 smid, u8 msix_index, u32 reply)
+ le16_to_cpu(mpi_reply->DevHandle));
+ mpt3sas_trigger_scsi(ioc, data.skey, data.asc, data.ascq);
+
+- if (!(ioc->logging_level & MPT_DEBUG_REPLY) &&
++ if ((ioc->logging_level & MPT_DEBUG_REPLY) &&
+ ((scmd->sense_buffer[2] == UNIT_ATTENTION) ||
+ (scmd->sense_buffer[2] == MEDIUM_ERROR) ||
+ (scmd->sense_buffer[2] == HARDWARE_ERROR)))
+diff --git a/drivers/spi/spi-fsl-dspi.c b/drivers/spi/spi-fsl-dspi.c
+index 9e9dadb..eec5e3f 100644
+--- a/drivers/spi/spi-fsl-dspi.c
++++ b/drivers/spi/spi-fsl-dspi.c
+@@ -760,7 +760,6 @@ static int dspi_remove(struct platform_device *pdev)
+ /* Disconnect from the SPI framework */
+ clk_disable_unprepare(dspi->clk);
+ spi_unregister_master(dspi->master);
+- spi_master_put(dspi->master);
+
+ return 0;
+ }
+diff --git a/drivers/staging/android/ion/Kconfig b/drivers/staging/android/ion/Kconfig
+index 19c1572..800245e 100644
+--- a/drivers/staging/android/ion/Kconfig
++++ b/drivers/staging/android/ion/Kconfig
+@@ -36,6 +36,7 @@ config ION_TEGRA
+ config ION_HISI
+ tristate "Ion for Hisilicon"
+ depends on ARCH_HISI && ION
++ select ION_OF
+ help
+ Choose this option if you wish to use ion on Hisilicon Platform.
+
+diff --git a/drivers/staging/ks7010/ks_hostif.c b/drivers/staging/ks7010/ks_hostif.c
+index a8822fe..f4cee81 100644
+--- a/drivers/staging/ks7010/ks_hostif.c
++++ b/drivers/staging/ks7010/ks_hostif.c
+@@ -69,16 +69,20 @@ inline u32 get_DWORD(struct ks_wlan_private *priv)
+ return data;
+ }
+
+-void ks_wlan_hw_wakeup_task(struct work_struct *work)
++static void ks_wlan_hw_wakeup_task(struct work_struct *work)
+ {
+ struct ks_wlan_private *priv =
+ container_of(work, struct ks_wlan_private, ks_wlan_wakeup_task);
+ int ps_status = atomic_read(&priv->psstatus.status);
++ long time_left;
+
+ if (ps_status == PS_SNOOZE) {
+ ks_wlan_hw_wakeup_request(priv);
+- if (!wait_for_completion_interruptible_timeout(&priv->psstatus.wakeup_wait, HZ / 50)) { /* 20ms timeout */
+- DPRINTK(1, "wake up timeout !!!\n");
++ time_left = wait_for_completion_interruptible_timeout(
++ &priv->psstatus.wakeup_wait,
++ msecs_to_jiffies(20));
++ if (time_left <= 0) {
++ DPRINTK(1, "wake up timeout or interrupted !!!\n");
+ schedule_work(&priv->ks_wlan_wakeup_task);
+ return;
+ }
+@@ -1505,7 +1509,7 @@ void hostif_infrastructure_set_request(struct ks_wlan_private *priv)
+ ks_wlan_hw_tx(priv, pp, hif_align_size(sizeof(*pp)), NULL, NULL, NULL);
+ }
+
+-void hostif_infrastructure_set2_request(struct ks_wlan_private *priv)
++static void hostif_infrastructure_set2_request(struct ks_wlan_private *priv)
+ {
+ struct hostif_infrastructure_set2_request_t *pp;
+ uint16_t capability;
+diff --git a/drivers/staging/rtl8188eu/core/rtw_cmd.c b/drivers/staging/rtl8188eu/core/rtw_cmd.c
+index 7748523..32d3a9c 100644
+--- a/drivers/staging/rtl8188eu/core/rtw_cmd.c
++++ b/drivers/staging/rtl8188eu/core/rtw_cmd.c
+@@ -670,13 +670,13 @@ u8 rtw_addbareq_cmd(struct adapter *padapter, u8 tid, u8 *addr)
+ u8 res = _SUCCESS;
+
+
+- ph2c = kzalloc(sizeof(struct cmd_obj), GFP_KERNEL);
++ ph2c = kzalloc(sizeof(struct cmd_obj), GFP_ATOMIC);
+ if (!ph2c) {
+ res = _FAIL;
+ goto exit;
+ }
+
+- paddbareq_parm = kzalloc(sizeof(struct addBaReq_parm), GFP_KERNEL);
++ paddbareq_parm = kzalloc(sizeof(struct addBaReq_parm), GFP_ATOMIC);
+ if (!paddbareq_parm) {
+ kfree(ph2c);
+ res = _FAIL;
+diff --git a/drivers/staging/sm750fb/ddk750_mode.c b/drivers/staging/sm750fb/ddk750_mode.c
+index ccb4e06..e29d4bd 100644
+--- a/drivers/staging/sm750fb/ddk750_mode.c
++++ b/drivers/staging/sm750fb/ddk750_mode.c
+@@ -63,7 +63,7 @@ static unsigned long displayControlAdjust_SM750LE(mode_parameter_t *pModeParam,
+ dispControl |= (CRT_DISPLAY_CTRL_CRTSELECT | CRT_DISPLAY_CTRL_RGBBIT);
+
+ /* Set bit 14 of display controller */
+- dispControl = DISPLAY_CTRL_CLOCK_PHASE;
++ dispControl |= DISPLAY_CTRL_CLOCK_PHASE;
+
+ POKE32(CRT_DISPLAY_CTRL, dispControl);
+
+diff --git a/drivers/uio/uio_dmem_genirq.c b/drivers/uio/uio_dmem_genirq.c
+index 915facb..e1134a4 100644
+--- a/drivers/uio/uio_dmem_genirq.c
++++ b/drivers/uio/uio_dmem_genirq.c
+@@ -229,7 +229,7 @@ static int uio_dmem_genirq_probe(struct platform_device *pdev)
+ ++uiomem;
+ }
+
+- priv->dmem_region_start = i;
++ priv->dmem_region_start = uiomem - &uioinfo->mem[0];
+ priv->num_dmem_regions = pdata->num_dynamic_regions;
+
+ for (i = 0; i < pdata->num_dynamic_regions; ++i) {
+diff --git a/fs/9p/acl.c b/fs/9p/acl.c
+index 5b6a174..b3c2cc7 100644
+--- a/fs/9p/acl.c
++++ b/fs/9p/acl.c
+@@ -276,32 +276,26 @@ static int v9fs_xattr_set_acl(const struct xattr_handler *handler,
+ switch (handler->flags) {
+ case ACL_TYPE_ACCESS:
+ if (acl) {
+- umode_t mode = inode->i_mode;
+- retval = posix_acl_equiv_mode(acl, &mode);
+- if (retval < 0)
++ struct iattr iattr;
++
++ retval = posix_acl_update_mode(inode, &iattr.ia_mode, &acl);
++ if (retval)
+ goto err_out;
+- else {
+- struct iattr iattr;
+- if (retval == 0) {
+- /*
+- * ACL can be represented
+- * by the mode bits. So don't
+- * update ACL.
+- */
+- acl = NULL;
+- value = NULL;
+- size = 0;
+- }
+- /* Updte the mode bits */
+- iattr.ia_mode = ((mode & S_IALLUGO) |
+- (inode->i_mode & ~S_IALLUGO));
+- iattr.ia_valid = ATTR_MODE;
+- /* FIXME should we update ctime ?
+- * What is the following setxattr update the
+- * mode ?
++ if (!acl) {
++ /*
++ * ACL can be represented
++ * by the mode bits. So don't
++ * update ACL.
+ */
+- v9fs_vfs_setattr_dotl(dentry, &iattr);
++ value = NULL;
++ size = 0;
+ }
++ iattr.ia_valid = ATTR_MODE;
++ /* FIXME should we update ctime ?
++ * What is the following setxattr update the
++ * mode ?
++ */
++ v9fs_vfs_setattr_dotl(dentry, &iattr);
+ }
+ break;
+ case ACL_TYPE_DEFAULT:
+diff --git a/fs/btrfs/acl.c b/fs/btrfs/acl.c
+index 53bb7af..247b8df 100644
+--- a/fs/btrfs/acl.c
++++ b/fs/btrfs/acl.c
+@@ -79,11 +79,9 @@ static int __btrfs_set_acl(struct btrfs_trans_handle *trans,
+ case ACL_TYPE_ACCESS:
+ name = XATTR_NAME_POSIX_ACL_ACCESS;
+ if (acl) {
+- ret = posix_acl_equiv_mode(acl, &inode->i_mode);
+- if (ret < 0)
++ ret = posix_acl_update_mode(inode, &inode->i_mode, &acl);
++ if (ret)
+ return ret;
+- if (ret == 0)
+- acl = NULL;
+ }
+ ret = 0;
+ break;
+diff --git a/fs/ceph/acl.c b/fs/ceph/acl.c
+index 4f67227..d0b6b342 100644
+--- a/fs/ceph/acl.c
++++ b/fs/ceph/acl.c
+@@ -95,11 +95,9 @@ int ceph_set_acl(struct inode *inode, struct posix_acl *acl, int type)
+ case ACL_TYPE_ACCESS:
+ name = XATTR_NAME_POSIX_ACL_ACCESS;
+ if (acl) {
+- ret = posix_acl_equiv_mode(acl, &new_mode);
+- if (ret < 0)
++ ret = posix_acl_update_mode(inode, &new_mode, &acl);
++ if (ret)
+ goto out;
+- if (ret == 0)
+- acl = NULL;
+ }
+ break;
+ case ACL_TYPE_DEFAULT:
+diff --git a/fs/ext2/acl.c b/fs/ext2/acl.c
+index 42f1d18..e725aa0 100644
+--- a/fs/ext2/acl.c
++++ b/fs/ext2/acl.c
+@@ -190,15 +190,11 @@ ext2_set_acl(struct inode *inode, struct posix_acl *acl, int type)
+ case ACL_TYPE_ACCESS:
+ name_index = EXT2_XATTR_INDEX_POSIX_ACL_ACCESS;
+ if (acl) {
+- error = posix_acl_equiv_mode(acl, &inode->i_mode);
+- if (error < 0)
++ error = posix_acl_update_mode(inode, &inode->i_mode, &acl);
++ if (error)
+ return error;
+- else {
+- inode->i_ctime = CURRENT_TIME_SEC;
+- mark_inode_dirty(inode);
+- if (error == 0)
+- acl = NULL;
+- }
++ inode->i_ctime = CURRENT_TIME_SEC;
++ mark_inode_dirty(inode);
+ }
+ break;
+
+diff --git a/fs/ext4/acl.c b/fs/ext4/acl.c
+index c6601a4..dfa5199 100644
+--- a/fs/ext4/acl.c
++++ b/fs/ext4/acl.c
+@@ -193,15 +193,11 @@ __ext4_set_acl(handle_t *handle, struct inode *inode, int type,
+ case ACL_TYPE_ACCESS:
+ name_index = EXT4_XATTR_INDEX_POSIX_ACL_ACCESS;
+ if (acl) {
+- error = posix_acl_equiv_mode(acl, &inode->i_mode);
+- if (error < 0)
++ error = posix_acl_update_mode(inode, &inode->i_mode, &acl);
++ if (error)
+ return error;
+- else {
+- inode->i_ctime = ext4_current_time(inode);
+- ext4_mark_inode_dirty(handle, inode);
+- if (error == 0)
+- acl = NULL;
+- }
++ inode->i_ctime = ext4_current_time(inode);
++ ext4_mark_inode_dirty(handle, inode);
+ }
+ break;
+
+diff --git a/fs/f2fs/acl.c b/fs/f2fs/acl.c
+index 4dcc9e2..3134424 100644
+--- a/fs/f2fs/acl.c
++++ b/fs/f2fs/acl.c
+@@ -210,12 +210,10 @@ static int __f2fs_set_acl(struct inode *inode, int type,
+ case ACL_TYPE_ACCESS:
+ name_index = F2FS_XATTR_INDEX_POSIX_ACL_ACCESS;
+ if (acl) {
+- error = posix_acl_equiv_mode(acl, &inode->i_mode);
+- if (error < 0)
++ error = posix_acl_update_mode(inode, &inode->i_mode, &acl);
++ if (error)
+ return error;
+ set_acl_inode(inode, inode->i_mode);
+- if (error == 0)
+- acl = NULL;
+ }
+ break;
+
+diff --git a/fs/gfs2/acl.c b/fs/gfs2/acl.c
+index 363ba9e..2524807 100644
+--- a/fs/gfs2/acl.c
++++ b/fs/gfs2/acl.c
+@@ -92,17 +92,11 @@ int __gfs2_set_acl(struct inode *inode, struct posix_acl *acl, int type)
+ if (type == ACL_TYPE_ACCESS) {
+ umode_t mode = inode->i_mode;
+
+- error = posix_acl_equiv_mode(acl, &mode);
+- if (error < 0)
++ error = posix_acl_update_mode(inode, &inode->i_mode, &acl);
++ if (error)
+ return error;
+-
+- if (error == 0)
+- acl = NULL;
+-
+- if (mode != inode->i_mode) {
+- inode->i_mode = mode;
++ if (mode != inode->i_mode)
+ mark_inode_dirty(inode);
+- }
+ }
+
+ if (acl) {
+diff --git a/fs/hfsplus/posix_acl.c b/fs/hfsplus/posix_acl.c
+index ab7ea25..9b92058 100644
+--- a/fs/hfsplus/posix_acl.c
++++ b/fs/hfsplus/posix_acl.c
+@@ -65,8 +65,8 @@ int hfsplus_set_posix_acl(struct inode *inode, struct posix_acl *acl,
+ case ACL_TYPE_ACCESS:
+ xattr_name = XATTR_NAME_POSIX_ACL_ACCESS;
+ if (acl) {
+- err = posix_acl_equiv_mode(acl, &inode->i_mode);
+- if (err < 0)
++ err = posix_acl_update_mode(inode, &inode->i_mode, &acl);
++ if (err)
+ return err;
+ }
+ err = 0;
+diff --git a/fs/jffs2/acl.c b/fs/jffs2/acl.c
+index bc2693d..2a0f2a1 100644
+--- a/fs/jffs2/acl.c
++++ b/fs/jffs2/acl.c
+@@ -233,9 +233,10 @@ int jffs2_set_acl(struct inode *inode, struct posix_acl *acl, int type)
+ case ACL_TYPE_ACCESS:
+ xprefix = JFFS2_XPREFIX_ACL_ACCESS;
+ if (acl) {
+- umode_t mode = inode->i_mode;
+- rc = posix_acl_equiv_mode(acl, &mode);
+- if (rc < 0)
++ umode_t mode;
++
++ rc = posix_acl_update_mode(inode, &mode, &acl);
++ if (rc)
+ return rc;
+ if (inode->i_mode != mode) {
+ struct iattr attr;
+@@ -247,8 +248,6 @@ int jffs2_set_acl(struct inode *inode, struct posix_acl *acl, int type)
+ if (rc < 0)
+ return rc;
+ }
+- if (rc == 0)
+- acl = NULL;
+ }
+ break;
+ case ACL_TYPE_DEFAULT:
+diff --git a/fs/jfs/acl.c b/fs/jfs/acl.c
+index 21fa92b..3a1e155 100644
+--- a/fs/jfs/acl.c
++++ b/fs/jfs/acl.c
+@@ -78,13 +78,11 @@ static int __jfs_set_acl(tid_t tid, struct inode *inode, int type,
+ case ACL_TYPE_ACCESS:
+ ea_name = XATTR_NAME_POSIX_ACL_ACCESS;
+ if (acl) {
+- rc = posix_acl_equiv_mode(acl, &inode->i_mode);
+- if (rc < 0)
++ rc = posix_acl_update_mode(inode, &inode->i_mode, &acl);
++ if (rc)
+ return rc;
+ inode->i_ctime = CURRENT_TIME;
+ mark_inode_dirty(inode);
+- if (rc == 0)
+- acl = NULL;
+ }
+ break;
+ case ACL_TYPE_DEFAULT:
+diff --git a/fs/ocfs2/acl.c b/fs/ocfs2/acl.c
+index 2162434..164307b 100644
+--- a/fs/ocfs2/acl.c
++++ b/fs/ocfs2/acl.c
+@@ -241,13 +241,11 @@ int ocfs2_set_acl(handle_t *handle,
+ case ACL_TYPE_ACCESS:
+ name_index = OCFS2_XATTR_INDEX_POSIX_ACL_ACCESS;
+ if (acl) {
+- umode_t mode = inode->i_mode;
+- ret = posix_acl_equiv_mode(acl, &mode);
+- if (ret < 0)
+- return ret;
++ umode_t mode;
+
+- if (ret == 0)
+- acl = NULL;
++ ret = posix_acl_update_mode(inode, &mode, &acl);
++ if (ret)
++ return ret;
+
+ ret = ocfs2_acl_set_mode(inode, di_bh,
+ handle, mode);
+diff --git a/fs/orangefs/acl.c b/fs/orangefs/acl.c
+index 28f2195..7a37544 100644
+--- a/fs/orangefs/acl.c
++++ b/fs/orangefs/acl.c
+@@ -73,14 +73,11 @@ int orangefs_set_acl(struct inode *inode, struct posix_acl *acl, int type)
+ case ACL_TYPE_ACCESS:
+ name = XATTR_NAME_POSIX_ACL_ACCESS;
+ if (acl) {
+- umode_t mode = inode->i_mode;
+- /*
+- * can we represent this with the traditional file
+- * mode permission bits?
+- */
+- error = posix_acl_equiv_mode(acl, &mode);
+- if (error < 0) {
+- gossip_err("%s: posix_acl_equiv_mode err: %d\n",
++ umode_t mode;
++
++ error = posix_acl_update_mode(inode, &mode, &acl);
++ if (error) {
++ gossip_err("%s: posix_acl_update_mode err: %d\n",
+ __func__,
+ error);
+ return error;
+@@ -90,8 +87,6 @@ int orangefs_set_acl(struct inode *inode, struct posix_acl *acl, int type)
+ SetModeFlag(orangefs_inode);
+ inode->i_mode = mode;
+ mark_inode_dirty_sync(inode);
+- if (error == 0)
+- acl = NULL;
+ }
+ break;
+ case ACL_TYPE_DEFAULT:
+diff --git a/fs/posix_acl.c b/fs/posix_acl.c
+index 59d47ab0..bfc3ec3 100644
+--- a/fs/posix_acl.c
++++ b/fs/posix_acl.c
+@@ -626,6 +626,37 @@ posix_acl_create(struct inode *dir, umode_t *mode,
+ }
+ EXPORT_SYMBOL_GPL(posix_acl_create);
+
++/**
++ * posix_acl_update_mode - update mode in set_acl
++ *
++ * Update the file mode when setting an ACL: compute the new file permission
++ * bits based on the ACL. In addition, if the ACL is equivalent to the new
++ * file mode, set *acl to NULL to indicate that no ACL should be set.
++ *
++ * As with chmod, clear the setgit bit if the caller is not in the owning group
++ * or capable of CAP_FSETID (see inode_change_ok).
++ *
++ * Called from set_acl inode operations.
++ */
++int posix_acl_update_mode(struct inode *inode, umode_t *mode_p,
++ struct posix_acl **acl)
++{
++ umode_t mode = inode->i_mode;
++ int error;
++
++ error = posix_acl_equiv_mode(*acl, &mode);
++ if (error < 0)
++ return error;
++ if (error == 0)
++ *acl = NULL;
++ if (!in_group_p(inode->i_gid) &&
++ !capable_wrt_inode_uidgid(inode, CAP_FSETID))
++ mode &= ~S_ISGID;
++ *mode_p = mode;
++ return 0;
++}
++EXPORT_SYMBOL(posix_acl_update_mode);
++
+ /*
+ * Fix up the uids and gids in posix acl extended attributes in place.
+ */
+diff --git a/fs/reiserfs/xattr_acl.c b/fs/reiserfs/xattr_acl.c
+index dbed42f..2737668 100644
+--- a/fs/reiserfs/xattr_acl.c
++++ b/fs/reiserfs/xattr_acl.c
+@@ -242,13 +242,9 @@ __reiserfs_set_acl(struct reiserfs_transaction_handle *th, struct inode *inode,
+ case ACL_TYPE_ACCESS:
+ name = XATTR_NAME_POSIX_ACL_ACCESS;
+ if (acl) {
+- error = posix_acl_equiv_mode(acl, &inode->i_mode);
+- if (error < 0)
++ error = posix_acl_update_mode(inode, &inode->i_mode, &acl);
++ if (error)
+ return error;
+- else {
+- if (error == 0)
+- acl = NULL;
+- }
+ }
+ break;
+ case ACL_TYPE_DEFAULT:
+diff --git a/fs/xfs/xfs_acl.c b/fs/xfs/xfs_acl.c
+index b6e527b..8a0dec8 100644
+--- a/fs/xfs/xfs_acl.c
++++ b/fs/xfs/xfs_acl.c
+@@ -257,16 +257,11 @@ xfs_set_acl(struct inode *inode, struct posix_acl *acl, int type)
+ return error;
+
+ if (type == ACL_TYPE_ACCESS) {
+- umode_t mode = inode->i_mode;
+- error = posix_acl_equiv_mode(acl, &mode);
+-
+- if (error <= 0) {
+- acl = NULL;
+-
+- if (error < 0)
+- return error;
+- }
++ umode_t mode;
+
++ error = posix_acl_update_mode(inode, &mode, &acl);
++ if (error)
++ return error;
+ error = xfs_set_mode(inode, mode);
+ if (error)
+ return error;
+diff --git a/include/drm/drmP.h b/include/drm/drmP.h
+index d377865..988903a 100644
+--- a/include/drm/drmP.h
++++ b/include/drm/drmP.h
+@@ -938,7 +938,8 @@ static inline int drm_debugfs_remove_files(const struct drm_info_list *files,
+ #endif
+
+ extern struct dma_buf *drm_gem_prime_export(struct drm_device *dev,
+- struct drm_gem_object *obj, int flags);
++ struct drm_gem_object *obj,
++ int flags);
+ extern int drm_gem_prime_handle_to_fd(struct drm_device *dev,
+ struct drm_file *file_priv, uint32_t handle, uint32_t flags,
+ int *prime_fd);
+diff --git a/include/linux/hugetlb.h b/include/linux/hugetlb.h
+index c26d463..fe99e6f 100644
+--- a/include/linux/hugetlb.h
++++ b/include/linux/hugetlb.h
+@@ -450,8 +450,8 @@ static inline pgoff_t basepage_index(struct page *page)
+ return __basepage_index(page);
+ }
+
+-extern void dissolve_free_huge_pages(unsigned long start_pfn,
+- unsigned long end_pfn);
++extern int dissolve_free_huge_pages(unsigned long start_pfn,
++ unsigned long end_pfn);
+ static inline bool hugepage_migration_supported(struct hstate *h)
+ {
+ #ifdef CONFIG_ARCH_ENABLE_HUGEPAGE_MIGRATION
+@@ -518,7 +518,7 @@ static inline pgoff_t basepage_index(struct page *page)
+ {
+ return page->index;
+ }
+-#define dissolve_free_huge_pages(s, e) do {} while (0)
++#define dissolve_free_huge_pages(s, e) 0
+ #define hugepage_migration_supported(h) false
+
+ static inline spinlock_t *huge_pte_lockptr(struct hstate *h,
+diff --git a/include/linux/libnvdimm.h b/include/linux/libnvdimm.h
+index b519e13..bbfce62 100644
+--- a/include/linux/libnvdimm.h
++++ b/include/linux/libnvdimm.h
+@@ -129,6 +129,8 @@ static inline struct nd_blk_region_desc *to_blk_region_desc(
+ }
+
+ int nvdimm_bus_add_poison(struct nvdimm_bus *nvdimm_bus, u64 addr, u64 length);
++void nvdimm_clear_from_poison_list(struct nvdimm_bus *nvdimm_bus,
++ phys_addr_t start, unsigned int len);
+ struct nvdimm_bus *nvdimm_bus_register(struct device *parent,
+ struct nvdimm_bus_descriptor *nfit_desc);
+ void nvdimm_bus_unregister(struct nvdimm_bus *nvdimm_bus);
+diff --git a/include/linux/posix_acl.h b/include/linux/posix_acl.h
+index d5d3d74..bf1046d 100644
+--- a/include/linux/posix_acl.h
++++ b/include/linux/posix_acl.h
+@@ -93,6 +93,7 @@ extern int set_posix_acl(struct inode *, int, struct posix_acl *);
+ extern int posix_acl_chmod(struct inode *, umode_t);
+ extern int posix_acl_create(struct inode *, umode_t *, struct posix_acl **,
+ struct posix_acl **);
++extern int posix_acl_update_mode(struct inode *, umode_t *, struct posix_acl **);
+
+ extern int simple_set_acl(struct inode *, struct posix_acl *, int);
+ extern int simple_acl_create(struct inode *, struct inode *);
+diff --git a/kernel/irq/generic-chip.c b/kernel/irq/generic-chip.c
+index abd286a..a4775f3 100644
+--- a/kernel/irq/generic-chip.c
++++ b/kernel/irq/generic-chip.c
+@@ -411,8 +411,29 @@ int irq_map_generic_chip(struct irq_domain *d, unsigned int virq,
+ }
+ EXPORT_SYMBOL_GPL(irq_map_generic_chip);
+
++static void irq_unmap_generic_chip(struct irq_domain *d, unsigned int virq)
++{
++ struct irq_data *data = irq_domain_get_irq_data(d, virq);
++ struct irq_domain_chip_generic *dgc = d->gc;
++ unsigned int hw_irq = data->hwirq;
++ struct irq_chip_generic *gc;
++ int irq_idx;
++
++ gc = irq_get_domain_generic_chip(d, hw_irq);
++ if (!gc)
++ return;
++
++ irq_idx = hw_irq % dgc->irqs_per_chip;
++
++ clear_bit(irq_idx, &gc->installed);
++ irq_domain_set_info(d, virq, hw_irq, &no_irq_chip, NULL, NULL, NULL,
++ NULL);
++
++}
++
+ struct irq_domain_ops irq_generic_chip_ops = {
+ .map = irq_map_generic_chip,
++ .unmap = irq_unmap_generic_chip,
+ .xlate = irq_domain_xlate_onetwocell,
+ };
+ EXPORT_SYMBOL_GPL(irq_generic_chip_ops);
+diff --git a/mm/hugetlb.c b/mm/hugetlb.c
+index 603bdd0..770d83e 100644
+--- a/mm/hugetlb.c
++++ b/mm/hugetlb.c
+@@ -1437,22 +1437,32 @@ static int free_pool_huge_page(struct hstate *h, nodemask_t *nodes_allowed,
+
+ /*
+ * Dissolve a given free hugepage into free buddy pages. This function does
+- * nothing for in-use (including surplus) hugepages.
++ * nothing for in-use (including surplus) hugepages. Returns -EBUSY if the
++ * number of free hugepages would be reduced below the number of reserved
++ * hugepages.
+ */
+-static void dissolve_free_huge_page(struct page *page)
++static int dissolve_free_huge_page(struct page *page)
+ {
++ int rc = 0;
++
+ spin_lock(&hugetlb_lock);
+ if (PageHuge(page) && !page_count(page)) {
+ struct page *head = compound_head(page);
+ struct hstate *h = page_hstate(head);
+ int nid = page_to_nid(head);
++ if (h->free_huge_pages - h->resv_huge_pages == 0) {
++ rc = -EBUSY;
++ goto out;
++ }
+ list_del(&head->lru);
+ h->free_huge_pages--;
+ h->free_huge_pages_node[nid]--;
+ h->max_huge_pages--;
+ update_and_free_page(h, head);
+ }
++out:
+ spin_unlock(&hugetlb_lock);
++ return rc;
+ }
+
+ /*
+@@ -1460,16 +1470,28 @@ static void dissolve_free_huge_page(struct page *page)
+ * make specified memory blocks removable from the system.
+ * Note that this will dissolve a free gigantic hugepage completely, if any
+ * part of it lies within the given range.
++ * Also note that if dissolve_free_huge_page() returns with an error, all
++ * free hugepages that were dissolved before that error are lost.
+ */
+-void dissolve_free_huge_pages(unsigned long start_pfn, unsigned long end_pfn)
++int dissolve_free_huge_pages(unsigned long start_pfn, unsigned long end_pfn)
+ {
+ unsigned long pfn;
++ struct page *page;
++ int rc = 0;
+
+ if (!hugepages_supported())
+- return;
++ return rc;
++
++ for (pfn = start_pfn; pfn < end_pfn; pfn += 1 << minimum_order) {
++ page = pfn_to_page(pfn);
++ if (PageHuge(page) && !page_count(page)) {
++ rc = dissolve_free_huge_page(page);
++ if (rc)
++ break;
++ }
++ }
+
+- for (pfn = start_pfn; pfn < end_pfn; pfn += 1 << minimum_order)
+- dissolve_free_huge_page(pfn_to_page(pfn));
++ return rc;
+ }
+
+ /*
+diff --git a/mm/memory_hotplug.c b/mm/memory_hotplug.c
+index 9d29ba0..9629273 100644
+--- a/mm/memory_hotplug.c
++++ b/mm/memory_hotplug.c
+@@ -1945,7 +1945,9 @@ static int __ref __offline_pages(unsigned long start_pfn,
+ * dissolve free hugepages in the memory block before doing offlining
+ * actually in order to make hugetlbfs's object counting consistent.
+ */
+- dissolve_free_huge_pages(start_pfn, end_pfn);
++ ret = dissolve_free_huge_pages(start_pfn, end_pfn);
++ if (ret)
++ goto failed_removal;
+ /* check again */
+ offlined_pages = check_pages_isolated(start_pfn, end_pfn);
+ if (offlined_pages < 0) {
+diff --git a/sound/soc/intel/boards/bxt_da7219_max98357a.c b/sound/soc/intel/boards/bxt_da7219_max98357a.c
+index 3774b11..49b65d4 100644
+--- a/sound/soc/intel/boards/bxt_da7219_max98357a.c
++++ b/sound/soc/intel/boards/bxt_da7219_max98357a.c
+@@ -255,7 +255,7 @@ static struct snd_soc_ops broxton_da7219_ops = {
+ /* broxton digital audio interface glue - connects codec <--> CPU */
+ static struct snd_soc_dai_link broxton_dais[] = {
+ /* Front End DAI links */
+- [BXT_DPCM_AUDIO_PB]
++ [BXT_DPCM_AUDIO_PB] =
+ {
+ .name = "Bxt Audio Port",
+ .stream_name = "Audio",
+@@ -271,7 +271,7 @@ static struct snd_soc_dai_link broxton_dais[] = {
+ .dpcm_playback = 1,
+ .ops = &broxton_da7219_fe_ops,
+ },
+- [BXT_DPCM_AUDIO_CP]
++ [BXT_DPCM_AUDIO_CP] =
+ {
+ .name = "Bxt Audio Capture Port",
+ .stream_name = "Audio Record",
+@@ -286,7 +286,7 @@ static struct snd_soc_dai_link broxton_dais[] = {
+ .dpcm_capture = 1,
+ .ops = &broxton_da7219_fe_ops,
+ },
+- [BXT_DPCM_AUDIO_REF_CP]
++ [BXT_DPCM_AUDIO_REF_CP] =
+ {
+ .name = "Bxt Audio Reference cap",
+ .stream_name = "Refcap",
+@@ -300,7 +300,7 @@ static struct snd_soc_dai_link broxton_dais[] = {
+ .nonatomic = 1,
+ .dynamic = 1,
+ },
+- [BXT_DPCM_AUDIO_HDMI1_PB]
++ [BXT_DPCM_AUDIO_HDMI1_PB] =
+ {
+ .name = "Bxt HDMI Port1",
+ .stream_name = "Hdmi1",
+@@ -313,7 +313,7 @@ static struct snd_soc_dai_link broxton_dais[] = {
+ .nonatomic = 1,
+ .dynamic = 1,
+ },
+- [BXT_DPCM_AUDIO_HDMI2_PB]
++ [BXT_DPCM_AUDIO_HDMI2_PB] =
+ {
+ .name = "Bxt HDMI Port2",
+ .stream_name = "Hdmi2",
+@@ -326,7 +326,7 @@ static struct snd_soc_dai_link broxton_dais[] = {
+ .nonatomic = 1,
+ .dynamic = 1,
+ },
+- [BXT_DPCM_AUDIO_HDMI3_PB]
++ [BXT_DPCM_AUDIO_HDMI3_PB] =
+ {
+ .name = "Bxt HDMI Port3",
+ .stream_name = "Hdmi3",
+diff --git a/sound/soc/intel/boards/bxt_rt298.c b/sound/soc/intel/boards/bxt_rt298.c
+index 253d7bf..d610bdca 100644
+--- a/sound/soc/intel/boards/bxt_rt298.c
++++ b/sound/soc/intel/boards/bxt_rt298.c
+@@ -271,7 +271,7 @@ static const struct snd_soc_ops broxton_rt286_fe_ops = {
+ /* broxton digital audio interface glue - connects codec <--> CPU */
+ static struct snd_soc_dai_link broxton_rt298_dais[] = {
+ /* Front End DAI links */
+- [BXT_DPCM_AUDIO_PB]
++ [BXT_DPCM_AUDIO_PB] =
+ {
+ .name = "Bxt Audio Port",
+ .stream_name = "Audio",
+@@ -286,7 +286,7 @@ static struct snd_soc_dai_link broxton_rt298_dais[] = {
+ .dpcm_playback = 1,
+ .ops = &broxton_rt286_fe_ops,
+ },
+- [BXT_DPCM_AUDIO_CP]
++ [BXT_DPCM_AUDIO_CP] =
+ {
+ .name = "Bxt Audio Capture Port",
+ .stream_name = "Audio Record",
+@@ -300,7 +300,7 @@ static struct snd_soc_dai_link broxton_rt298_dais[] = {
+ .dpcm_capture = 1,
+ .ops = &broxton_rt286_fe_ops,
+ },
+- [BXT_DPCM_AUDIO_REF_CP]
++ [BXT_DPCM_AUDIO_REF_CP] =
+ {
+ .name = "Bxt Audio Reference cap",
+ .stream_name = "refcap",
+@@ -313,7 +313,7 @@ static struct snd_soc_dai_link broxton_rt298_dais[] = {
+ .nonatomic = 1,
+ .dynamic = 1,
+ },
+- [BXT_DPCM_AUDIO_DMIC_CP]
++ [BXT_DPCM_AUDIO_DMIC_CP] =
+ {
+ .name = "Bxt Audio DMIC cap",
+ .stream_name = "dmiccap",
+@@ -327,7 +327,7 @@ static struct snd_soc_dai_link broxton_rt298_dais[] = {
+ .dynamic = 1,
+ .ops = &broxton_dmic_ops,
+ },
+- [BXT_DPCM_AUDIO_HDMI1_PB]
++ [BXT_DPCM_AUDIO_HDMI1_PB] =
+ {
+ .name = "Bxt HDMI Port1",
+ .stream_name = "Hdmi1",
+@@ -340,7 +340,7 @@ static struct snd_soc_dai_link broxton_rt298_dais[] = {
+ .nonatomic = 1,
+ .dynamic = 1,
+ },
+- [BXT_DPCM_AUDIO_HDMI2_PB]
++ [BXT_DPCM_AUDIO_HDMI2_PB] =
+ {
+ .name = "Bxt HDMI Port2",
+ .stream_name = "Hdmi2",
+@@ -353,7 +353,7 @@ static struct snd_soc_dai_link broxton_rt298_dais[] = {
+ .nonatomic = 1,
+ .dynamic = 1,
+ },
+- [BXT_DPCM_AUDIO_HDMI3_PB]
++ [BXT_DPCM_AUDIO_HDMI3_PB] =
+ {
+ .name = "Bxt HDMI Port3",
+ .stream_name = "Hdmi3",
+diff --git a/sound/soc/soc-dapm.c b/sound/soc/soc-dapm.c
+index d908ff8..801082f 100644
+--- a/sound/soc/soc-dapm.c
++++ b/sound/soc/soc-dapm.c
+@@ -823,6 +823,7 @@ static int dapm_create_or_share_kcontrol(struct snd_soc_dapm_widget *w,
+ case snd_soc_dapm_switch:
+ case snd_soc_dapm_mixer:
+ case snd_soc_dapm_pga:
++ case snd_soc_dapm_out_drv:
+ wname_in_long_name = true;
+ kcname_in_long_name = true;
+ break;
+@@ -3049,6 +3050,9 @@ int snd_soc_dapm_get_volsw(struct snd_kcontrol *kcontrol,
+ }
+ mutex_unlock(&card->dapm_mutex);
+
++ if (ret)
++ return ret;
++
+ if (invert)
+ ucontrol->value.integer.value[0] = max - val;
+ else
+@@ -3200,7 +3204,7 @@ int snd_soc_dapm_put_enum_double(struct snd_kcontrol *kcontrol,
+ if (e->shift_l != e->shift_r) {
+ if (item[1] > e->items)
+ return -EINVAL;
+- val |= snd_soc_enum_item_to_val(e, item[1]) << e->shift_l;
++ val |= snd_soc_enum_item_to_val(e, item[1]) << e->shift_r;
+ mask |= e->mask << e->shift_r;
+ }
+
+diff --git a/sound/soc/soc-topology.c b/sound/soc/soc-topology.c
+index ee7f15a..3406907 100644
+--- a/sound/soc/soc-topology.c
++++ b/sound/soc/soc-topology.c
+@@ -1475,6 +1475,7 @@ static int soc_tplg_dapm_widget_create(struct soc_tplg *tplg,
+ if (widget == NULL) {
+ dev_err(tplg->dev, "ASoC: failed to create widget %s controls\n",
+ w->name);
++ ret = -ENOMEM;
+ goto hdr_err;
+ }
+
+diff --git a/tools/perf/perf-sys.h b/tools/perf/perf-sys.h
+index 7ed72a4..e4b717e 100644
+--- a/tools/perf/perf-sys.h
++++ b/tools/perf/perf-sys.h
+@@ -20,7 +20,6 @@
+ #endif
+
+ #ifdef __powerpc__
+-#include "../../arch/powerpc/include/uapi/asm/unistd.h"
+ #define CPUINFO_PROC {"cpu"}
+ #endif
+
+diff --git a/tools/perf/ui/browsers/hists.c b/tools/perf/ui/browsers/hists.c
+index 13d4143..7aee954 100644
+--- a/tools/perf/ui/browsers/hists.c
++++ b/tools/perf/ui/browsers/hists.c
+@@ -1091,7 +1091,6 @@ static int __hpp__slsmg_color_printf(struct perf_hpp *hpp, const char *fmt, ...)
+ ret = scnprintf(hpp->buf, hpp->size, fmt, len, percent);
+ ui_browser__printf(arg->b, "%s", hpp->buf);
+
+- advance_hpp(hpp, ret);
+ return ret;
+ }
+
+@@ -2046,6 +2045,7 @@ void hist_browser__init(struct hist_browser *browser,
+ struct hists *hists)
+ {
+ struct perf_hpp_fmt *fmt;
++ struct perf_hpp_list_node *node;
+
+ browser->hists = hists;
+ browser->b.refresh = hist_browser__refresh;
+@@ -2058,6 +2058,11 @@ void hist_browser__init(struct hist_browser *browser,
+ perf_hpp__reset_width(fmt, hists);
+ ++browser->b.columns;
+ }
++ /* hierarchy entries have their own hpp list */
++ list_for_each_entry(node, &hists->hpp_formats, list) {
++ perf_hpp_list__for_each_format(&node->hpp, fmt)
++ perf_hpp__reset_width(fmt, hists);
++ }
+ }
+
+ struct hist_browser *hist_browser__new(struct hists *hists)
+diff --git a/tools/perf/ui/stdio/hist.c b/tools/perf/ui/stdio/hist.c
+index f04a631..d0cae75 100644
+--- a/tools/perf/ui/stdio/hist.c
++++ b/tools/perf/ui/stdio/hist.c
+@@ -628,14 +628,6 @@ hists__fprintf_hierarchy_headers(struct hists *hists,
+ struct perf_hpp *hpp,
+ FILE *fp)
+ {
+- struct perf_hpp_list_node *fmt_node;
+- struct perf_hpp_fmt *fmt;
+-
+- list_for_each_entry(fmt_node, &hists->hpp_formats, list) {
+- perf_hpp_list__for_each_format(&fmt_node->hpp, fmt)
+- perf_hpp__reset_width(fmt, hists);
+- }
+-
+ return print_hierarchy_header(hists, hpp, symbol_conf.field_sep, fp);
+ }
+
+@@ -714,6 +706,7 @@ size_t hists__fprintf(struct hists *hists, bool show_header, int max_rows,
+ bool use_callchain)
+ {
+ struct perf_hpp_fmt *fmt;
++ struct perf_hpp_list_node *node;
+ struct rb_node *nd;
+ size_t ret = 0;
+ const char *sep = symbol_conf.field_sep;
+@@ -726,6 +719,11 @@ size_t hists__fprintf(struct hists *hists, bool show_header, int max_rows,
+
+ hists__for_each_format(hists, fmt)
+ perf_hpp__reset_width(fmt, hists);
++ /* hierarchy entries have their own hpp list */
++ list_for_each_entry(node, &hists->hpp_formats, list) {
++ perf_hpp_list__for_each_format(&node->hpp, fmt)
++ perf_hpp__reset_width(fmt, hists);
++ }
+
+ if (symbol_conf.col_width_list_str)
+ perf_hpp__set_user_width(symbol_conf.col_width_list_str);
+diff --git a/tools/perf/util/data-convert-bt.c b/tools/perf/util/data-convert-bt.c
+index 4f979bb..7123f4d 100644
+--- a/tools/perf/util/data-convert-bt.c
++++ b/tools/perf/util/data-convert-bt.c
+@@ -437,7 +437,7 @@ add_bpf_output_values(struct bt_ctf_event_class *event_class,
+ int ret;
+
+ if (nr_elements * sizeof(u32) != raw_size)
+- pr_warning("Incorrect raw_size (%u) in bpf output event, skip %lu bytes\n",
++ pr_warning("Incorrect raw_size (%u) in bpf output event, skip %zu bytes\n",
+ raw_size, nr_elements * sizeof(u32) - raw_size);
+
+ len_type = bt_ctf_event_class_get_field_by_name(event_class, "raw_len");
+diff --git a/tools/perf/util/symbol-elf.c b/tools/perf/util/symbol-elf.c
+index a811c13..f77b316 100644
+--- a/tools/perf/util/symbol-elf.c
++++ b/tools/perf/util/symbol-elf.c
+@@ -1113,9 +1113,8 @@ int dso__load_sym(struct dso *dso, struct map *map,
+ * For misannotated, zeroed, ASM function sizes.
+ */
+ if (nr > 0) {
+- if (!symbol_conf.allow_aliases)
+- symbols__fixup_duplicate(&dso->symbols[map->type]);
+ symbols__fixup_end(&dso->symbols[map->type]);
++ symbols__fixup_duplicate(&dso->symbols[map->type]);
+ if (kmap) {
+ /*
+ * We need to fixup this here too because we create new
+diff --git a/tools/perf/util/symbol.c b/tools/perf/util/symbol.c
+index 37e8d20..f29f336 100644
+--- a/tools/perf/util/symbol.c
++++ b/tools/perf/util/symbol.c
+@@ -152,6 +152,9 @@ void symbols__fixup_duplicate(struct rb_root *symbols)
+ struct rb_node *nd;
+ struct symbol *curr, *next;
+
++ if (symbol_conf.allow_aliases)
++ return;
++
+ nd = rb_first(symbols);
+
+ while (nd) {
+@@ -1234,8 +1237,8 @@ int __dso__load_kallsyms(struct dso *dso, const char *filename,
+ if (kallsyms__delta(map, filename, &delta))
+ return -1;
+
+- symbols__fixup_duplicate(&dso->symbols[map->type]);
+ symbols__fixup_end(&dso->symbols[map->type]);
++ symbols__fixup_duplicate(&dso->symbols[map->type]);
+
+ if (dso->kernel == DSO_TYPE_GUEST_KERNEL)
+ dso->symtab_type = DSO_BINARY_TYPE__GUEST_KALLSYMS;