mirror of
https://github.com/Fishwaldo/build.git
synced 2025-03-28 09:41:41 +00:00
- legacy received upstream patches - current had broken headers installation + few missing patches - dev was bumped to 5.8.y
6900 lines
225 KiB
Diff
6900 lines
225 KiB
Diff
diff --git a/Documentation/ABI/testing/sysfs-bus-iio b/Documentation/ABI/testing/sysfs-bus-iio
|
|
index 64e65450f4833..e21e2ca3e4f91 100644
|
|
--- a/Documentation/ABI/testing/sysfs-bus-iio
|
|
+++ b/Documentation/ABI/testing/sysfs-bus-iio
|
|
@@ -1524,7 +1524,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_concentrationX_voc_raw
|
|
KernelVersion: 4.3
|
|
Contact: linux-iio@vger.kernel.org
|
|
Description:
|
|
- Raw (unscaled no offset etc.) percentage reading of a substance.
|
|
+ Raw (unscaled no offset etc.) reading of a substance. Units
|
|
+ after application of scale and offset are percents.
|
|
|
|
What: /sys/bus/iio/devices/iio:deviceX/in_resistance_raw
|
|
What: /sys/bus/iio/devices/iio:deviceX/in_resistanceX_raw
|
|
diff --git a/Documentation/devicetree/bindings/iio/multiplexer/io-channel-mux.txt b/Documentation/devicetree/bindings/iio/multiplexer/io-channel-mux.txt
|
|
index c82794002595f..89647d7143879 100644
|
|
--- a/Documentation/devicetree/bindings/iio/multiplexer/io-channel-mux.txt
|
|
+++ b/Documentation/devicetree/bindings/iio/multiplexer/io-channel-mux.txt
|
|
@@ -21,7 +21,7 @@ controller state. The mux controller state is described in
|
|
|
|
Example:
|
|
mux: mux-controller {
|
|
- compatible = "mux-gpio";
|
|
+ compatible = "gpio-mux";
|
|
#mux-control-cells = <0>;
|
|
|
|
mux-gpios = <&pioA 0 GPIO_ACTIVE_HIGH>,
|
|
diff --git a/Makefile b/Makefile
|
|
index b30927f29e2b7..8e2a1418c5ae6 100644
|
|
--- a/Makefile
|
|
+++ b/Makefile
|
|
@@ -1,7 +1,7 @@
|
|
# SPDX-License-Identifier: GPL-2.0
|
|
VERSION = 4
|
|
PATCHLEVEL = 14
|
|
-SUBLEVEL = 193
|
|
+SUBLEVEL = 194
|
|
EXTRAVERSION =
|
|
NAME = Petit Gorille
|
|
|
|
diff --git a/arch/arm/kernel/stacktrace.c b/arch/arm/kernel/stacktrace.c
|
|
index 65228bf4c6dfe..ba9b9a77bcd2c 100644
|
|
--- a/arch/arm/kernel/stacktrace.c
|
|
+++ b/arch/arm/kernel/stacktrace.c
|
|
@@ -20,6 +20,19 @@
|
|
* A simple function epilogue looks like this:
|
|
* ldm sp, {fp, sp, pc}
|
|
*
|
|
+ * When compiled with clang, pc and sp are not pushed. A simple function
|
|
+ * prologue looks like this when built with clang:
|
|
+ *
|
|
+ * stmdb {..., fp, lr}
|
|
+ * add fp, sp, #x
|
|
+ * sub sp, sp, #y
|
|
+ *
|
|
+ * A simple function epilogue looks like this when built with clang:
|
|
+ *
|
|
+ * sub sp, fp, #x
|
|
+ * ldm {..., fp, pc}
|
|
+ *
|
|
+ *
|
|
* Note that with framepointer enabled, even the leaf functions have the same
|
|
* prologue and epilogue, therefore we can ignore the LR value in this case.
|
|
*/
|
|
@@ -32,6 +45,16 @@ int notrace unwind_frame(struct stackframe *frame)
|
|
low = frame->sp;
|
|
high = ALIGN(low, THREAD_SIZE);
|
|
|
|
+#ifdef CONFIG_CC_IS_CLANG
|
|
+ /* check current frame pointer is within bounds */
|
|
+ if (fp < low + 4 || fp > high - 4)
|
|
+ return -EINVAL;
|
|
+
|
|
+ frame->sp = frame->fp;
|
|
+ frame->fp = *(unsigned long *)(fp);
|
|
+ frame->pc = frame->lr;
|
|
+ frame->lr = *(unsigned long *)(fp + 4);
|
|
+#else
|
|
/* check current frame pointer is within bounds */
|
|
if (fp < low + 12 || fp > high - 4)
|
|
return -EINVAL;
|
|
@@ -40,6 +63,7 @@ int notrace unwind_frame(struct stackframe *frame)
|
|
frame->fp = *(unsigned long *)(fp - 12);
|
|
frame->sp = *(unsigned long *)(fp - 8);
|
|
frame->pc = *(unsigned long *)(fp - 4);
|
|
+#endif
|
|
|
|
return 0;
|
|
}
|
|
diff --git a/arch/arm/mach-at91/pm.c b/arch/arm/mach-at91/pm.c
|
|
index 849014c01cf4d..bebaa0b0aef40 100644
|
|
--- a/arch/arm/mach-at91/pm.c
|
|
+++ b/arch/arm/mach-at91/pm.c
|
|
@@ -456,13 +456,13 @@ static void __init at91_pm_sram_init(void)
|
|
sram_pool = gen_pool_get(&pdev->dev, NULL);
|
|
if (!sram_pool) {
|
|
pr_warn("%s: sram pool unavailable!\n", __func__);
|
|
- return;
|
|
+ goto out_put_device;
|
|
}
|
|
|
|
sram_base = gen_pool_alloc(sram_pool, at91_pm_suspend_in_sram_sz);
|
|
if (!sram_base) {
|
|
pr_warn("%s: unable to alloc sram!\n", __func__);
|
|
- return;
|
|
+ goto out_put_device;
|
|
}
|
|
|
|
sram_pbase = gen_pool_virt_to_phys(sram_pool, sram_base);
|
|
@@ -470,12 +470,17 @@ static void __init at91_pm_sram_init(void)
|
|
at91_pm_suspend_in_sram_sz, false);
|
|
if (!at91_suspend_sram_fn) {
|
|
pr_warn("SRAM: Could not map\n");
|
|
- return;
|
|
+ goto out_put_device;
|
|
}
|
|
|
|
/* Copy the pm suspend handler to SRAM */
|
|
at91_suspend_sram_fn = fncpy(at91_suspend_sram_fn,
|
|
&at91_pm_suspend_in_sram, at91_pm_suspend_in_sram_sz);
|
|
+ return;
|
|
+
|
|
+out_put_device:
|
|
+ put_device(&pdev->dev);
|
|
+ return;
|
|
}
|
|
|
|
static void __init at91_pm_backup_init(void)
|
|
diff --git a/arch/arm/mach-socfpga/pm.c b/arch/arm/mach-socfpga/pm.c
|
|
index c378ab0c24317..93f2245c97750 100644
|
|
--- a/arch/arm/mach-socfpga/pm.c
|
|
+++ b/arch/arm/mach-socfpga/pm.c
|
|
@@ -60,14 +60,14 @@ static int socfpga_setup_ocram_self_refresh(void)
|
|
if (!ocram_pool) {
|
|
pr_warn("%s: ocram pool unavailable!\n", __func__);
|
|
ret = -ENODEV;
|
|
- goto put_node;
|
|
+ goto put_device;
|
|
}
|
|
|
|
ocram_base = gen_pool_alloc(ocram_pool, socfpga_sdram_self_refresh_sz);
|
|
if (!ocram_base) {
|
|
pr_warn("%s: unable to alloc ocram!\n", __func__);
|
|
ret = -ENOMEM;
|
|
- goto put_node;
|
|
+ goto put_device;
|
|
}
|
|
|
|
ocram_pbase = gen_pool_virt_to_phys(ocram_pool, ocram_base);
|
|
@@ -78,7 +78,7 @@ static int socfpga_setup_ocram_self_refresh(void)
|
|
if (!suspend_ocram_base) {
|
|
pr_warn("%s: __arm_ioremap_exec failed!\n", __func__);
|
|
ret = -ENOMEM;
|
|
- goto put_node;
|
|
+ goto put_device;
|
|
}
|
|
|
|
/* Copy the code that puts DDR in self refresh to ocram */
|
|
@@ -92,6 +92,8 @@ static int socfpga_setup_ocram_self_refresh(void)
|
|
if (!socfpga_sdram_self_refresh_in_ocram)
|
|
ret = -EFAULT;
|
|
|
|
+put_device:
|
|
+ put_device(&pdev->dev);
|
|
put_node:
|
|
of_node_put(np);
|
|
|
|
diff --git a/arch/arm64/boot/dts/exynos/exynos7-espresso.dts b/arch/arm64/boot/dts/exynos/exynos7-espresso.dts
|
|
index 4a8b1fb51243c..c8824b918693d 100644
|
|
--- a/arch/arm64/boot/dts/exynos/exynos7-espresso.dts
|
|
+++ b/arch/arm64/boot/dts/exynos/exynos7-espresso.dts
|
|
@@ -155,6 +155,7 @@
|
|
regulator-min-microvolt = <700000>;
|
|
regulator-max-microvolt = <1150000>;
|
|
regulator-enable-ramp-delay = <125>;
|
|
+ regulator-always-on;
|
|
};
|
|
|
|
ldo8_reg: LDO8 {
|
|
diff --git a/arch/arm64/boot/dts/hisilicon/hi3660-hikey960.dts b/arch/arm64/boot/dts/hisilicon/hi3660-hikey960.dts
|
|
index e9f87cb61ade7..8587912e1eb00 100644
|
|
--- a/arch/arm64/boot/dts/hisilicon/hi3660-hikey960.dts
|
|
+++ b/arch/arm64/boot/dts/hisilicon/hi3660-hikey960.dts
|
|
@@ -210,6 +210,17 @@
|
|
status = "ok";
|
|
compatible = "adi,adv7533";
|
|
reg = <0x39>;
|
|
+ adi,dsi-lanes = <4>;
|
|
+ ports {
|
|
+ #address-cells = <1>;
|
|
+ #size-cells = <0>;
|
|
+ port@0 {
|
|
+ reg = <0>;
|
|
+ };
|
|
+ port@1 {
|
|
+ reg = <1>;
|
|
+ };
|
|
+ };
|
|
};
|
|
};
|
|
|
|
diff --git a/arch/arm64/boot/dts/hisilicon/hi6220-hikey.dts b/arch/arm64/boot/dts/hisilicon/hi6220-hikey.dts
|
|
index 6887cc1a743d4..f78e6468b02fc 100644
|
|
--- a/arch/arm64/boot/dts/hisilicon/hi6220-hikey.dts
|
|
+++ b/arch/arm64/boot/dts/hisilicon/hi6220-hikey.dts
|
|
@@ -513,7 +513,7 @@
|
|
reg = <0x39>;
|
|
interrupt-parent = <&gpio1>;
|
|
interrupts = <1 2>;
|
|
- pd-gpio = <&gpio0 4 0>;
|
|
+ pd-gpios = <&gpio0 4 0>;
|
|
adi,dsi-lanes = <4>;
|
|
#sound-dai-cells = <0>;
|
|
|
|
diff --git a/arch/arm64/boot/dts/qcom/msm8916-pins.dtsi b/arch/arm64/boot/dts/qcom/msm8916-pins.dtsi
|
|
index 4cb0b58341432..69ba1d79bcd5d 100644
|
|
--- a/arch/arm64/boot/dts/qcom/msm8916-pins.dtsi
|
|
+++ b/arch/arm64/boot/dts/qcom/msm8916-pins.dtsi
|
|
@@ -542,7 +542,7 @@
|
|
pins = "gpio63", "gpio64", "gpio65", "gpio66",
|
|
"gpio67", "gpio68";
|
|
drive-strength = <8>;
|
|
- bias-pull-none;
|
|
+ bias-disable;
|
|
};
|
|
};
|
|
cdc_pdm_lines_sus: pdm_lines_off {
|
|
@@ -571,7 +571,7 @@
|
|
pins = "gpio113", "gpio114", "gpio115",
|
|
"gpio116";
|
|
drive-strength = <8>;
|
|
- bias-pull-none;
|
|
+ bias-disable;
|
|
};
|
|
};
|
|
|
|
@@ -599,7 +599,7 @@
|
|
pinconf {
|
|
pins = "gpio110";
|
|
drive-strength = <8>;
|
|
- bias-pull-none;
|
|
+ bias-disable;
|
|
};
|
|
};
|
|
|
|
@@ -625,7 +625,7 @@
|
|
pinconf {
|
|
pins = "gpio116";
|
|
drive-strength = <8>;
|
|
- bias-pull-none;
|
|
+ bias-disable;
|
|
};
|
|
};
|
|
ext_mclk_tlmm_lines_sus: mclk_lines_off {
|
|
@@ -653,7 +653,7 @@
|
|
pins = "gpio112", "gpio117", "gpio118",
|
|
"gpio119";
|
|
drive-strength = <8>;
|
|
- bias-pull-none;
|
|
+ bias-disable;
|
|
};
|
|
};
|
|
ext_sec_tlmm_lines_sus: tlmm_lines_off {
|
|
diff --git a/arch/arm64/boot/dts/rockchip/rk3399-puma.dtsi b/arch/arm64/boot/dts/rockchip/rk3399-puma.dtsi
|
|
index 1fc5060d7027e..0d5679380b2a6 100644
|
|
--- a/arch/arm64/boot/dts/rockchip/rk3399-puma.dtsi
|
|
+++ b/arch/arm64/boot/dts/rockchip/rk3399-puma.dtsi
|
|
@@ -138,7 +138,7 @@
|
|
|
|
vcc5v0_host: vcc5v0-host-regulator {
|
|
compatible = "regulator-fixed";
|
|
- gpio = <&gpio4 RK_PA3 GPIO_ACTIVE_HIGH>;
|
|
+ gpio = <&gpio4 RK_PA3 GPIO_ACTIVE_LOW>;
|
|
enable-active-low;
|
|
pinctrl-names = "default";
|
|
pinctrl-0 = <&vcc5v0_host_en>;
|
|
@@ -193,7 +193,7 @@
|
|
phy-mode = "rgmii";
|
|
pinctrl-names = "default";
|
|
pinctrl-0 = <&rgmii_pins>;
|
|
- snps,reset-gpio = <&gpio3 RK_PC0 GPIO_ACTIVE_HIGH>;
|
|
+ snps,reset-gpio = <&gpio3 RK_PC0 GPIO_ACTIVE_LOW>;
|
|
snps,reset-active-low;
|
|
snps,reset-delays-us = <0 10000 50000>;
|
|
tx_delay = <0x10>;
|
|
diff --git a/arch/m68k/mac/iop.c b/arch/m68k/mac/iop.c
|
|
index 4c1e606e7d03b..0b94f6672c5f3 100644
|
|
--- a/arch/m68k/mac/iop.c
|
|
+++ b/arch/m68k/mac/iop.c
|
|
@@ -183,7 +183,7 @@ static __inline__ void iop_writeb(volatile struct mac_iop *iop, __u16 addr, __u8
|
|
|
|
static __inline__ void iop_stop(volatile struct mac_iop *iop)
|
|
{
|
|
- iop->status_ctrl &= ~IOP_RUN;
|
|
+ iop->status_ctrl = IOP_AUTOINC;
|
|
}
|
|
|
|
static __inline__ void iop_start(volatile struct mac_iop *iop)
|
|
@@ -191,14 +191,9 @@ static __inline__ void iop_start(volatile struct mac_iop *iop)
|
|
iop->status_ctrl = IOP_RUN | IOP_AUTOINC;
|
|
}
|
|
|
|
-static __inline__ void iop_bypass(volatile struct mac_iop *iop)
|
|
-{
|
|
- iop->status_ctrl |= IOP_BYPASS;
|
|
-}
|
|
-
|
|
static __inline__ void iop_interrupt(volatile struct mac_iop *iop)
|
|
{
|
|
- iop->status_ctrl |= IOP_IRQ;
|
|
+ iop->status_ctrl = IOP_IRQ | IOP_RUN | IOP_AUTOINC;
|
|
}
|
|
|
|
static int iop_alive(volatile struct mac_iop *iop)
|
|
@@ -244,7 +239,6 @@ void __init iop_preinit(void)
|
|
} else {
|
|
iop_base[IOP_NUM_SCC] = (struct mac_iop *) SCC_IOP_BASE_QUADRA;
|
|
}
|
|
- iop_base[IOP_NUM_SCC]->status_ctrl = 0x87;
|
|
iop_scc_present = 1;
|
|
} else {
|
|
iop_base[IOP_NUM_SCC] = NULL;
|
|
@@ -256,7 +250,7 @@ void __init iop_preinit(void)
|
|
} else {
|
|
iop_base[IOP_NUM_ISM] = (struct mac_iop *) ISM_IOP_BASE_QUADRA;
|
|
}
|
|
- iop_base[IOP_NUM_ISM]->status_ctrl = 0;
|
|
+ iop_stop(iop_base[IOP_NUM_ISM]);
|
|
iop_ism_present = 1;
|
|
} else {
|
|
iop_base[IOP_NUM_ISM] = NULL;
|
|
@@ -416,7 +410,8 @@ static void iop_handle_send(uint iop_num, uint chan)
|
|
msg->status = IOP_MSGSTATUS_UNUSED;
|
|
msg = msg->next;
|
|
iop_send_queue[iop_num][chan] = msg;
|
|
- if (msg) iop_do_send(msg);
|
|
+ if (msg && iop_readb(iop, IOP_ADDR_SEND_STATE + chan) == IOP_MSG_IDLE)
|
|
+ iop_do_send(msg);
|
|
}
|
|
|
|
/*
|
|
@@ -490,16 +485,12 @@ int iop_send_message(uint iop_num, uint chan, void *privdata,
|
|
|
|
if (!(q = iop_send_queue[iop_num][chan])) {
|
|
iop_send_queue[iop_num][chan] = msg;
|
|
+ iop_do_send(msg);
|
|
} else {
|
|
while (q->next) q = q->next;
|
|
q->next = msg;
|
|
}
|
|
|
|
- if (iop_readb(iop_base[iop_num],
|
|
- IOP_ADDR_SEND_STATE + chan) == IOP_MSG_IDLE) {
|
|
- iop_do_send(msg);
|
|
- }
|
|
-
|
|
return 0;
|
|
}
|
|
|
|
diff --git a/arch/mips/cavium-octeon/octeon-usb.c b/arch/mips/cavium-octeon/octeon-usb.c
|
|
index bfdfaf32d2c49..75189ff2f3c78 100644
|
|
--- a/arch/mips/cavium-octeon/octeon-usb.c
|
|
+++ b/arch/mips/cavium-octeon/octeon-usb.c
|
|
@@ -517,6 +517,7 @@ static int __init dwc3_octeon_device_init(void)
|
|
|
|
res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
|
|
if (res == NULL) {
|
|
+ put_device(&pdev->dev);
|
|
dev_err(&pdev->dev, "No memory resources\n");
|
|
return -ENXIO;
|
|
}
|
|
@@ -528,8 +529,10 @@ static int __init dwc3_octeon_device_init(void)
|
|
* know the difference.
|
|
*/
|
|
base = devm_ioremap_resource(&pdev->dev, res);
|
|
- if (IS_ERR(base))
|
|
+ if (IS_ERR(base)) {
|
|
+ put_device(&pdev->dev);
|
|
return PTR_ERR(base);
|
|
+ }
|
|
|
|
mutex_lock(&dwc3_octeon_clocks_mutex);
|
|
dwc3_octeon_clocks_start(&pdev->dev, (u64)base);
|
|
diff --git a/arch/mips/kernel/topology.c b/arch/mips/kernel/topology.c
|
|
index cd3e1f82e1a5d..08ad6371fbe08 100644
|
|
--- a/arch/mips/kernel/topology.c
|
|
+++ b/arch/mips/kernel/topology.c
|
|
@@ -20,7 +20,7 @@ static int __init topology_init(void)
|
|
for_each_present_cpu(i) {
|
|
struct cpu *c = &per_cpu(cpu_devices, i);
|
|
|
|
- c->hotpluggable = 1;
|
|
+ c->hotpluggable = !!i;
|
|
ret = register_cpu(c, i);
|
|
if (ret)
|
|
printk(KERN_WARNING "topology_init: register_cpu %d "
|
|
diff --git a/arch/parisc/include/asm/barrier.h b/arch/parisc/include/asm/barrier.h
|
|
index dbaaca84f27f3..640d46edf32e7 100644
|
|
--- a/arch/parisc/include/asm/barrier.h
|
|
+++ b/arch/parisc/include/asm/barrier.h
|
|
@@ -26,6 +26,67 @@
|
|
#define __smp_rmb() mb()
|
|
#define __smp_wmb() mb()
|
|
|
|
+#define __smp_store_release(p, v) \
|
|
+do { \
|
|
+ typeof(p) __p = (p); \
|
|
+ union { typeof(*p) __val; char __c[1]; } __u = \
|
|
+ { .__val = (__force typeof(*p)) (v) }; \
|
|
+ compiletime_assert_atomic_type(*p); \
|
|
+ switch (sizeof(*p)) { \
|
|
+ case 1: \
|
|
+ asm volatile("stb,ma %0,0(%1)" \
|
|
+ : : "r"(*(__u8 *)__u.__c), "r"(__p) \
|
|
+ : "memory"); \
|
|
+ break; \
|
|
+ case 2: \
|
|
+ asm volatile("sth,ma %0,0(%1)" \
|
|
+ : : "r"(*(__u16 *)__u.__c), "r"(__p) \
|
|
+ : "memory"); \
|
|
+ break; \
|
|
+ case 4: \
|
|
+ asm volatile("stw,ma %0,0(%1)" \
|
|
+ : : "r"(*(__u32 *)__u.__c), "r"(__p) \
|
|
+ : "memory"); \
|
|
+ break; \
|
|
+ case 8: \
|
|
+ if (IS_ENABLED(CONFIG_64BIT)) \
|
|
+ asm volatile("std,ma %0,0(%1)" \
|
|
+ : : "r"(*(__u64 *)__u.__c), "r"(__p) \
|
|
+ : "memory"); \
|
|
+ break; \
|
|
+ } \
|
|
+} while (0)
|
|
+
|
|
+#define __smp_load_acquire(p) \
|
|
+({ \
|
|
+ union { typeof(*p) __val; char __c[1]; } __u; \
|
|
+ typeof(p) __p = (p); \
|
|
+ compiletime_assert_atomic_type(*p); \
|
|
+ switch (sizeof(*p)) { \
|
|
+ case 1: \
|
|
+ asm volatile("ldb,ma 0(%1),%0" \
|
|
+ : "=r"(*(__u8 *)__u.__c) : "r"(__p) \
|
|
+ : "memory"); \
|
|
+ break; \
|
|
+ case 2: \
|
|
+ asm volatile("ldh,ma 0(%1),%0" \
|
|
+ : "=r"(*(__u16 *)__u.__c) : "r"(__p) \
|
|
+ : "memory"); \
|
|
+ break; \
|
|
+ case 4: \
|
|
+ asm volatile("ldw,ma 0(%1),%0" \
|
|
+ : "=r"(*(__u32 *)__u.__c) : "r"(__p) \
|
|
+ : "memory"); \
|
|
+ break; \
|
|
+ case 8: \
|
|
+ if (IS_ENABLED(CONFIG_64BIT)) \
|
|
+ asm volatile("ldd,ma 0(%1),%0" \
|
|
+ : "=r"(*(__u64 *)__u.__c) : "r"(__p) \
|
|
+ : "memory"); \
|
|
+ break; \
|
|
+ } \
|
|
+ __u.__val; \
|
|
+})
|
|
#include <asm-generic/barrier.h>
|
|
|
|
#endif /* !__ASSEMBLY__ */
|
|
diff --git a/arch/powerpc/include/asm/percpu.h b/arch/powerpc/include/asm/percpu.h
|
|
index dce863a7635cd..8e5b7d0b851c6 100644
|
|
--- a/arch/powerpc/include/asm/percpu.h
|
|
+++ b/arch/powerpc/include/asm/percpu.h
|
|
@@ -10,8 +10,6 @@
|
|
|
|
#ifdef CONFIG_SMP
|
|
|
|
-#include <asm/paca.h>
|
|
-
|
|
#define __my_cpu_offset local_paca->data_offset
|
|
|
|
#endif /* CONFIG_SMP */
|
|
@@ -19,4 +17,6 @@
|
|
|
|
#include <asm-generic/percpu.h>
|
|
|
|
+#include <asm/paca.h>
|
|
+
|
|
#endif /* _ASM_POWERPC_PERCPU_H_ */
|
|
diff --git a/arch/powerpc/kernel/vdso.c b/arch/powerpc/kernel/vdso.c
|
|
index 22b01a3962f06..3edaee28b6383 100644
|
|
--- a/arch/powerpc/kernel/vdso.c
|
|
+++ b/arch/powerpc/kernel/vdso.c
|
|
@@ -704,7 +704,7 @@ int vdso_getcpu_init(void)
|
|
node = cpu_to_node(cpu);
|
|
WARN_ON_ONCE(node > 0xffff);
|
|
|
|
- val = (cpu & 0xfff) | ((node & 0xffff) << 16);
|
|
+ val = (cpu & 0xffff) | ((node & 0xffff) << 16);
|
|
mtspr(SPRN_SPRG_VDSO_WRITE, val);
|
|
get_paca()->sprg_vdso = val;
|
|
|
|
diff --git a/arch/powerpc/platforms/pseries/hotplug-memory.c b/arch/powerpc/platforms/pseries/hotplug-memory.c
|
|
index a0847be0b0358..1a3cffdaa1e8a 100644
|
|
--- a/arch/powerpc/platforms/pseries/hotplug-memory.c
|
|
+++ b/arch/powerpc/platforms/pseries/hotplug-memory.c
|
|
@@ -30,7 +30,7 @@ static bool rtas_hp_event;
|
|
unsigned long pseries_memory_block_size(void)
|
|
{
|
|
struct device_node *np;
|
|
- unsigned int memblock_size = MIN_MEMORY_BLOCK_SIZE;
|
|
+ u64 memblock_size = MIN_MEMORY_BLOCK_SIZE;
|
|
struct resource r;
|
|
|
|
np = of_find_node_by_path("/ibm,dynamic-reconfiguration-memory");
|
|
diff --git a/arch/sh/boards/mach-landisk/setup.c b/arch/sh/boards/mach-landisk/setup.c
|
|
index f1147caebacf0..af69fb7fef7c7 100644
|
|
--- a/arch/sh/boards/mach-landisk/setup.c
|
|
+++ b/arch/sh/boards/mach-landisk/setup.c
|
|
@@ -85,6 +85,9 @@ device_initcall(landisk_devices_setup);
|
|
|
|
static void __init landisk_setup(char **cmdline_p)
|
|
{
|
|
+ /* I/O port identity mapping */
|
|
+ __set_io_port_base(0);
|
|
+
|
|
/* LED ON */
|
|
__raw_writeb(__raw_readb(PA_LED) | 0x03, PA_LED);
|
|
|
|
diff --git a/arch/x86/crypto/aes_ctrby8_avx-x86_64.S b/arch/x86/crypto/aes_ctrby8_avx-x86_64.S
|
|
index 5f6a5af9c489b..77043a82da510 100644
|
|
--- a/arch/x86/crypto/aes_ctrby8_avx-x86_64.S
|
|
+++ b/arch/x86/crypto/aes_ctrby8_avx-x86_64.S
|
|
@@ -127,10 +127,6 @@ ddq_add_8:
|
|
|
|
/* generate a unique variable for ddq_add_x */
|
|
|
|
-.macro setddq n
|
|
- var_ddq_add = ddq_add_\n
|
|
-.endm
|
|
-
|
|
/* generate a unique variable for xmm register */
|
|
.macro setxdata n
|
|
var_xdata = %xmm\n
|
|
@@ -140,9 +136,7 @@ ddq_add_8:
|
|
|
|
.macro club name, id
|
|
.altmacro
|
|
- .if \name == DDQ_DATA
|
|
- setddq %\id
|
|
- .elseif \name == XDATA
|
|
+ .if \name == XDATA
|
|
setxdata %\id
|
|
.endif
|
|
.noaltmacro
|
|
@@ -165,9 +159,8 @@ ddq_add_8:
|
|
|
|
.set i, 1
|
|
.rept (by - 1)
|
|
- club DDQ_DATA, i
|
|
club XDATA, i
|
|
- vpaddq var_ddq_add(%rip), xcounter, var_xdata
|
|
+ vpaddq (ddq_add_1 + 16 * (i - 1))(%rip), xcounter, var_xdata
|
|
vptest ddq_low_msk(%rip), var_xdata
|
|
jnz 1f
|
|
vpaddq ddq_high_add_1(%rip), var_xdata, var_xdata
|
|
@@ -180,8 +173,7 @@ ddq_add_8:
|
|
vmovdqa 1*16(p_keys), xkeyA
|
|
|
|
vpxor xkey0, xdata0, xdata0
|
|
- club DDQ_DATA, by
|
|
- vpaddq var_ddq_add(%rip), xcounter, xcounter
|
|
+ vpaddq (ddq_add_1 + 16 * (by - 1))(%rip), xcounter, xcounter
|
|
vptest ddq_low_msk(%rip), xcounter
|
|
jnz 1f
|
|
vpaddq ddq_high_add_1(%rip), xcounter, xcounter
|
|
diff --git a/arch/x86/kernel/apic/io_apic.c b/arch/x86/kernel/apic/io_apic.c
|
|
index b5652233e6745..a1c4a13782da8 100644
|
|
--- a/arch/x86/kernel/apic/io_apic.c
|
|
+++ b/arch/x86/kernel/apic/io_apic.c
|
|
@@ -2252,8 +2252,13 @@ static int mp_irqdomain_create(int ioapic)
|
|
|
|
static void ioapic_destroy_irqdomain(int idx)
|
|
{
|
|
+ struct ioapic_domain_cfg *cfg = &ioapics[idx].irqdomain_cfg;
|
|
+ struct fwnode_handle *fn = ioapics[idx].irqdomain->fwnode;
|
|
+
|
|
if (ioapics[idx].irqdomain) {
|
|
irq_domain_remove(ioapics[idx].irqdomain);
|
|
+ if (!cfg->dev)
|
|
+ irq_domain_free_fwnode(fn);
|
|
ioapics[idx].irqdomain = NULL;
|
|
}
|
|
}
|
|
diff --git a/arch/x86/kernel/apic/vector.c b/arch/x86/kernel/apic/vector.c
|
|
index 36cd34524ac19..637cf4dfccc9a 100644
|
|
--- a/arch/x86/kernel/apic/vector.c
|
|
+++ b/arch/x86/kernel/apic/vector.c
|
|
@@ -368,6 +368,10 @@ static int x86_vector_alloc_irqs(struct irq_domain *domain, unsigned int virq,
|
|
irq_data->chip = &lapic_controller;
|
|
irq_data->chip_data = data;
|
|
irq_data->hwirq = virq + i;
|
|
+
|
|
+ /* Don't invoke affinity setter on deactivated interrupts */
|
|
+ irqd_set_affinity_on_activate(irq_data);
|
|
+
|
|
err = assign_irq_vector_policy(virq + i, node, data, info,
|
|
irq_data);
|
|
if (err) {
|
|
diff --git a/arch/x86/kernel/cpu/mcheck/mce-inject.c b/arch/x86/kernel/cpu/mcheck/mce-inject.c
|
|
index e57b59762f9f5..94aa91b09c288 100644
|
|
--- a/arch/x86/kernel/cpu/mcheck/mce-inject.c
|
|
+++ b/arch/x86/kernel/cpu/mcheck/mce-inject.c
|
|
@@ -518,7 +518,7 @@ static void do_inject(void)
|
|
*/
|
|
if (inj_type == DFR_INT_INJ) {
|
|
i_mce.status |= MCI_STATUS_DEFERRED;
|
|
- i_mce.status |= (i_mce.status & ~MCI_STATUS_UC);
|
|
+ i_mce.status &= ~MCI_STATUS_UC;
|
|
}
|
|
|
|
/*
|
|
diff --git a/arch/x86/kernel/ptrace.c b/arch/x86/kernel/ptrace.c
|
|
index 734549492a18b..dc4d27000aa35 100644
|
|
--- a/arch/x86/kernel/ptrace.c
|
|
+++ b/arch/x86/kernel/ptrace.c
|
|
@@ -374,7 +374,7 @@ static unsigned long task_seg_base(struct task_struct *task,
|
|
*/
|
|
mutex_lock(&task->mm->context.lock);
|
|
ldt = task->mm->context.ldt;
|
|
- if (unlikely(idx >= ldt->nr_entries))
|
|
+ if (unlikely(!ldt || idx >= ldt->nr_entries))
|
|
base = 0;
|
|
else
|
|
base = get_desc_base(ldt->entries + idx);
|
|
diff --git a/arch/xtensa/kernel/perf_event.c b/arch/xtensa/kernel/perf_event.c
|
|
index ff1d81385ed7a..768e1f7ab8715 100644
|
|
--- a/arch/xtensa/kernel/perf_event.c
|
|
+++ b/arch/xtensa/kernel/perf_event.c
|
|
@@ -404,7 +404,7 @@ static struct pmu xtensa_pmu = {
|
|
.read = xtensa_pmu_read,
|
|
};
|
|
|
|
-static int xtensa_pmu_setup(int cpu)
|
|
+static int xtensa_pmu_setup(unsigned int cpu)
|
|
{
|
|
unsigned i;
|
|
|
|
diff --git a/drivers/acpi/acpica/exprep.c b/drivers/acpi/acpica/exprep.c
|
|
index 8de060664204e..e23f3d54bb31c 100644
|
|
--- a/drivers/acpi/acpica/exprep.c
|
|
+++ b/drivers/acpi/acpica/exprep.c
|
|
@@ -507,10 +507,6 @@ acpi_status acpi_ex_prep_field_value(struct acpi_create_field_info *info)
|
|
(u8)access_byte_width;
|
|
}
|
|
}
|
|
- /* An additional reference for the container */
|
|
-
|
|
- acpi_ut_add_reference(obj_desc->field.region_obj);
|
|
-
|
|
ACPI_DEBUG_PRINT((ACPI_DB_BFIELD,
|
|
"RegionField: BitOff %X, Off %X, Gran %X, Region %p\n",
|
|
obj_desc->field.start_field_bit_offset,
|
|
diff --git a/drivers/acpi/acpica/utdelete.c b/drivers/acpi/acpica/utdelete.c
|
|
index c6eb9fae70f9a..61a979d0fbc5a 100644
|
|
--- a/drivers/acpi/acpica/utdelete.c
|
|
+++ b/drivers/acpi/acpica/utdelete.c
|
|
@@ -593,11 +593,6 @@ acpi_ut_update_object_reference(union acpi_operand_object *object, u16 action)
|
|
next_object = object->buffer_field.buffer_obj;
|
|
break;
|
|
|
|
- case ACPI_TYPE_LOCAL_REGION_FIELD:
|
|
-
|
|
- next_object = object->field.region_obj;
|
|
- break;
|
|
-
|
|
case ACPI_TYPE_LOCAL_BANK_FIELD:
|
|
|
|
next_object = object->bank_field.bank_obj;
|
|
@@ -638,6 +633,7 @@ acpi_ut_update_object_reference(union acpi_operand_object *object, u16 action)
|
|
}
|
|
break;
|
|
|
|
+ case ACPI_TYPE_LOCAL_REGION_FIELD:
|
|
case ACPI_TYPE_REGION:
|
|
default:
|
|
|
|
diff --git a/drivers/android/binder.c b/drivers/android/binder.c
|
|
index 05e75d18b4d93..bd74a29cf86c4 100644
|
|
--- a/drivers/android/binder.c
|
|
+++ b/drivers/android/binder.c
|
|
@@ -2813,6 +2813,12 @@ static void binder_transaction(struct binder_proc *proc,
|
|
goto err_dead_binder;
|
|
}
|
|
e->to_node = target_node->debug_id;
|
|
+ if (WARN_ON(proc == target_proc)) {
|
|
+ return_error = BR_FAILED_REPLY;
|
|
+ return_error_param = -EINVAL;
|
|
+ return_error_line = __LINE__;
|
|
+ goto err_invalid_target_handle;
|
|
+ }
|
|
if (security_binder_transaction(proc->tsk,
|
|
target_proc->tsk) < 0) {
|
|
return_error = BR_FAILED_REPLY;
|
|
@@ -3288,10 +3294,17 @@ static int binder_thread_write(struct binder_proc *proc,
|
|
struct binder_node *ctx_mgr_node;
|
|
mutex_lock(&context->context_mgr_node_lock);
|
|
ctx_mgr_node = context->binder_context_mgr_node;
|
|
- if (ctx_mgr_node)
|
|
+ if (ctx_mgr_node) {
|
|
+ if (ctx_mgr_node->proc == proc) {
|
|
+ binder_user_error("%d:%d context manager tried to acquire desc 0\n",
|
|
+ proc->pid, thread->pid);
|
|
+ mutex_unlock(&context->context_mgr_node_lock);
|
|
+ return -EINVAL;
|
|
+ }
|
|
ret = binder_inc_ref_for_node(
|
|
proc, ctx_mgr_node,
|
|
strong, NULL, &rdata);
|
|
+ }
|
|
mutex_unlock(&context->context_mgr_node_lock);
|
|
}
|
|
if (ret)
|
|
diff --git a/drivers/atm/atmtcp.c b/drivers/atm/atmtcp.c
|
|
index afebeb1c3e1e9..723bad1201cc5 100644
|
|
--- a/drivers/atm/atmtcp.c
|
|
+++ b/drivers/atm/atmtcp.c
|
|
@@ -432,9 +432,15 @@ static int atmtcp_remove_persistent(int itf)
|
|
return -EMEDIUMTYPE;
|
|
}
|
|
dev_data = PRIV(dev);
|
|
- if (!dev_data->persist) return 0;
|
|
+ if (!dev_data->persist) {
|
|
+ atm_dev_put(dev);
|
|
+ return 0;
|
|
+ }
|
|
dev_data->persist = 0;
|
|
- if (PRIV(dev)->vcc) return 0;
|
|
+ if (PRIV(dev)->vcc) {
|
|
+ atm_dev_put(dev);
|
|
+ return 0;
|
|
+ }
|
|
kfree(dev_data);
|
|
atm_dev_put(dev);
|
|
atm_dev_deregister(dev);
|
|
diff --git a/drivers/bluetooth/hci_serdev.c b/drivers/bluetooth/hci_serdev.c
|
|
index 69c00a3db5382..72cf2d97b682c 100644
|
|
--- a/drivers/bluetooth/hci_serdev.c
|
|
+++ b/drivers/bluetooth/hci_serdev.c
|
|
@@ -361,7 +361,8 @@ void hci_uart_unregister_device(struct hci_uart *hu)
|
|
struct hci_dev *hdev = hu->hdev;
|
|
|
|
clear_bit(HCI_UART_PROTO_READY, &hu->flags);
|
|
- hci_unregister_dev(hdev);
|
|
+ if (test_bit(HCI_UART_REGISTERED, &hu->flags))
|
|
+ hci_unregister_dev(hdev);
|
|
hci_free_dev(hdev);
|
|
|
|
cancel_work_sync(&hu->write_work);
|
|
diff --git a/drivers/char/agp/intel-gtt.c b/drivers/char/agp/intel-gtt.c
|
|
index 7516ba981b635..34cc853772bc4 100644
|
|
--- a/drivers/char/agp/intel-gtt.c
|
|
+++ b/drivers/char/agp/intel-gtt.c
|
|
@@ -304,8 +304,10 @@ static int intel_gtt_setup_scratch_page(void)
|
|
if (intel_private.needs_dmar) {
|
|
dma_addr = pci_map_page(intel_private.pcidev, page, 0,
|
|
PAGE_SIZE, PCI_DMA_BIDIRECTIONAL);
|
|
- if (pci_dma_mapping_error(intel_private.pcidev, dma_addr))
|
|
+ if (pci_dma_mapping_error(intel_private.pcidev, dma_addr)) {
|
|
+ __free_page(page);
|
|
return -EINVAL;
|
|
+ }
|
|
|
|
intel_private.scratch_page_dma = dma_addr;
|
|
} else
|
|
diff --git a/drivers/clk/sirf/clk-atlas6.c b/drivers/clk/sirf/clk-atlas6.c
|
|
index 665fa681b2e1e..1e6bdf22c3b64 100644
|
|
--- a/drivers/clk/sirf/clk-atlas6.c
|
|
+++ b/drivers/clk/sirf/clk-atlas6.c
|
|
@@ -136,7 +136,7 @@ static void __init atlas6_clk_init(struct device_node *np)
|
|
|
|
for (i = pll1; i < maxclk; i++) {
|
|
atlas6_clks[i] = clk_register(NULL, atlas6_clk_hw_array[i]);
|
|
- BUG_ON(!atlas6_clks[i]);
|
|
+ BUG_ON(IS_ERR(atlas6_clks[i]));
|
|
}
|
|
clk_register_clkdev(atlas6_clks[cpu], NULL, "cpu");
|
|
clk_register_clkdev(atlas6_clks[io], NULL, "io");
|
|
diff --git a/drivers/crypto/cavium/cpt/cptvf_algs.c b/drivers/crypto/cavium/cpt/cptvf_algs.c
|
|
index df21d996db7ed..2d1b28c29a8e5 100644
|
|
--- a/drivers/crypto/cavium/cpt/cptvf_algs.c
|
|
+++ b/drivers/crypto/cavium/cpt/cptvf_algs.c
|
|
@@ -205,6 +205,7 @@ static inline int cvm_enc_dec(struct ablkcipher_request *req, u32 enc)
|
|
int status;
|
|
|
|
memset(req_info, 0, sizeof(struct cpt_request_info));
|
|
+ req_info->may_sleep = (req->base.flags & CRYPTO_TFM_REQ_MAY_SLEEP) != 0;
|
|
memset(fctx, 0, sizeof(struct fc_context));
|
|
create_input_list(req, enc, enc_iv_len);
|
|
create_output_list(req, enc_iv_len);
|
|
diff --git a/drivers/crypto/cavium/cpt/cptvf_reqmanager.c b/drivers/crypto/cavium/cpt/cptvf_reqmanager.c
|
|
index b0ba4331944b5..43fe69d0981ac 100644
|
|
--- a/drivers/crypto/cavium/cpt/cptvf_reqmanager.c
|
|
+++ b/drivers/crypto/cavium/cpt/cptvf_reqmanager.c
|
|
@@ -136,7 +136,7 @@ static inline int setup_sgio_list(struct cpt_vf *cptvf,
|
|
|
|
/* Setup gather (input) components */
|
|
g_sz_bytes = ((req->incnt + 3) / 4) * sizeof(struct sglist_component);
|
|
- info->gather_components = kzalloc(g_sz_bytes, GFP_KERNEL);
|
|
+ info->gather_components = kzalloc(g_sz_bytes, req->may_sleep ? GFP_KERNEL : GFP_ATOMIC);
|
|
if (!info->gather_components) {
|
|
ret = -ENOMEM;
|
|
goto scatter_gather_clean;
|
|
@@ -153,7 +153,7 @@ static inline int setup_sgio_list(struct cpt_vf *cptvf,
|
|
|
|
/* Setup scatter (output) components */
|
|
s_sz_bytes = ((req->outcnt + 3) / 4) * sizeof(struct sglist_component);
|
|
- info->scatter_components = kzalloc(s_sz_bytes, GFP_KERNEL);
|
|
+ info->scatter_components = kzalloc(s_sz_bytes, req->may_sleep ? GFP_KERNEL : GFP_ATOMIC);
|
|
if (!info->scatter_components) {
|
|
ret = -ENOMEM;
|
|
goto scatter_gather_clean;
|
|
@@ -170,7 +170,7 @@ static inline int setup_sgio_list(struct cpt_vf *cptvf,
|
|
|
|
/* Create and initialize DPTR */
|
|
info->dlen = g_sz_bytes + s_sz_bytes + SG_LIST_HDR_SIZE;
|
|
- info->in_buffer = kzalloc(info->dlen, GFP_KERNEL);
|
|
+ info->in_buffer = kzalloc(info->dlen, req->may_sleep ? GFP_KERNEL : GFP_ATOMIC);
|
|
if (!info->in_buffer) {
|
|
ret = -ENOMEM;
|
|
goto scatter_gather_clean;
|
|
@@ -198,7 +198,7 @@ static inline int setup_sgio_list(struct cpt_vf *cptvf,
|
|
}
|
|
|
|
/* Create and initialize RPTR */
|
|
- info->out_buffer = kzalloc(COMPLETION_CODE_SIZE, GFP_KERNEL);
|
|
+ info->out_buffer = kzalloc(COMPLETION_CODE_SIZE, req->may_sleep ? GFP_KERNEL : GFP_ATOMIC);
|
|
if (!info->out_buffer) {
|
|
ret = -ENOMEM;
|
|
goto scatter_gather_clean;
|
|
@@ -434,7 +434,7 @@ int process_request(struct cpt_vf *cptvf, struct cpt_request_info *req)
|
|
struct cpt_vq_command vq_cmd;
|
|
union cpt_inst_s cptinst;
|
|
|
|
- info = kzalloc(sizeof(*info), GFP_KERNEL);
|
|
+ info = kzalloc(sizeof(*info), req->may_sleep ? GFP_KERNEL : GFP_ATOMIC);
|
|
if (unlikely(!info)) {
|
|
dev_err(&pdev->dev, "Unable to allocate memory for info_buffer\n");
|
|
return -ENOMEM;
|
|
@@ -456,7 +456,7 @@ int process_request(struct cpt_vf *cptvf, struct cpt_request_info *req)
|
|
* Get buffer for union cpt_res_s response
|
|
* structure and its physical address
|
|
*/
|
|
- info->completion_addr = kzalloc(sizeof(union cpt_res_s), GFP_KERNEL);
|
|
+ info->completion_addr = kzalloc(sizeof(union cpt_res_s), req->may_sleep ? GFP_KERNEL : GFP_ATOMIC);
|
|
if (unlikely(!info->completion_addr)) {
|
|
dev_err(&pdev->dev, "Unable to allocate memory for completion_addr\n");
|
|
ret = -ENOMEM;
|
|
diff --git a/drivers/crypto/cavium/cpt/request_manager.h b/drivers/crypto/cavium/cpt/request_manager.h
|
|
index 80ee074c6e0cb..09930d95ad24b 100644
|
|
--- a/drivers/crypto/cavium/cpt/request_manager.h
|
|
+++ b/drivers/crypto/cavium/cpt/request_manager.h
|
|
@@ -65,6 +65,8 @@ struct cpt_request_info {
|
|
union ctrl_info ctrl; /* User control information */
|
|
struct cptvf_request req; /* Request Information (Core specific) */
|
|
|
|
+ bool may_sleep;
|
|
+
|
|
struct buf_ptr in[MAX_BUF_CNT];
|
|
struct buf_ptr out[MAX_BUF_CNT];
|
|
|
|
diff --git a/drivers/crypto/ccp/ccp-dev.h b/drivers/crypto/ccp/ccp-dev.h
|
|
index 7442b0422f8ac..bd43b5c1450c1 100644
|
|
--- a/drivers/crypto/ccp/ccp-dev.h
|
|
+++ b/drivers/crypto/ccp/ccp-dev.h
|
|
@@ -471,6 +471,7 @@ struct ccp_sg_workarea {
|
|
unsigned int sg_used;
|
|
|
|
struct scatterlist *dma_sg;
|
|
+ struct scatterlist *dma_sg_head;
|
|
struct device *dma_dev;
|
|
unsigned int dma_count;
|
|
enum dma_data_direction dma_dir;
|
|
diff --git a/drivers/crypto/ccp/ccp-ops.c b/drivers/crypto/ccp/ccp-ops.c
|
|
index 43b74cf0787e1..626b643d610eb 100644
|
|
--- a/drivers/crypto/ccp/ccp-ops.c
|
|
+++ b/drivers/crypto/ccp/ccp-ops.c
|
|
@@ -67,7 +67,7 @@ static u32 ccp_gen_jobid(struct ccp_device *ccp)
|
|
static void ccp_sg_free(struct ccp_sg_workarea *wa)
|
|
{
|
|
if (wa->dma_count)
|
|
- dma_unmap_sg(wa->dma_dev, wa->dma_sg, wa->nents, wa->dma_dir);
|
|
+ dma_unmap_sg(wa->dma_dev, wa->dma_sg_head, wa->nents, wa->dma_dir);
|
|
|
|
wa->dma_count = 0;
|
|
}
|
|
@@ -96,6 +96,7 @@ static int ccp_init_sg_workarea(struct ccp_sg_workarea *wa, struct device *dev,
|
|
return 0;
|
|
|
|
wa->dma_sg = sg;
|
|
+ wa->dma_sg_head = sg;
|
|
wa->dma_dev = dev;
|
|
wa->dma_dir = dma_dir;
|
|
wa->dma_count = dma_map_sg(dev, sg, wa->nents, dma_dir);
|
|
@@ -108,14 +109,28 @@ static int ccp_init_sg_workarea(struct ccp_sg_workarea *wa, struct device *dev,
|
|
static void ccp_update_sg_workarea(struct ccp_sg_workarea *wa, unsigned int len)
|
|
{
|
|
unsigned int nbytes = min_t(u64, len, wa->bytes_left);
|
|
+ unsigned int sg_combined_len = 0;
|
|
|
|
if (!wa->sg)
|
|
return;
|
|
|
|
wa->sg_used += nbytes;
|
|
wa->bytes_left -= nbytes;
|
|
- if (wa->sg_used == wa->sg->length) {
|
|
- wa->sg = sg_next(wa->sg);
|
|
+ if (wa->sg_used == sg_dma_len(wa->dma_sg)) {
|
|
+ /* Advance to the next DMA scatterlist entry */
|
|
+ wa->dma_sg = sg_next(wa->dma_sg);
|
|
+
|
|
+ /* In the case that the DMA mapped scatterlist has entries
|
|
+ * that have been merged, the non-DMA mapped scatterlist
|
|
+ * must be advanced multiple times for each merged entry.
|
|
+ * This ensures that the current non-DMA mapped entry
|
|
+ * corresponds to the current DMA mapped entry.
|
|
+ */
|
|
+ do {
|
|
+ sg_combined_len += wa->sg->length;
|
|
+ wa->sg = sg_next(wa->sg);
|
|
+ } while (wa->sg_used > sg_combined_len);
|
|
+
|
|
wa->sg_used = 0;
|
|
}
|
|
}
|
|
@@ -304,7 +319,7 @@ static unsigned int ccp_queue_buf(struct ccp_data *data, unsigned int from)
|
|
/* Update the structures and generate the count */
|
|
buf_count = 0;
|
|
while (sg_wa->bytes_left && (buf_count < dm_wa->length)) {
|
|
- nbytes = min(sg_wa->sg->length - sg_wa->sg_used,
|
|
+ nbytes = min(sg_dma_len(sg_wa->dma_sg) - sg_wa->sg_used,
|
|
dm_wa->length - buf_count);
|
|
nbytes = min_t(u64, sg_wa->bytes_left, nbytes);
|
|
|
|
@@ -336,11 +351,11 @@ static void ccp_prepare_data(struct ccp_data *src, struct ccp_data *dst,
|
|
* and destination. The resulting len values will always be <= UINT_MAX
|
|
* because the dma length is an unsigned int.
|
|
*/
|
|
- sg_src_len = sg_dma_len(src->sg_wa.sg) - src->sg_wa.sg_used;
|
|
+ sg_src_len = sg_dma_len(src->sg_wa.dma_sg) - src->sg_wa.sg_used;
|
|
sg_src_len = min_t(u64, src->sg_wa.bytes_left, sg_src_len);
|
|
|
|
if (dst) {
|
|
- sg_dst_len = sg_dma_len(dst->sg_wa.sg) - dst->sg_wa.sg_used;
|
|
+ sg_dst_len = sg_dma_len(dst->sg_wa.dma_sg) - dst->sg_wa.sg_used;
|
|
sg_dst_len = min_t(u64, src->sg_wa.bytes_left, sg_dst_len);
|
|
op_len = min(sg_src_len, sg_dst_len);
|
|
} else {
|
|
@@ -370,7 +385,7 @@ static void ccp_prepare_data(struct ccp_data *src, struct ccp_data *dst,
|
|
/* Enough data in the sg element, but we need to
|
|
* adjust for any previously copied data
|
|
*/
|
|
- op->src.u.dma.address = sg_dma_address(src->sg_wa.sg);
|
|
+ op->src.u.dma.address = sg_dma_address(src->sg_wa.dma_sg);
|
|
op->src.u.dma.offset = src->sg_wa.sg_used;
|
|
op->src.u.dma.length = op_len & ~(block_size - 1);
|
|
|
|
@@ -391,7 +406,7 @@ static void ccp_prepare_data(struct ccp_data *src, struct ccp_data *dst,
|
|
/* Enough room in the sg element, but we need to
|
|
* adjust for any previously used area
|
|
*/
|
|
- op->dst.u.dma.address = sg_dma_address(dst->sg_wa.sg);
|
|
+ op->dst.u.dma.address = sg_dma_address(dst->sg_wa.dma_sg);
|
|
op->dst.u.dma.offset = dst->sg_wa.sg_used;
|
|
op->dst.u.dma.length = op->src.u.dma.length;
|
|
}
|
|
@@ -2034,7 +2049,7 @@ ccp_run_passthru_cmd(struct ccp_cmd_queue *cmd_q, struct ccp_cmd *cmd)
|
|
dst.sg_wa.sg_used = 0;
|
|
for (i = 1; i <= src.sg_wa.dma_count; i++) {
|
|
if (!dst.sg_wa.sg ||
|
|
- (dst.sg_wa.sg->length < src.sg_wa.sg->length)) {
|
|
+ (sg_dma_len(dst.sg_wa.sg) < sg_dma_len(src.sg_wa.sg))) {
|
|
ret = -EINVAL;
|
|
goto e_dst;
|
|
}
|
|
@@ -2060,8 +2075,8 @@ ccp_run_passthru_cmd(struct ccp_cmd_queue *cmd_q, struct ccp_cmd *cmd)
|
|
goto e_dst;
|
|
}
|
|
|
|
- dst.sg_wa.sg_used += src.sg_wa.sg->length;
|
|
- if (dst.sg_wa.sg_used == dst.sg_wa.sg->length) {
|
|
+ dst.sg_wa.sg_used += sg_dma_len(src.sg_wa.sg);
|
|
+ if (dst.sg_wa.sg_used == sg_dma_len(dst.sg_wa.sg)) {
|
|
dst.sg_wa.sg = sg_next(dst.sg_wa.sg);
|
|
dst.sg_wa.sg_used = 0;
|
|
}
|
|
diff --git a/drivers/crypto/qat/qat_common/qat_uclo.c b/drivers/crypto/qat/qat_common/qat_uclo.c
|
|
index e2454d90d9498..4f1cd83bf56f9 100644
|
|
--- a/drivers/crypto/qat/qat_common/qat_uclo.c
|
|
+++ b/drivers/crypto/qat/qat_common/qat_uclo.c
|
|
@@ -332,13 +332,18 @@ static int qat_uclo_create_batch_init_list(struct icp_qat_fw_loader_handle
|
|
}
|
|
return 0;
|
|
out_err:
|
|
+ /* Do not free the list head unless we allocated it. */
|
|
+ tail_old = tail_old->next;
|
|
+ if (flag) {
|
|
+ kfree(*init_tab_base);
|
|
+ *init_tab_base = NULL;
|
|
+ }
|
|
+
|
|
while (tail_old) {
|
|
mem_init = tail_old->next;
|
|
kfree(tail_old);
|
|
tail_old = mem_init;
|
|
}
|
|
- if (flag)
|
|
- kfree(*init_tab_base);
|
|
return -ENOMEM;
|
|
}
|
|
|
|
diff --git a/drivers/edac/edac_device_sysfs.c b/drivers/edac/edac_device_sysfs.c
|
|
index 0e7ea3591b781..5e75937537997 100644
|
|
--- a/drivers/edac/edac_device_sysfs.c
|
|
+++ b/drivers/edac/edac_device_sysfs.c
|
|
@@ -275,6 +275,7 @@ int edac_device_register_sysfs_main_kobj(struct edac_device_ctl_info *edac_dev)
|
|
|
|
/* Error exit stack */
|
|
err_kobj_reg:
|
|
+ kobject_put(&edac_dev->kobj);
|
|
module_put(edac_dev->owner);
|
|
|
|
err_out:
|
|
diff --git a/drivers/edac/edac_pci_sysfs.c b/drivers/edac/edac_pci_sysfs.c
|
|
index 72c9eb9fdffbe..53042af7262e2 100644
|
|
--- a/drivers/edac/edac_pci_sysfs.c
|
|
+++ b/drivers/edac/edac_pci_sysfs.c
|
|
@@ -386,7 +386,7 @@ static int edac_pci_main_kobj_setup(void)
|
|
|
|
/* Error unwind statck */
|
|
kobject_init_and_add_fail:
|
|
- kfree(edac_pci_top_main_kobj);
|
|
+ kobject_put(edac_pci_top_main_kobj);
|
|
|
|
kzalloc_fail:
|
|
module_put(THIS_MODULE);
|
|
diff --git a/drivers/gpu/drm/arm/malidp_planes.c b/drivers/gpu/drm/arm/malidp_planes.c
|
|
index 16b8b310ae5c7..7072d738b072b 100644
|
|
--- a/drivers/gpu/drm/arm/malidp_planes.c
|
|
+++ b/drivers/gpu/drm/arm/malidp_planes.c
|
|
@@ -369,7 +369,7 @@ int malidp_de_planes_init(struct drm_device *drm)
|
|
const struct malidp_hw_regmap *map = &malidp->dev->map;
|
|
struct malidp_plane *plane = NULL;
|
|
enum drm_plane_type plane_type;
|
|
- unsigned long crtcs = 1 << drm->mode_config.num_crtc;
|
|
+ unsigned long crtcs = BIT(drm->mode_config.num_crtc);
|
|
unsigned long flags = DRM_MODE_ROTATE_0 | DRM_MODE_ROTATE_90 | DRM_MODE_ROTATE_180 |
|
|
DRM_MODE_ROTATE_270 | DRM_MODE_REFLECT_X | DRM_MODE_REFLECT_Y;
|
|
u32 *formats;
|
|
diff --git a/drivers/gpu/drm/bridge/sil-sii8620.c b/drivers/gpu/drm/bridge/sil-sii8620.c
|
|
index 0cb69ee94ac16..b93486892f4ae 100644
|
|
--- a/drivers/gpu/drm/bridge/sil-sii8620.c
|
|
+++ b/drivers/gpu/drm/bridge/sil-sii8620.c
|
|
@@ -167,7 +167,7 @@ static void sii8620_read_buf(struct sii8620 *ctx, u16 addr, u8 *buf, int len)
|
|
|
|
static u8 sii8620_readb(struct sii8620 *ctx, u16 addr)
|
|
{
|
|
- u8 ret;
|
|
+ u8 ret = 0;
|
|
|
|
sii8620_read_buf(ctx, addr, &ret, 1);
|
|
return ret;
|
|
diff --git a/drivers/gpu/drm/drm_debugfs.c b/drivers/gpu/drm/drm_debugfs.c
|
|
index c1807d5754b2a..454deba13ee5b 100644
|
|
--- a/drivers/gpu/drm/drm_debugfs.c
|
|
+++ b/drivers/gpu/drm/drm_debugfs.c
|
|
@@ -250,13 +250,13 @@ static ssize_t connector_write(struct file *file, const char __user *ubuf,
|
|
|
|
buf[len] = '\0';
|
|
|
|
- if (!strcmp(buf, "on"))
|
|
+ if (sysfs_streq(buf, "on"))
|
|
connector->force = DRM_FORCE_ON;
|
|
- else if (!strcmp(buf, "digital"))
|
|
+ else if (sysfs_streq(buf, "digital"))
|
|
connector->force = DRM_FORCE_ON_DIGITAL;
|
|
- else if (!strcmp(buf, "off"))
|
|
+ else if (sysfs_streq(buf, "off"))
|
|
connector->force = DRM_FORCE_OFF;
|
|
- else if (!strcmp(buf, "unspecified"))
|
|
+ else if (sysfs_streq(buf, "unspecified"))
|
|
connector->force = DRM_FORCE_UNSPECIFIED;
|
|
else
|
|
return -EINVAL;
|
|
diff --git a/drivers/gpu/drm/drm_mipi_dsi.c b/drivers/gpu/drm/drm_mipi_dsi.c
|
|
index 4b47226b90d4b..6f0de951b75d5 100644
|
|
--- a/drivers/gpu/drm/drm_mipi_dsi.c
|
|
+++ b/drivers/gpu/drm/drm_mipi_dsi.c
|
|
@@ -1029,11 +1029,11 @@ EXPORT_SYMBOL(mipi_dsi_dcs_set_pixel_format);
|
|
*/
|
|
int mipi_dsi_dcs_set_tear_scanline(struct mipi_dsi_device *dsi, u16 scanline)
|
|
{
|
|
- u8 payload[3] = { MIPI_DCS_SET_TEAR_SCANLINE, scanline >> 8,
|
|
- scanline & 0xff };
|
|
+ u8 payload[2] = { scanline >> 8, scanline & 0xff };
|
|
ssize_t err;
|
|
|
|
- err = mipi_dsi_generic_write(dsi, payload, sizeof(payload));
|
|
+ err = mipi_dsi_dcs_write(dsi, MIPI_DCS_SET_TEAR_SCANLINE, payload,
|
|
+ sizeof(payload));
|
|
if (err < 0)
|
|
return err;
|
|
|
|
diff --git a/drivers/gpu/drm/imx/imx-ldb.c b/drivers/gpu/drm/imx/imx-ldb.c
|
|
index 4f2e6c7e04c15..d38648a7ef2db 100644
|
|
--- a/drivers/gpu/drm/imx/imx-ldb.c
|
|
+++ b/drivers/gpu/drm/imx/imx-ldb.c
|
|
@@ -311,18 +311,19 @@ static void imx_ldb_encoder_disable(struct drm_encoder *encoder)
|
|
{
|
|
struct imx_ldb_channel *imx_ldb_ch = enc_to_imx_ldb_ch(encoder);
|
|
struct imx_ldb *ldb = imx_ldb_ch->ldb;
|
|
+ int dual = ldb->ldb_ctrl & LDB_SPLIT_MODE_EN;
|
|
int mux, ret;
|
|
|
|
drm_panel_disable(imx_ldb_ch->panel);
|
|
|
|
- if (imx_ldb_ch == &ldb->channel[0])
|
|
+ if (imx_ldb_ch == &ldb->channel[0] || dual)
|
|
ldb->ldb_ctrl &= ~LDB_CH0_MODE_EN_MASK;
|
|
- else if (imx_ldb_ch == &ldb->channel[1])
|
|
+ if (imx_ldb_ch == &ldb->channel[1] || dual)
|
|
ldb->ldb_ctrl &= ~LDB_CH1_MODE_EN_MASK;
|
|
|
|
regmap_write(ldb->regmap, IOMUXC_GPR2, ldb->ldb_ctrl);
|
|
|
|
- if (ldb->ldb_ctrl & LDB_SPLIT_MODE_EN) {
|
|
+ if (dual) {
|
|
clk_disable_unprepare(ldb->clk[0]);
|
|
clk_disable_unprepare(ldb->clk[1]);
|
|
}
|
|
diff --git a/drivers/gpu/drm/imx/imx-tve.c b/drivers/gpu/drm/imx/imx-tve.c
|
|
index bc27c26994641..c22c3e6e9b7ac 100644
|
|
--- a/drivers/gpu/drm/imx/imx-tve.c
|
|
+++ b/drivers/gpu/drm/imx/imx-tve.c
|
|
@@ -498,6 +498,13 @@ static int imx_tve_register(struct drm_device *drm, struct imx_tve *tve)
|
|
return 0;
|
|
}
|
|
|
|
+static void imx_tve_disable_regulator(void *data)
|
|
+{
|
|
+ struct imx_tve *tve = data;
|
|
+
|
|
+ regulator_disable(tve->dac_reg);
|
|
+}
|
|
+
|
|
static bool imx_tve_readable_reg(struct device *dev, unsigned int reg)
|
|
{
|
|
return (reg % 4 == 0) && (reg <= 0xdc);
|
|
@@ -622,6 +629,9 @@ static int imx_tve_bind(struct device *dev, struct device *master, void *data)
|
|
ret = regulator_enable(tve->dac_reg);
|
|
if (ret)
|
|
return ret;
|
|
+ ret = devm_add_action_or_reset(dev, imx_tve_disable_regulator, tve);
|
|
+ if (ret)
|
|
+ return ret;
|
|
}
|
|
|
|
tve->clk = devm_clk_get(dev, "tve");
|
|
@@ -668,18 +678,8 @@ static int imx_tve_bind(struct device *dev, struct device *master, void *data)
|
|
return 0;
|
|
}
|
|
|
|
-static void imx_tve_unbind(struct device *dev, struct device *master,
|
|
- void *data)
|
|
-{
|
|
- struct imx_tve *tve = dev_get_drvdata(dev);
|
|
-
|
|
- if (!IS_ERR(tve->dac_reg))
|
|
- regulator_disable(tve->dac_reg);
|
|
-}
|
|
-
|
|
static const struct component_ops imx_tve_ops = {
|
|
.bind = imx_tve_bind,
|
|
- .unbind = imx_tve_unbind,
|
|
};
|
|
|
|
static int imx_tve_probe(struct platform_device *pdev)
|
|
diff --git a/drivers/gpu/drm/nouveau/nouveau_drm.c b/drivers/gpu/drm/nouveau/nouveau_drm.c
|
|
index d00524a5d7f08..fb6b1d0f7fef3 100644
|
|
--- a/drivers/gpu/drm/nouveau/nouveau_drm.c
|
|
+++ b/drivers/gpu/drm/nouveau/nouveau_drm.c
|
|
@@ -840,8 +840,10 @@ nouveau_drm_open(struct drm_device *dev, struct drm_file *fpriv)
|
|
|
|
/* need to bring up power immediately if opening device */
|
|
ret = pm_runtime_get_sync(dev->dev);
|
|
- if (ret < 0 && ret != -EACCES)
|
|
+ if (ret < 0 && ret != -EACCES) {
|
|
+ pm_runtime_put_autosuspend(dev->dev);
|
|
return ret;
|
|
+ }
|
|
|
|
get_task_comm(tmpname, current);
|
|
snprintf(name, sizeof(name), "%s[%d]", tmpname, pid_nr(fpriv->pid));
|
|
@@ -930,8 +932,10 @@ nouveau_drm_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
|
|
long ret;
|
|
|
|
ret = pm_runtime_get_sync(dev->dev);
|
|
- if (ret < 0 && ret != -EACCES)
|
|
+ if (ret < 0 && ret != -EACCES) {
|
|
+ pm_runtime_put_autosuspend(dev->dev);
|
|
return ret;
|
|
+ }
|
|
|
|
switch (_IOC_NR(cmd) - DRM_COMMAND_BASE) {
|
|
case DRM_NOUVEAU_NVIF:
|
|
diff --git a/drivers/gpu/drm/nouveau/nouveau_fbcon.c b/drivers/gpu/drm/nouveau/nouveau_fbcon.c
|
|
index 2b12d82aac150..9ffb09679cc4a 100644
|
|
--- a/drivers/gpu/drm/nouveau/nouveau_fbcon.c
|
|
+++ b/drivers/gpu/drm/nouveau/nouveau_fbcon.c
|
|
@@ -310,7 +310,7 @@ nouveau_fbcon_create(struct drm_fb_helper *helper,
|
|
struct nouveau_framebuffer *fb;
|
|
struct nouveau_channel *chan;
|
|
struct nouveau_bo *nvbo;
|
|
- struct drm_mode_fb_cmd2 mode_cmd;
|
|
+ struct drm_mode_fb_cmd2 mode_cmd = {};
|
|
int ret;
|
|
|
|
mode_cmd.width = sizes->surface_width;
|
|
@@ -543,6 +543,7 @@ fini:
|
|
drm_fb_helper_fini(&fbcon->helper);
|
|
free:
|
|
kfree(fbcon);
|
|
+ drm->fbcon = NULL;
|
|
return ret;
|
|
}
|
|
|
|
diff --git a/drivers/gpu/drm/nouveau/nouveau_gem.c b/drivers/gpu/drm/nouveau/nouveau_gem.c
|
|
index 60ffb70bb9089..c6149b5be073e 100644
|
|
--- a/drivers/gpu/drm/nouveau/nouveau_gem.c
|
|
+++ b/drivers/gpu/drm/nouveau/nouveau_gem.c
|
|
@@ -42,8 +42,10 @@ nouveau_gem_object_del(struct drm_gem_object *gem)
|
|
int ret;
|
|
|
|
ret = pm_runtime_get_sync(dev);
|
|
- if (WARN_ON(ret < 0 && ret != -EACCES))
|
|
+ if (WARN_ON(ret < 0 && ret != -EACCES)) {
|
|
+ pm_runtime_put_autosuspend(dev);
|
|
return;
|
|
+ }
|
|
|
|
if (gem->import_attach)
|
|
drm_prime_gem_destroy(gem, nvbo->bo.sg);
|
|
diff --git a/drivers/gpu/drm/panel/panel-simple.c b/drivers/gpu/drm/panel/panel-simple.c
|
|
index c1daed3fe8428..6df312ba1826b 100644
|
|
--- a/drivers/gpu/drm/panel/panel-simple.c
|
|
+++ b/drivers/gpu/drm/panel/panel-simple.c
|
|
@@ -1253,7 +1253,7 @@ static const struct drm_display_mode lg_lb070wv8_mode = {
|
|
static const struct panel_desc lg_lb070wv8 = {
|
|
.modes = &lg_lb070wv8_mode,
|
|
.num_modes = 1,
|
|
- .bpc = 16,
|
|
+ .bpc = 8,
|
|
.size = {
|
|
.width = 151,
|
|
.height = 91,
|
|
diff --git a/drivers/gpu/drm/radeon/ci_dpm.c b/drivers/gpu/drm/radeon/ci_dpm.c
|
|
index 6e607cc7b6e5a..81bc2b89222f2 100644
|
|
--- a/drivers/gpu/drm/radeon/ci_dpm.c
|
|
+++ b/drivers/gpu/drm/radeon/ci_dpm.c
|
|
@@ -4342,7 +4342,7 @@ static int ci_set_mc_special_registers(struct radeon_device *rdev,
|
|
table->mc_reg_table_entry[k].mc_data[j] |= 0x100;
|
|
}
|
|
j++;
|
|
- if (j > SMU7_DISCRETE_MC_REGISTER_ARRAY_SIZE)
|
|
+ if (j >= SMU7_DISCRETE_MC_REGISTER_ARRAY_SIZE)
|
|
return -EINVAL;
|
|
|
|
if (!pi->mem_gddr5) {
|
|
diff --git a/drivers/gpu/drm/radeon/radeon_display.c b/drivers/gpu/drm/radeon/radeon_display.c
|
|
index d86110cdf0852..b2334349799d1 100644
|
|
--- a/drivers/gpu/drm/radeon/radeon_display.c
|
|
+++ b/drivers/gpu/drm/radeon/radeon_display.c
|
|
@@ -627,8 +627,10 @@ radeon_crtc_set_config(struct drm_mode_set *set,
|
|
dev = set->crtc->dev;
|
|
|
|
ret = pm_runtime_get_sync(dev->dev);
|
|
- if (ret < 0)
|
|
+ if (ret < 0) {
|
|
+ pm_runtime_put_autosuspend(dev->dev);
|
|
return ret;
|
|
+ }
|
|
|
|
ret = drm_crtc_helper_set_config(set, ctx);
|
|
|
|
diff --git a/drivers/gpu/drm/radeon/radeon_drv.c b/drivers/gpu/drm/radeon/radeon_drv.c
|
|
index f6908e2f9e55a..41e8abd099784 100644
|
|
--- a/drivers/gpu/drm/radeon/radeon_drv.c
|
|
+++ b/drivers/gpu/drm/radeon/radeon_drv.c
|
|
@@ -496,8 +496,10 @@ long radeon_drm_ioctl(struct file *filp,
|
|
long ret;
|
|
dev = file_priv->minor->dev;
|
|
ret = pm_runtime_get_sync(dev->dev);
|
|
- if (ret < 0)
|
|
+ if (ret < 0) {
|
|
+ pm_runtime_put_autosuspend(dev->dev);
|
|
return ret;
|
|
+ }
|
|
|
|
ret = drm_ioctl(filp, cmd, arg);
|
|
|
|
diff --git a/drivers/gpu/drm/radeon/radeon_kms.c b/drivers/gpu/drm/radeon/radeon_kms.c
|
|
index dfee8f7d94ae5..2e28cf8118404 100644
|
|
--- a/drivers/gpu/drm/radeon/radeon_kms.c
|
|
+++ b/drivers/gpu/drm/radeon/radeon_kms.c
|
|
@@ -659,8 +659,10 @@ int radeon_driver_open_kms(struct drm_device *dev, struct drm_file *file_priv)
|
|
file_priv->driver_priv = NULL;
|
|
|
|
r = pm_runtime_get_sync(dev->dev);
|
|
- if (r < 0)
|
|
+ if (r < 0) {
|
|
+ pm_runtime_put_autosuspend(dev->dev);
|
|
return r;
|
|
+ }
|
|
|
|
/* new gpu have virtual address space support */
|
|
if (rdev->family >= CHIP_CAYMAN) {
|
|
diff --git a/drivers/gpu/drm/tilcdc/tilcdc_panel.c b/drivers/gpu/drm/tilcdc/tilcdc_panel.c
|
|
index 1813a3623ce60..0484b2cf0e2b5 100644
|
|
--- a/drivers/gpu/drm/tilcdc/tilcdc_panel.c
|
|
+++ b/drivers/gpu/drm/tilcdc/tilcdc_panel.c
|
|
@@ -152,12 +152,16 @@ static int panel_connector_get_modes(struct drm_connector *connector)
|
|
int i;
|
|
|
|
for (i = 0; i < timings->num_timings; i++) {
|
|
- struct drm_display_mode *mode = drm_mode_create(dev);
|
|
+ struct drm_display_mode *mode;
|
|
struct videomode vm;
|
|
|
|
if (videomode_from_timings(timings, &vm, i))
|
|
break;
|
|
|
|
+ mode = drm_mode_create(dev);
|
|
+ if (!mode)
|
|
+ break;
|
|
+
|
|
drm_display_mode_from_videomode(&vm, mode);
|
|
|
|
mode->type = DRM_MODE_TYPE_DRIVER;
|
|
diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c b/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c
|
|
index 11f1c30ead548..848c9d009be2a 100644
|
|
--- a/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c
|
|
+++ b/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c
|
|
@@ -2707,7 +2707,7 @@ int vmw_kms_fbdev_init_data(struct vmw_private *dev_priv,
|
|
++i;
|
|
}
|
|
|
|
- if (i != unit) {
|
|
+ if (&con->head == &dev_priv->dev->mode_config.connector_list) {
|
|
DRM_ERROR("Could not find initial display unit.\n");
|
|
return -EINVAL;
|
|
}
|
|
@@ -2729,13 +2729,13 @@ int vmw_kms_fbdev_init_data(struct vmw_private *dev_priv,
|
|
break;
|
|
}
|
|
|
|
- if (mode->type & DRM_MODE_TYPE_PREFERRED)
|
|
- *p_mode = mode;
|
|
- else {
|
|
+ if (&mode->head == &con->modes) {
|
|
WARN_ONCE(true, "Could not find initial preferred mode.\n");
|
|
*p_mode = list_first_entry(&con->modes,
|
|
struct drm_display_mode,
|
|
head);
|
|
+ } else {
|
|
+ *p_mode = mode;
|
|
}
|
|
|
|
return 0;
|
|
diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_ldu.c b/drivers/gpu/drm/vmwgfx/vmwgfx_ldu.c
|
|
index 3824595fece12..39f4ad0dab8db 100644
|
|
--- a/drivers/gpu/drm/vmwgfx/vmwgfx_ldu.c
|
|
+++ b/drivers/gpu/drm/vmwgfx/vmwgfx_ldu.c
|
|
@@ -79,7 +79,7 @@ static int vmw_ldu_commit_list(struct vmw_private *dev_priv)
|
|
struct vmw_legacy_display_unit *entry;
|
|
struct drm_framebuffer *fb = NULL;
|
|
struct drm_crtc *crtc = NULL;
|
|
- int i = 0;
|
|
+ int i;
|
|
|
|
/* If there is no display topology the host just assumes
|
|
* that the guest will set the same layout as the host.
|
|
@@ -90,12 +90,11 @@ static int vmw_ldu_commit_list(struct vmw_private *dev_priv)
|
|
crtc = &entry->base.crtc;
|
|
w = max(w, crtc->x + crtc->mode.hdisplay);
|
|
h = max(h, crtc->y + crtc->mode.vdisplay);
|
|
- i++;
|
|
}
|
|
|
|
if (crtc == NULL)
|
|
return 0;
|
|
- fb = entry->base.crtc.primary->state->fb;
|
|
+ fb = crtc->primary->state->fb;
|
|
|
|
return vmw_kms_write_svga(dev_priv, w, h, fb->pitches[0],
|
|
fb->format->cpp[0] * 8,
|
|
diff --git a/drivers/gpu/host1x/debug.c b/drivers/gpu/host1x/debug.c
|
|
index 2aae0e63214c2..0b8c23c399c2a 100644
|
|
--- a/drivers/gpu/host1x/debug.c
|
|
+++ b/drivers/gpu/host1x/debug.c
|
|
@@ -25,6 +25,8 @@
|
|
#include "debug.h"
|
|
#include "channel.h"
|
|
|
|
+static DEFINE_MUTEX(debug_lock);
|
|
+
|
|
unsigned int host1x_debug_trace_cmdbuf;
|
|
|
|
static pid_t host1x_debug_force_timeout_pid;
|
|
@@ -49,12 +51,14 @@ static int show_channel(struct host1x_channel *ch, void *data, bool show_fifo)
|
|
struct output *o = data;
|
|
|
|
mutex_lock(&ch->cdma.lock);
|
|
+ mutex_lock(&debug_lock);
|
|
|
|
if (show_fifo)
|
|
host1x_hw_show_channel_fifo(m, ch, o);
|
|
|
|
host1x_hw_show_channel_cdma(m, ch, o);
|
|
|
|
+ mutex_unlock(&debug_lock);
|
|
mutex_unlock(&ch->cdma.lock);
|
|
|
|
return 0;
|
|
diff --git a/drivers/gpu/ipu-v3/ipu-image-convert.c b/drivers/gpu/ipu-v3/ipu-image-convert.c
|
|
index a5e33d58e02f7..d2f9e65522676 100644
|
|
--- a/drivers/gpu/ipu-v3/ipu-image-convert.c
|
|
+++ b/drivers/gpu/ipu-v3/ipu-image-convert.c
|
|
@@ -992,9 +992,10 @@ done:
|
|
return IRQ_WAKE_THREAD;
|
|
}
|
|
|
|
-static irqreturn_t norotate_irq(int irq, void *data)
|
|
+static irqreturn_t eof_irq(int irq, void *data)
|
|
{
|
|
struct ipu_image_convert_chan *chan = data;
|
|
+ struct ipu_image_convert_priv *priv = chan->priv;
|
|
struct ipu_image_convert_ctx *ctx;
|
|
struct ipu_image_convert_run *run;
|
|
unsigned long flags;
|
|
@@ -1011,45 +1012,26 @@ static irqreturn_t norotate_irq(int irq, void *data)
|
|
|
|
ctx = run->ctx;
|
|
|
|
- if (ipu_rot_mode_is_irt(ctx->rot_mode)) {
|
|
- /* this is a rotation operation, just ignore */
|
|
- spin_unlock_irqrestore(&chan->irqlock, flags);
|
|
- return IRQ_HANDLED;
|
|
- }
|
|
-
|
|
- ret = do_irq(run);
|
|
-out:
|
|
- spin_unlock_irqrestore(&chan->irqlock, flags);
|
|
- return ret;
|
|
-}
|
|
-
|
|
-static irqreturn_t rotate_irq(int irq, void *data)
|
|
-{
|
|
- struct ipu_image_convert_chan *chan = data;
|
|
- struct ipu_image_convert_priv *priv = chan->priv;
|
|
- struct ipu_image_convert_ctx *ctx;
|
|
- struct ipu_image_convert_run *run;
|
|
- unsigned long flags;
|
|
- irqreturn_t ret;
|
|
-
|
|
- spin_lock_irqsave(&chan->irqlock, flags);
|
|
-
|
|
- /* get current run and its context */
|
|
- run = chan->current_run;
|
|
- if (!run) {
|
|
+ if (irq == chan->out_eof_irq) {
|
|
+ if (ipu_rot_mode_is_irt(ctx->rot_mode)) {
|
|
+ /* this is a rotation op, just ignore */
|
|
+ ret = IRQ_HANDLED;
|
|
+ goto out;
|
|
+ }
|
|
+ } else if (irq == chan->rot_out_eof_irq) {
|
|
+ if (!ipu_rot_mode_is_irt(ctx->rot_mode)) {
|
|
+ /* this was NOT a rotation op, shouldn't happen */
|
|
+ dev_err(priv->ipu->dev,
|
|
+ "Unexpected rotation interrupt\n");
|
|
+ ret = IRQ_HANDLED;
|
|
+ goto out;
|
|
+ }
|
|
+ } else {
|
|
+ dev_err(priv->ipu->dev, "Received unknown irq %d\n", irq);
|
|
ret = IRQ_NONE;
|
|
goto out;
|
|
}
|
|
|
|
- ctx = run->ctx;
|
|
-
|
|
- if (!ipu_rot_mode_is_irt(ctx->rot_mode)) {
|
|
- /* this was NOT a rotation operation, shouldn't happen */
|
|
- dev_err(priv->ipu->dev, "Unexpected rotation interrupt\n");
|
|
- spin_unlock_irqrestore(&chan->irqlock, flags);
|
|
- return IRQ_HANDLED;
|
|
- }
|
|
-
|
|
ret = do_irq(run);
|
|
out:
|
|
spin_unlock_irqrestore(&chan->irqlock, flags);
|
|
@@ -1142,7 +1124,7 @@ static int get_ipu_resources(struct ipu_image_convert_chan *chan)
|
|
chan->out_chan,
|
|
IPU_IRQ_EOF);
|
|
|
|
- ret = request_threaded_irq(chan->out_eof_irq, norotate_irq, do_bh,
|
|
+ ret = request_threaded_irq(chan->out_eof_irq, eof_irq, do_bh,
|
|
0, "ipu-ic", chan);
|
|
if (ret < 0) {
|
|
dev_err(priv->ipu->dev, "could not acquire irq %d\n",
|
|
@@ -1155,7 +1137,7 @@ static int get_ipu_resources(struct ipu_image_convert_chan *chan)
|
|
chan->rotation_out_chan,
|
|
IPU_IRQ_EOF);
|
|
|
|
- ret = request_threaded_irq(chan->rot_out_eof_irq, rotate_irq, do_bh,
|
|
+ ret = request_threaded_irq(chan->rot_out_eof_irq, eof_irq, do_bh,
|
|
0, "ipu-ic", chan);
|
|
if (ret < 0) {
|
|
dev_err(priv->ipu->dev, "could not acquire irq %d\n",
|
|
diff --git a/drivers/hid/hid-input.c b/drivers/hid/hid-input.c
|
|
index 14e4003fde4dd..204ccf6745333 100644
|
|
--- a/drivers/hid/hid-input.c
|
|
+++ b/drivers/hid/hid-input.c
|
|
@@ -362,13 +362,13 @@ static int hidinput_query_battery_capacity(struct hid_device *dev)
|
|
u8 *buf;
|
|
int ret;
|
|
|
|
- buf = kmalloc(2, GFP_KERNEL);
|
|
+ buf = kmalloc(4, GFP_KERNEL);
|
|
if (!buf)
|
|
return -ENOMEM;
|
|
|
|
- ret = hid_hw_raw_request(dev, dev->battery_report_id, buf, 2,
|
|
+ ret = hid_hw_raw_request(dev, dev->battery_report_id, buf, 4,
|
|
dev->battery_report_type, HID_REQ_GET_REPORT);
|
|
- if (ret != 2) {
|
|
+ if (ret < 2) {
|
|
kfree(buf);
|
|
return -ENODATA;
|
|
}
|
|
diff --git a/drivers/hv/channel_mgmt.c b/drivers/hv/channel_mgmt.c
|
|
index 43eaf54736f4e..462f7f363faab 100644
|
|
--- a/drivers/hv/channel_mgmt.c
|
|
+++ b/drivers/hv/channel_mgmt.c
|
|
@@ -1228,6 +1228,8 @@ channel_message_table[CHANNELMSG_COUNT] = {
|
|
{ CHANNELMSG_19, 0, NULL },
|
|
{ CHANNELMSG_20, 0, NULL },
|
|
{ CHANNELMSG_TL_CONNECT_REQUEST, 0, NULL },
|
|
+ { CHANNELMSG_22, 0, NULL },
|
|
+ { CHANNELMSG_TL_CONNECT_RESULT, 0, NULL },
|
|
};
|
|
|
|
/*
|
|
@@ -1239,23 +1241,14 @@ void vmbus_onmessage(void *context)
|
|
{
|
|
struct hv_message *msg = context;
|
|
struct vmbus_channel_message_header *hdr;
|
|
- int size;
|
|
|
|
hdr = (struct vmbus_channel_message_header *)msg->u.payload;
|
|
- size = msg->header.payload_size;
|
|
|
|
- if (hdr->msgtype >= CHANNELMSG_COUNT) {
|
|
- pr_err("Received invalid channel message type %d size %d\n",
|
|
- hdr->msgtype, size);
|
|
- print_hex_dump_bytes("", DUMP_PREFIX_NONE,
|
|
- (unsigned char *)msg->u.payload, size);
|
|
- return;
|
|
- }
|
|
-
|
|
- if (channel_message_table[hdr->msgtype].message_handler)
|
|
- channel_message_table[hdr->msgtype].message_handler(hdr);
|
|
- else
|
|
- pr_err("Unhandled channel message type %d\n", hdr->msgtype);
|
|
+ /*
|
|
+ * vmbus_on_msg_dpc() makes sure the hdr->msgtype here can not go
|
|
+ * out of bound and the message_handler pointer can not be NULL.
|
|
+ */
|
|
+ channel_message_table[hdr->msgtype].message_handler(hdr);
|
|
}
|
|
|
|
/*
|
|
diff --git a/drivers/hv/vmbus_drv.c b/drivers/hv/vmbus_drv.c
|
|
index 1fd812ed679b4..45b8ccdfb0852 100644
|
|
--- a/drivers/hv/vmbus_drv.c
|
|
+++ b/drivers/hv/vmbus_drv.c
|
|
@@ -890,6 +890,10 @@ void vmbus_on_msg_dpc(unsigned long data)
|
|
}
|
|
|
|
entry = &channel_message_table[hdr->msgtype];
|
|
+
|
|
+ if (!entry->message_handler)
|
|
+ goto msg_handled;
|
|
+
|
|
if (entry->handler_type == VMHT_BLOCKING) {
|
|
ctx = kmalloc(sizeof(*ctx), GFP_ATOMIC);
|
|
if (ctx == NULL)
|
|
diff --git a/drivers/hwtracing/coresight/coresight-tmc-etf.c b/drivers/hwtracing/coresight/coresight-tmc-etf.c
|
|
index 0a00f4e941fbb..9bddbfbfbe03b 100644
|
|
--- a/drivers/hwtracing/coresight/coresight-tmc-etf.c
|
|
+++ b/drivers/hwtracing/coresight/coresight-tmc-etf.c
|
|
@@ -587,15 +587,14 @@ int tmc_read_unprepare_etb(struct tmc_drvdata *drvdata)
|
|
|
|
spin_lock_irqsave(&drvdata->spinlock, flags);
|
|
|
|
- /* There is no point in reading a TMC in HW FIFO mode */
|
|
- mode = readl_relaxed(drvdata->base + TMC_MODE);
|
|
- if (mode != TMC_MODE_CIRCULAR_BUFFER) {
|
|
- spin_unlock_irqrestore(&drvdata->spinlock, flags);
|
|
- return -EINVAL;
|
|
- }
|
|
-
|
|
/* Re-enable the TMC if need be */
|
|
if (drvdata->mode == CS_MODE_SYSFS) {
|
|
+ /* There is no point in reading a TMC in HW FIFO mode */
|
|
+ mode = readl_relaxed(drvdata->base + TMC_MODE);
|
|
+ if (mode != TMC_MODE_CIRCULAR_BUFFER) {
|
|
+ spin_unlock_irqrestore(&drvdata->spinlock, flags);
|
|
+ return -EINVAL;
|
|
+ }
|
|
/*
|
|
* The trace run will continue with the same allocated trace
|
|
* buffer. As such zero-out the buffer so that we don't end
|
|
diff --git a/drivers/i2c/busses/i2c-rcar.c b/drivers/i2c/busses/i2c-rcar.c
|
|
index db9ca8e926ca7..ed0f068109785 100644
|
|
--- a/drivers/i2c/busses/i2c-rcar.c
|
|
+++ b/drivers/i2c/busses/i2c-rcar.c
|
|
@@ -538,13 +538,14 @@ static bool rcar_i2c_slave_irq(struct rcar_i2c_priv *priv)
|
|
rcar_i2c_write(priv, ICSIER, SDR | SSR | SAR);
|
|
}
|
|
|
|
- rcar_i2c_write(priv, ICSSR, ~SAR & 0xff);
|
|
+ /* Clear SSR, too, because of old STOPs to other clients than us */
|
|
+ rcar_i2c_write(priv, ICSSR, ~(SAR | SSR) & 0xff);
|
|
}
|
|
|
|
/* master sent stop */
|
|
if (ssr_filtered & SSR) {
|
|
i2c_slave_event(priv->slave, I2C_SLAVE_STOP, &value);
|
|
- rcar_i2c_write(priv, ICSIER, SAR | SSR);
|
|
+ rcar_i2c_write(priv, ICSIER, SAR);
|
|
rcar_i2c_write(priv, ICSSR, ~SSR & 0xff);
|
|
}
|
|
|
|
@@ -802,7 +803,7 @@ static int rcar_reg_slave(struct i2c_client *slave)
|
|
priv->slave = slave;
|
|
rcar_i2c_write(priv, ICSAR, slave->addr);
|
|
rcar_i2c_write(priv, ICSSR, 0);
|
|
- rcar_i2c_write(priv, ICSIER, SAR | SSR);
|
|
+ rcar_i2c_write(priv, ICSIER, SAR);
|
|
rcar_i2c_write(priv, ICSCR, SIE | SDBS);
|
|
|
|
return 0;
|
|
@@ -814,12 +815,14 @@ static int rcar_unreg_slave(struct i2c_client *slave)
|
|
|
|
WARN_ON(!priv->slave);
|
|
|
|
- /* disable irqs and ensure none is running before clearing ptr */
|
|
+ /* ensure no irq is running before clearing ptr */
|
|
+ disable_irq(priv->irq);
|
|
rcar_i2c_write(priv, ICSIER, 0);
|
|
- rcar_i2c_write(priv, ICSCR, 0);
|
|
+ rcar_i2c_write(priv, ICSSR, 0);
|
|
+ enable_irq(priv->irq);
|
|
+ rcar_i2c_write(priv, ICSCR, SDBS);
|
|
rcar_i2c_write(priv, ICSAR, 0); /* Gen2: must be 0 if not using slave */
|
|
|
|
- synchronize_irq(priv->irq);
|
|
priv->slave = NULL;
|
|
|
|
pm_runtime_put(rcar_i2c_priv_to_dev(priv));
|
|
diff --git a/drivers/i2c/i2c-core-slave.c b/drivers/i2c/i2c-core-slave.c
|
|
index 4a78c65e99713..d89bc31e06227 100644
|
|
--- a/drivers/i2c/i2c-core-slave.c
|
|
+++ b/drivers/i2c/i2c-core-slave.c
|
|
@@ -22,10 +22,8 @@ int i2c_slave_register(struct i2c_client *client, i2c_slave_cb_t slave_cb)
|
|
{
|
|
int ret;
|
|
|
|
- if (!client || !slave_cb) {
|
|
- WARN(1, "insufficient data\n");
|
|
+ if (WARN(IS_ERR_OR_NULL(client) || !slave_cb, "insufficient data\n"))
|
|
return -EINVAL;
|
|
- }
|
|
|
|
if (!(client->flags & I2C_CLIENT_SLAVE))
|
|
dev_warn(&client->dev, "%s: client slave flag not set. You might see address collisions\n",
|
|
@@ -64,6 +62,9 @@ int i2c_slave_unregister(struct i2c_client *client)
|
|
{
|
|
int ret;
|
|
|
|
+ if (IS_ERR_OR_NULL(client))
|
|
+ return -EINVAL;
|
|
+
|
|
if (!client->adapter->algo->unreg_slave) {
|
|
dev_err(&client->dev, "%s: not supported by adapter\n", __func__);
|
|
return -EOPNOTSUPP;
|
|
diff --git a/drivers/iio/dac/ad5592r-base.c b/drivers/iio/dac/ad5592r-base.c
|
|
index 69bde59098542..5c998ac8c840b 100644
|
|
--- a/drivers/iio/dac/ad5592r-base.c
|
|
+++ b/drivers/iio/dac/ad5592r-base.c
|
|
@@ -417,7 +417,7 @@ static int ad5592r_read_raw(struct iio_dev *iio_dev,
|
|
s64 tmp = *val * (3767897513LL / 25LL);
|
|
*val = div_s64_rem(tmp, 1000000000LL, val2);
|
|
|
|
- ret = IIO_VAL_INT_PLUS_MICRO;
|
|
+ return IIO_VAL_INT_PLUS_MICRO;
|
|
} else {
|
|
int mult;
|
|
|
|
@@ -448,7 +448,7 @@ static int ad5592r_read_raw(struct iio_dev *iio_dev,
|
|
ret = IIO_VAL_INT;
|
|
break;
|
|
default:
|
|
- ret = -EINVAL;
|
|
+ return -EINVAL;
|
|
}
|
|
|
|
unlock:
|
|
diff --git a/drivers/infiniband/ulp/ipoib/ipoib.h b/drivers/infiniband/ulp/ipoib/ipoib.h
|
|
index 4a5c7a07a6315..268e23ba4a636 100644
|
|
--- a/drivers/infiniband/ulp/ipoib/ipoib.h
|
|
+++ b/drivers/infiniband/ulp/ipoib/ipoib.h
|
|
@@ -509,7 +509,7 @@ void ipoib_ib_dev_cleanup(struct net_device *dev);
|
|
|
|
int ipoib_ib_dev_open_default(struct net_device *dev);
|
|
int ipoib_ib_dev_open(struct net_device *dev);
|
|
-int ipoib_ib_dev_stop(struct net_device *dev);
|
|
+void ipoib_ib_dev_stop(struct net_device *dev);
|
|
void ipoib_ib_dev_up(struct net_device *dev);
|
|
void ipoib_ib_dev_down(struct net_device *dev);
|
|
int ipoib_ib_dev_stop_default(struct net_device *dev);
|
|
diff --git a/drivers/infiniband/ulp/ipoib/ipoib_ib.c b/drivers/infiniband/ulp/ipoib/ipoib_ib.c
|
|
index d77e8e2ae05f2..8e1f48fe6f2e7 100644
|
|
--- a/drivers/infiniband/ulp/ipoib/ipoib_ib.c
|
|
+++ b/drivers/infiniband/ulp/ipoib/ipoib_ib.c
|
|
@@ -809,7 +809,7 @@ timeout:
|
|
return 0;
|
|
}
|
|
|
|
-int ipoib_ib_dev_stop(struct net_device *dev)
|
|
+void ipoib_ib_dev_stop(struct net_device *dev)
|
|
{
|
|
struct ipoib_dev_priv *priv = ipoib_priv(dev);
|
|
|
|
@@ -817,8 +817,6 @@ int ipoib_ib_dev_stop(struct net_device *dev)
|
|
|
|
clear_bit(IPOIB_FLAG_INITIALIZED, &priv->flags);
|
|
ipoib_flush_ah(dev);
|
|
-
|
|
- return 0;
|
|
}
|
|
|
|
void ipoib_ib_tx_timer_func(unsigned long ctx)
|
|
diff --git a/drivers/input/mouse/sentelic.c b/drivers/input/mouse/sentelic.c
|
|
index 11c32ac8234b2..779d0b9341c0d 100644
|
|
--- a/drivers/input/mouse/sentelic.c
|
|
+++ b/drivers/input/mouse/sentelic.c
|
|
@@ -454,7 +454,7 @@ static ssize_t fsp_attr_set_setreg(struct psmouse *psmouse, void *data,
|
|
|
|
fsp_reg_write_enable(psmouse, false);
|
|
|
|
- return count;
|
|
+ return retval;
|
|
}
|
|
|
|
PSMOUSE_DEFINE_WO_ATTR(setreg, S_IWUSR, NULL, fsp_attr_set_setreg);
|
|
diff --git a/drivers/iommu/intel_irq_remapping.c b/drivers/iommu/intel_irq_remapping.c
|
|
index 154949a499c21..7cc5b04e30b7a 100644
|
|
--- a/drivers/iommu/intel_irq_remapping.c
|
|
+++ b/drivers/iommu/intel_irq_remapping.c
|
|
@@ -601,13 +601,21 @@ out_free_table:
|
|
|
|
static void intel_teardown_irq_remapping(struct intel_iommu *iommu)
|
|
{
|
|
+ struct fwnode_handle *fn;
|
|
+
|
|
if (iommu && iommu->ir_table) {
|
|
if (iommu->ir_msi_domain) {
|
|
+ fn = iommu->ir_msi_domain->fwnode;
|
|
+
|
|
irq_domain_remove(iommu->ir_msi_domain);
|
|
+ irq_domain_free_fwnode(fn);
|
|
iommu->ir_msi_domain = NULL;
|
|
}
|
|
if (iommu->ir_domain) {
|
|
+ fn = iommu->ir_domain->fwnode;
|
|
+
|
|
irq_domain_remove(iommu->ir_domain);
|
|
+ irq_domain_free_fwnode(fn);
|
|
iommu->ir_domain = NULL;
|
|
}
|
|
free_pages((unsigned long)iommu->ir_table->base,
|
|
diff --git a/drivers/iommu/omap-iommu-debug.c b/drivers/iommu/omap-iommu-debug.c
|
|
index 505548aafeff2..cec33e90e3998 100644
|
|
--- a/drivers/iommu/omap-iommu-debug.c
|
|
+++ b/drivers/iommu/omap-iommu-debug.c
|
|
@@ -101,8 +101,11 @@ static ssize_t debug_read_regs(struct file *file, char __user *userbuf,
|
|
mutex_lock(&iommu_debug_lock);
|
|
|
|
bytes = omap_iommu_dump_ctx(obj, p, count);
|
|
+ if (bytes < 0)
|
|
+ goto err;
|
|
bytes = simple_read_from_buffer(userbuf, count, ppos, buf, bytes);
|
|
|
|
+err:
|
|
mutex_unlock(&iommu_debug_lock);
|
|
kfree(buf);
|
|
|
|
diff --git a/drivers/irqchip/irq-gic-v3-its.c b/drivers/irqchip/irq-gic-v3-its.c
|
|
index 84b23d902d5b8..1d2267c6d31aa 100644
|
|
--- a/drivers/irqchip/irq-gic-v3-its.c
|
|
+++ b/drivers/irqchip/irq-gic-v3-its.c
|
|
@@ -2199,6 +2199,7 @@ static int its_irq_domain_alloc(struct irq_domain *domain, unsigned int virq,
|
|
{
|
|
msi_alloc_info_t *info = args;
|
|
struct its_device *its_dev = info->scratchpad[0].ptr;
|
|
+ struct irq_data *irqd;
|
|
irq_hw_number_t hwirq;
|
|
int err;
|
|
int i;
|
|
@@ -2214,7 +2215,9 @@ static int its_irq_domain_alloc(struct irq_domain *domain, unsigned int virq,
|
|
|
|
irq_domain_set_hwirq_and_chip(domain, virq + i,
|
|
hwirq + i, &its_irq_chip, its_dev);
|
|
- irqd_set_single_target(irq_desc_get_irq_data(irq_to_desc(virq + i)));
|
|
+ irqd = irq_get_irq_data(virq + i);
|
|
+ irqd_set_single_target(irqd);
|
|
+ irqd_set_affinity_on_activate(irqd);
|
|
pr_debug("ID:%d pID:%d vID:%d\n",
|
|
(int)(hwirq + i - its_dev->event_map.lpi_base),
|
|
(int)(hwirq + i), virq + i);
|
|
diff --git a/drivers/irqchip/irq-mtk-sysirq.c b/drivers/irqchip/irq-mtk-sysirq.c
|
|
index 90aaf190157f7..42455f31b0611 100644
|
|
--- a/drivers/irqchip/irq-mtk-sysirq.c
|
|
+++ b/drivers/irqchip/irq-mtk-sysirq.c
|
|
@@ -23,7 +23,7 @@
|
|
#include <linux/spinlock.h>
|
|
|
|
struct mtk_sysirq_chip_data {
|
|
- spinlock_t lock;
|
|
+ raw_spinlock_t lock;
|
|
u32 nr_intpol_bases;
|
|
void __iomem **intpol_bases;
|
|
u32 *intpol_words;
|
|
@@ -45,7 +45,7 @@ static int mtk_sysirq_set_type(struct irq_data *data, unsigned int type)
|
|
reg_index = chip_data->which_word[hwirq];
|
|
offset = hwirq & 0x1f;
|
|
|
|
- spin_lock_irqsave(&chip_data->lock, flags);
|
|
+ raw_spin_lock_irqsave(&chip_data->lock, flags);
|
|
value = readl_relaxed(base + reg_index * 4);
|
|
if (type == IRQ_TYPE_LEVEL_LOW || type == IRQ_TYPE_EDGE_FALLING) {
|
|
if (type == IRQ_TYPE_LEVEL_LOW)
|
|
@@ -61,7 +61,7 @@ static int mtk_sysirq_set_type(struct irq_data *data, unsigned int type)
|
|
|
|
data = data->parent_data;
|
|
ret = data->chip->irq_set_type(data, type);
|
|
- spin_unlock_irqrestore(&chip_data->lock, flags);
|
|
+ raw_spin_unlock_irqrestore(&chip_data->lock, flags);
|
|
return ret;
|
|
}
|
|
|
|
@@ -220,7 +220,7 @@ static int __init mtk_sysirq_of_init(struct device_node *node,
|
|
ret = -ENOMEM;
|
|
goto out_free_which_word;
|
|
}
|
|
- spin_lock_init(&chip_data->lock);
|
|
+ raw_spin_lock_init(&chip_data->lock);
|
|
|
|
return 0;
|
|
|
|
diff --git a/drivers/leds/led-class.c b/drivers/leds/led-class.c
|
|
index b0e2d55acbd6f..6c7269fcfa77c 100644
|
|
--- a/drivers/leds/led-class.c
|
|
+++ b/drivers/leds/led-class.c
|
|
@@ -173,6 +173,7 @@ void led_classdev_suspend(struct led_classdev *led_cdev)
|
|
{
|
|
led_cdev->flags |= LED_SUSPENDED;
|
|
led_set_brightness_nopm(led_cdev, 0);
|
|
+ flush_work(&led_cdev->set_brightness_work);
|
|
}
|
|
EXPORT_SYMBOL_GPL(led_classdev_suspend);
|
|
|
|
diff --git a/drivers/leds/leds-88pm860x.c b/drivers/leds/leds-88pm860x.c
|
|
index 77a104d2b1243..13f414ff6fd00 100644
|
|
--- a/drivers/leds/leds-88pm860x.c
|
|
+++ b/drivers/leds/leds-88pm860x.c
|
|
@@ -207,21 +207,33 @@ static int pm860x_led_probe(struct platform_device *pdev)
|
|
data->cdev.brightness_set_blocking = pm860x_led_set;
|
|
mutex_init(&data->lock);
|
|
|
|
- ret = devm_led_classdev_register(chip->dev, &data->cdev);
|
|
+ ret = led_classdev_register(chip->dev, &data->cdev);
|
|
if (ret < 0) {
|
|
dev_err(&pdev->dev, "Failed to register LED: %d\n", ret);
|
|
return ret;
|
|
}
|
|
pm860x_led_set(&data->cdev, 0);
|
|
+
|
|
+ platform_set_drvdata(pdev, data);
|
|
+
|
|
return 0;
|
|
}
|
|
|
|
+static int pm860x_led_remove(struct platform_device *pdev)
|
|
+{
|
|
+ struct pm860x_led *data = platform_get_drvdata(pdev);
|
|
+
|
|
+ led_classdev_unregister(&data->cdev);
|
|
+
|
|
+ return 0;
|
|
+}
|
|
|
|
static struct platform_driver pm860x_led_driver = {
|
|
.driver = {
|
|
.name = "88pm860x-led",
|
|
},
|
|
.probe = pm860x_led_probe,
|
|
+ .remove = pm860x_led_remove,
|
|
};
|
|
|
|
module_platform_driver(pm860x_led_driver);
|
|
diff --git a/drivers/leds/leds-da903x.c b/drivers/leds/leds-da903x.c
|
|
index 5ff7d72f73aa4..ecc265bb69a02 100644
|
|
--- a/drivers/leds/leds-da903x.c
|
|
+++ b/drivers/leds/leds-da903x.c
|
|
@@ -113,12 +113,23 @@ static int da903x_led_probe(struct platform_device *pdev)
|
|
led->flags = pdata->flags;
|
|
led->master = pdev->dev.parent;
|
|
|
|
- ret = devm_led_classdev_register(led->master, &led->cdev);
|
|
+ ret = led_classdev_register(led->master, &led->cdev);
|
|
if (ret) {
|
|
dev_err(&pdev->dev, "failed to register LED %d\n", id);
|
|
return ret;
|
|
}
|
|
|
|
+ platform_set_drvdata(pdev, led);
|
|
+
|
|
+ return 0;
|
|
+}
|
|
+
|
|
+static int da903x_led_remove(struct platform_device *pdev)
|
|
+{
|
|
+ struct da903x_led *led = platform_get_drvdata(pdev);
|
|
+
|
|
+ led_classdev_unregister(&led->cdev);
|
|
+
|
|
return 0;
|
|
}
|
|
|
|
@@ -127,6 +138,7 @@ static struct platform_driver da903x_led_driver = {
|
|
.name = "da903x-led",
|
|
},
|
|
.probe = da903x_led_probe,
|
|
+ .remove = da903x_led_remove,
|
|
};
|
|
|
|
module_platform_driver(da903x_led_driver);
|
|
diff --git a/drivers/leds/leds-lm3533.c b/drivers/leds/leds-lm3533.c
|
|
index 72224b599ffce..c1e562a4d6adf 100644
|
|
--- a/drivers/leds/leds-lm3533.c
|
|
+++ b/drivers/leds/leds-lm3533.c
|
|
@@ -698,7 +698,7 @@ static int lm3533_led_probe(struct platform_device *pdev)
|
|
|
|
platform_set_drvdata(pdev, led);
|
|
|
|
- ret = devm_led_classdev_register(pdev->dev.parent, &led->cdev);
|
|
+ ret = led_classdev_register(pdev->dev.parent, &led->cdev);
|
|
if (ret) {
|
|
dev_err(&pdev->dev, "failed to register LED %d\n", pdev->id);
|
|
return ret;
|
|
@@ -708,13 +708,18 @@ static int lm3533_led_probe(struct platform_device *pdev)
|
|
|
|
ret = lm3533_led_setup(led, pdata);
|
|
if (ret)
|
|
- return ret;
|
|
+ goto err_deregister;
|
|
|
|
ret = lm3533_ctrlbank_enable(&led->cb);
|
|
if (ret)
|
|
- return ret;
|
|
+ goto err_deregister;
|
|
|
|
return 0;
|
|
+
|
|
+err_deregister:
|
|
+ led_classdev_unregister(&led->cdev);
|
|
+
|
|
+ return ret;
|
|
}
|
|
|
|
static int lm3533_led_remove(struct platform_device *pdev)
|
|
@@ -724,6 +729,7 @@ static int lm3533_led_remove(struct platform_device *pdev)
|
|
dev_dbg(&pdev->dev, "%s\n", __func__);
|
|
|
|
lm3533_ctrlbank_disable(&led->cb);
|
|
+ led_classdev_unregister(&led->cdev);
|
|
|
|
return 0;
|
|
}
|
|
diff --git a/drivers/leds/leds-lm355x.c b/drivers/leds/leds-lm355x.c
|
|
index 6cb94f9a2f3f3..b9c60dd2b1327 100644
|
|
--- a/drivers/leds/leds-lm355x.c
|
|
+++ b/drivers/leds/leds-lm355x.c
|
|
@@ -168,18 +168,19 @@ static int lm355x_chip_init(struct lm355x_chip_data *chip)
|
|
/* input and output pins configuration */
|
|
switch (chip->type) {
|
|
case CHIP_LM3554:
|
|
- reg_val = pdata->pin_tx2 | pdata->ntc_pin;
|
|
+ reg_val = (u32)pdata->pin_tx2 | (u32)pdata->ntc_pin;
|
|
ret = regmap_update_bits(chip->regmap, 0xE0, 0x28, reg_val);
|
|
if (ret < 0)
|
|
goto out;
|
|
- reg_val = pdata->pass_mode;
|
|
+ reg_val = (u32)pdata->pass_mode;
|
|
ret = regmap_update_bits(chip->regmap, 0xA0, 0x04, reg_val);
|
|
if (ret < 0)
|
|
goto out;
|
|
break;
|
|
|
|
case CHIP_LM3556:
|
|
- reg_val = pdata->pin_tx2 | pdata->ntc_pin | pdata->pass_mode;
|
|
+ reg_val = (u32)pdata->pin_tx2 | (u32)pdata->ntc_pin |
|
|
+ (u32)pdata->pass_mode;
|
|
ret = regmap_update_bits(chip->regmap, 0x0A, 0xC4, reg_val);
|
|
if (ret < 0)
|
|
goto out;
|
|
diff --git a/drivers/leds/leds-wm831x-status.c b/drivers/leds/leds-wm831x-status.c
|
|
index be93b20e792a7..4f0ba19c35773 100644
|
|
--- a/drivers/leds/leds-wm831x-status.c
|
|
+++ b/drivers/leds/leds-wm831x-status.c
|
|
@@ -283,12 +283,23 @@ static int wm831x_status_probe(struct platform_device *pdev)
|
|
drvdata->cdev.blink_set = wm831x_status_blink_set;
|
|
drvdata->cdev.groups = wm831x_status_groups;
|
|
|
|
- ret = devm_led_classdev_register(wm831x->dev, &drvdata->cdev);
|
|
+ ret = led_classdev_register(wm831x->dev, &drvdata->cdev);
|
|
if (ret < 0) {
|
|
dev_err(&pdev->dev, "Failed to register LED: %d\n", ret);
|
|
return ret;
|
|
}
|
|
|
|
+ platform_set_drvdata(pdev, drvdata);
|
|
+
|
|
+ return 0;
|
|
+}
|
|
+
|
|
+static int wm831x_status_remove(struct platform_device *pdev)
|
|
+{
|
|
+ struct wm831x_status *drvdata = platform_get_drvdata(pdev);
|
|
+
|
|
+ led_classdev_unregister(&drvdata->cdev);
|
|
+
|
|
return 0;
|
|
}
|
|
|
|
@@ -297,6 +308,7 @@ static struct platform_driver wm831x_status_driver = {
|
|
.name = "wm831x-status",
|
|
},
|
|
.probe = wm831x_status_probe,
|
|
+ .remove = wm831x_status_remove,
|
|
};
|
|
|
|
module_platform_driver(wm831x_status_driver);
|
|
diff --git a/drivers/md/bcache/bset.c b/drivers/md/bcache/bset.c
|
|
index 1edf9515345ed..03fb06c61e1ca 100644
|
|
--- a/drivers/md/bcache/bset.c
|
|
+++ b/drivers/md/bcache/bset.c
|
|
@@ -319,7 +319,7 @@ int bch_btree_keys_alloc(struct btree_keys *b, unsigned page_order, gfp_t gfp)
|
|
|
|
b->page_order = page_order;
|
|
|
|
- t->data = (void *) __get_free_pages(gfp, b->page_order);
|
|
+ t->data = (void *) __get_free_pages(__GFP_COMP|gfp, b->page_order);
|
|
if (!t->data)
|
|
goto err;
|
|
|
|
diff --git a/drivers/md/bcache/btree.c b/drivers/md/bcache/btree.c
|
|
index 66c764491a830..9fca837d0b41e 100644
|
|
--- a/drivers/md/bcache/btree.c
|
|
+++ b/drivers/md/bcache/btree.c
|
|
@@ -794,7 +794,7 @@ int bch_btree_cache_alloc(struct cache_set *c)
|
|
mutex_init(&c->verify_lock);
|
|
|
|
c->verify_ondisk = (void *)
|
|
- __get_free_pages(GFP_KERNEL, ilog2(bucket_pages(c)));
|
|
+ __get_free_pages(GFP_KERNEL|__GFP_COMP, ilog2(bucket_pages(c)));
|
|
|
|
c->verify_data = mca_bucket_alloc(c, &ZERO_KEY, GFP_KERNEL);
|
|
|
|
diff --git a/drivers/md/bcache/journal.c b/drivers/md/bcache/journal.c
|
|
index 6394be5ee9a8f..6aafda26903c8 100644
|
|
--- a/drivers/md/bcache/journal.c
|
|
+++ b/drivers/md/bcache/journal.c
|
|
@@ -838,8 +838,8 @@ int bch_journal_alloc(struct cache_set *c)
|
|
j->w[1].c = c;
|
|
|
|
if (!(init_fifo(&j->pin, JOURNAL_PIN, GFP_KERNEL)) ||
|
|
- !(j->w[0].data = (void *) __get_free_pages(GFP_KERNEL, JSET_BITS)) ||
|
|
- !(j->w[1].data = (void *) __get_free_pages(GFP_KERNEL, JSET_BITS)))
|
|
+ !(j->w[0].data = (void *) __get_free_pages(GFP_KERNEL|__GFP_COMP, JSET_BITS)) ||
|
|
+ !(j->w[1].data = (void *) __get_free_pages(GFP_KERNEL|__GFP_COMP, JSET_BITS)))
|
|
return -ENOMEM;
|
|
|
|
return 0;
|
|
diff --git a/drivers/md/bcache/super.c b/drivers/md/bcache/super.c
|
|
index 690aeb09bbf55..7fcc1ba12bc01 100644
|
|
--- a/drivers/md/bcache/super.c
|
|
+++ b/drivers/md/bcache/super.c
|
|
@@ -1468,7 +1468,7 @@ void bch_cache_set_unregister(struct cache_set *c)
|
|
}
|
|
|
|
#define alloc_bucket_pages(gfp, c) \
|
|
- ((void *) __get_free_pages(__GFP_ZERO|gfp, ilog2(bucket_pages(c))))
|
|
+ ((void *) __get_free_pages(__GFP_ZERO|__GFP_COMP|gfp, ilog2(bucket_pages(c))))
|
|
|
|
struct cache_set *bch_cache_set_alloc(struct cache_sb *sb)
|
|
{
|
|
@@ -1780,7 +1780,14 @@ found:
|
|
sysfs_create_link(&c->kobj, &ca->kobj, buf))
|
|
goto err;
|
|
|
|
- if (ca->sb.seq > c->sb.seq) {
|
|
+ /*
|
|
+ * A special case is both ca->sb.seq and c->sb.seq are 0,
|
|
+ * such condition happens on a new created cache device whose
|
|
+ * super block is never flushed yet. In this case c->sb.version
|
|
+ * and other members should be updated too, otherwise we will
|
|
+ * have a mistaken super block version in cache set.
|
|
+ */
|
|
+ if (ca->sb.seq > c->sb.seq || c->sb.seq == 0) {
|
|
c->sb.version = ca->sb.version;
|
|
memcpy(c->sb.set_uuid, ca->sb.set_uuid, 16);
|
|
c->sb.flags = ca->sb.flags;
|
|
diff --git a/drivers/md/dm-cache-target.c b/drivers/md/dm-cache-target.c
|
|
index 69cdb29ef6be9..280873b13e744 100644
|
|
--- a/drivers/md/dm-cache-target.c
|
|
+++ b/drivers/md/dm-cache-target.c
|
|
@@ -410,7 +410,6 @@ struct cache {
|
|
spinlock_t lock;
|
|
struct list_head deferred_cells;
|
|
struct bio_list deferred_bios;
|
|
- struct bio_list deferred_writethrough_bios;
|
|
sector_t migration_threshold;
|
|
wait_queue_head_t migration_wait;
|
|
atomic_t nr_allocated_migrations;
|
|
@@ -446,10 +445,10 @@ struct cache {
|
|
struct dm_kcopyd_client *copier;
|
|
struct workqueue_struct *wq;
|
|
struct work_struct deferred_bio_worker;
|
|
- struct work_struct deferred_writethrough_worker;
|
|
struct work_struct migration_worker;
|
|
struct delayed_work waker;
|
|
struct dm_bio_prison_v2 *prison;
|
|
+ struct bio_set *bs;
|
|
|
|
mempool_t *migration_pool;
|
|
|
|
@@ -490,15 +489,6 @@ struct per_bio_data {
|
|
struct dm_bio_prison_cell_v2 *cell;
|
|
struct dm_hook_info hook_info;
|
|
sector_t len;
|
|
-
|
|
- /*
|
|
- * writethrough fields. These MUST remain at the end of this
|
|
- * structure and the 'cache' member must be the first as it
|
|
- * is used to determine the offset of the writethrough fields.
|
|
- */
|
|
- struct cache *cache;
|
|
- dm_cblock_t cblock;
|
|
- struct dm_bio_details bio_details;
|
|
};
|
|
|
|
struct dm_cache_migration {
|
|
@@ -515,19 +505,19 @@ struct dm_cache_migration {
|
|
|
|
/*----------------------------------------------------------------*/
|
|
|
|
-static bool writethrough_mode(struct cache_features *f)
|
|
+static bool writethrough_mode(struct cache *cache)
|
|
{
|
|
- return f->io_mode == CM_IO_WRITETHROUGH;
|
|
+ return cache->features.io_mode == CM_IO_WRITETHROUGH;
|
|
}
|
|
|
|
-static bool writeback_mode(struct cache_features *f)
|
|
+static bool writeback_mode(struct cache *cache)
|
|
{
|
|
- return f->io_mode == CM_IO_WRITEBACK;
|
|
+ return cache->features.io_mode == CM_IO_WRITEBACK;
|
|
}
|
|
|
|
-static inline bool passthrough_mode(struct cache_features *f)
|
|
+static inline bool passthrough_mode(struct cache *cache)
|
|
{
|
|
- return unlikely(f->io_mode == CM_IO_PASSTHROUGH);
|
|
+ return unlikely(cache->features.io_mode == CM_IO_PASSTHROUGH);
|
|
}
|
|
|
|
/*----------------------------------------------------------------*/
|
|
@@ -537,14 +527,9 @@ static void wake_deferred_bio_worker(struct cache *cache)
|
|
queue_work(cache->wq, &cache->deferred_bio_worker);
|
|
}
|
|
|
|
-static void wake_deferred_writethrough_worker(struct cache *cache)
|
|
-{
|
|
- queue_work(cache->wq, &cache->deferred_writethrough_worker);
|
|
-}
|
|
-
|
|
static void wake_migration_worker(struct cache *cache)
|
|
{
|
|
- if (passthrough_mode(&cache->features))
|
|
+ if (passthrough_mode(cache))
|
|
return;
|
|
|
|
queue_work(cache->wq, &cache->migration_worker);
|
|
@@ -618,15 +603,9 @@ static unsigned lock_level(struct bio *bio)
|
|
* Per bio data
|
|
*--------------------------------------------------------------*/
|
|
|
|
-/*
|
|
- * If using writeback, leave out struct per_bio_data's writethrough fields.
|
|
- */
|
|
-#define PB_DATA_SIZE_WB (offsetof(struct per_bio_data, cache))
|
|
-#define PB_DATA_SIZE_WT (sizeof(struct per_bio_data))
|
|
-
|
|
static size_t get_per_bio_data_size(struct cache *cache)
|
|
{
|
|
- return writethrough_mode(&cache->features) ? PB_DATA_SIZE_WT : PB_DATA_SIZE_WB;
|
|
+ return sizeof(struct per_bio_data);
|
|
}
|
|
|
|
static struct per_bio_data *get_per_bio_data(struct bio *bio, size_t data_size)
|
|
@@ -868,16 +847,23 @@ static void check_if_tick_bio_needed(struct cache *cache, struct bio *bio)
|
|
spin_unlock_irqrestore(&cache->lock, flags);
|
|
}
|
|
|
|
-static void remap_to_origin_clear_discard(struct cache *cache, struct bio *bio,
|
|
- dm_oblock_t oblock)
|
|
+static void __remap_to_origin_clear_discard(struct cache *cache, struct bio *bio,
|
|
+ dm_oblock_t oblock, bool bio_has_pbd)
|
|
{
|
|
- // FIXME: this is called way too much.
|
|
- check_if_tick_bio_needed(cache, bio);
|
|
+ if (bio_has_pbd)
|
|
+ check_if_tick_bio_needed(cache, bio);
|
|
remap_to_origin(cache, bio);
|
|
if (bio_data_dir(bio) == WRITE)
|
|
clear_discard(cache, oblock_to_dblock(cache, oblock));
|
|
}
|
|
|
|
+static void remap_to_origin_clear_discard(struct cache *cache, struct bio *bio,
|
|
+ dm_oblock_t oblock)
|
|
+{
|
|
+ // FIXME: check_if_tick_bio_needed() is called way too much through this interface
|
|
+ __remap_to_origin_clear_discard(cache, bio, oblock, true);
|
|
+}
|
|
+
|
|
static void remap_to_cache_dirty(struct cache *cache, struct bio *bio,
|
|
dm_oblock_t oblock, dm_cblock_t cblock)
|
|
{
|
|
@@ -937,57 +923,26 @@ static void issue_op(struct bio *bio, void *context)
|
|
accounted_request(cache, bio);
|
|
}
|
|
|
|
-static void defer_writethrough_bio(struct cache *cache, struct bio *bio)
|
|
-{
|
|
- unsigned long flags;
|
|
-
|
|
- spin_lock_irqsave(&cache->lock, flags);
|
|
- bio_list_add(&cache->deferred_writethrough_bios, bio);
|
|
- spin_unlock_irqrestore(&cache->lock, flags);
|
|
-
|
|
- wake_deferred_writethrough_worker(cache);
|
|
-}
|
|
-
|
|
-static void writethrough_endio(struct bio *bio)
|
|
-{
|
|
- struct per_bio_data *pb = get_per_bio_data(bio, PB_DATA_SIZE_WT);
|
|
-
|
|
- dm_unhook_bio(&pb->hook_info, bio);
|
|
-
|
|
- if (bio->bi_status) {
|
|
- bio_endio(bio);
|
|
- return;
|
|
- }
|
|
-
|
|
- dm_bio_restore(&pb->bio_details, bio);
|
|
- remap_to_cache(pb->cache, bio, pb->cblock);
|
|
-
|
|
- /*
|
|
- * We can't issue this bio directly, since we're in interrupt
|
|
- * context. So it gets put on a bio list for processing by the
|
|
- * worker thread.
|
|
- */
|
|
- defer_writethrough_bio(pb->cache, bio);
|
|
-}
|
|
-
|
|
/*
|
|
- * FIXME: send in parallel, huge latency as is.
|
|
* When running in writethrough mode we need to send writes to clean blocks
|
|
- * to both the cache and origin devices. In future we'd like to clone the
|
|
- * bio and send them in parallel, but for now we're doing them in
|
|
- * series as this is easier.
|
|
+ * to both the cache and origin devices. Clone the bio and send them in parallel.
|
|
*/
|
|
-static void remap_to_origin_then_cache(struct cache *cache, struct bio *bio,
|
|
- dm_oblock_t oblock, dm_cblock_t cblock)
|
|
+static void remap_to_origin_and_cache(struct cache *cache, struct bio *bio,
|
|
+ dm_oblock_t oblock, dm_cblock_t cblock)
|
|
{
|
|
- struct per_bio_data *pb = get_per_bio_data(bio, PB_DATA_SIZE_WT);
|
|
+ struct bio *origin_bio = bio_clone_fast(bio, GFP_NOIO, cache->bs);
|
|
|
|
- pb->cache = cache;
|
|
- pb->cblock = cblock;
|
|
- dm_hook_bio(&pb->hook_info, bio, writethrough_endio, NULL);
|
|
- dm_bio_record(&pb->bio_details, bio);
|
|
+ BUG_ON(!origin_bio);
|
|
|
|
- remap_to_origin_clear_discard(pb->cache, bio, oblock);
|
|
+ bio_chain(origin_bio, bio);
|
|
+ /*
|
|
+ * Passing false to __remap_to_origin_clear_discard() skips
|
|
+ * all code that might use per_bio_data (since clone doesn't have it)
|
|
+ */
|
|
+ __remap_to_origin_clear_discard(cache, origin_bio, oblock, false);
|
|
+ submit_bio(origin_bio);
|
|
+
|
|
+ remap_to_cache(cache, bio, cblock);
|
|
}
|
|
|
|
/*----------------------------------------------------------------
|
|
@@ -1209,7 +1164,7 @@ static bool bio_writes_complete_block(struct cache *cache, struct bio *bio)
|
|
|
|
static bool optimisable_bio(struct cache *cache, struct bio *bio, dm_oblock_t block)
|
|
{
|
|
- return writeback_mode(&cache->features) &&
|
|
+ return writeback_mode(cache) &&
|
|
(is_discarded_oblock(cache, block) || bio_writes_complete_block(cache, bio));
|
|
}
|
|
|
|
@@ -1862,7 +1817,7 @@ static int map_bio(struct cache *cache, struct bio *bio, dm_oblock_t block,
|
|
* Passthrough always maps to the origin, invalidating any
|
|
* cache blocks that are written to.
|
|
*/
|
|
- if (passthrough_mode(&cache->features)) {
|
|
+ if (passthrough_mode(cache)) {
|
|
if (bio_data_dir(bio) == WRITE) {
|
|
bio_drop_shared_lock(cache, bio);
|
|
atomic_inc(&cache->stats.demotion);
|
|
@@ -1871,9 +1826,9 @@ static int map_bio(struct cache *cache, struct bio *bio, dm_oblock_t block,
|
|
remap_to_origin_clear_discard(cache, bio, block);
|
|
|
|
} else {
|
|
- if (bio_data_dir(bio) == WRITE && writethrough_mode(&cache->features) &&
|
|
+ if (bio_data_dir(bio) == WRITE && writethrough_mode(cache) &&
|
|
!is_dirty(cache, cblock)) {
|
|
- remap_to_origin_then_cache(cache, bio, block, cblock);
|
|
+ remap_to_origin_and_cache(cache, bio, block, cblock);
|
|
accounted_begin(cache, bio);
|
|
} else
|
|
remap_to_cache_dirty(cache, bio, block, cblock);
|
|
@@ -2003,28 +1958,6 @@ static void process_deferred_bios(struct work_struct *ws)
|
|
schedule_commit(&cache->committer);
|
|
}
|
|
|
|
-static void process_deferred_writethrough_bios(struct work_struct *ws)
|
|
-{
|
|
- struct cache *cache = container_of(ws, struct cache, deferred_writethrough_worker);
|
|
-
|
|
- unsigned long flags;
|
|
- struct bio_list bios;
|
|
- struct bio *bio;
|
|
-
|
|
- bio_list_init(&bios);
|
|
-
|
|
- spin_lock_irqsave(&cache->lock, flags);
|
|
- bio_list_merge(&bios, &cache->deferred_writethrough_bios);
|
|
- bio_list_init(&cache->deferred_writethrough_bios);
|
|
- spin_unlock_irqrestore(&cache->lock, flags);
|
|
-
|
|
- /*
|
|
- * These bios have already been through accounted_begin()
|
|
- */
|
|
- while ((bio = bio_list_pop(&bios)))
|
|
- generic_make_request(bio);
|
|
-}
|
|
-
|
|
/*----------------------------------------------------------------
|
|
* Main worker loop
|
|
*--------------------------------------------------------------*/
|
|
@@ -2132,6 +2065,9 @@ static void destroy(struct cache *cache)
|
|
kfree(cache->ctr_args[i]);
|
|
kfree(cache->ctr_args);
|
|
|
|
+ if (cache->bs)
|
|
+ bioset_free(cache->bs);
|
|
+
|
|
kfree(cache);
|
|
}
|
|
|
|
@@ -2589,6 +2525,13 @@ static int cache_create(struct cache_args *ca, struct cache **result)
|
|
cache->features = ca->features;
|
|
ti->per_io_data_size = get_per_bio_data_size(cache);
|
|
|
|
+ if (writethrough_mode(cache)) {
|
|
+ /* Create bioset for writethrough bios issued to origin */
|
|
+ cache->bs = bioset_create(BIO_POOL_SIZE, 0, 0);
|
|
+ if (!cache->bs)
|
|
+ goto bad;
|
|
+ }
|
|
+
|
|
cache->callbacks.congested_fn = cache_is_congested;
|
|
dm_table_add_target_callbacks(ti->table, &cache->callbacks);
|
|
|
|
@@ -2649,7 +2592,7 @@ static int cache_create(struct cache_args *ca, struct cache **result)
|
|
goto bad;
|
|
}
|
|
|
|
- if (passthrough_mode(&cache->features)) {
|
|
+ if (passthrough_mode(cache)) {
|
|
bool all_clean;
|
|
|
|
r = dm_cache_metadata_all_clean(cache->cmd, &all_clean);
|
|
@@ -2670,7 +2613,6 @@ static int cache_create(struct cache_args *ca, struct cache **result)
|
|
spin_lock_init(&cache->lock);
|
|
INIT_LIST_HEAD(&cache->deferred_cells);
|
|
bio_list_init(&cache->deferred_bios);
|
|
- bio_list_init(&cache->deferred_writethrough_bios);
|
|
atomic_set(&cache->nr_allocated_migrations, 0);
|
|
atomic_set(&cache->nr_io_migrations, 0);
|
|
init_waitqueue_head(&cache->migration_wait);
|
|
@@ -2709,8 +2651,6 @@ static int cache_create(struct cache_args *ca, struct cache **result)
|
|
goto bad;
|
|
}
|
|
INIT_WORK(&cache->deferred_bio_worker, process_deferred_bios);
|
|
- INIT_WORK(&cache->deferred_writethrough_worker,
|
|
- process_deferred_writethrough_bios);
|
|
INIT_WORK(&cache->migration_worker, check_migrations);
|
|
INIT_DELAYED_WORK(&cache->waker, do_waker);
|
|
|
|
@@ -3279,13 +3219,13 @@ static void cache_status(struct dm_target *ti, status_type_t type,
|
|
else
|
|
DMEMIT("1 ");
|
|
|
|
- if (writethrough_mode(&cache->features))
|
|
+ if (writethrough_mode(cache))
|
|
DMEMIT("writethrough ");
|
|
|
|
- else if (passthrough_mode(&cache->features))
|
|
+ else if (passthrough_mode(cache))
|
|
DMEMIT("passthrough ");
|
|
|
|
- else if (writeback_mode(&cache->features))
|
|
+ else if (writeback_mode(cache))
|
|
DMEMIT("writeback ");
|
|
|
|
else {
|
|
@@ -3451,7 +3391,7 @@ static int process_invalidate_cblocks_message(struct cache *cache, unsigned coun
|
|
unsigned i;
|
|
struct cblock_range range;
|
|
|
|
- if (!passthrough_mode(&cache->features)) {
|
|
+ if (!passthrough_mode(cache)) {
|
|
DMERR("%s: cache has to be in passthrough mode for invalidation",
|
|
cache_device_name(cache));
|
|
return -EPERM;
|
|
diff --git a/drivers/md/dm-rq.c b/drivers/md/dm-rq.c
|
|
index eadfcfd106fff..cac8ec16e6031 100644
|
|
--- a/drivers/md/dm-rq.c
|
|
+++ b/drivers/md/dm-rq.c
|
|
@@ -95,9 +95,6 @@ static void dm_old_stop_queue(struct request_queue *q)
|
|
|
|
static void dm_mq_stop_queue(struct request_queue *q)
|
|
{
|
|
- if (blk_mq_queue_stopped(q))
|
|
- return;
|
|
-
|
|
blk_mq_quiesce_queue(q);
|
|
}
|
|
|
|
diff --git a/drivers/md/md-cluster.c b/drivers/md/md-cluster.c
|
|
index 10057ac85476e..035d5ec8e677f 100644
|
|
--- a/drivers/md/md-cluster.c
|
|
+++ b/drivers/md/md-cluster.c
|
|
@@ -1423,6 +1423,7 @@ static void unlock_all_bitmaps(struct mddev *mddev)
|
|
}
|
|
}
|
|
kfree(cinfo->other_bitmap_lockres);
|
|
+ cinfo->other_bitmap_lockres = NULL;
|
|
}
|
|
}
|
|
|
|
diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c
|
|
index d5c14d56a7141..cd055664dce3f 100644
|
|
--- a/drivers/md/raid5.c
|
|
+++ b/drivers/md/raid5.c
|
|
@@ -3593,6 +3593,7 @@ static int need_this_block(struct stripe_head *sh, struct stripe_head_state *s,
|
|
* is missing/faulty, then we need to read everything we can.
|
|
*/
|
|
if (sh->raid_conf->level != 6 &&
|
|
+ sh->raid_conf->rmw_level != PARITY_DISABLE_RMW &&
|
|
sh->sector < sh->raid_conf->mddev->recovery_cp)
|
|
/* reconstruct-write isn't being forced */
|
|
return 0;
|
|
@@ -4829,7 +4830,7 @@ static void handle_stripe(struct stripe_head *sh)
|
|
* or to load a block that is being partially written.
|
|
*/
|
|
if (s.to_read || s.non_overwrite
|
|
- || (conf->level == 6 && s.to_write && s.failed)
|
|
+ || (s.to_write && s.failed)
|
|
|| (s.syncing && (s.uptodate + s.compute < disks))
|
|
|| s.replacing
|
|
|| s.expanding)
|
|
diff --git a/drivers/media/firewire/firedtv-fw.c b/drivers/media/firewire/firedtv-fw.c
|
|
index 247f0e7cb5f7f..5d634706a7eaa 100644
|
|
--- a/drivers/media/firewire/firedtv-fw.c
|
|
+++ b/drivers/media/firewire/firedtv-fw.c
|
|
@@ -271,6 +271,8 @@ static int node_probe(struct fw_unit *unit, const struct ieee1394_device_id *id)
|
|
|
|
name_len = fw_csr_string(unit->directory, CSR_MODEL,
|
|
name, sizeof(name));
|
|
+ if (name_len < 0)
|
|
+ return name_len;
|
|
for (i = ARRAY_SIZE(model_names); --i; )
|
|
if (strlen(model_names[i]) <= name_len &&
|
|
strncmp(name, model_names[i], name_len) == 0)
|
|
diff --git a/drivers/media/platform/exynos4-is/media-dev.c b/drivers/media/platform/exynos4-is/media-dev.c
|
|
index b2eb830c0360a..f772c9b92d9ba 100644
|
|
--- a/drivers/media/platform/exynos4-is/media-dev.c
|
|
+++ b/drivers/media/platform/exynos4-is/media-dev.c
|
|
@@ -1258,6 +1258,9 @@ static int fimc_md_get_pinctrl(struct fimc_md *fmd)
|
|
|
|
pctl->state_idle = pinctrl_lookup_state(pctl->pinctrl,
|
|
PINCTRL_STATE_IDLE);
|
|
+ if (IS_ERR(pctl->state_idle))
|
|
+ return PTR_ERR(pctl->state_idle);
|
|
+
|
|
return 0;
|
|
}
|
|
|
|
diff --git a/drivers/media/platform/omap3isp/isppreview.c b/drivers/media/platform/omap3isp/isppreview.c
|
|
index e981eb2330f18..ac005ae4d21b4 100644
|
|
--- a/drivers/media/platform/omap3isp/isppreview.c
|
|
+++ b/drivers/media/platform/omap3isp/isppreview.c
|
|
@@ -2290,7 +2290,7 @@ static int preview_init_entities(struct isp_prev_device *prev)
|
|
me->ops = &preview_media_ops;
|
|
ret = media_entity_pads_init(me, PREV_PADS_NUM, pads);
|
|
if (ret < 0)
|
|
- return ret;
|
|
+ goto error_handler_free;
|
|
|
|
preview_init_formats(sd, NULL);
|
|
|
|
@@ -2323,6 +2323,8 @@ error_video_out:
|
|
omap3isp_video_cleanup(&prev->video_in);
|
|
error_video_in:
|
|
media_entity_cleanup(&prev->subdev.entity);
|
|
+error_handler_free:
|
|
+ v4l2_ctrl_handler_free(&prev->ctrls);
|
|
return ret;
|
|
}
|
|
|
|
diff --git a/drivers/mfd/arizona-core.c b/drivers/mfd/arizona-core.c
|
|
index ad8a5296c50ba..9aa33141e7f14 100644
|
|
--- a/drivers/mfd/arizona-core.c
|
|
+++ b/drivers/mfd/arizona-core.c
|
|
@@ -1528,6 +1528,15 @@ err_irq:
|
|
arizona_irq_exit(arizona);
|
|
err_pm:
|
|
pm_runtime_disable(arizona->dev);
|
|
+
|
|
+ switch (arizona->pdata.clk32k_src) {
|
|
+ case ARIZONA_32KZ_MCLK1:
|
|
+ case ARIZONA_32KZ_MCLK2:
|
|
+ arizona_clk32k_disable(arizona);
|
|
+ break;
|
|
+ default:
|
|
+ break;
|
|
+ }
|
|
err_reset:
|
|
arizona_enable_reset(arizona);
|
|
regulator_disable(arizona->dcvdd);
|
|
@@ -1550,6 +1559,15 @@ int arizona_dev_exit(struct arizona *arizona)
|
|
regulator_disable(arizona->dcvdd);
|
|
regulator_put(arizona->dcvdd);
|
|
|
|
+ switch (arizona->pdata.clk32k_src) {
|
|
+ case ARIZONA_32KZ_MCLK1:
|
|
+ case ARIZONA_32KZ_MCLK2:
|
|
+ arizona_clk32k_disable(arizona);
|
|
+ break;
|
|
+ default:
|
|
+ break;
|
|
+ }
|
|
+
|
|
mfd_remove_devices(arizona->dev);
|
|
arizona_free_irq(arizona, ARIZONA_IRQ_UNDERCLOCKED, arizona);
|
|
arizona_free_irq(arizona, ARIZONA_IRQ_OVERCLOCKED, arizona);
|
|
diff --git a/drivers/mfd/dln2.c b/drivers/mfd/dln2.c
|
|
index 672831d5ee32e..97a69cd6f1278 100644
|
|
--- a/drivers/mfd/dln2.c
|
|
+++ b/drivers/mfd/dln2.c
|
|
@@ -294,7 +294,11 @@ static void dln2_rx(struct urb *urb)
|
|
len = urb->actual_length - sizeof(struct dln2_header);
|
|
|
|
if (handle == DLN2_HANDLE_EVENT) {
|
|
+ unsigned long flags;
|
|
+
|
|
+ spin_lock_irqsave(&dln2->event_cb_lock, flags);
|
|
dln2_run_event_callbacks(dln2, id, echo, data, len);
|
|
+ spin_unlock_irqrestore(&dln2->event_cb_lock, flags);
|
|
} else {
|
|
/* URB will be re-submitted in _dln2_transfer (free_rx_slot) */
|
|
if (dln2_transfer_complete(dln2, urb, handle, echo))
|
|
diff --git a/drivers/misc/cxl/sysfs.c b/drivers/misc/cxl/sysfs.c
|
|
index 393a80bdb846a..b0285c5d8d381 100644
|
|
--- a/drivers/misc/cxl/sysfs.c
|
|
+++ b/drivers/misc/cxl/sysfs.c
|
|
@@ -606,7 +606,7 @@ static struct afu_config_record *cxl_sysfs_afu_new_cr(struct cxl_afu *afu, int c
|
|
rc = kobject_init_and_add(&cr->kobj, &afu_config_record_type,
|
|
&afu->dev.kobj, "cr%i", cr->cr);
|
|
if (rc)
|
|
- goto err;
|
|
+ goto err1;
|
|
|
|
rc = sysfs_create_bin_file(&cr->kobj, &cr->config_attr);
|
|
if (rc)
|
|
diff --git a/drivers/mtd/mtdchar.c b/drivers/mtd/mtdchar.c
|
|
index fa4d12217652b..18dd333f2d407 100644
|
|
--- a/drivers/mtd/mtdchar.c
|
|
+++ b/drivers/mtd/mtdchar.c
|
|
@@ -372,9 +372,6 @@ static int mtdchar_writeoob(struct file *file, struct mtd_info *mtd,
|
|
uint32_t retlen;
|
|
int ret = 0;
|
|
|
|
- if (!(file->f_mode & FMODE_WRITE))
|
|
- return -EPERM;
|
|
-
|
|
if (length > 4096)
|
|
return -EINVAL;
|
|
|
|
@@ -681,6 +678,48 @@ static int mtdchar_ioctl(struct file *file, u_int cmd, u_long arg)
|
|
return -EFAULT;
|
|
}
|
|
|
|
+ /*
|
|
+ * Check the file mode to require "dangerous" commands to have write
|
|
+ * permissions.
|
|
+ */
|
|
+ switch (cmd) {
|
|
+ /* "safe" commands */
|
|
+ case MEMGETREGIONCOUNT:
|
|
+ case MEMGETREGIONINFO:
|
|
+ case MEMGETINFO:
|
|
+ case MEMREADOOB:
|
|
+ case MEMREADOOB64:
|
|
+ case MEMLOCK:
|
|
+ case MEMUNLOCK:
|
|
+ case MEMISLOCKED:
|
|
+ case MEMGETOOBSEL:
|
|
+ case MEMGETBADBLOCK:
|
|
+ case MEMSETBADBLOCK:
|
|
+ case OTPSELECT:
|
|
+ case OTPGETREGIONCOUNT:
|
|
+ case OTPGETREGIONINFO:
|
|
+ case OTPLOCK:
|
|
+ case ECCGETLAYOUT:
|
|
+ case ECCGETSTATS:
|
|
+ case MTDFILEMODE:
|
|
+ case BLKPG:
|
|
+ case BLKRRPART:
|
|
+ break;
|
|
+
|
|
+ /* "dangerous" commands */
|
|
+ case MEMERASE:
|
|
+ case MEMERASE64:
|
|
+ case MEMWRITEOOB:
|
|
+ case MEMWRITEOOB64:
|
|
+ case MEMWRITE:
|
|
+ if (!(file->f_mode & FMODE_WRITE))
|
|
+ return -EPERM;
|
|
+ break;
|
|
+
|
|
+ default:
|
|
+ return -ENOTTY;
|
|
+ }
|
|
+
|
|
switch (cmd) {
|
|
case MEMGETREGIONCOUNT:
|
|
if (copy_to_user(argp, &(mtd->numeraseregions), sizeof(int)))
|
|
@@ -728,9 +767,6 @@ static int mtdchar_ioctl(struct file *file, u_int cmd, u_long arg)
|
|
{
|
|
struct erase_info *erase;
|
|
|
|
- if(!(file->f_mode & FMODE_WRITE))
|
|
- return -EPERM;
|
|
-
|
|
erase=kzalloc(sizeof(struct erase_info),GFP_KERNEL);
|
|
if (!erase)
|
|
ret = -ENOMEM;
|
|
@@ -1051,9 +1087,6 @@ static int mtdchar_ioctl(struct file *file, u_int cmd, u_long arg)
|
|
ret = 0;
|
|
break;
|
|
}
|
|
-
|
|
- default:
|
|
- ret = -ENOTTY;
|
|
}
|
|
|
|
return ret;
|
|
@@ -1097,6 +1130,11 @@ static long mtdchar_compat_ioctl(struct file *file, unsigned int cmd,
|
|
struct mtd_oob_buf32 buf;
|
|
struct mtd_oob_buf32 __user *buf_user = argp;
|
|
|
|
+ if (!(file->f_mode & FMODE_WRITE)) {
|
|
+ ret = -EPERM;
|
|
+ break;
|
|
+ }
|
|
+
|
|
if (copy_from_user(&buf, argp, sizeof(buf)))
|
|
ret = -EFAULT;
|
|
else
|
|
diff --git a/drivers/mtd/nand/qcom_nandc.c b/drivers/mtd/nand/qcom_nandc.c
|
|
index 65d1be2c30497..b57678970033f 100644
|
|
--- a/drivers/mtd/nand/qcom_nandc.c
|
|
+++ b/drivers/mtd/nand/qcom_nandc.c
|
|
@@ -435,11 +435,13 @@ struct qcom_nand_host {
|
|
* among different NAND controllers.
|
|
* @ecc_modes - ecc mode for NAND
|
|
* @is_bam - whether NAND controller is using BAM
|
|
+ * @is_qpic - whether NAND CTRL is part of qpic IP
|
|
* @dev_cmd_reg_start - NAND_DEV_CMD_* registers starting offset
|
|
*/
|
|
struct qcom_nandc_props {
|
|
u32 ecc_modes;
|
|
bool is_bam;
|
|
+ bool is_qpic;
|
|
u32 dev_cmd_reg_start;
|
|
};
|
|
|
|
@@ -2508,7 +2510,8 @@ static int qcom_nandc_setup(struct qcom_nand_controller *nandc)
|
|
u32 nand_ctrl;
|
|
|
|
/* kill onenand */
|
|
- nandc_write(nandc, SFLASHC_BURST_CFG, 0);
|
|
+ if (!nandc->props->is_qpic)
|
|
+ nandc_write(nandc, SFLASHC_BURST_CFG, 0);
|
|
nandc_write(nandc, dev_cmd_reg_addr(nandc, NAND_DEV_CMD_VLD),
|
|
NAND_DEV_CMD_VLD_VAL);
|
|
|
|
@@ -2779,12 +2782,14 @@ static const struct qcom_nandc_props ipq806x_nandc_props = {
|
|
static const struct qcom_nandc_props ipq4019_nandc_props = {
|
|
.ecc_modes = (ECC_BCH_4BIT | ECC_BCH_8BIT),
|
|
.is_bam = true,
|
|
+ .is_qpic = true,
|
|
.dev_cmd_reg_start = 0x0,
|
|
};
|
|
|
|
static const struct qcom_nandc_props ipq8074_nandc_props = {
|
|
.ecc_modes = (ECC_BCH_4BIT | ECC_BCH_8BIT),
|
|
.is_bam = true,
|
|
+ .is_qpic = true,
|
|
.dev_cmd_reg_start = 0x7000,
|
|
};
|
|
|
|
diff --git a/drivers/net/dsa/mv88e6xxx/chip.c b/drivers/net/dsa/mv88e6xxx/chip.c
|
|
index 10ea01459a36b..f4268f0322663 100644
|
|
--- a/drivers/net/dsa/mv88e6xxx/chip.c
|
|
+++ b/drivers/net/dsa/mv88e6xxx/chip.c
|
|
@@ -2450,7 +2450,6 @@ static const struct mv88e6xxx_ops mv88e6097_ops = {
|
|
.port_set_frame_mode = mv88e6351_port_set_frame_mode,
|
|
.port_set_egress_floods = mv88e6352_port_set_egress_floods,
|
|
.port_set_ether_type = mv88e6351_port_set_ether_type,
|
|
- .port_set_jumbo_size = mv88e6165_port_set_jumbo_size,
|
|
.port_egress_rate_limiting = mv88e6095_port_egress_rate_limiting,
|
|
.port_pause_limit = mv88e6097_port_pause_limit,
|
|
.port_disable_learn_limit = mv88e6xxx_port_disable_learn_limit,
|
|
diff --git a/drivers/net/ethernet/aquantia/atlantic/hw_atl/hw_atl_a0.c b/drivers/net/ethernet/aquantia/atlantic/hw_atl/hw_atl_a0.c
|
|
index b83ee74d28391..77e5c69268146 100644
|
|
--- a/drivers/net/ethernet/aquantia/atlantic/hw_atl/hw_atl_a0.c
|
|
+++ b/drivers/net/ethernet/aquantia/atlantic/hw_atl/hw_atl_a0.c
|
|
@@ -746,7 +746,7 @@ static int hw_atl_a0_hw_multicast_list_set(struct aq_hw_s *self,
|
|
int err = 0;
|
|
|
|
if (count > (HW_ATL_A0_MAC_MAX - HW_ATL_A0_MAC_MIN)) {
|
|
- err = EBADRQC;
|
|
+ err = -EBADRQC;
|
|
goto err_exit;
|
|
}
|
|
for (self->aq_nic_cfg->mc_list_count = 0U;
|
|
diff --git a/drivers/net/ethernet/cavium/liquidio/cn23xx_pf_device.c b/drivers/net/ethernet/cavium/liquidio/cn23xx_pf_device.c
|
|
index 2e089b5ff8f32..30f0e54f658e9 100644
|
|
--- a/drivers/net/ethernet/cavium/liquidio/cn23xx_pf_device.c
|
|
+++ b/drivers/net/ethernet/cavium/liquidio/cn23xx_pf_device.c
|
|
@@ -1167,7 +1167,7 @@ static int cn23xx_get_pf_num(struct octeon_device *oct)
|
|
oct->pf_num = ((fdl_bit >> CN23XX_PCIE_SRIOV_FDL_BIT_POS) &
|
|
CN23XX_PCIE_SRIOV_FDL_MASK);
|
|
} else {
|
|
- ret = EINVAL;
|
|
+ ret = -EINVAL;
|
|
|
|
/* Under some virtual environments, extended PCI regs are
|
|
* inaccessible, in which case the above read will have failed.
|
|
diff --git a/drivers/net/ethernet/freescale/fman/fman.c b/drivers/net/ethernet/freescale/fman/fman.c
|
|
index 9080d2332d030..cdd48b1cc84a7 100644
|
|
--- a/drivers/net/ethernet/freescale/fman/fman.c
|
|
+++ b/drivers/net/ethernet/freescale/fman/fman.c
|
|
@@ -1396,8 +1396,7 @@ static void enable_time_stamp(struct fman *fman)
|
|
{
|
|
struct fman_fpm_regs __iomem *fpm_rg = fman->fpm_regs;
|
|
u16 fm_clk_freq = fman->state->fm_clk_freq;
|
|
- u32 tmp, intgr, ts_freq;
|
|
- u64 frac;
|
|
+ u32 tmp, intgr, ts_freq, frac;
|
|
|
|
ts_freq = (u32)(1 << fman->state->count1_micro_bit);
|
|
/* configure timestamp so that bit 8 will count 1 microsecond
|
|
diff --git a/drivers/net/ethernet/freescale/fman/fman_dtsec.c b/drivers/net/ethernet/freescale/fman/fman_dtsec.c
|
|
index 7af31ddd093f8..61238b3af2041 100644
|
|
--- a/drivers/net/ethernet/freescale/fman/fman_dtsec.c
|
|
+++ b/drivers/net/ethernet/freescale/fman/fman_dtsec.c
|
|
@@ -1159,7 +1159,7 @@ int dtsec_del_hash_mac_address(struct fman_mac *dtsec, enet_addr_t *eth_addr)
|
|
list_for_each(pos,
|
|
&dtsec->multicast_addr_hash->lsts[bucket]) {
|
|
hash_entry = ETH_HASH_ENTRY_OBJ(pos);
|
|
- if (hash_entry->addr == addr) {
|
|
+ if (hash_entry && hash_entry->addr == addr) {
|
|
list_del_init(&hash_entry->node);
|
|
kfree(hash_entry);
|
|
break;
|
|
@@ -1172,7 +1172,7 @@ int dtsec_del_hash_mac_address(struct fman_mac *dtsec, enet_addr_t *eth_addr)
|
|
list_for_each(pos,
|
|
&dtsec->unicast_addr_hash->lsts[bucket]) {
|
|
hash_entry = ETH_HASH_ENTRY_OBJ(pos);
|
|
- if (hash_entry->addr == addr) {
|
|
+ if (hash_entry && hash_entry->addr == addr) {
|
|
list_del_init(&hash_entry->node);
|
|
kfree(hash_entry);
|
|
break;
|
|
diff --git a/drivers/net/ethernet/freescale/fman/fman_mac.h b/drivers/net/ethernet/freescale/fman/fman_mac.h
|
|
index dd6d0526f6c1f..19f327efdaff3 100644
|
|
--- a/drivers/net/ethernet/freescale/fman/fman_mac.h
|
|
+++ b/drivers/net/ethernet/freescale/fman/fman_mac.h
|
|
@@ -252,7 +252,7 @@ static inline struct eth_hash_t *alloc_hash_table(u16 size)
|
|
struct eth_hash_t *hash;
|
|
|
|
/* Allocate address hash table */
|
|
- hash = kmalloc_array(size, sizeof(struct eth_hash_t *), GFP_KERNEL);
|
|
+ hash = kmalloc(sizeof(*hash), GFP_KERNEL);
|
|
if (!hash)
|
|
return NULL;
|
|
|
|
diff --git a/drivers/net/ethernet/freescale/fman/fman_memac.c b/drivers/net/ethernet/freescale/fman/fman_memac.c
|
|
index b33650a897f18..460f9e58e9877 100644
|
|
--- a/drivers/net/ethernet/freescale/fman/fman_memac.c
|
|
+++ b/drivers/net/ethernet/freescale/fman/fman_memac.c
|
|
@@ -855,7 +855,6 @@ int memac_set_tx_pause_frames(struct fman_mac *memac, u8 priority,
|
|
|
|
tmp = ioread32be(®s->command_config);
|
|
tmp &= ~CMD_CFG_PFC_MODE;
|
|
- priority = 0;
|
|
|
|
iowrite32be(tmp, ®s->command_config);
|
|
|
|
@@ -957,7 +956,7 @@ int memac_del_hash_mac_address(struct fman_mac *memac, enet_addr_t *eth_addr)
|
|
|
|
list_for_each(pos, &memac->multicast_addr_hash->lsts[hash]) {
|
|
hash_entry = ETH_HASH_ENTRY_OBJ(pos);
|
|
- if (hash_entry->addr == addr) {
|
|
+ if (hash_entry && hash_entry->addr == addr) {
|
|
list_del_init(&hash_entry->node);
|
|
kfree(hash_entry);
|
|
break;
|
|
diff --git a/drivers/net/ethernet/freescale/fman/fman_port.c b/drivers/net/ethernet/freescale/fman/fman_port.c
|
|
index 495190764155a..ac3d791f52821 100644
|
|
--- a/drivers/net/ethernet/freescale/fman/fman_port.c
|
|
+++ b/drivers/net/ethernet/freescale/fman/fman_port.c
|
|
@@ -1744,6 +1744,7 @@ static int fman_port_probe(struct platform_device *of_dev)
|
|
struct fman_port *port;
|
|
struct fman *fman;
|
|
struct device_node *fm_node, *port_node;
|
|
+ struct platform_device *fm_pdev;
|
|
struct resource res;
|
|
struct resource *dev_res;
|
|
u32 val;
|
|
@@ -1768,8 +1769,14 @@ static int fman_port_probe(struct platform_device *of_dev)
|
|
goto return_err;
|
|
}
|
|
|
|
- fman = dev_get_drvdata(&of_find_device_by_node(fm_node)->dev);
|
|
+ fm_pdev = of_find_device_by_node(fm_node);
|
|
of_node_put(fm_node);
|
|
+ if (!fm_pdev) {
|
|
+ err = -EINVAL;
|
|
+ goto return_err;
|
|
+ }
|
|
+
|
|
+ fman = dev_get_drvdata(&fm_pdev->dev);
|
|
if (!fman) {
|
|
err = -EINVAL;
|
|
goto return_err;
|
|
diff --git a/drivers/net/ethernet/freescale/fman/fman_tgec.c b/drivers/net/ethernet/freescale/fman/fman_tgec.c
|
|
index e575259d20f40..c8ad9b8a75f8e 100644
|
|
--- a/drivers/net/ethernet/freescale/fman/fman_tgec.c
|
|
+++ b/drivers/net/ethernet/freescale/fman/fman_tgec.c
|
|
@@ -585,7 +585,7 @@ int tgec_del_hash_mac_address(struct fman_mac *tgec, enet_addr_t *eth_addr)
|
|
|
|
list_for_each(pos, &tgec->multicast_addr_hash->lsts[hash]) {
|
|
hash_entry = ETH_HASH_ENTRY_OBJ(pos);
|
|
- if (hash_entry->addr == addr) {
|
|
+ if (hash_entry && hash_entry->addr == addr) {
|
|
list_del_init(&hash_entry->node);
|
|
kfree(hash_entry);
|
|
break;
|
|
diff --git a/drivers/net/ethernet/intel/igb/igb_main.c b/drivers/net/ethernet/intel/igb/igb_main.c
|
|
index 9c7e75b3b6c7a..50fa0401c7014 100644
|
|
--- a/drivers/net/ethernet/intel/igb/igb_main.c
|
|
+++ b/drivers/net/ethernet/intel/igb/igb_main.c
|
|
@@ -5487,9 +5487,18 @@ static void igb_reset_task(struct work_struct *work)
|
|
struct igb_adapter *adapter;
|
|
adapter = container_of(work, struct igb_adapter, reset_task);
|
|
|
|
+ rtnl_lock();
|
|
+ /* If we're already down or resetting, just bail */
|
|
+ if (test_bit(__IGB_DOWN, &adapter->state) ||
|
|
+ test_bit(__IGB_RESETTING, &adapter->state)) {
|
|
+ rtnl_unlock();
|
|
+ return;
|
|
+ }
|
|
+
|
|
igb_dump(adapter);
|
|
netdev_err(adapter->netdev, "Reset adapter\n");
|
|
igb_reinit_locked(adapter);
|
|
+ rtnl_unlock();
|
|
}
|
|
|
|
/**
|
|
diff --git a/drivers/net/ethernet/mediatek/mtk_eth_soc.c b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
|
index 9ba699cbdbc5e..a52909db67f68 100644
|
|
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
|
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
|
@@ -2452,6 +2452,8 @@ static int mtk_add_mac(struct mtk_eth *eth, struct device_node *np)
|
|
eth->netdev[id]->irq = eth->irq[0];
|
|
eth->netdev[id]->dev.of_node = np;
|
|
|
|
+ eth->netdev[id]->max_mtu = MTK_MAX_RX_LENGTH - MTK_RX_ETH_HLEN;
|
|
+
|
|
return 0;
|
|
|
|
free_netdev:
|
|
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/en_rep.c b/drivers/net/ethernet/mellanox/mlx5/core/en_rep.c
|
|
index e69674d38f167..a3107d133b404 100644
|
|
--- a/drivers/net/ethernet/mellanox/mlx5/core/en_rep.c
|
|
+++ b/drivers/net/ethernet/mellanox/mlx5/core/en_rep.c
|
|
@@ -180,7 +180,7 @@ int mlx5e_attr_get(struct net_device *dev, struct switchdev_attr *attr)
|
|
struct mlx5_eswitch_rep *rep = rpriv->rep;
|
|
struct mlx5_eswitch *esw = priv->mdev->priv.eswitch;
|
|
|
|
- if (esw->mode == SRIOV_NONE)
|
|
+ if (esw->mode != SRIOV_OFFLOADS)
|
|
return -EOPNOTSUPP;
|
|
|
|
switch (attr->id) {
|
|
diff --git a/drivers/net/ethernet/qualcomm/emac/emac.c b/drivers/net/ethernet/qualcomm/emac/emac.c
|
|
index 759543512117c..5ab83751a471f 100644
|
|
--- a/drivers/net/ethernet/qualcomm/emac/emac.c
|
|
+++ b/drivers/net/ethernet/qualcomm/emac/emac.c
|
|
@@ -493,13 +493,24 @@ static int emac_clks_phase1_init(struct platform_device *pdev,
|
|
|
|
ret = clk_prepare_enable(adpt->clk[EMAC_CLK_CFG_AHB]);
|
|
if (ret)
|
|
- return ret;
|
|
+ goto disable_clk_axi;
|
|
|
|
ret = clk_set_rate(adpt->clk[EMAC_CLK_HIGH_SPEED], 19200000);
|
|
if (ret)
|
|
- return ret;
|
|
+ goto disable_clk_cfg_ahb;
|
|
+
|
|
+ ret = clk_prepare_enable(adpt->clk[EMAC_CLK_HIGH_SPEED]);
|
|
+ if (ret)
|
|
+ goto disable_clk_cfg_ahb;
|
|
|
|
- return clk_prepare_enable(adpt->clk[EMAC_CLK_HIGH_SPEED]);
|
|
+ return 0;
|
|
+
|
|
+disable_clk_cfg_ahb:
|
|
+ clk_disable_unprepare(adpt->clk[EMAC_CLK_CFG_AHB]);
|
|
+disable_clk_axi:
|
|
+ clk_disable_unprepare(adpt->clk[EMAC_CLK_AXI]);
|
|
+
|
|
+ return ret;
|
|
}
|
|
|
|
/* Enable clocks; needs emac_clks_phase1_init to be called before */
|
|
diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c
|
|
index bcc5d1e16ce2c..1924788d28da0 100644
|
|
--- a/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c
|
|
+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c
|
|
@@ -362,6 +362,7 @@ static int ipq806x_gmac_probe(struct platform_device *pdev)
|
|
plat_dat->has_gmac = true;
|
|
plat_dat->bsp_priv = gmac;
|
|
plat_dat->fix_mac_speed = ipq806x_gmac_fix_mac_speed;
|
|
+ plat_dat->multicast_filter_bins = 0;
|
|
|
|
err = stmmac_dvr_probe(&pdev->dev, plat_dat, &stmmac_res);
|
|
if (err)
|
|
diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c b/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c
|
|
index f76d4a7281af0..f07d9d3456a4f 100644
|
|
--- a/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c
|
|
+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c
|
|
@@ -176,6 +176,9 @@ static void dwmac1000_set_filter(struct mac_device_info *hw,
|
|
value = GMAC_FRAME_FILTER_PR;
|
|
} else if (dev->flags & IFF_ALLMULTI) {
|
|
value = GMAC_FRAME_FILTER_PM; /* pass all multi */
|
|
+ } else if (!netdev_mc_empty(dev) && (mcbitslog2 == 0)) {
|
|
+ /* Fall back to all multicast if we've no filter */
|
|
+ value = GMAC_FRAME_FILTER_PM;
|
|
} else if (!netdev_mc_empty(dev)) {
|
|
struct netdev_hw_addr *ha;
|
|
|
|
diff --git a/drivers/net/ethernet/toshiba/spider_net.c b/drivers/net/ethernet/toshiba/spider_net.c
|
|
index da136b8843dd9..a0fed9035f537 100644
|
|
--- a/drivers/net/ethernet/toshiba/spider_net.c
|
|
+++ b/drivers/net/ethernet/toshiba/spider_net.c
|
|
@@ -296,8 +296,8 @@ spider_net_free_chain(struct spider_net_card *card,
|
|
descr = descr->next;
|
|
} while (descr != chain->ring);
|
|
|
|
- dma_free_coherent(&card->pdev->dev, chain->num_desc,
|
|
- chain->hwring, chain->dma_addr);
|
|
+ dma_free_coherent(&card->pdev->dev, chain->num_desc * sizeof(struct spider_net_hw_descr),
|
|
+ chain->hwring, chain->dma_addr);
|
|
}
|
|
|
|
/**
|
|
diff --git a/drivers/net/hyperv/netvsc_drv.c b/drivers/net/hyperv/netvsc_drv.c
|
|
index 14451e14d99dc..10c3480c2da89 100644
|
|
--- a/drivers/net/hyperv/netvsc_drv.c
|
|
+++ b/drivers/net/hyperv/netvsc_drv.c
|
|
@@ -532,12 +532,13 @@ static int netvsc_start_xmit(struct sk_buff *skb, struct net_device *net)
|
|
u32 hash;
|
|
struct hv_page_buffer pb[MAX_PAGE_BUFFER_COUNT];
|
|
|
|
- /* if VF is present and up then redirect packets
|
|
- * already called with rcu_read_lock_bh
|
|
+ /* If VF is present and up then redirect packets to it.
|
|
+ * Skip the VF if it is marked down or has no carrier.
|
|
+ * If netpoll is in uses, then VF can not be used either.
|
|
*/
|
|
vf_netdev = rcu_dereference_bh(net_device_ctx->vf_netdev);
|
|
if (vf_netdev && netif_running(vf_netdev) &&
|
|
- !netpoll_tx_running(net))
|
|
+ netif_carrier_ok(vf_netdev) && !netpoll_tx_running(net))
|
|
return netvsc_vf_xmit(net, vf_netdev, skb);
|
|
|
|
/* We will atmost need two pages to describe the rndis
|
|
diff --git a/drivers/net/usb/hso.c b/drivers/net/usb/hso.c
|
|
index 7988c41bff1d5..0e3d13e192e38 100644
|
|
--- a/drivers/net/usb/hso.c
|
|
+++ b/drivers/net/usb/hso.c
|
|
@@ -2272,12 +2272,14 @@ static int hso_serial_common_create(struct hso_serial *serial, int num_urbs,
|
|
|
|
minor = get_free_serial_index();
|
|
if (minor < 0)
|
|
- goto exit;
|
|
+ goto exit2;
|
|
|
|
/* register our minor number */
|
|
serial->parent->dev = tty_port_register_device_attr(&serial->port,
|
|
tty_drv, minor, &serial->parent->interface->dev,
|
|
serial->parent, hso_serial_dev_groups);
|
|
+ if (IS_ERR(serial->parent->dev))
|
|
+ goto exit2;
|
|
dev = serial->parent->dev;
|
|
|
|
/* fill in specific data for later use */
|
|
@@ -2323,6 +2325,7 @@ static int hso_serial_common_create(struct hso_serial *serial, int num_urbs,
|
|
return 0;
|
|
exit:
|
|
hso_serial_tty_unregister(serial);
|
|
+exit2:
|
|
hso_serial_common_free(serial);
|
|
return -1;
|
|
}
|
|
diff --git a/drivers/net/usb/lan78xx.c b/drivers/net/usb/lan78xx.c
|
|
index 895f307979c82..120e99914fd62 100644
|
|
--- a/drivers/net/usb/lan78xx.c
|
|
+++ b/drivers/net/usb/lan78xx.c
|
|
@@ -363,10 +363,6 @@ struct lan78xx_net {
|
|
struct tasklet_struct bh;
|
|
struct delayed_work wq;
|
|
|
|
- struct usb_host_endpoint *ep_blkin;
|
|
- struct usb_host_endpoint *ep_blkout;
|
|
- struct usb_host_endpoint *ep_intr;
|
|
-
|
|
int msg_enable;
|
|
|
|
struct urb *urb_intr;
|
|
@@ -2751,78 +2747,12 @@ lan78xx_start_xmit(struct sk_buff *skb, struct net_device *net)
|
|
return NETDEV_TX_OK;
|
|
}
|
|
|
|
-static int
|
|
-lan78xx_get_endpoints(struct lan78xx_net *dev, struct usb_interface *intf)
|
|
-{
|
|
- int tmp;
|
|
- struct usb_host_interface *alt = NULL;
|
|
- struct usb_host_endpoint *in = NULL, *out = NULL;
|
|
- struct usb_host_endpoint *status = NULL;
|
|
-
|
|
- for (tmp = 0; tmp < intf->num_altsetting; tmp++) {
|
|
- unsigned ep;
|
|
-
|
|
- in = NULL;
|
|
- out = NULL;
|
|
- status = NULL;
|
|
- alt = intf->altsetting + tmp;
|
|
-
|
|
- for (ep = 0; ep < alt->desc.bNumEndpoints; ep++) {
|
|
- struct usb_host_endpoint *e;
|
|
- int intr = 0;
|
|
-
|
|
- e = alt->endpoint + ep;
|
|
- switch (e->desc.bmAttributes) {
|
|
- case USB_ENDPOINT_XFER_INT:
|
|
- if (!usb_endpoint_dir_in(&e->desc))
|
|
- continue;
|
|
- intr = 1;
|
|
- /* FALLTHROUGH */
|
|
- case USB_ENDPOINT_XFER_BULK:
|
|
- break;
|
|
- default:
|
|
- continue;
|
|
- }
|
|
- if (usb_endpoint_dir_in(&e->desc)) {
|
|
- if (!intr && !in)
|
|
- in = e;
|
|
- else if (intr && !status)
|
|
- status = e;
|
|
- } else {
|
|
- if (!out)
|
|
- out = e;
|
|
- }
|
|
- }
|
|
- if (in && out)
|
|
- break;
|
|
- }
|
|
- if (!alt || !in || !out)
|
|
- return -EINVAL;
|
|
-
|
|
- dev->pipe_in = usb_rcvbulkpipe(dev->udev,
|
|
- in->desc.bEndpointAddress &
|
|
- USB_ENDPOINT_NUMBER_MASK);
|
|
- dev->pipe_out = usb_sndbulkpipe(dev->udev,
|
|
- out->desc.bEndpointAddress &
|
|
- USB_ENDPOINT_NUMBER_MASK);
|
|
- dev->ep_intr = status;
|
|
-
|
|
- return 0;
|
|
-}
|
|
-
|
|
static int lan78xx_bind(struct lan78xx_net *dev, struct usb_interface *intf)
|
|
{
|
|
struct lan78xx_priv *pdata = NULL;
|
|
int ret;
|
|
int i;
|
|
|
|
- ret = lan78xx_get_endpoints(dev, intf);
|
|
- if (ret) {
|
|
- netdev_warn(dev->net, "lan78xx_get_endpoints failed: %d\n",
|
|
- ret);
|
|
- return ret;
|
|
- }
|
|
-
|
|
dev->data[0] = (unsigned long)kzalloc(sizeof(*pdata), GFP_KERNEL);
|
|
|
|
pdata = (struct lan78xx_priv *)(dev->data[0]);
|
|
@@ -3567,6 +3497,7 @@ static void lan78xx_stat_monitor(unsigned long param)
|
|
static int lan78xx_probe(struct usb_interface *intf,
|
|
const struct usb_device_id *id)
|
|
{
|
|
+ struct usb_host_endpoint *ep_blkin, *ep_blkout, *ep_intr;
|
|
struct lan78xx_net *dev;
|
|
struct net_device *netdev;
|
|
struct usb_device *udev;
|
|
@@ -3617,6 +3548,34 @@ static int lan78xx_probe(struct usb_interface *intf,
|
|
|
|
mutex_init(&dev->stats.access_lock);
|
|
|
|
+ if (intf->cur_altsetting->desc.bNumEndpoints < 3) {
|
|
+ ret = -ENODEV;
|
|
+ goto out2;
|
|
+ }
|
|
+
|
|
+ dev->pipe_in = usb_rcvbulkpipe(udev, BULK_IN_PIPE);
|
|
+ ep_blkin = usb_pipe_endpoint(udev, dev->pipe_in);
|
|
+ if (!ep_blkin || !usb_endpoint_is_bulk_in(&ep_blkin->desc)) {
|
|
+ ret = -ENODEV;
|
|
+ goto out2;
|
|
+ }
|
|
+
|
|
+ dev->pipe_out = usb_sndbulkpipe(udev, BULK_OUT_PIPE);
|
|
+ ep_blkout = usb_pipe_endpoint(udev, dev->pipe_out);
|
|
+ if (!ep_blkout || !usb_endpoint_is_bulk_out(&ep_blkout->desc)) {
|
|
+ ret = -ENODEV;
|
|
+ goto out2;
|
|
+ }
|
|
+
|
|
+ ep_intr = &intf->cur_altsetting->endpoint[2];
|
|
+ if (!usb_endpoint_is_int_in(&ep_intr->desc)) {
|
|
+ ret = -ENODEV;
|
|
+ goto out2;
|
|
+ }
|
|
+
|
|
+ dev->pipe_intr = usb_rcvintpipe(dev->udev,
|
|
+ usb_endpoint_num(&ep_intr->desc));
|
|
+
|
|
ret = lan78xx_bind(dev, intf);
|
|
if (ret < 0)
|
|
goto out2;
|
|
@@ -3629,23 +3588,7 @@ static int lan78xx_probe(struct usb_interface *intf,
|
|
netdev->max_mtu = MAX_SINGLE_PACKET_SIZE;
|
|
netif_set_gso_max_size(netdev, MAX_SINGLE_PACKET_SIZE - MAX_HEADER);
|
|
|
|
- if (intf->cur_altsetting->desc.bNumEndpoints < 3) {
|
|
- ret = -ENODEV;
|
|
- goto out3;
|
|
- }
|
|
-
|
|
- dev->ep_blkin = (intf->cur_altsetting)->endpoint + 0;
|
|
- dev->ep_blkout = (intf->cur_altsetting)->endpoint + 1;
|
|
- dev->ep_intr = (intf->cur_altsetting)->endpoint + 2;
|
|
-
|
|
- dev->pipe_in = usb_rcvbulkpipe(udev, BULK_IN_PIPE);
|
|
- dev->pipe_out = usb_sndbulkpipe(udev, BULK_OUT_PIPE);
|
|
-
|
|
- dev->pipe_intr = usb_rcvintpipe(dev->udev,
|
|
- dev->ep_intr->desc.bEndpointAddress &
|
|
- USB_ENDPOINT_NUMBER_MASK);
|
|
- period = dev->ep_intr->desc.bInterval;
|
|
-
|
|
+ period = ep_intr->desc.bInterval;
|
|
maxp = usb_maxpacket(dev->udev, dev->pipe_intr, 0);
|
|
buf = kmalloc(maxp, GFP_KERNEL);
|
|
if (buf) {
|
|
diff --git a/drivers/net/vxlan.c b/drivers/net/vxlan.c
|
|
index afdc2c290fd03..82efa5bbf568b 100644
|
|
--- a/drivers/net/vxlan.c
|
|
+++ b/drivers/net/vxlan.c
|
|
@@ -974,6 +974,7 @@ static int vxlan_fdb_dump(struct sk_buff *skb, struct netlink_callback *cb,
|
|
for (h = 0; h < FDB_HASH_SIZE; ++h) {
|
|
struct vxlan_fdb *f;
|
|
|
|
+ rcu_read_lock();
|
|
hlist_for_each_entry_rcu(f, &vxlan->fdb_head[h], hlist) {
|
|
struct vxlan_rdst *rd;
|
|
|
|
@@ -986,12 +987,15 @@ static int vxlan_fdb_dump(struct sk_buff *skb, struct netlink_callback *cb,
|
|
cb->nlh->nlmsg_seq,
|
|
RTM_NEWNEIGH,
|
|
NLM_F_MULTI, rd);
|
|
- if (err < 0)
|
|
+ if (err < 0) {
|
|
+ rcu_read_unlock();
|
|
goto out;
|
|
+ }
|
|
skip:
|
|
*idx += 1;
|
|
}
|
|
}
|
|
+ rcu_read_unlock();
|
|
}
|
|
out:
|
|
return err;
|
|
@@ -2218,7 +2222,7 @@ static void vxlan_xmit_one(struct sk_buff *skb, struct net_device *dev,
|
|
skb_dst_update_pmtu(skb, mtu);
|
|
}
|
|
|
|
- tos = ip_tunnel_ecn_encap(RT_TOS(tos), old_iph, skb);
|
|
+ tos = ip_tunnel_ecn_encap(tos, old_iph, skb);
|
|
ttl = ttl ? : ip4_dst_hoplimit(&rt->dst);
|
|
err = vxlan_build_skb(skb, ndst, sizeof(struct iphdr),
|
|
vni, md, flags, udp_sum);
|
|
@@ -2259,7 +2263,7 @@ static void vxlan_xmit_one(struct sk_buff *skb, struct net_device *dev,
|
|
skb_dst_update_pmtu(skb, mtu);
|
|
}
|
|
|
|
- tos = ip_tunnel_ecn_encap(RT_TOS(tos), old_iph, skb);
|
|
+ tos = ip_tunnel_ecn_encap(tos, old_iph, skb);
|
|
ttl = ttl ? : ip6_dst_hoplimit(ndst);
|
|
skb_scrub_packet(skb, xnet);
|
|
err = vxlan_build_skb(skb, ndst, sizeof(struct ipv6hdr),
|
|
diff --git a/drivers/net/wan/lapbether.c b/drivers/net/wan/lapbether.c
|
|
index ac34257e9f203..c94dfa70f2a33 100644
|
|
--- a/drivers/net/wan/lapbether.c
|
|
+++ b/drivers/net/wan/lapbether.c
|
|
@@ -160,6 +160,12 @@ static netdev_tx_t lapbeth_xmit(struct sk_buff *skb,
|
|
if (!netif_running(dev))
|
|
goto drop;
|
|
|
|
+ /* There should be a pseudo header of 1 byte added by upper layers.
|
|
+ * Check to make sure it is there before reading it.
|
|
+ */
|
|
+ if (skb->len < 1)
|
|
+ goto drop;
|
|
+
|
|
switch (skb->data[0]) {
|
|
case X25_IFACE_DATA:
|
|
break;
|
|
@@ -308,6 +314,7 @@ static void lapbeth_setup(struct net_device *dev)
|
|
dev->netdev_ops = &lapbeth_netdev_ops;
|
|
dev->needs_free_netdev = true;
|
|
dev->type = ARPHRD_X25;
|
|
+ dev->hard_header_len = 0;
|
|
dev->mtu = 1000;
|
|
dev->addr_len = 0;
|
|
}
|
|
@@ -334,7 +341,8 @@ static int lapbeth_new_device(struct net_device *dev)
|
|
* then this driver prepends a length field of 2 bytes,
|
|
* then the underlying Ethernet device prepends its own header.
|
|
*/
|
|
- ndev->hard_header_len = -1 + 3 + 2 + dev->hard_header_len;
|
|
+ ndev->needed_headroom = -1 + 3 + 2 + dev->hard_header_len
|
|
+ + dev->needed_headroom;
|
|
|
|
lapbeth = netdev_priv(ndev);
|
|
lapbeth->axdev = ndev;
|
|
diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fwil_types.h b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fwil_types.h
|
|
index e0d22fedb2b45..05bd636011ec9 100644
|
|
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fwil_types.h
|
|
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fwil_types.h
|
|
@@ -30,7 +30,7 @@
|
|
#define BRCMF_ARP_OL_PEER_AUTO_REPLY 0x00000008
|
|
|
|
#define BRCMF_BSS_INFO_VERSION 109 /* curr ver of brcmf_bss_info_le struct */
|
|
-#define BRCMF_BSS_RSSI_ON_CHANNEL 0x0002
|
|
+#define BRCMF_BSS_RSSI_ON_CHANNEL 0x0004
|
|
|
|
#define BRCMF_STA_WME 0x00000002 /* WMM association */
|
|
#define BRCMF_STA_AUTHE 0x00000008 /* Authenticated */
|
|
diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fwsignal.c b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fwsignal.c
|
|
index 2370060ef980a..0807331284895 100644
|
|
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fwsignal.c
|
|
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fwsignal.c
|
|
@@ -653,6 +653,7 @@ static inline int brcmf_fws_hanger_poppkt(struct brcmf_fws_hanger *h,
|
|
static void brcmf_fws_psq_flush(struct brcmf_fws_info *fws, struct pktq *q,
|
|
int ifidx)
|
|
{
|
|
+ struct brcmf_fws_hanger_item *hi;
|
|
bool (*matchfn)(struct sk_buff *, void *) = NULL;
|
|
struct sk_buff *skb;
|
|
int prec;
|
|
@@ -664,6 +665,9 @@ static void brcmf_fws_psq_flush(struct brcmf_fws_info *fws, struct pktq *q,
|
|
skb = brcmu_pktq_pdeq_match(q, prec, matchfn, &ifidx);
|
|
while (skb) {
|
|
hslot = brcmf_skb_htod_tag_get_field(skb, HSLOT);
|
|
+ hi = &fws->hanger.items[hslot];
|
|
+ WARN_ON(skb != hi->pkt);
|
|
+ hi->state = BRCMF_FWS_HANGER_ITEM_STATE_FREE;
|
|
brcmf_fws_hanger_poppkt(&fws->hanger, hslot, &skb,
|
|
true);
|
|
brcmu_pkt_buf_free_skb(skb);
|
|
diff --git a/drivers/net/wireless/intel/iwlegacy/common.c b/drivers/net/wireless/intel/iwlegacy/common.c
|
|
index 6e6b124f0d5e3..3ca84577803cc 100644
|
|
--- a/drivers/net/wireless/intel/iwlegacy/common.c
|
|
+++ b/drivers/net/wireless/intel/iwlegacy/common.c
|
|
@@ -4302,8 +4302,8 @@ il_apm_init(struct il_priv *il)
|
|
* power savings, even without L1.
|
|
*/
|
|
if (il->cfg->set_l0s) {
|
|
- pcie_capability_read_word(il->pci_dev, PCI_EXP_LNKCTL, &lctl);
|
|
- if (lctl & PCI_EXP_LNKCTL_ASPM_L1) {
|
|
+ ret = pcie_capability_read_word(il->pci_dev, PCI_EXP_LNKCTL, &lctl);
|
|
+ if (!ret && (lctl & PCI_EXP_LNKCTL_ASPM_L1)) {
|
|
/* L1-ASPM enabled; disable(!) L0S */
|
|
il_set_bit(il, CSR_GIO_REG,
|
|
CSR_GIO_REG_VAL_L0S_ENABLED);
|
|
diff --git a/drivers/net/wireless/marvell/mwifiex/sta_cmdresp.c b/drivers/net/wireless/marvell/mwifiex/sta_cmdresp.c
|
|
index 0fba5b10ef2d7..19ce279df24d9 100644
|
|
--- a/drivers/net/wireless/marvell/mwifiex/sta_cmdresp.c
|
|
+++ b/drivers/net/wireless/marvell/mwifiex/sta_cmdresp.c
|
|
@@ -585,6 +585,11 @@ static int mwifiex_ret_802_11_key_material_v1(struct mwifiex_private *priv,
|
|
{
|
|
struct host_cmd_ds_802_11_key_material *key =
|
|
&resp->params.key_material;
|
|
+ int len;
|
|
+
|
|
+ len = le16_to_cpu(key->key_param_set.key_len);
|
|
+ if (len > sizeof(key->key_param_set.key))
|
|
+ return -EINVAL;
|
|
|
|
if (le16_to_cpu(key->action) == HostCmd_ACT_GEN_SET) {
|
|
if ((le16_to_cpu(key->key_param_set.key_info) & KEY_MCAST)) {
|
|
@@ -598,9 +603,8 @@ static int mwifiex_ret_802_11_key_material_v1(struct mwifiex_private *priv,
|
|
|
|
memset(priv->aes_key.key_param_set.key, 0,
|
|
sizeof(key->key_param_set.key));
|
|
- priv->aes_key.key_param_set.key_len = key->key_param_set.key_len;
|
|
- memcpy(priv->aes_key.key_param_set.key, key->key_param_set.key,
|
|
- le16_to_cpu(priv->aes_key.key_param_set.key_len));
|
|
+ priv->aes_key.key_param_set.key_len = cpu_to_le16(len);
|
|
+ memcpy(priv->aes_key.key_param_set.key, key->key_param_set.key, len);
|
|
|
|
return 0;
|
|
}
|
|
@@ -615,9 +619,14 @@ static int mwifiex_ret_802_11_key_material_v2(struct mwifiex_private *priv,
|
|
struct host_cmd_ds_command *resp)
|
|
{
|
|
struct host_cmd_ds_802_11_key_material_v2 *key_v2;
|
|
- __le16 len;
|
|
+ int len;
|
|
|
|
key_v2 = &resp->params.key_material_v2;
|
|
+
|
|
+ len = le16_to_cpu(key_v2->key_param_set.key_params.aes.key_len);
|
|
+ if (len > WLAN_KEY_LEN_CCMP)
|
|
+ return -EINVAL;
|
|
+
|
|
if (le16_to_cpu(key_v2->action) == HostCmd_ACT_GEN_SET) {
|
|
if ((le16_to_cpu(key_v2->key_param_set.key_info) & KEY_MCAST)) {
|
|
mwifiex_dbg(priv->adapter, INFO, "info: key: GTK is set\n");
|
|
@@ -633,10 +642,9 @@ static int mwifiex_ret_802_11_key_material_v2(struct mwifiex_private *priv,
|
|
memset(priv->aes_key_v2.key_param_set.key_params.aes.key, 0,
|
|
WLAN_KEY_LEN_CCMP);
|
|
priv->aes_key_v2.key_param_set.key_params.aes.key_len =
|
|
- key_v2->key_param_set.key_params.aes.key_len;
|
|
- len = priv->aes_key_v2.key_param_set.key_params.aes.key_len;
|
|
+ cpu_to_le16(len);
|
|
memcpy(priv->aes_key_v2.key_param_set.key_params.aes.key,
|
|
- key_v2->key_param_set.key_params.aes.key, le16_to_cpu(len));
|
|
+ key_v2->key_param_set.key_params.aes.key, len);
|
|
|
|
return 0;
|
|
}
|
|
diff --git a/drivers/net/wireless/ti/wl1251/event.c b/drivers/net/wireless/ti/wl1251/event.c
|
|
index f5acd24d0e2b1..988abb49771f9 100644
|
|
--- a/drivers/net/wireless/ti/wl1251/event.c
|
|
+++ b/drivers/net/wireless/ti/wl1251/event.c
|
|
@@ -84,7 +84,7 @@ static int wl1251_event_ps_report(struct wl1251 *wl,
|
|
break;
|
|
}
|
|
|
|
- return 0;
|
|
+ return ret;
|
|
}
|
|
|
|
static void wl1251_event_mbox_dump(struct event_mailbox *mbox)
|
|
diff --git a/drivers/parisc/sba_iommu.c b/drivers/parisc/sba_iommu.c
|
|
index 5468490d2298b..55b3274328eb8 100644
|
|
--- a/drivers/parisc/sba_iommu.c
|
|
+++ b/drivers/parisc/sba_iommu.c
|
|
@@ -1291,7 +1291,7 @@ sba_ioc_init_pluto(struct parisc_device *sba, struct ioc *ioc, int ioc_num)
|
|
** (one that doesn't overlap memory or LMMIO space) in the
|
|
** IBASE and IMASK registers.
|
|
*/
|
|
- ioc->ibase = READ_REG(ioc->ioc_hpa + IOC_IBASE);
|
|
+ ioc->ibase = READ_REG(ioc->ioc_hpa + IOC_IBASE) & ~0x1fffffULL;
|
|
iova_space_size = ~(READ_REG(ioc->ioc_hpa + IOC_IMASK) & 0xFFFFFFFFUL) + 1;
|
|
|
|
if ((ioc->ibase < 0xfed00000UL) && ((ioc->ibase + iova_space_size) > 0xfee00000UL)) {
|
|
diff --git a/drivers/pci/access.c b/drivers/pci/access.c
|
|
index 913d6722ece98..8c585e7ca5209 100644
|
|
--- a/drivers/pci/access.c
|
|
+++ b/drivers/pci/access.c
|
|
@@ -205,17 +205,13 @@ EXPORT_SYMBOL(pci_bus_set_ops);
|
|
static DECLARE_WAIT_QUEUE_HEAD(pci_cfg_wait);
|
|
|
|
static noinline void pci_wait_cfg(struct pci_dev *dev)
|
|
+ __must_hold(&pci_lock)
|
|
{
|
|
- DECLARE_WAITQUEUE(wait, current);
|
|
-
|
|
- __add_wait_queue(&pci_cfg_wait, &wait);
|
|
do {
|
|
- set_current_state(TASK_UNINTERRUPTIBLE);
|
|
raw_spin_unlock_irq(&pci_lock);
|
|
- schedule();
|
|
+ wait_event(pci_cfg_wait, !dev->block_cfg_access);
|
|
raw_spin_lock_irq(&pci_lock);
|
|
} while (dev->block_cfg_access);
|
|
- __remove_wait_queue(&pci_cfg_wait, &wait);
|
|
}
|
|
|
|
/* Returns 0 on success, negative values indicate error. */
|
|
diff --git a/drivers/pci/host/vmd.c b/drivers/pci/host/vmd.c
|
|
index 05f191ae0ff1b..79d56638878cf 100644
|
|
--- a/drivers/pci/host/vmd.c
|
|
+++ b/drivers/pci/host/vmd.c
|
|
@@ -651,6 +651,7 @@ static int vmd_enable_domain(struct vmd_dev *vmd)
|
|
if (!vmd->bus) {
|
|
pci_free_resource_list(&resources);
|
|
irq_domain_remove(vmd->irq_domain);
|
|
+ irq_domain_free_fwnode(fn);
|
|
return -ENODEV;
|
|
}
|
|
|
|
@@ -753,6 +754,7 @@ static void vmd_cleanup_srcu(struct vmd_dev *vmd)
|
|
static void vmd_remove(struct pci_dev *dev)
|
|
{
|
|
struct vmd_dev *vmd = pci_get_drvdata(dev);
|
|
+ struct fwnode_handle *fn = vmd->irq_domain->fwnode;
|
|
|
|
sysfs_remove_link(&vmd->dev->dev.kobj, "domain");
|
|
pci_stop_root_bus(vmd->bus);
|
|
@@ -761,6 +763,7 @@ static void vmd_remove(struct pci_dev *dev)
|
|
vmd_teardown_dma_ops(vmd);
|
|
vmd_detach_resources(vmd);
|
|
irq_domain_remove(vmd->irq_domain);
|
|
+ irq_domain_free_fwnode(fn);
|
|
}
|
|
|
|
#ifdef CONFIG_PM_SLEEP
|
|
diff --git a/drivers/pci/hotplug/acpiphp_glue.c b/drivers/pci/hotplug/acpiphp_glue.c
|
|
index 711875afdd70a..f2c1008e0f76c 100644
|
|
--- a/drivers/pci/hotplug/acpiphp_glue.c
|
|
+++ b/drivers/pci/hotplug/acpiphp_glue.c
|
|
@@ -136,13 +136,21 @@ static struct acpiphp_context *acpiphp_grab_context(struct acpi_device *adev)
|
|
struct acpiphp_context *context;
|
|
|
|
acpi_lock_hp_context();
|
|
+
|
|
context = acpiphp_get_context(adev);
|
|
- if (!context || context->func.parent->is_going_away) {
|
|
- acpi_unlock_hp_context();
|
|
- return NULL;
|
|
+ if (!context)
|
|
+ goto unlock;
|
|
+
|
|
+ if (context->func.parent->is_going_away) {
|
|
+ acpiphp_put_context(context);
|
|
+ context = NULL;
|
|
+ goto unlock;
|
|
}
|
|
+
|
|
get_bridge(context->func.parent);
|
|
acpiphp_put_context(context);
|
|
+
|
|
+unlock:
|
|
acpi_unlock_hp_context();
|
|
return context;
|
|
}
|
|
diff --git a/drivers/pci/pcie/aspm.c b/drivers/pci/pcie/aspm.c
|
|
index 04d5c62588b77..f41c105adfbd4 100644
|
|
--- a/drivers/pci/pcie/aspm.c
|
|
+++ b/drivers/pci/pcie/aspm.c
|
|
@@ -1111,6 +1111,7 @@ static int pcie_aspm_get_policy(char *buffer, struct kernel_param *kp)
|
|
cnt += sprintf(buffer + cnt, "[%s] ", policy_str[i]);
|
|
else
|
|
cnt += sprintf(buffer + cnt, "%s ", policy_str[i]);
|
|
+ cnt += sprintf(buffer + cnt, "\n");
|
|
return cnt;
|
|
}
|
|
|
|
diff --git a/drivers/pci/quirks.c b/drivers/pci/quirks.c
|
|
index 243b16ce0c8eb..da790f26d2950 100644
|
|
--- a/drivers/pci/quirks.c
|
|
+++ b/drivers/pci/quirks.c
|
|
@@ -4307,6 +4307,8 @@ static int pci_quirk_amd_sb_acs(struct pci_dev *dev, u16 acs_flags)
|
|
if (ACPI_FAILURE(status))
|
|
return -ENODEV;
|
|
|
|
+ acpi_put_table(header);
|
|
+
|
|
/* Filter out flags not applicable to multifunction */
|
|
acs_flags &= (PCI_ACS_RR | PCI_ACS_CR | PCI_ACS_EC | PCI_ACS_DT);
|
|
|
|
diff --git a/drivers/pinctrl/pinctrl-single.c b/drivers/pinctrl/pinctrl-single.c
|
|
index b8b3d932cd73a..f751b5c3bf7e8 100644
|
|
--- a/drivers/pinctrl/pinctrl-single.c
|
|
+++ b/drivers/pinctrl/pinctrl-single.c
|
|
@@ -888,7 +888,7 @@ static int pcs_parse_pinconf(struct pcs_device *pcs, struct device_node *np,
|
|
|
|
/* If pinconf isn't supported, don't parse properties in below. */
|
|
if (!PCS_HAS_PINCONF)
|
|
- return 0;
|
|
+ return -ENOTSUPP;
|
|
|
|
/* cacluate how much properties are supported in current node */
|
|
for (i = 0; i < ARRAY_SIZE(prop2); i++) {
|
|
@@ -900,7 +900,7 @@ static int pcs_parse_pinconf(struct pcs_device *pcs, struct device_node *np,
|
|
nconfs++;
|
|
}
|
|
if (!nconfs)
|
|
- return 0;
|
|
+ return -ENOTSUPP;
|
|
|
|
func->conf = devm_kzalloc(pcs->dev,
|
|
sizeof(struct pcs_conf_vals) * nconfs,
|
|
@@ -1024,9 +1024,12 @@ static int pcs_parse_one_pinctrl_entry(struct pcs_device *pcs,
|
|
|
|
if (PCS_HAS_PINCONF) {
|
|
res = pcs_parse_pinconf(pcs, np, function, map);
|
|
- if (res)
|
|
+ if (res == 0)
|
|
+ *num_maps = 2;
|
|
+ else if (res == -ENOTSUPP)
|
|
+ *num_maps = 1;
|
|
+ else
|
|
goto free_pingroups;
|
|
- *num_maps = 2;
|
|
} else {
|
|
*num_maps = 1;
|
|
}
|
|
diff --git a/drivers/platform/x86/intel-hid.c b/drivers/platform/x86/intel-hid.c
|
|
index e34fd70b67afe..3add7b3f9658b 100644
|
|
--- a/drivers/platform/x86/intel-hid.c
|
|
+++ b/drivers/platform/x86/intel-hid.c
|
|
@@ -366,7 +366,7 @@ check_acpi_dev(acpi_handle handle, u32 lvl, void *context, void **rv)
|
|
return AE_OK;
|
|
|
|
if (acpi_match_device_ids(dev, ids) == 0)
|
|
- if (acpi_create_platform_device(dev, NULL))
|
|
+ if (!IS_ERR_OR_NULL(acpi_create_platform_device(dev, NULL)))
|
|
dev_info(&dev->dev,
|
|
"intel-hid: created platform device\n");
|
|
|
|
diff --git a/drivers/platform/x86/intel-vbtn.c b/drivers/platform/x86/intel-vbtn.c
|
|
index 58c5ff36523ab..d7fa2b88d27ab 100644
|
|
--- a/drivers/platform/x86/intel-vbtn.c
|
|
+++ b/drivers/platform/x86/intel-vbtn.c
|
|
@@ -178,7 +178,7 @@ check_acpi_dev(acpi_handle handle, u32 lvl, void *context, void **rv)
|
|
return AE_OK;
|
|
|
|
if (acpi_match_device_ids(dev, ids) == 0)
|
|
- if (acpi_create_platform_device(dev, NULL))
|
|
+ if (!IS_ERR_OR_NULL(acpi_create_platform_device(dev, NULL)))
|
|
dev_info(&dev->dev,
|
|
"intel-vbtn: created platform device\n");
|
|
|
|
diff --git a/drivers/power/supply/88pm860x_battery.c b/drivers/power/supply/88pm860x_battery.c
|
|
index 63c57dc82ac1d..4eda5065b5bbc 100644
|
|
--- a/drivers/power/supply/88pm860x_battery.c
|
|
+++ b/drivers/power/supply/88pm860x_battery.c
|
|
@@ -436,7 +436,7 @@ static void pm860x_init_battery(struct pm860x_battery_info *info)
|
|
int ret;
|
|
int data;
|
|
int bat_remove;
|
|
- int soc;
|
|
+ int soc = 0;
|
|
|
|
/* measure enable on GPADC1 */
|
|
data = MEAS1_GP1;
|
|
@@ -499,7 +499,9 @@ static void pm860x_init_battery(struct pm860x_battery_info *info)
|
|
}
|
|
mutex_unlock(&info->lock);
|
|
|
|
- calc_soc(info, OCV_MODE_ACTIVE, &soc);
|
|
+ ret = calc_soc(info, OCV_MODE_ACTIVE, &soc);
|
|
+ if (ret < 0)
|
|
+ goto out;
|
|
|
|
data = pm860x_reg_read(info->i2c, PM8607_POWER_UP_LOG);
|
|
bat_remove = data & BAT_WU_LOG;
|
|
diff --git a/drivers/pwm/pwm-bcm-iproc.c b/drivers/pwm/pwm-bcm-iproc.c
|
|
index 31b01035d0ab3..8cfba3614e601 100644
|
|
--- a/drivers/pwm/pwm-bcm-iproc.c
|
|
+++ b/drivers/pwm/pwm-bcm-iproc.c
|
|
@@ -85,8 +85,6 @@ static void iproc_pwmc_get_state(struct pwm_chip *chip, struct pwm_device *pwm,
|
|
u64 tmp, multi, rate;
|
|
u32 value, prescale;
|
|
|
|
- rate = clk_get_rate(ip->clk);
|
|
-
|
|
value = readl(ip->base + IPROC_PWM_CTRL_OFFSET);
|
|
|
|
if (value & BIT(IPROC_PWM_CTRL_EN_SHIFT(pwm->hwpwm)))
|
|
@@ -99,6 +97,13 @@ static void iproc_pwmc_get_state(struct pwm_chip *chip, struct pwm_device *pwm,
|
|
else
|
|
state->polarity = PWM_POLARITY_INVERSED;
|
|
|
|
+ rate = clk_get_rate(ip->clk);
|
|
+ if (rate == 0) {
|
|
+ state->period = 0;
|
|
+ state->duty_cycle = 0;
|
|
+ return;
|
|
+ }
|
|
+
|
|
value = readl(ip->base + IPROC_PWM_PRESCALE_OFFSET);
|
|
prescale = value >> IPROC_PWM_PRESCALE_SHIFT(pwm->hwpwm);
|
|
prescale &= IPROC_PWM_PRESCALE_MAX;
|
|
diff --git a/drivers/s390/net/qeth_l2_main.c b/drivers/s390/net/qeth_l2_main.c
|
|
index 6fa07c2469150..ae310d5ced105 100644
|
|
--- a/drivers/s390/net/qeth_l2_main.c
|
|
+++ b/drivers/s390/net/qeth_l2_main.c
|
|
@@ -1559,6 +1559,10 @@ static void qeth_bridge_state_change(struct qeth_card *card,
|
|
int extrasize;
|
|
|
|
QETH_CARD_TEXT(card, 2, "brstchng");
|
|
+ if (qports->num_entries == 0) {
|
|
+ QETH_CARD_TEXT(card, 2, "BPempty");
|
|
+ return;
|
|
+ }
|
|
if (qports->entry_length != sizeof(struct qeth_sbp_port_entry)) {
|
|
QETH_CARD_TEXT_(card, 2, "BPsz%04x", qports->entry_length);
|
|
return;
|
|
diff --git a/drivers/scsi/arm/cumana_2.c b/drivers/scsi/arm/cumana_2.c
|
|
index edce5f3cfdba0..93ba83e3148eb 100644
|
|
--- a/drivers/scsi/arm/cumana_2.c
|
|
+++ b/drivers/scsi/arm/cumana_2.c
|
|
@@ -454,7 +454,7 @@ static int cumanascsi2_probe(struct expansion_card *ec,
|
|
|
|
if (info->info.scsi.dma != NO_DMA)
|
|
free_dma(info->info.scsi.dma);
|
|
- free_irq(ec->irq, host);
|
|
+ free_irq(ec->irq, info);
|
|
|
|
out_release:
|
|
fas216_release(host);
|
|
diff --git a/drivers/scsi/arm/eesox.c b/drivers/scsi/arm/eesox.c
|
|
index e93e047f43165..65bb34ce93b94 100644
|
|
--- a/drivers/scsi/arm/eesox.c
|
|
+++ b/drivers/scsi/arm/eesox.c
|
|
@@ -575,7 +575,7 @@ static int eesoxscsi_probe(struct expansion_card *ec, const struct ecard_id *id)
|
|
|
|
if (info->info.scsi.dma != NO_DMA)
|
|
free_dma(info->info.scsi.dma);
|
|
- free_irq(ec->irq, host);
|
|
+ free_irq(ec->irq, info);
|
|
|
|
out_remove:
|
|
fas216_remove(host);
|
|
diff --git a/drivers/scsi/arm/powertec.c b/drivers/scsi/arm/powertec.c
|
|
index 79aa88911b7f3..b5e4a25ea1ef3 100644
|
|
--- a/drivers/scsi/arm/powertec.c
|
|
+++ b/drivers/scsi/arm/powertec.c
|
|
@@ -382,7 +382,7 @@ static int powertecscsi_probe(struct expansion_card *ec,
|
|
|
|
if (info->info.scsi.dma != NO_DMA)
|
|
free_dma(info->info.scsi.dma);
|
|
- free_irq(ec->irq, host);
|
|
+ free_irq(ec->irq, info);
|
|
|
|
out_release:
|
|
fas216_release(host);
|
|
diff --git a/drivers/scsi/mesh.c b/drivers/scsi/mesh.c
|
|
index 1753e42826dd9..a880abf5abaad 100644
|
|
--- a/drivers/scsi/mesh.c
|
|
+++ b/drivers/scsi/mesh.c
|
|
@@ -1044,6 +1044,8 @@ static void handle_error(struct mesh_state *ms)
|
|
while ((in_8(&mr->bus_status1) & BS1_RST) != 0)
|
|
udelay(1);
|
|
printk("done\n");
|
|
+ if (ms->dma_started)
|
|
+ halt_dma(ms);
|
|
handle_reset(ms);
|
|
/* request_q is empty, no point in mesh_start() */
|
|
return;
|
|
@@ -1356,7 +1358,8 @@ static void halt_dma(struct mesh_state *ms)
|
|
ms->conn_tgt, ms->data_ptr, scsi_bufflen(cmd),
|
|
ms->tgts[ms->conn_tgt].data_goes_out);
|
|
}
|
|
- scsi_dma_unmap(cmd);
|
|
+ if (cmd)
|
|
+ scsi_dma_unmap(cmd);
|
|
ms->dma_started = 0;
|
|
}
|
|
|
|
@@ -1711,6 +1714,9 @@ static int mesh_host_reset(struct scsi_cmnd *cmd)
|
|
|
|
spin_lock_irqsave(ms->host->host_lock, flags);
|
|
|
|
+ if (ms->dma_started)
|
|
+ halt_dma(ms);
|
|
+
|
|
/* Reset the controller & dbdma channel */
|
|
out_le32(&md->control, (RUN|PAUSE|FLUSH|WAKE) << 16); /* stop dma */
|
|
out_8(&mr->exception, 0xff); /* clear all exception bits */
|
|
diff --git a/drivers/scsi/scsi_debug.c b/drivers/scsi/scsi_debug.c
|
|
index ac936b5ca74e5..aba1a3396890b 100644
|
|
--- a/drivers/scsi/scsi_debug.c
|
|
+++ b/drivers/scsi/scsi_debug.c
|
|
@@ -4993,6 +4993,12 @@ static int __init scsi_debug_init(void)
|
|
pr_err("submit_queues must be 1 or more\n");
|
|
return -EINVAL;
|
|
}
|
|
+
|
|
+ if ((sdebug_max_queue > SDEBUG_CANQUEUE) || (sdebug_max_queue < 1)) {
|
|
+ pr_err("max_queue must be in range [1, %d]\n", SDEBUG_CANQUEUE);
|
|
+ return -EINVAL;
|
|
+ }
|
|
+
|
|
sdebug_q_arr = kcalloc(submit_queues, sizeof(struct sdebug_queue),
|
|
GFP_KERNEL);
|
|
if (sdebug_q_arr == NULL)
|
|
diff --git a/drivers/spi/spi-lantiq-ssc.c b/drivers/spi/spi-lantiq-ssc.c
|
|
index d5976615d924b..dc740b5f720ba 100644
|
|
--- a/drivers/spi/spi-lantiq-ssc.c
|
|
+++ b/drivers/spi/spi-lantiq-ssc.c
|
|
@@ -187,6 +187,7 @@ struct lantiq_ssc_spi {
|
|
unsigned int tx_fifo_size;
|
|
unsigned int rx_fifo_size;
|
|
unsigned int base_cs;
|
|
+ unsigned int fdx_tx_level;
|
|
};
|
|
|
|
static u32 lantiq_ssc_readl(const struct lantiq_ssc_spi *spi, u32 reg)
|
|
@@ -484,6 +485,7 @@ static void tx_fifo_write(struct lantiq_ssc_spi *spi)
|
|
u32 data;
|
|
unsigned int tx_free = tx_fifo_free(spi);
|
|
|
|
+ spi->fdx_tx_level = 0;
|
|
while (spi->tx_todo && tx_free) {
|
|
switch (spi->bits_per_word) {
|
|
case 2 ... 8:
|
|
@@ -512,6 +514,7 @@ static void tx_fifo_write(struct lantiq_ssc_spi *spi)
|
|
|
|
lantiq_ssc_writel(spi, data, LTQ_SPI_TB);
|
|
tx_free--;
|
|
+ spi->fdx_tx_level++;
|
|
}
|
|
}
|
|
|
|
@@ -523,6 +526,13 @@ static void rx_fifo_read_full_duplex(struct lantiq_ssc_spi *spi)
|
|
u32 data;
|
|
unsigned int rx_fill = rx_fifo_level(spi);
|
|
|
|
+ /*
|
|
+ * Wait until all expected data to be shifted in.
|
|
+ * Otherwise, rx overrun may occur.
|
|
+ */
|
|
+ while (rx_fill != spi->fdx_tx_level)
|
|
+ rx_fill = rx_fifo_level(spi);
|
|
+
|
|
while (rx_fill) {
|
|
data = lantiq_ssc_readl(spi, LTQ_SPI_RB);
|
|
|
|
diff --git a/drivers/spi/spidev.c b/drivers/spi/spidev.c
|
|
index 167047760d79a..e444e7cc6968d 100644
|
|
--- a/drivers/spi/spidev.c
|
|
+++ b/drivers/spi/spidev.c
|
|
@@ -232,6 +232,11 @@ static int spidev_message(struct spidev_data *spidev,
|
|
for (n = n_xfers, k_tmp = k_xfers, u_tmp = u_xfers;
|
|
n;
|
|
n--, k_tmp++, u_tmp++) {
|
|
+ /* Ensure that also following allocations from rx_buf/tx_buf will meet
|
|
+ * DMA alignment requirements.
|
|
+ */
|
|
+ unsigned int len_aligned = ALIGN(u_tmp->len, ARCH_KMALLOC_MINALIGN);
|
|
+
|
|
k_tmp->len = u_tmp->len;
|
|
|
|
total += k_tmp->len;
|
|
@@ -247,17 +252,17 @@ static int spidev_message(struct spidev_data *spidev,
|
|
|
|
if (u_tmp->rx_buf) {
|
|
/* this transfer needs space in RX bounce buffer */
|
|
- rx_total += k_tmp->len;
|
|
+ rx_total += len_aligned;
|
|
if (rx_total > bufsiz) {
|
|
status = -EMSGSIZE;
|
|
goto done;
|
|
}
|
|
k_tmp->rx_buf = rx_buf;
|
|
- rx_buf += k_tmp->len;
|
|
+ rx_buf += len_aligned;
|
|
}
|
|
if (u_tmp->tx_buf) {
|
|
/* this transfer needs space in TX bounce buffer */
|
|
- tx_total += k_tmp->len;
|
|
+ tx_total += len_aligned;
|
|
if (tx_total > bufsiz) {
|
|
status = -EMSGSIZE;
|
|
goto done;
|
|
@@ -267,7 +272,7 @@ static int spidev_message(struct spidev_data *spidev,
|
|
(uintptr_t) u_tmp->tx_buf,
|
|
u_tmp->len))
|
|
goto done;
|
|
- tx_buf += k_tmp->len;
|
|
+ tx_buf += len_aligned;
|
|
}
|
|
|
|
k_tmp->cs_change = !!u_tmp->cs_change;
|
|
@@ -297,16 +302,16 @@ static int spidev_message(struct spidev_data *spidev,
|
|
goto done;
|
|
|
|
/* copy any rx data out of bounce buffer */
|
|
- rx_buf = spidev->rx_buffer;
|
|
- for (n = n_xfers, u_tmp = u_xfers; n; n--, u_tmp++) {
|
|
+ for (n = n_xfers, k_tmp = k_xfers, u_tmp = u_xfers;
|
|
+ n;
|
|
+ n--, k_tmp++, u_tmp++) {
|
|
if (u_tmp->rx_buf) {
|
|
if (copy_to_user((u8 __user *)
|
|
- (uintptr_t) u_tmp->rx_buf, rx_buf,
|
|
+ (uintptr_t) u_tmp->rx_buf, k_tmp->rx_buf,
|
|
u_tmp->len)) {
|
|
status = -EFAULT;
|
|
goto done;
|
|
}
|
|
- rx_buf += u_tmp->len;
|
|
}
|
|
}
|
|
status = total;
|
|
diff --git a/drivers/staging/android/ashmem.c b/drivers/staging/android/ashmem.c
|
|
index 9481c0b233860..22cae548df49f 100644
|
|
--- a/drivers/staging/android/ashmem.c
|
|
+++ b/drivers/staging/android/ashmem.c
|
|
@@ -100,6 +100,15 @@ static DEFINE_MUTEX(ashmem_mutex);
|
|
static struct kmem_cache *ashmem_area_cachep __read_mostly;
|
|
static struct kmem_cache *ashmem_range_cachep __read_mostly;
|
|
|
|
+/*
|
|
+ * A separate lockdep class for the backing shmem inodes to resolve the lockdep
|
|
+ * warning about the race between kswapd taking fs_reclaim before inode_lock
|
|
+ * and write syscall taking inode_lock and then fs_reclaim.
|
|
+ * Note that such race is impossible because ashmem does not support write
|
|
+ * syscalls operating on the backing shmem.
|
|
+ */
|
|
+static struct lock_class_key backing_shmem_inode_class;
|
|
+
|
|
static inline unsigned long range_size(struct ashmem_range *range)
|
|
{
|
|
return range->pgend - range->pgstart + 1;
|
|
@@ -406,6 +415,7 @@ static int ashmem_mmap(struct file *file, struct vm_area_struct *vma)
|
|
if (!asma->file) {
|
|
char *name = ASHMEM_NAME_DEF;
|
|
struct file *vmfile;
|
|
+ struct inode *inode;
|
|
|
|
if (asma->name[ASHMEM_NAME_PREFIX_LEN] != '\0')
|
|
name = asma->name;
|
|
@@ -417,6 +427,8 @@ static int ashmem_mmap(struct file *file, struct vm_area_struct *vma)
|
|
goto out;
|
|
}
|
|
vmfile->f_mode |= FMODE_LSEEK;
|
|
+ inode = file_inode(vmfile);
|
|
+ lockdep_set_class(&inode->i_rwsem, &backing_shmem_inode_class);
|
|
asma->file = vmfile;
|
|
/*
|
|
* override mmap operation of the vmfile so that it can't be
|
|
diff --git a/drivers/staging/rtl8192u/r8192U_core.c b/drivers/staging/rtl8192u/r8192U_core.c
|
|
index fbbd1b59dc11d..b5941ae410d9a 100644
|
|
--- a/drivers/staging/rtl8192u/r8192U_core.c
|
|
+++ b/drivers/staging/rtl8192u/r8192U_core.c
|
|
@@ -2519,7 +2519,7 @@ static int rtl8192_read_eeprom_info(struct net_device *dev)
|
|
ret = eprom_read(dev, (EEPROM_TxPwIndex_CCK >> 1));
|
|
if (ret < 0)
|
|
return ret;
|
|
- priv->EEPROMTxPowerLevelCCK = ((u16)ret & 0xff) >> 8;
|
|
+ priv->EEPROMTxPowerLevelCCK = ((u16)ret & 0xff00) >> 8;
|
|
} else
|
|
priv->EEPROMTxPowerLevelCCK = 0x10;
|
|
RT_TRACE(COMP_EPROM, "CCK Tx Power Levl: 0x%02x\n", priv->EEPROMTxPowerLevelCCK);
|
|
diff --git a/drivers/thermal/ti-soc-thermal/ti-thermal-common.c b/drivers/thermal/ti-soc-thermal/ti-thermal-common.c
|
|
index fa98c398d70f3..d43fbe4ad767e 100644
|
|
--- a/drivers/thermal/ti-soc-thermal/ti-thermal-common.c
|
|
+++ b/drivers/thermal/ti-soc-thermal/ti-thermal-common.c
|
|
@@ -183,7 +183,7 @@ int ti_thermal_expose_sensor(struct ti_bandgap *bgp, int id,
|
|
|
|
data = ti_bandgap_get_sensor_data(bgp, id);
|
|
|
|
- if (!IS_ERR_OR_NULL(data))
|
|
+ if (IS_ERR_OR_NULL(data))
|
|
data = ti_thermal_build_data(bgp, id);
|
|
|
|
if (!data)
|
|
diff --git a/drivers/usb/dwc2/platform.c b/drivers/usb/dwc2/platform.c
|
|
index 442cb93935dd4..405dccf92a315 100644
|
|
--- a/drivers/usb/dwc2/platform.c
|
|
+++ b/drivers/usb/dwc2/platform.c
|
|
@@ -459,6 +459,7 @@ static int dwc2_driver_probe(struct platform_device *dev)
|
|
if (hsotg->gadget_enabled) {
|
|
retval = usb_add_gadget_udc(hsotg->dev, &hsotg->gadget);
|
|
if (retval) {
|
|
+ hsotg->gadget.udc = NULL;
|
|
dwc2_hsotg_remove(hsotg);
|
|
goto error;
|
|
}
|
|
@@ -467,7 +468,8 @@ static int dwc2_driver_probe(struct platform_device *dev)
|
|
return 0;
|
|
|
|
error:
|
|
- dwc2_lowlevel_hw_disable(hsotg);
|
|
+ if (hsotg->dr_mode != USB_DR_MODE_PERIPHERAL)
|
|
+ dwc2_lowlevel_hw_disable(hsotg);
|
|
return retval;
|
|
}
|
|
|
|
diff --git a/drivers/usb/gadget/udc/bdc/bdc_core.c b/drivers/usb/gadget/udc/bdc/bdc_core.c
|
|
index 7a8af4b916cff..58ba04d858bab 100644
|
|
--- a/drivers/usb/gadget/udc/bdc/bdc_core.c
|
|
+++ b/drivers/usb/gadget/udc/bdc/bdc_core.c
|
|
@@ -288,6 +288,7 @@ static void bdc_mem_init(struct bdc *bdc, bool reinit)
|
|
* in that case reinit is passed as 1
|
|
*/
|
|
if (reinit) {
|
|
+ int i;
|
|
/* Enable interrupts */
|
|
temp = bdc_readl(bdc->regs, BDC_BDCSC);
|
|
temp |= BDC_GIE;
|
|
@@ -297,6 +298,9 @@ static void bdc_mem_init(struct bdc *bdc, bool reinit)
|
|
/* Initialize SRR to 0 */
|
|
memset(bdc->srr.sr_bds, 0,
|
|
NUM_SR_ENTRIES * sizeof(struct bdc_bd));
|
|
+ /* clear ep flags to avoid post disconnect stops/deconfigs */
|
|
+ for (i = 1; i < bdc->num_eps; ++i)
|
|
+ bdc->bdc_ep_array[i]->flags = 0;
|
|
} else {
|
|
/* One time initiaization only */
|
|
/* Enable status report function pointers */
|
|
@@ -609,9 +613,14 @@ static int bdc_remove(struct platform_device *pdev)
|
|
static int bdc_suspend(struct device *dev)
|
|
{
|
|
struct bdc *bdc = dev_get_drvdata(dev);
|
|
+ int ret;
|
|
|
|
- clk_disable_unprepare(bdc->clk);
|
|
- return 0;
|
|
+ /* Halt the controller */
|
|
+ ret = bdc_stop(bdc);
|
|
+ if (!ret)
|
|
+ clk_disable_unprepare(bdc->clk);
|
|
+
|
|
+ return ret;
|
|
}
|
|
|
|
static int bdc_resume(struct device *dev)
|
|
diff --git a/drivers/usb/gadget/udc/bdc/bdc_ep.c b/drivers/usb/gadget/udc/bdc/bdc_ep.c
|
|
index be9f40bc9c12b..bb2d5ebd97b52 100644
|
|
--- a/drivers/usb/gadget/udc/bdc/bdc_ep.c
|
|
+++ b/drivers/usb/gadget/udc/bdc/bdc_ep.c
|
|
@@ -621,7 +621,6 @@ int bdc_ep_enable(struct bdc_ep *ep)
|
|
}
|
|
bdc_dbg_bd_list(bdc, ep);
|
|
/* only for ep0: config ep is called for ep0 from connect event */
|
|
- ep->flags |= BDC_EP_ENABLED;
|
|
if (ep->ep_num == 1)
|
|
return ret;
|
|
|
|
@@ -765,10 +764,13 @@ static int ep_dequeue(struct bdc_ep *ep, struct bdc_req *req)
|
|
__func__, ep->name, start_bdi, end_bdi);
|
|
dev_dbg(bdc->dev, "ep_dequeue ep=%p ep->desc=%p\n",
|
|
ep, (void *)ep->usb_ep.desc);
|
|
- /* Stop the ep to see where the HW is ? */
|
|
- ret = bdc_stop_ep(bdc, ep->ep_num);
|
|
- /* if there is an issue with stopping ep, then no need to go further */
|
|
- if (ret)
|
|
+ /* if still connected, stop the ep to see where the HW is ? */
|
|
+ if (!(bdc_readl(bdc->regs, BDC_USPC) & BDC_PST_MASK)) {
|
|
+ ret = bdc_stop_ep(bdc, ep->ep_num);
|
|
+ /* if there is an issue, then no need to go further */
|
|
+ if (ret)
|
|
+ return 0;
|
|
+ } else
|
|
return 0;
|
|
|
|
/*
|
|
@@ -1917,7 +1919,9 @@ static int bdc_gadget_ep_disable(struct usb_ep *_ep)
|
|
__func__, ep->name, ep->flags);
|
|
|
|
if (!(ep->flags & BDC_EP_ENABLED)) {
|
|
- dev_warn(bdc->dev, "%s is already disabled\n", ep->name);
|
|
+ if (bdc->gadget.speed != USB_SPEED_UNKNOWN)
|
|
+ dev_warn(bdc->dev, "%s is already disabled\n",
|
|
+ ep->name);
|
|
return 0;
|
|
}
|
|
spin_lock_irqsave(&bdc->lock, flags);
|
|
diff --git a/drivers/usb/gadget/udc/net2280.c b/drivers/usb/gadget/udc/net2280.c
|
|
index 170327f84ea19..f1ac9a49e2bf1 100644
|
|
--- a/drivers/usb/gadget/udc/net2280.c
|
|
+++ b/drivers/usb/gadget/udc/net2280.c
|
|
@@ -3786,8 +3786,10 @@ static int net2280_probe(struct pci_dev *pdev, const struct pci_device_id *id)
|
|
return 0;
|
|
|
|
done:
|
|
- if (dev)
|
|
+ if (dev) {
|
|
net2280_remove(pdev);
|
|
+ kfree(dev);
|
|
+ }
|
|
return retval;
|
|
}
|
|
|
|
diff --git a/drivers/usb/host/xhci-pci.c b/drivers/usb/host/xhci-pci.c
|
|
index d4e29039305b8..72c3ba0824f70 100644
|
|
--- a/drivers/usb/host/xhci-pci.c
|
|
+++ b/drivers/usb/host/xhci-pci.c
|
|
@@ -59,7 +59,10 @@
|
|
#define PCI_DEVICE_ID_AMD_PROMONTORYA_3 0x43ba
|
|
#define PCI_DEVICE_ID_AMD_PROMONTORYA_2 0x43bb
|
|
#define PCI_DEVICE_ID_AMD_PROMONTORYA_1 0x43bc
|
|
+#define PCI_DEVICE_ID_ASMEDIA_1042_XHCI 0x1042
|
|
#define PCI_DEVICE_ID_ASMEDIA_1042A_XHCI 0x1142
|
|
+#define PCI_DEVICE_ID_ASMEDIA_1142_XHCI 0x1242
|
|
+#define PCI_DEVICE_ID_ASMEDIA_2142_XHCI 0x2142
|
|
|
|
static const char hcd_name[] = "xhci_hcd";
|
|
|
|
@@ -230,13 +233,14 @@ static void xhci_pci_quirks(struct device *dev, struct xhci_hcd *xhci)
|
|
xhci->quirks |= XHCI_BROKEN_STREAMS;
|
|
|
|
if (pdev->vendor == PCI_VENDOR_ID_ASMEDIA &&
|
|
- pdev->device == 0x1042)
|
|
+ pdev->device == PCI_DEVICE_ID_ASMEDIA_1042_XHCI)
|
|
xhci->quirks |= XHCI_BROKEN_STREAMS;
|
|
if (pdev->vendor == PCI_VENDOR_ID_ASMEDIA &&
|
|
- pdev->device == 0x1142)
|
|
+ pdev->device == PCI_DEVICE_ID_ASMEDIA_1042A_XHCI)
|
|
xhci->quirks |= XHCI_TRUST_TX_LENGTH;
|
|
if (pdev->vendor == PCI_VENDOR_ID_ASMEDIA &&
|
|
- pdev->device == 0x2142)
|
|
+ (pdev->device == PCI_DEVICE_ID_ASMEDIA_1142_XHCI ||
|
|
+ pdev->device == PCI_DEVICE_ID_ASMEDIA_2142_XHCI))
|
|
xhci->quirks |= XHCI_NO_64BIT_SUPPORT;
|
|
|
|
if (pdev->vendor == PCI_VENDOR_ID_ASMEDIA &&
|
|
diff --git a/drivers/usb/misc/iowarrior.c b/drivers/usb/misc/iowarrior.c
|
|
index 1ec32e5aa004c..27e1ab9e1b079 100644
|
|
--- a/drivers/usb/misc/iowarrior.c
|
|
+++ b/drivers/usb/misc/iowarrior.c
|
|
@@ -1,8 +1,9 @@
|
|
/*
|
|
* Native support for the I/O-Warrior USB devices
|
|
*
|
|
- * Copyright (c) 2003-2005 Code Mercenaries GmbH
|
|
- * written by Christian Lucht <lucht@codemercs.com>
|
|
+ * Copyright (c) 2003-2005, 2020 Code Mercenaries GmbH
|
|
+ * written by Christian Lucht <lucht@codemercs.com> and
|
|
+ * Christoph Jung <jung@codemercs.com>
|
|
*
|
|
* based on
|
|
|
|
@@ -821,14 +822,28 @@ static int iowarrior_probe(struct usb_interface *interface,
|
|
|
|
/* we have to check the report_size often, so remember it in the endianness suitable for our machine */
|
|
dev->report_size = usb_endpoint_maxp(dev->int_in_endpoint);
|
|
- if ((dev->interface->cur_altsetting->desc.bInterfaceNumber == 0) &&
|
|
- ((dev->product_id == USB_DEVICE_ID_CODEMERCS_IOW56) ||
|
|
- (dev->product_id == USB_DEVICE_ID_CODEMERCS_IOW56AM) ||
|
|
- (dev->product_id == USB_DEVICE_ID_CODEMERCS_IOW28) ||
|
|
- (dev->product_id == USB_DEVICE_ID_CODEMERCS_IOW28L) ||
|
|
- (dev->product_id == USB_DEVICE_ID_CODEMERCS_IOW100)))
|
|
- /* IOWarrior56 has wMaxPacketSize different from report size */
|
|
- dev->report_size = 7;
|
|
+
|
|
+ /*
|
|
+ * Some devices need the report size to be different than the
|
|
+ * endpoint size.
|
|
+ */
|
|
+ if (dev->interface->cur_altsetting->desc.bInterfaceNumber == 0) {
|
|
+ switch (dev->product_id) {
|
|
+ case USB_DEVICE_ID_CODEMERCS_IOW56:
|
|
+ case USB_DEVICE_ID_CODEMERCS_IOW56AM:
|
|
+ dev->report_size = 7;
|
|
+ break;
|
|
+
|
|
+ case USB_DEVICE_ID_CODEMERCS_IOW28:
|
|
+ case USB_DEVICE_ID_CODEMERCS_IOW28L:
|
|
+ dev->report_size = 4;
|
|
+ break;
|
|
+
|
|
+ case USB_DEVICE_ID_CODEMERCS_IOW100:
|
|
+ dev->report_size = 13;
|
|
+ break;
|
|
+ }
|
|
+ }
|
|
|
|
/* create the urb and buffer for reading */
|
|
dev->int_in_urb = usb_alloc_urb(0, GFP_KERNEL);
|
|
diff --git a/drivers/usb/serial/cp210x.c b/drivers/usb/serial/cp210x.c
|
|
index 8dd9852f399db..630c8338d7912 100644
|
|
--- a/drivers/usb/serial/cp210x.c
|
|
+++ b/drivers/usb/serial/cp210x.c
|
|
@@ -271,6 +271,8 @@ static struct usb_serial_driver cp210x_device = {
|
|
.break_ctl = cp210x_break_ctl,
|
|
.set_termios = cp210x_set_termios,
|
|
.tx_empty = cp210x_tx_empty,
|
|
+ .throttle = usb_serial_generic_throttle,
|
|
+ .unthrottle = usb_serial_generic_unthrottle,
|
|
.tiocmget = cp210x_tiocmget,
|
|
.tiocmset = cp210x_tiocmset,
|
|
.attach = cp210x_attach,
|
|
@@ -925,6 +927,7 @@ static void cp210x_get_termios_port(struct usb_serial_port *port,
|
|
u32 baud;
|
|
u16 bits;
|
|
u32 ctl_hs;
|
|
+ u32 flow_repl;
|
|
|
|
cp210x_read_u32_reg(port, CP210X_GET_BAUDRATE, &baud);
|
|
|
|
@@ -1025,6 +1028,22 @@ static void cp210x_get_termios_port(struct usb_serial_port *port,
|
|
ctl_hs = le32_to_cpu(flow_ctl.ulControlHandshake);
|
|
if (ctl_hs & CP210X_SERIAL_CTS_HANDSHAKE) {
|
|
dev_dbg(dev, "%s - flow control = CRTSCTS\n", __func__);
|
|
+ /*
|
|
+ * When the port is closed, the CP210x hardware disables
|
|
+ * auto-RTS and RTS is deasserted but it leaves auto-CTS when
|
|
+ * in hardware flow control mode. When re-opening the port, if
|
|
+ * auto-CTS is enabled on the cp210x, then auto-RTS must be
|
|
+ * re-enabled in the driver.
|
|
+ */
|
|
+ flow_repl = le32_to_cpu(flow_ctl.ulFlowReplace);
|
|
+ flow_repl &= ~CP210X_SERIAL_RTS_MASK;
|
|
+ flow_repl |= CP210X_SERIAL_RTS_SHIFT(CP210X_SERIAL_RTS_FLOW_CTL);
|
|
+ flow_ctl.ulFlowReplace = cpu_to_le32(flow_repl);
|
|
+ cp210x_write_reg_block(port,
|
|
+ CP210X_SET_FLOW,
|
|
+ &flow_ctl,
|
|
+ sizeof(flow_ctl));
|
|
+
|
|
cflag |= CRTSCTS;
|
|
} else {
|
|
dev_dbg(dev, "%s - flow control = NONE\n", __func__);
|
|
diff --git a/drivers/usb/serial/ftdi_sio.c b/drivers/usb/serial/ftdi_sio.c
|
|
index a962065227c48..8abb30c797d30 100644
|
|
--- a/drivers/usb/serial/ftdi_sio.c
|
|
+++ b/drivers/usb/serial/ftdi_sio.c
|
|
@@ -2042,12 +2042,11 @@ static int ftdi_prepare_write_buffer(struct usb_serial_port *port,
|
|
#define FTDI_RS_ERR_MASK (FTDI_RS_BI | FTDI_RS_PE | FTDI_RS_FE | FTDI_RS_OE)
|
|
|
|
static int ftdi_process_packet(struct usb_serial_port *port,
|
|
- struct ftdi_private *priv, char *packet, int len)
|
|
+ struct ftdi_private *priv, unsigned char *buf, int len)
|
|
{
|
|
+ unsigned char status;
|
|
int i;
|
|
- char status;
|
|
char flag;
|
|
- char *ch;
|
|
|
|
if (len < 2) {
|
|
dev_dbg(&port->dev, "malformed packet\n");
|
|
@@ -2057,7 +2056,7 @@ static int ftdi_process_packet(struct usb_serial_port *port,
|
|
/* Compare new line status to the old one, signal if different/
|
|
N.B. packet may be processed more than once, but differences
|
|
are only processed once. */
|
|
- status = packet[0] & FTDI_STATUS_B0_MASK;
|
|
+ status = buf[0] & FTDI_STATUS_B0_MASK;
|
|
if (status != priv->prev_status) {
|
|
char diff_status = status ^ priv->prev_status;
|
|
|
|
@@ -2083,13 +2082,12 @@ static int ftdi_process_packet(struct usb_serial_port *port,
|
|
}
|
|
|
|
/* save if the transmitter is empty or not */
|
|
- if (packet[1] & FTDI_RS_TEMT)
|
|
+ if (buf[1] & FTDI_RS_TEMT)
|
|
priv->transmit_empty = 1;
|
|
else
|
|
priv->transmit_empty = 0;
|
|
|
|
- len -= 2;
|
|
- if (!len)
|
|
+ if (len == 2)
|
|
return 0; /* status only */
|
|
|
|
/*
|
|
@@ -2097,40 +2095,41 @@ static int ftdi_process_packet(struct usb_serial_port *port,
|
|
* data payload to avoid over-reporting.
|
|
*/
|
|
flag = TTY_NORMAL;
|
|
- if (packet[1] & FTDI_RS_ERR_MASK) {
|
|
+ if (buf[1] & FTDI_RS_ERR_MASK) {
|
|
/* Break takes precedence over parity, which takes precedence
|
|
* over framing errors */
|
|
- if (packet[1] & FTDI_RS_BI) {
|
|
+ if (buf[1] & FTDI_RS_BI) {
|
|
flag = TTY_BREAK;
|
|
port->icount.brk++;
|
|
usb_serial_handle_break(port);
|
|
- } else if (packet[1] & FTDI_RS_PE) {
|
|
+ } else if (buf[1] & FTDI_RS_PE) {
|
|
flag = TTY_PARITY;
|
|
port->icount.parity++;
|
|
- } else if (packet[1] & FTDI_RS_FE) {
|
|
+ } else if (buf[1] & FTDI_RS_FE) {
|
|
flag = TTY_FRAME;
|
|
port->icount.frame++;
|
|
}
|
|
/* Overrun is special, not associated with a char */
|
|
- if (packet[1] & FTDI_RS_OE) {
|
|
+ if (buf[1] & FTDI_RS_OE) {
|
|
port->icount.overrun++;
|
|
tty_insert_flip_char(&port->port, 0, TTY_OVERRUN);
|
|
}
|
|
}
|
|
|
|
- port->icount.rx += len;
|
|
- ch = packet + 2;
|
|
+ port->icount.rx += len - 2;
|
|
|
|
if (port->port.console && port->sysrq) {
|
|
- for (i = 0; i < len; i++, ch++) {
|
|
- if (!usb_serial_handle_sysrq_char(port, *ch))
|
|
- tty_insert_flip_char(&port->port, *ch, flag);
|
|
+ for (i = 2; i < len; i++) {
|
|
+ if (usb_serial_handle_sysrq_char(port, buf[i]))
|
|
+ continue;
|
|
+ tty_insert_flip_char(&port->port, buf[i], flag);
|
|
}
|
|
} else {
|
|
- tty_insert_flip_string_fixed_flag(&port->port, ch, flag, len);
|
|
+ tty_insert_flip_string_fixed_flag(&port->port, buf + 2, flag,
|
|
+ len - 2);
|
|
}
|
|
|
|
- return len;
|
|
+ return len - 2;
|
|
}
|
|
|
|
static void ftdi_process_read_urb(struct urb *urb)
|
|
diff --git a/drivers/usb/serial/iuu_phoenix.c b/drivers/usb/serial/iuu_phoenix.c
|
|
index a1a11f8bb2a3d..0c9e24b217f7d 100644
|
|
--- a/drivers/usb/serial/iuu_phoenix.c
|
|
+++ b/drivers/usb/serial/iuu_phoenix.c
|
|
@@ -359,10 +359,11 @@ static void iuu_led_activity_on(struct urb *urb)
|
|
struct usb_serial_port *port = urb->context;
|
|
int result;
|
|
char *buf_ptr = port->write_urb->transfer_buffer;
|
|
- *buf_ptr++ = IUU_SET_LED;
|
|
+
|
|
if (xmas) {
|
|
- get_random_bytes(buf_ptr, 6);
|
|
- *(buf_ptr+7) = 1;
|
|
+ buf_ptr[0] = IUU_SET_LED;
|
|
+ get_random_bytes(buf_ptr + 1, 6);
|
|
+ buf_ptr[7] = 1;
|
|
} else {
|
|
iuu_rgbf_fill_buffer(buf_ptr, 255, 255, 0, 0, 0, 0, 255);
|
|
}
|
|
@@ -380,13 +381,14 @@ static void iuu_led_activity_off(struct urb *urb)
|
|
struct usb_serial_port *port = urb->context;
|
|
int result;
|
|
char *buf_ptr = port->write_urb->transfer_buffer;
|
|
+
|
|
if (xmas) {
|
|
iuu_rxcmd(urb);
|
|
return;
|
|
- } else {
|
|
- *buf_ptr++ = IUU_SET_LED;
|
|
- iuu_rgbf_fill_buffer(buf_ptr, 0, 0, 255, 255, 0, 0, 255);
|
|
}
|
|
+
|
|
+ iuu_rgbf_fill_buffer(buf_ptr, 0, 0, 255, 255, 0, 0, 255);
|
|
+
|
|
usb_fill_bulk_urb(port->write_urb, port->serial->dev,
|
|
usb_sndbulkpipe(port->serial->dev,
|
|
port->bulk_out_endpointAddress),
|
|
diff --git a/drivers/usb/serial/qcserial.c b/drivers/usb/serial/qcserial.c
|
|
index 27b4082f4d190..7662b2eb50d85 100644
|
|
--- a/drivers/usb/serial/qcserial.c
|
|
+++ b/drivers/usb/serial/qcserial.c
|
|
@@ -159,6 +159,7 @@ static const struct usb_device_id id_table[] = {
|
|
{DEVICE_SWI(0x1199, 0x9056)}, /* Sierra Wireless Modem */
|
|
{DEVICE_SWI(0x1199, 0x9060)}, /* Sierra Wireless Modem */
|
|
{DEVICE_SWI(0x1199, 0x9061)}, /* Sierra Wireless Modem */
|
|
+ {DEVICE_SWI(0x1199, 0x9062)}, /* Sierra Wireless EM7305 QDL */
|
|
{DEVICE_SWI(0x1199, 0x9063)}, /* Sierra Wireless EM7305 */
|
|
{DEVICE_SWI(0x1199, 0x9070)}, /* Sierra Wireless MC74xx */
|
|
{DEVICE_SWI(0x1199, 0x9071)}, /* Sierra Wireless MC74xx */
|
|
diff --git a/drivers/video/console/newport_con.c b/drivers/video/console/newport_con.c
|
|
index 42d02a206059b..d3b0850391e0d 100644
|
|
--- a/drivers/video/console/newport_con.c
|
|
+++ b/drivers/video/console/newport_con.c
|
|
@@ -31,6 +31,8 @@
|
|
#include <linux/linux_logo.h>
|
|
#include <linux/font.h>
|
|
|
|
+#define NEWPORT_LEN 0x10000
|
|
+
|
|
#define FONT_DATA ((unsigned char *)font_vga_8x16.data)
|
|
|
|
/* borrowed from fbcon.c */
|
|
@@ -42,6 +44,7 @@
|
|
static unsigned char *font_data[MAX_NR_CONSOLES];
|
|
|
|
static struct newport_regs *npregs;
|
|
+static unsigned long newport_addr;
|
|
|
|
static int logo_active;
|
|
static int topscan;
|
|
@@ -701,7 +704,6 @@ const struct consw newport_con = {
|
|
static int newport_probe(struct gio_device *dev,
|
|
const struct gio_device_id *id)
|
|
{
|
|
- unsigned long newport_addr;
|
|
int err;
|
|
|
|
if (!dev->resource.start)
|
|
@@ -711,7 +713,7 @@ static int newport_probe(struct gio_device *dev,
|
|
return -EBUSY; /* we only support one Newport as console */
|
|
|
|
newport_addr = dev->resource.start + 0xF0000;
|
|
- if (!request_mem_region(newport_addr, 0x10000, "Newport"))
|
|
+ if (!request_mem_region(newport_addr, NEWPORT_LEN, "Newport"))
|
|
return -ENODEV;
|
|
|
|
npregs = (struct newport_regs *)/* ioremap cannot fail */
|
|
@@ -719,6 +721,11 @@ static int newport_probe(struct gio_device *dev,
|
|
console_lock();
|
|
err = do_take_over_console(&newport_con, 0, MAX_NR_CONSOLES - 1, 1);
|
|
console_unlock();
|
|
+
|
|
+ if (err) {
|
|
+ iounmap((void *)npregs);
|
|
+ release_mem_region(newport_addr, NEWPORT_LEN);
|
|
+ }
|
|
return err;
|
|
}
|
|
|
|
@@ -726,6 +733,7 @@ static void newport_remove(struct gio_device *dev)
|
|
{
|
|
give_up_console(&newport_con);
|
|
iounmap((void *)npregs);
|
|
+ release_mem_region(newport_addr, NEWPORT_LEN);
|
|
}
|
|
|
|
static struct gio_device_id newport_ids[] = {
|
|
diff --git a/drivers/video/console/vgacon.c b/drivers/video/console/vgacon.c
|
|
index ff6612a3ddc8d..8f061c18e115e 100644
|
|
--- a/drivers/video/console/vgacon.c
|
|
+++ b/drivers/video/console/vgacon.c
|
|
@@ -246,6 +246,10 @@ static void vgacon_scrollback_update(struct vc_data *c, int t, int count)
|
|
p = (void *) (c->vc_origin + t * c->vc_size_row);
|
|
|
|
while (count--) {
|
|
+ if ((vgacon_scrollback_cur->tail + c->vc_size_row) >
|
|
+ vgacon_scrollback_cur->size)
|
|
+ vgacon_scrollback_cur->tail = 0;
|
|
+
|
|
scr_memcpyw(vgacon_scrollback_cur->data +
|
|
vgacon_scrollback_cur->tail,
|
|
p, c->vc_size_row);
|
|
diff --git a/drivers/video/fbdev/neofb.c b/drivers/video/fbdev/neofb.c
|
|
index 5d3a444083f74..2018e1ca33eb6 100644
|
|
--- a/drivers/video/fbdev/neofb.c
|
|
+++ b/drivers/video/fbdev/neofb.c
|
|
@@ -1820,6 +1820,7 @@ static int neo_scan_monitor(struct fb_info *info)
|
|
#else
|
|
printk(KERN_ERR
|
|
"neofb: Only 640x480, 800x600/480 and 1024x768 panels are currently supported\n");
|
|
+ kfree(info->monspecs.modedb);
|
|
return -1;
|
|
#endif
|
|
default:
|
|
diff --git a/drivers/video/fbdev/omap2/omapfb/dss/dss.c b/drivers/video/fbdev/omap2/omapfb/dss/dss.c
|
|
index 48c6500c24e1f..4429ad37b64cd 100644
|
|
--- a/drivers/video/fbdev/omap2/omapfb/dss/dss.c
|
|
+++ b/drivers/video/fbdev/omap2/omapfb/dss/dss.c
|
|
@@ -843,7 +843,7 @@ static const struct dss_features omap34xx_dss_feats = {
|
|
};
|
|
|
|
static const struct dss_features omap3630_dss_feats = {
|
|
- .fck_div_max = 32,
|
|
+ .fck_div_max = 31,
|
|
.dss_fck_multiplier = 1,
|
|
.parent_clk_name = "dpll4_ck",
|
|
.dpi_select_source = &dss_dpi_select_source_omap2_omap3,
|
|
diff --git a/drivers/video/fbdev/pxafb.c b/drivers/video/fbdev/pxafb.c
|
|
index 29f00eccdd015..08ee77d5df8b2 100644
|
|
--- a/drivers/video/fbdev/pxafb.c
|
|
+++ b/drivers/video/fbdev/pxafb.c
|
|
@@ -2449,8 +2449,8 @@ static int pxafb_remove(struct platform_device *dev)
|
|
|
|
free_pages_exact(fbi->video_mem, fbi->video_mem_size);
|
|
|
|
- dma_free_wc(&dev->dev, fbi->dma_buff_size, fbi->dma_buff,
|
|
- fbi->dma_buff_phys);
|
|
+ dma_free_coherent(&dev->dev, fbi->dma_buff_size, fbi->dma_buff,
|
|
+ fbi->dma_buff_phys);
|
|
|
|
iounmap(fbi->mmio_base);
|
|
|
|
diff --git a/drivers/video/fbdev/sm712fb.c b/drivers/video/fbdev/sm712fb.c
|
|
index f1dcc6766d1ef..1781ca697f66b 100644
|
|
--- a/drivers/video/fbdev/sm712fb.c
|
|
+++ b/drivers/video/fbdev/sm712fb.c
|
|
@@ -1429,6 +1429,8 @@ static int smtc_map_smem(struct smtcfb_info *sfb,
|
|
static void smtc_unmap_smem(struct smtcfb_info *sfb)
|
|
{
|
|
if (sfb && sfb->fb->screen_base) {
|
|
+ if (sfb->chip_id == 0x720)
|
|
+ sfb->fb->screen_base -= 0x00200000;
|
|
iounmap(sfb->fb->screen_base);
|
|
sfb->fb->screen_base = NULL;
|
|
}
|
|
diff --git a/drivers/watchdog/f71808e_wdt.c b/drivers/watchdog/f71808e_wdt.c
|
|
index 88cd2a52d8d32..ae4974701e5c7 100644
|
|
--- a/drivers/watchdog/f71808e_wdt.c
|
|
+++ b/drivers/watchdog/f71808e_wdt.c
|
|
@@ -688,9 +688,9 @@ static int __init watchdog_init(int sioaddr)
|
|
* into the module have been registered yet.
|
|
*/
|
|
watchdog.sioaddr = sioaddr;
|
|
- watchdog.ident.options = WDIOC_SETTIMEOUT
|
|
- | WDIOF_MAGICCLOSE
|
|
- | WDIOF_KEEPALIVEPING;
|
|
+ watchdog.ident.options = WDIOF_MAGICCLOSE
|
|
+ | WDIOF_KEEPALIVEPING
|
|
+ | WDIOF_CARDRESET;
|
|
|
|
snprintf(watchdog.ident.identity,
|
|
sizeof(watchdog.ident.identity), "%s watchdog",
|
|
@@ -704,6 +704,13 @@ static int __init watchdog_init(int sioaddr)
|
|
wdt_conf = superio_inb(sioaddr, F71808FG_REG_WDT_CONF);
|
|
watchdog.caused_reboot = wdt_conf & BIT(F71808FG_FLAG_WDTMOUT_STS);
|
|
|
|
+ /*
|
|
+ * We don't want WDTMOUT_STS to stick around till regular reboot.
|
|
+ * Write 1 to the bit to clear it to zero.
|
|
+ */
|
|
+ superio_outb(sioaddr, F71808FG_REG_WDT_CONF,
|
|
+ wdt_conf | BIT(F71808FG_FLAG_WDTMOUT_STS));
|
|
+
|
|
superio_exit(sioaddr);
|
|
|
|
err = watchdog_set_timeout(timeout);
|
|
diff --git a/drivers/xen/balloon.c b/drivers/xen/balloon.c
|
|
index 3f9260af701f0..a8e0836dffd4b 100644
|
|
--- a/drivers/xen/balloon.c
|
|
+++ b/drivers/xen/balloon.c
|
|
@@ -633,11 +633,13 @@ static int add_ballooned_pages(int nr_pages)
|
|
if (xen_hotplug_unpopulated) {
|
|
st = reserve_additional_memory();
|
|
if (st != BP_ECANCELED) {
|
|
+ int rc;
|
|
+
|
|
mutex_unlock(&balloon_mutex);
|
|
- wait_event(balloon_wq,
|
|
+ rc = wait_event_interruptible(balloon_wq,
|
|
!list_empty(&ballooned_pages));
|
|
mutex_lock(&balloon_mutex);
|
|
- return 0;
|
|
+ return rc ? -ENOMEM : 0;
|
|
}
|
|
}
|
|
|
|
@@ -695,6 +697,12 @@ int alloc_xenballooned_pages(int nr_pages, struct page **pages)
|
|
out_undo:
|
|
mutex_unlock(&balloon_mutex);
|
|
free_xenballooned_pages(pgno, pages);
|
|
+ /*
|
|
+ * NB: free_xenballooned_pages will only subtract pgno pages, but since
|
|
+ * target_unpopulated is incremented with nr_pages at the start we need
|
|
+ * to remove the remaining ones also, or accounting will be screwed.
|
|
+ */
|
|
+ balloon_stats.target_unpopulated -= nr_pages - pgno;
|
|
return ret;
|
|
}
|
|
EXPORT_SYMBOL(alloc_xenballooned_pages);
|
|
diff --git a/fs/9p/v9fs.c b/fs/9p/v9fs.c
|
|
index c52f10efdc9c6..b4dbe7b711512 100644
|
|
--- a/fs/9p/v9fs.c
|
|
+++ b/fs/9p/v9fs.c
|
|
@@ -513,10 +513,9 @@ void v9fs_session_close(struct v9fs_session_info *v9ses)
|
|
}
|
|
|
|
#ifdef CONFIG_9P_FSCACHE
|
|
- if (v9ses->fscache) {
|
|
+ if (v9ses->fscache)
|
|
v9fs_cache_session_put_cookie(v9ses);
|
|
- kfree(v9ses->cachetag);
|
|
- }
|
|
+ kfree(v9ses->cachetag);
|
|
#endif
|
|
kfree(v9ses->uname);
|
|
kfree(v9ses->aname);
|
|
diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c
|
|
index 096c015b22a46..893066970c689 100644
|
|
--- a/fs/btrfs/disk-io.c
|
|
+++ b/fs/btrfs/disk-io.c
|
|
@@ -1509,9 +1509,16 @@ int btrfs_init_fs_root(struct btrfs_root *root)
|
|
spin_lock_init(&root->ino_cache_lock);
|
|
init_waitqueue_head(&root->ino_cache_wait);
|
|
|
|
- ret = get_anon_bdev(&root->anon_dev);
|
|
- if (ret)
|
|
- goto fail;
|
|
+ /*
|
|
+ * Don't assign anonymous block device to roots that are not exposed to
|
|
+ * userspace, the id pool is limited to 1M
|
|
+ */
|
|
+ if (is_fstree(root->root_key.objectid) &&
|
|
+ btrfs_root_refs(&root->root_item) > 0) {
|
|
+ ret = get_anon_bdev(&root->anon_dev);
|
|
+ if (ret)
|
|
+ goto fail;
|
|
+ }
|
|
|
|
mutex_lock(&root->objectid_mutex);
|
|
ret = btrfs_find_highest_objectid(root,
|
|
diff --git a/fs/btrfs/extent_io.c b/fs/btrfs/extent_io.c
|
|
index 6d2bfbb63d9ba..ef1fd6a09d8e5 100644
|
|
--- a/fs/btrfs/extent_io.c
|
|
+++ b/fs/btrfs/extent_io.c
|
|
@@ -4323,6 +4323,8 @@ int try_release_extent_mapping(struct extent_map_tree *map,
|
|
|
|
/* once for us */
|
|
free_extent_map(em);
|
|
+
|
|
+ cond_resched(); /* Allow large-extent preemption. */
|
|
}
|
|
}
|
|
return try_release_extent_state(map, tree, page, mask);
|
|
diff --git a/fs/btrfs/free-space-cache.c b/fs/btrfs/free-space-cache.c
|
|
index abeb26d48d0a2..57f89708fab1c 100644
|
|
--- a/fs/btrfs/free-space-cache.c
|
|
+++ b/fs/btrfs/free-space-cache.c
|
|
@@ -2169,7 +2169,7 @@ out:
|
|
static bool try_merge_free_space(struct btrfs_free_space_ctl *ctl,
|
|
struct btrfs_free_space *info, bool update_stat)
|
|
{
|
|
- struct btrfs_free_space *left_info;
|
|
+ struct btrfs_free_space *left_info = NULL;
|
|
struct btrfs_free_space *right_info;
|
|
bool merged = false;
|
|
u64 offset = info->offset;
|
|
@@ -2184,7 +2184,7 @@ static bool try_merge_free_space(struct btrfs_free_space_ctl *ctl,
|
|
if (right_info && rb_prev(&right_info->offset_index))
|
|
left_info = rb_entry(rb_prev(&right_info->offset_index),
|
|
struct btrfs_free_space, offset_index);
|
|
- else
|
|
+ else if (!right_info)
|
|
left_info = tree_search_offset(ctl, offset - 1, 0, 0);
|
|
|
|
if (right_info && !right_info->bitmap) {
|
|
diff --git a/fs/btrfs/tree-log.c b/fs/btrfs/tree-log.c
|
|
index bcfb7a772c8e5..3d30bf90d59ec 100644
|
|
--- a/fs/btrfs/tree-log.c
|
|
+++ b/fs/btrfs/tree-log.c
|
|
@@ -3854,11 +3854,8 @@ static noinline int copy_items(struct btrfs_trans_handle *trans,
|
|
fs_info->csum_root,
|
|
ds + cs, ds + cs + cl - 1,
|
|
&ordered_sums, 0);
|
|
- if (ret) {
|
|
- btrfs_release_path(dst_path);
|
|
- kfree(ins_data);
|
|
- return ret;
|
|
- }
|
|
+ if (ret)
|
|
+ break;
|
|
}
|
|
}
|
|
}
|
|
@@ -3871,7 +3868,6 @@ static noinline int copy_items(struct btrfs_trans_handle *trans,
|
|
* we have to do this after the loop above to avoid changing the
|
|
* log tree while trying to change the log tree.
|
|
*/
|
|
- ret = 0;
|
|
while (!list_empty(&ordered_sums)) {
|
|
struct btrfs_ordered_sum *sums = list_entry(ordered_sums.next,
|
|
struct btrfs_ordered_sum,
|
|
diff --git a/fs/cifs/smb2pdu.c b/fs/cifs/smb2pdu.c
|
|
index 1c87a429ce72f..2097b5fd51baa 100644
|
|
--- a/fs/cifs/smb2pdu.c
|
|
+++ b/fs/cifs/smb2pdu.c
|
|
@@ -942,6 +942,8 @@ SMB2_auth_kerberos(struct SMB2_sess_data *sess_data)
|
|
spnego_key = cifs_get_spnego_key(ses);
|
|
if (IS_ERR(spnego_key)) {
|
|
rc = PTR_ERR(spnego_key);
|
|
+ if (rc == -ENOKEY)
|
|
+ cifs_dbg(VFS, "Verify user has a krb5 ticket and keyutils is installed\n");
|
|
spnego_key = NULL;
|
|
goto out;
|
|
}
|
|
diff --git a/fs/dlm/lockspace.c b/fs/dlm/lockspace.c
|
|
index 9c8c9a09b4a6d..7a6b0327ceb0b 100644
|
|
--- a/fs/dlm/lockspace.c
|
|
+++ b/fs/dlm/lockspace.c
|
|
@@ -633,6 +633,9 @@ static int new_lockspace(const char *name, const char *cluster,
|
|
wait_event(ls->ls_recover_lock_wait,
|
|
test_bit(LSFL_RECOVER_LOCK, &ls->ls_flags));
|
|
|
|
+ /* let kobject handle freeing of ls if there's an error */
|
|
+ do_unreg = 1;
|
|
+
|
|
ls->ls_kobj.kset = dlm_kset;
|
|
error = kobject_init_and_add(&ls->ls_kobj, &dlm_ktype, NULL,
|
|
"%s", ls->ls_name);
|
|
@@ -640,9 +643,6 @@ static int new_lockspace(const char *name, const char *cluster,
|
|
goto out_recoverd;
|
|
kobject_uevent(&ls->ls_kobj, KOBJ_ADD);
|
|
|
|
- /* let kobject handle freeing of ls if there's an error */
|
|
- do_unreg = 1;
|
|
-
|
|
/* This uevent triggers dlm_controld in userspace to add us to the
|
|
group of nodes that are members of this lockspace (managed by the
|
|
cluster infrastructure.) Once it's done that, it tells us who the
|
|
diff --git a/fs/ext2/ialloc.c b/fs/ext2/ialloc.c
|
|
index a1fc3dabca41b..6d5fce776d8e3 100644
|
|
--- a/fs/ext2/ialloc.c
|
|
+++ b/fs/ext2/ialloc.c
|
|
@@ -80,6 +80,7 @@ static void ext2_release_inode(struct super_block *sb, int group, int dir)
|
|
if (dir)
|
|
le16_add_cpu(&desc->bg_used_dirs_count, -1);
|
|
spin_unlock(sb_bgl_lock(EXT2_SB(sb), group));
|
|
+ percpu_counter_inc(&EXT2_SB(sb)->s_freeinodes_counter);
|
|
if (dir)
|
|
percpu_counter_dec(&EXT2_SB(sb)->s_dirs_counter);
|
|
mark_buffer_dirty(bh);
|
|
@@ -531,7 +532,7 @@ got:
|
|
goto fail;
|
|
}
|
|
|
|
- percpu_counter_add(&sbi->s_freeinodes_counter, -1);
|
|
+ percpu_counter_dec(&sbi->s_freeinodes_counter);
|
|
if (S_ISDIR(mode))
|
|
percpu_counter_inc(&sbi->s_dirs_counter);
|
|
|
|
diff --git a/fs/minix/inode.c b/fs/minix/inode.c
|
|
index b6829d6796432..d49337b5abfad 100644
|
|
--- a/fs/minix/inode.c
|
|
+++ b/fs/minix/inode.c
|
|
@@ -155,6 +155,23 @@ static int minix_remount (struct super_block * sb, int * flags, char * data)
|
|
return 0;
|
|
}
|
|
|
|
+static bool minix_check_superblock(struct minix_sb_info *sbi)
|
|
+{
|
|
+ if (sbi->s_imap_blocks == 0 || sbi->s_zmap_blocks == 0)
|
|
+ return false;
|
|
+
|
|
+ /*
|
|
+ * s_max_size must not exceed the block mapping limitation. This check
|
|
+ * is only needed for V1 filesystems, since V2/V3 support an extra level
|
|
+ * of indirect blocks which places the limit well above U32_MAX.
|
|
+ */
|
|
+ if (sbi->s_version == MINIX_V1 &&
|
|
+ sbi->s_max_size > (7 + 512 + 512*512) * BLOCK_SIZE)
|
|
+ return false;
|
|
+
|
|
+ return true;
|
|
+}
|
|
+
|
|
static int minix_fill_super(struct super_block *s, void *data, int silent)
|
|
{
|
|
struct buffer_head *bh;
|
|
@@ -233,11 +250,12 @@ static int minix_fill_super(struct super_block *s, void *data, int silent)
|
|
} else
|
|
goto out_no_fs;
|
|
|
|
+ if (!minix_check_superblock(sbi))
|
|
+ goto out_illegal_sb;
|
|
+
|
|
/*
|
|
* Allocate the buffer map to keep the superblock small.
|
|
*/
|
|
- if (sbi->s_imap_blocks == 0 || sbi->s_zmap_blocks == 0)
|
|
- goto out_illegal_sb;
|
|
i = (sbi->s_imap_blocks + sbi->s_zmap_blocks) * sizeof(bh);
|
|
map = kzalloc(i, GFP_KERNEL);
|
|
if (!map)
|
|
@@ -471,6 +489,13 @@ static struct inode *V1_minix_iget(struct inode *inode)
|
|
iget_failed(inode);
|
|
return ERR_PTR(-EIO);
|
|
}
|
|
+ if (raw_inode->i_nlinks == 0) {
|
|
+ printk("MINIX-fs: deleted inode referenced: %lu\n",
|
|
+ inode->i_ino);
|
|
+ brelse(bh);
|
|
+ iget_failed(inode);
|
|
+ return ERR_PTR(-ESTALE);
|
|
+ }
|
|
inode->i_mode = raw_inode->i_mode;
|
|
i_uid_write(inode, raw_inode->i_uid);
|
|
i_gid_write(inode, raw_inode->i_gid);
|
|
@@ -504,6 +529,13 @@ static struct inode *V2_minix_iget(struct inode *inode)
|
|
iget_failed(inode);
|
|
return ERR_PTR(-EIO);
|
|
}
|
|
+ if (raw_inode->i_nlinks == 0) {
|
|
+ printk("MINIX-fs: deleted inode referenced: %lu\n",
|
|
+ inode->i_ino);
|
|
+ brelse(bh);
|
|
+ iget_failed(inode);
|
|
+ return ERR_PTR(-ESTALE);
|
|
+ }
|
|
inode->i_mode = raw_inode->i_mode;
|
|
i_uid_write(inode, raw_inode->i_uid);
|
|
i_gid_write(inode, raw_inode->i_gid);
|
|
diff --git a/fs/minix/itree_common.c b/fs/minix/itree_common.c
|
|
index 043c3fdbc8e7e..446148792f411 100644
|
|
--- a/fs/minix/itree_common.c
|
|
+++ b/fs/minix/itree_common.c
|
|
@@ -75,6 +75,7 @@ static int alloc_branch(struct inode *inode,
|
|
int n = 0;
|
|
int i;
|
|
int parent = minix_new_block(inode);
|
|
+ int err = -ENOSPC;
|
|
|
|
branch[0].key = cpu_to_block(parent);
|
|
if (parent) for (n = 1; n < num; n++) {
|
|
@@ -85,6 +86,11 @@ static int alloc_branch(struct inode *inode,
|
|
break;
|
|
branch[n].key = cpu_to_block(nr);
|
|
bh = sb_getblk(inode->i_sb, parent);
|
|
+ if (!bh) {
|
|
+ minix_free_block(inode, nr);
|
|
+ err = -ENOMEM;
|
|
+ break;
|
|
+ }
|
|
lock_buffer(bh);
|
|
memset(bh->b_data, 0, bh->b_size);
|
|
branch[n].bh = bh;
|
|
@@ -103,7 +109,7 @@ static int alloc_branch(struct inode *inode,
|
|
bforget(branch[i].bh);
|
|
for (i = 0; i < n; i++)
|
|
minix_free_block(inode, block_to_cpu(branch[i].key));
|
|
- return -ENOSPC;
|
|
+ return err;
|
|
}
|
|
|
|
static inline int splice_branch(struct inode *inode,
|
|
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c
|
|
index a19bbcfab7c5e..4cfb84119e017 100644
|
|
--- a/fs/nfs/nfs4proc.c
|
|
+++ b/fs/nfs/nfs4proc.c
|
|
@@ -5323,8 +5323,6 @@ static int _nfs4_get_security_label(struct inode *inode, void *buf,
|
|
return ret;
|
|
if (!(fattr.valid & NFS_ATTR_FATTR_V4_SECURITY_LABEL))
|
|
return -ENOENT;
|
|
- if (buflen < label.len)
|
|
- return -ERANGE;
|
|
return 0;
|
|
}
|
|
|
|
diff --git a/fs/nfs/nfs4xdr.c b/fs/nfs/nfs4xdr.c
|
|
index 0b2d051990e99..3cd04c98da6bc 100644
|
|
--- a/fs/nfs/nfs4xdr.c
|
|
+++ b/fs/nfs/nfs4xdr.c
|
|
@@ -4258,7 +4258,11 @@ static int decode_attr_security_label(struct xdr_stream *xdr, uint32_t *bitmap,
|
|
goto out_overflow;
|
|
if (len < NFS4_MAXLABELLEN) {
|
|
if (label) {
|
|
- memcpy(label->label, p, len);
|
|
+ if (label->len) {
|
|
+ if (label->len < len)
|
|
+ return -ERANGE;
|
|
+ memcpy(label->label, p, len);
|
|
+ }
|
|
label->len = len;
|
|
label->pi = pi;
|
|
label->lfs = lfs;
|
|
diff --git a/fs/ocfs2/ocfs2.h b/fs/ocfs2/ocfs2.h
|
|
index 9a50f222ac97f..b15537a76516d 100644
|
|
--- a/fs/ocfs2/ocfs2.h
|
|
+++ b/fs/ocfs2/ocfs2.h
|
|
@@ -336,8 +336,8 @@ struct ocfs2_super
|
|
spinlock_t osb_lock;
|
|
u32 s_next_generation;
|
|
unsigned long osb_flags;
|
|
- s16 s_inode_steal_slot;
|
|
- s16 s_meta_steal_slot;
|
|
+ u16 s_inode_steal_slot;
|
|
+ u16 s_meta_steal_slot;
|
|
atomic_t s_num_inodes_stolen;
|
|
atomic_t s_num_meta_stolen;
|
|
|
|
diff --git a/fs/ocfs2/suballoc.c b/fs/ocfs2/suballoc.c
|
|
index 4ca2f71565f9a..8d03630dfd590 100644
|
|
--- a/fs/ocfs2/suballoc.c
|
|
+++ b/fs/ocfs2/suballoc.c
|
|
@@ -895,9 +895,9 @@ static void __ocfs2_set_steal_slot(struct ocfs2_super *osb, int slot, int type)
|
|
{
|
|
spin_lock(&osb->osb_lock);
|
|
if (type == INODE_ALLOC_SYSTEM_INODE)
|
|
- osb->s_inode_steal_slot = slot;
|
|
+ osb->s_inode_steal_slot = (u16)slot;
|
|
else if (type == EXTENT_ALLOC_SYSTEM_INODE)
|
|
- osb->s_meta_steal_slot = slot;
|
|
+ osb->s_meta_steal_slot = (u16)slot;
|
|
spin_unlock(&osb->osb_lock);
|
|
}
|
|
|
|
diff --git a/fs/ocfs2/super.c b/fs/ocfs2/super.c
|
|
index 24ab735d91dd6..8216550faf45b 100644
|
|
--- a/fs/ocfs2/super.c
|
|
+++ b/fs/ocfs2/super.c
|
|
@@ -92,7 +92,7 @@ struct mount_options
|
|
unsigned long commit_interval;
|
|
unsigned long mount_opt;
|
|
unsigned int atime_quantum;
|
|
- signed short slot;
|
|
+ unsigned short slot;
|
|
int localalloc_opt;
|
|
unsigned int resv_level;
|
|
int dir_resv_level;
|
|
@@ -1369,7 +1369,7 @@ static int ocfs2_parse_options(struct super_block *sb,
|
|
goto bail;
|
|
}
|
|
if (option)
|
|
- mopt->slot = (s16)option;
|
|
+ mopt->slot = (u16)option;
|
|
break;
|
|
case Opt_commit:
|
|
if (match_int(&args[0], &option)) {
|
|
diff --git a/fs/ufs/super.c b/fs/ufs/super.c
|
|
index 6440003f8ddc6..e3f3a0df60276 100644
|
|
--- a/fs/ufs/super.c
|
|
+++ b/fs/ufs/super.c
|
|
@@ -99,7 +99,7 @@ static struct inode *ufs_nfs_get_inode(struct super_block *sb, u64 ino, u32 gene
|
|
struct ufs_sb_private_info *uspi = UFS_SB(sb)->s_uspi;
|
|
struct inode *inode;
|
|
|
|
- if (ino < UFS_ROOTINO || ino > uspi->s_ncg * uspi->s_ipg)
|
|
+ if (ino < UFS_ROOTINO || ino > (u64)uspi->s_ncg * uspi->s_ipg)
|
|
return ERR_PTR(-ESTALE);
|
|
|
|
inode = ufs_iget(sb, ino);
|
|
diff --git a/fs/xattr.c b/fs/xattr.c
|
|
index 50029811fbe38..94f9559ba0f86 100644
|
|
--- a/fs/xattr.c
|
|
+++ b/fs/xattr.c
|
|
@@ -204,10 +204,22 @@ int __vfs_setxattr_noperm(struct dentry *dentry, const char *name,
|
|
return error;
|
|
}
|
|
|
|
-
|
|
+/**
|
|
+ * __vfs_setxattr_locked: set an extended attribute while holding the inode
|
|
+ * lock
|
|
+ *
|
|
+ * @dentry - object to perform setxattr on
|
|
+ * @name - xattr name to set
|
|
+ * @value - value to set @name to
|
|
+ * @size - size of @value
|
|
+ * @flags - flags to pass into filesystem operations
|
|
+ * @delegated_inode - on return, will contain an inode pointer that
|
|
+ * a delegation was broken on, NULL if none.
|
|
+ */
|
|
int
|
|
-vfs_setxattr(struct dentry *dentry, const char *name, const void *value,
|
|
- size_t size, int flags)
|
|
+__vfs_setxattr_locked(struct dentry *dentry, const char *name,
|
|
+ const void *value, size_t size, int flags,
|
|
+ struct inode **delegated_inode)
|
|
{
|
|
struct inode *inode = dentry->d_inode;
|
|
int error;
|
|
@@ -216,15 +228,40 @@ vfs_setxattr(struct dentry *dentry, const char *name, const void *value,
|
|
if (error)
|
|
return error;
|
|
|
|
- inode_lock(inode);
|
|
error = security_inode_setxattr(dentry, name, value, size, flags);
|
|
if (error)
|
|
goto out;
|
|
|
|
+ error = try_break_deleg(inode, delegated_inode);
|
|
+ if (error)
|
|
+ goto out;
|
|
+
|
|
error = __vfs_setxattr_noperm(dentry, name, value, size, flags);
|
|
|
|
out:
|
|
+ return error;
|
|
+}
|
|
+EXPORT_SYMBOL_GPL(__vfs_setxattr_locked);
|
|
+
|
|
+int
|
|
+vfs_setxattr(struct dentry *dentry, const char *name, const void *value,
|
|
+ size_t size, int flags)
|
|
+{
|
|
+ struct inode *inode = dentry->d_inode;
|
|
+ struct inode *delegated_inode = NULL;
|
|
+ int error;
|
|
+
|
|
+retry_deleg:
|
|
+ inode_lock(inode);
|
|
+ error = __vfs_setxattr_locked(dentry, name, value, size, flags,
|
|
+ &delegated_inode);
|
|
inode_unlock(inode);
|
|
+
|
|
+ if (delegated_inode) {
|
|
+ error = break_deleg_wait(&delegated_inode);
|
|
+ if (!error)
|
|
+ goto retry_deleg;
|
|
+ }
|
|
return error;
|
|
}
|
|
EXPORT_SYMBOL_GPL(vfs_setxattr);
|
|
@@ -380,8 +417,18 @@ __vfs_removexattr(struct dentry *dentry, const char *name)
|
|
}
|
|
EXPORT_SYMBOL(__vfs_removexattr);
|
|
|
|
+/**
|
|
+ * __vfs_removexattr_locked: set an extended attribute while holding the inode
|
|
+ * lock
|
|
+ *
|
|
+ * @dentry - object to perform setxattr on
|
|
+ * @name - name of xattr to remove
|
|
+ * @delegated_inode - on return, will contain an inode pointer that
|
|
+ * a delegation was broken on, NULL if none.
|
|
+ */
|
|
int
|
|
-vfs_removexattr(struct dentry *dentry, const char *name)
|
|
+__vfs_removexattr_locked(struct dentry *dentry, const char *name,
|
|
+ struct inode **delegated_inode)
|
|
{
|
|
struct inode *inode = dentry->d_inode;
|
|
int error;
|
|
@@ -390,11 +437,14 @@ vfs_removexattr(struct dentry *dentry, const char *name)
|
|
if (error)
|
|
return error;
|
|
|
|
- inode_lock(inode);
|
|
error = security_inode_removexattr(dentry, name);
|
|
if (error)
|
|
goto out;
|
|
|
|
+ error = try_break_deleg(inode, delegated_inode);
|
|
+ if (error)
|
|
+ goto out;
|
|
+
|
|
error = __vfs_removexattr(dentry, name);
|
|
|
|
if (!error) {
|
|
@@ -403,12 +453,32 @@ vfs_removexattr(struct dentry *dentry, const char *name)
|
|
}
|
|
|
|
out:
|
|
+ return error;
|
|
+}
|
|
+EXPORT_SYMBOL_GPL(__vfs_removexattr_locked);
|
|
+
|
|
+int
|
|
+vfs_removexattr(struct dentry *dentry, const char *name)
|
|
+{
|
|
+ struct inode *inode = dentry->d_inode;
|
|
+ struct inode *delegated_inode = NULL;
|
|
+ int error;
|
|
+
|
|
+retry_deleg:
|
|
+ inode_lock(inode);
|
|
+ error = __vfs_removexattr_locked(dentry, name, &delegated_inode);
|
|
inode_unlock(inode);
|
|
+
|
|
+ if (delegated_inode) {
|
|
+ error = break_deleg_wait(&delegated_inode);
|
|
+ if (!error)
|
|
+ goto retry_deleg;
|
|
+ }
|
|
+
|
|
return error;
|
|
}
|
|
EXPORT_SYMBOL_GPL(vfs_removexattr);
|
|
|
|
-
|
|
/*
|
|
* Extended attribute SET operations
|
|
*/
|
|
diff --git a/fs/xfs/xfs_reflink.c b/fs/xfs/xfs_reflink.c
|
|
index db7f9fdd20a30..4d37f1b59436c 100644
|
|
--- a/fs/xfs/xfs_reflink.c
|
|
+++ b/fs/xfs/xfs_reflink.c
|
|
@@ -1076,6 +1076,7 @@ xfs_reflink_remap_extent(
|
|
xfs_filblks_t rlen;
|
|
xfs_filblks_t unmap_len;
|
|
xfs_off_t newlen;
|
|
+ int64_t qres;
|
|
int error;
|
|
|
|
unmap_len = irec->br_startoff + irec->br_blockcount - destoff;
|
|
@@ -1098,13 +1099,19 @@ xfs_reflink_remap_extent(
|
|
xfs_ilock(ip, XFS_ILOCK_EXCL);
|
|
xfs_trans_ijoin(tp, ip, 0);
|
|
|
|
- /* If we're not just clearing space, then do we have enough quota? */
|
|
- if (real_extent) {
|
|
- error = xfs_trans_reserve_quota_nblks(tp, ip,
|
|
- irec->br_blockcount, 0, XFS_QMOPT_RES_REGBLKS);
|
|
- if (error)
|
|
- goto out_cancel;
|
|
- }
|
|
+ /*
|
|
+ * Reserve quota for this operation. We don't know if the first unmap
|
|
+ * in the dest file will cause a bmap btree split, so we always reserve
|
|
+ * at least enough blocks for that split. If the extent being mapped
|
|
+ * in is written, we need to reserve quota for that too.
|
|
+ */
|
|
+ qres = XFS_EXTENTADD_SPACE_RES(mp, XFS_DATA_FORK);
|
|
+ if (real_extent)
|
|
+ qres += irec->br_blockcount;
|
|
+ error = xfs_trans_reserve_quota_nblks(tp, ip, qres, 0,
|
|
+ XFS_QMOPT_RES_REGBLKS);
|
|
+ if (error)
|
|
+ goto out_cancel;
|
|
|
|
trace_xfs_reflink_remap(ip, irec->br_startoff,
|
|
irec->br_blockcount, irec->br_startblock);
|
|
diff --git a/include/linux/bitfield.h b/include/linux/bitfield.h
|
|
index f2deb71958b2d..a0675db325e01 100644
|
|
--- a/include/linux/bitfield.h
|
|
+++ b/include/linux/bitfield.h
|
|
@@ -71,7 +71,7 @@
|
|
*/
|
|
#define FIELD_FIT(_mask, _val) \
|
|
({ \
|
|
- __BF_FIELD_CHECK(_mask, 0ULL, _val, "FIELD_FIT: "); \
|
|
+ __BF_FIELD_CHECK(_mask, 0ULL, 0ULL, "FIELD_FIT: "); \
|
|
!((((typeof(_mask))_val) << __bf_shf(_mask)) & ~(_mask)); \
|
|
})
|
|
|
|
diff --git a/include/linux/hyperv.h b/include/linux/hyperv.h
|
|
index 8d3ca6da33421..63cd81e5610d1 100644
|
|
--- a/include/linux/hyperv.h
|
|
+++ b/include/linux/hyperv.h
|
|
@@ -422,6 +422,8 @@ enum vmbus_channel_message_type {
|
|
CHANNELMSG_19 = 19,
|
|
CHANNELMSG_20 = 20,
|
|
CHANNELMSG_TL_CONNECT_REQUEST = 21,
|
|
+ CHANNELMSG_22 = 22,
|
|
+ CHANNELMSG_TL_CONNECT_RESULT = 23,
|
|
CHANNELMSG_COUNT
|
|
};
|
|
|
|
diff --git a/include/linux/intel-iommu.h b/include/linux/intel-iommu.h
|
|
index 4def15c32a018..d2364ba99f6ce 100644
|
|
--- a/include/linux/intel-iommu.h
|
|
+++ b/include/linux/intel-iommu.h
|
|
@@ -304,8 +304,8 @@ enum {
|
|
|
|
#define QI_DEV_EIOTLB_ADDR(a) ((u64)(a) & VTD_PAGE_MASK)
|
|
#define QI_DEV_EIOTLB_SIZE (((u64)1) << 11)
|
|
-#define QI_DEV_EIOTLB_GLOB(g) ((u64)g)
|
|
-#define QI_DEV_EIOTLB_PASID(p) (((u64)p) << 32)
|
|
+#define QI_DEV_EIOTLB_GLOB(g) ((u64)(g) & 0x1)
|
|
+#define QI_DEV_EIOTLB_PASID(p) ((u64)((p) & 0xfffff) << 32)
|
|
#define QI_DEV_EIOTLB_SID(sid) ((u64)((sid) & 0xffff) << 16)
|
|
#define QI_DEV_EIOTLB_QDEP(qd) ((u64)((qd) & 0x1f) << 4)
|
|
#define QI_DEV_EIOTLB_PFSID(pfsid) (((u64)(pfsid & 0xf) << 12) | \
|
|
diff --git a/include/linux/irq.h b/include/linux/irq.h
|
|
index 0d53626405bf8..c08758a63d268 100644
|
|
--- a/include/linux/irq.h
|
|
+++ b/include/linux/irq.h
|
|
@@ -212,6 +212,8 @@ struct irq_data {
|
|
* mask. Applies only to affinity managed irqs.
|
|
* IRQD_SINGLE_TARGET - IRQ allows only a single affinity target
|
|
* IRQD_DEFAULT_TRIGGER_SET - Expected trigger already been set
|
|
+ * IRQD_AFFINITY_ON_ACTIVATE - Affinity is set on activation. Don't call
|
|
+ * irq_chip::irq_set_affinity() when deactivated.
|
|
*/
|
|
enum {
|
|
IRQD_TRIGGER_MASK = 0xf,
|
|
@@ -233,6 +235,7 @@ enum {
|
|
IRQD_MANAGED_SHUTDOWN = (1 << 23),
|
|
IRQD_SINGLE_TARGET = (1 << 24),
|
|
IRQD_DEFAULT_TRIGGER_SET = (1 << 25),
|
|
+ IRQD_AFFINITY_ON_ACTIVATE = (1 << 29),
|
|
};
|
|
|
|
#define __irqd_to_state(d) ACCESS_PRIVATE((d)->common, state_use_accessors)
|
|
@@ -377,6 +380,15 @@ static inline bool irqd_is_managed_and_shutdown(struct irq_data *d)
|
|
return __irqd_to_state(d) & IRQD_MANAGED_SHUTDOWN;
|
|
}
|
|
|
|
+static inline void irqd_set_affinity_on_activate(struct irq_data *d)
|
|
+{
|
|
+ __irqd_to_state(d) |= IRQD_AFFINITY_ON_ACTIVATE;
|
|
+}
|
|
+
|
|
+static inline bool irqd_affinity_on_activate(struct irq_data *d)
|
|
+{
|
|
+ return __irqd_to_state(d) & IRQD_AFFINITY_ON_ACTIVATE;
|
|
+}
|
|
#undef __irqd_to_state
|
|
|
|
static inline irq_hw_number_t irqd_to_hwirq(struct irq_data *d)
|
|
diff --git a/include/linux/tracepoint.h b/include/linux/tracepoint.h
|
|
index a26ffbe09e715..06cb9184a42a0 100644
|
|
--- a/include/linux/tracepoint.h
|
|
+++ b/include/linux/tracepoint.h
|
|
@@ -318,7 +318,7 @@ extern void syscall_unregfunc(void);
|
|
static const char *___tp_str __tracepoint_string = str; \
|
|
___tp_str; \
|
|
})
|
|
-#define __tracepoint_string __attribute__((section("__tracepoint_str")))
|
|
+#define __tracepoint_string __attribute__((section("__tracepoint_str"), used))
|
|
#else
|
|
/*
|
|
* tracepoint_string() is used to save the string address for userspace
|
|
diff --git a/include/linux/xattr.h b/include/linux/xattr.h
|
|
index d70f77a4b62ab..b0945fb7242f5 100644
|
|
--- a/include/linux/xattr.h
|
|
+++ b/include/linux/xattr.h
|
|
@@ -52,8 +52,10 @@ ssize_t vfs_getxattr(struct dentry *, const char *, void *, size_t);
|
|
ssize_t vfs_listxattr(struct dentry *d, char *list, size_t size);
|
|
int __vfs_setxattr(struct dentry *, struct inode *, const char *, const void *, size_t, int);
|
|
int __vfs_setxattr_noperm(struct dentry *, const char *, const void *, size_t, int);
|
|
+int __vfs_setxattr_locked(struct dentry *, const char *, const void *, size_t, int, struct inode **);
|
|
int vfs_setxattr(struct dentry *, const char *, const void *, size_t, int);
|
|
int __vfs_removexattr(struct dentry *, const char *);
|
|
+int __vfs_removexattr_locked(struct dentry *, const char *, struct inode **);
|
|
int vfs_removexattr(struct dentry *, const char *);
|
|
|
|
ssize_t generic_listxattr(struct dentry *dentry, char *buffer, size_t buffer_size);
|
|
diff --git a/include/net/addrconf.h b/include/net/addrconf.h
|
|
index f30ee99a1d72a..a4cda47682100 100644
|
|
--- a/include/net/addrconf.h
|
|
+++ b/include/net/addrconf.h
|
|
@@ -270,6 +270,7 @@ int ipv6_sock_ac_join(struct sock *sk, int ifindex,
|
|
const struct in6_addr *addr);
|
|
int ipv6_sock_ac_drop(struct sock *sk, int ifindex,
|
|
const struct in6_addr *addr);
|
|
+void __ipv6_sock_ac_close(struct sock *sk);
|
|
void ipv6_sock_ac_close(struct sock *sk);
|
|
|
|
int __ipv6_dev_ac_inc(struct inet6_dev *idev, const struct in6_addr *addr);
|
|
diff --git a/include/net/inet_connection_sock.h b/include/net/inet_connection_sock.h
|
|
index 13e4c89a8231b..ceab3a5dd5309 100644
|
|
--- a/include/net/inet_connection_sock.h
|
|
+++ b/include/net/inet_connection_sock.h
|
|
@@ -321,5 +321,9 @@ int inet_csk_compat_getsockopt(struct sock *sk, int level, int optname,
|
|
int inet_csk_compat_setsockopt(struct sock *sk, int level, int optname,
|
|
char __user *optval, unsigned int optlen);
|
|
|
|
+/* update the fast reuse flag when adding a socket */
|
|
+void inet_csk_update_fastreuse(struct inet_bind_bucket *tb,
|
|
+ struct sock *sk);
|
|
+
|
|
struct dst_entry *inet_csk_update_pmtu(struct sock *sk, u32 mtu);
|
|
#endif /* _INET_CONNECTION_SOCK_H */
|
|
diff --git a/include/net/ip_vs.h b/include/net/ip_vs.h
|
|
index f4e5ac8aa3668..1fb79c78e2007 100644
|
|
--- a/include/net/ip_vs.h
|
|
+++ b/include/net/ip_vs.h
|
|
@@ -1607,18 +1607,16 @@ static inline void ip_vs_conn_drop_conntrack(struct ip_vs_conn *cp)
|
|
}
|
|
#endif /* CONFIG_IP_VS_NFCT */
|
|
|
|
-/* Really using conntrack? */
|
|
-static inline bool ip_vs_conn_uses_conntrack(struct ip_vs_conn *cp,
|
|
- struct sk_buff *skb)
|
|
+/* Using old conntrack that can not be redirected to another real server? */
|
|
+static inline bool ip_vs_conn_uses_old_conntrack(struct ip_vs_conn *cp,
|
|
+ struct sk_buff *skb)
|
|
{
|
|
#ifdef CONFIG_IP_VS_NFCT
|
|
enum ip_conntrack_info ctinfo;
|
|
struct nf_conn *ct;
|
|
|
|
- if (!(cp->flags & IP_VS_CONN_F_NFCT))
|
|
- return false;
|
|
ct = nf_ct_get(skb, &ctinfo);
|
|
- if (ct)
|
|
+ if (ct && nf_ct_is_confirmed(ct))
|
|
return true;
|
|
#endif
|
|
return false;
|
|
diff --git a/include/net/sock.h b/include/net/sock.h
|
|
index a2e10d0b12804..55d16db84ea44 100644
|
|
--- a/include/net/sock.h
|
|
+++ b/include/net/sock.h
|
|
@@ -816,6 +816,8 @@ static inline int sk_memalloc_socks(void)
|
|
{
|
|
return static_key_false(&memalloc_socks);
|
|
}
|
|
+
|
|
+void __receive_sock(struct file *file);
|
|
#else
|
|
|
|
static inline int sk_memalloc_socks(void)
|
|
@@ -823,6 +825,8 @@ static inline int sk_memalloc_socks(void)
|
|
return 0;
|
|
}
|
|
|
|
+static inline void __receive_sock(struct file *file)
|
|
+{ }
|
|
#endif
|
|
|
|
static inline gfp_t sk_gfp_mask(const struct sock *sk, gfp_t gfp_mask)
|
|
diff --git a/kernel/cgroup/cgroup.c b/kernel/cgroup/cgroup.c
|
|
index a2fed8fbd2bde..ada060e628ce3 100644
|
|
--- a/kernel/cgroup/cgroup.c
|
|
+++ b/kernel/cgroup/cgroup.c
|
|
@@ -5827,6 +5827,8 @@ void cgroup_sk_clone(struct sock_cgroup_data *skcd)
|
|
{
|
|
/* Socket clone path */
|
|
if (skcd->val) {
|
|
+ if (skcd->no_refcnt)
|
|
+ return;
|
|
/*
|
|
* We might be cloning a socket which is left in an empty
|
|
* cgroup and the cgroup might have already been rmdir'd.
|
|
diff --git a/kernel/irq/manage.c b/kernel/irq/manage.c
|
|
index 5277949e82e09..3193be58805c2 100644
|
|
--- a/kernel/irq/manage.c
|
|
+++ b/kernel/irq/manage.c
|
|
@@ -168,9 +168,9 @@ void irq_set_thread_affinity(struct irq_desc *desc)
|
|
set_bit(IRQTF_AFFINITY, &action->thread_flags);
|
|
}
|
|
|
|
+#ifdef CONFIG_GENERIC_IRQ_EFFECTIVE_AFF_MASK
|
|
static void irq_validate_effective_affinity(struct irq_data *data)
|
|
{
|
|
-#ifdef CONFIG_GENERIC_IRQ_EFFECTIVE_AFF_MASK
|
|
const struct cpumask *m = irq_data_get_effective_affinity_mask(data);
|
|
struct irq_chip *chip = irq_data_get_irq_chip(data);
|
|
|
|
@@ -178,9 +178,19 @@ static void irq_validate_effective_affinity(struct irq_data *data)
|
|
return;
|
|
pr_warn_once("irq_chip %s did not update eff. affinity mask of irq %u\n",
|
|
chip->name, data->irq);
|
|
-#endif
|
|
}
|
|
|
|
+static inline void irq_init_effective_affinity(struct irq_data *data,
|
|
+ const struct cpumask *mask)
|
|
+{
|
|
+ cpumask_copy(irq_data_get_effective_affinity_mask(data), mask);
|
|
+}
|
|
+#else
|
|
+static inline void irq_validate_effective_affinity(struct irq_data *data) { }
|
|
+static inline void irq_init_effective_affinity(struct irq_data *data,
|
|
+ const struct cpumask *mask) { }
|
|
+#endif
|
|
+
|
|
int irq_do_set_affinity(struct irq_data *data, const struct cpumask *mask,
|
|
bool force)
|
|
{
|
|
@@ -205,6 +215,30 @@ int irq_do_set_affinity(struct irq_data *data, const struct cpumask *mask,
|
|
return ret;
|
|
}
|
|
|
|
+static bool irq_set_affinity_deactivated(struct irq_data *data,
|
|
+ const struct cpumask *mask, bool force)
|
|
+{
|
|
+ struct irq_desc *desc = irq_data_to_desc(data);
|
|
+
|
|
+ /*
|
|
+ * Handle irq chips which can handle affinity only in activated
|
|
+ * state correctly
|
|
+ *
|
|
+ * If the interrupt is not yet activated, just store the affinity
|
|
+ * mask and do not call the chip driver at all. On activation the
|
|
+ * driver has to make sure anyway that the interrupt is in a
|
|
+ * useable state so startup works.
|
|
+ */
|
|
+ if (!IS_ENABLED(CONFIG_IRQ_DOMAIN_HIERARCHY) ||
|
|
+ irqd_is_activated(data) || !irqd_affinity_on_activate(data))
|
|
+ return false;
|
|
+
|
|
+ cpumask_copy(desc->irq_common_data.affinity, mask);
|
|
+ irq_init_effective_affinity(data, mask);
|
|
+ irqd_set(data, IRQD_AFFINITY_SET);
|
|
+ return true;
|
|
+}
|
|
+
|
|
int irq_set_affinity_locked(struct irq_data *data, const struct cpumask *mask,
|
|
bool force)
|
|
{
|
|
@@ -215,6 +249,9 @@ int irq_set_affinity_locked(struct irq_data *data, const struct cpumask *mask,
|
|
if (!chip || !chip->irq_set_affinity)
|
|
return -EINVAL;
|
|
|
|
+ if (irq_set_affinity_deactivated(data, mask, force))
|
|
+ return 0;
|
|
+
|
|
if (irq_can_move_pcntxt(data)) {
|
|
ret = irq_do_set_affinity(data, mask, force);
|
|
} else {
|
|
diff --git a/kernel/kprobes.c b/kernel/kprobes.c
|
|
index f2d2194b51ca3..7b3a5c35904a0 100644
|
|
--- a/kernel/kprobes.c
|
|
+++ b/kernel/kprobes.c
|
|
@@ -2134,6 +2134,13 @@ static void kill_kprobe(struct kprobe *p)
|
|
* the original probed function (which will be freed soon) any more.
|
|
*/
|
|
arch_remove_kprobe(p);
|
|
+
|
|
+ /*
|
|
+ * The module is going away. We should disarm the kprobe which
|
|
+ * is using ftrace.
|
|
+ */
|
|
+ if (kprobe_ftrace(p))
|
|
+ disarm_kprobe_ftrace(p);
|
|
}
|
|
|
|
/* Disable one kprobe */
|
|
diff --git a/kernel/sched/topology.c b/kernel/sched/topology.c
|
|
index 867d173dab482..152ffe0c24330 100644
|
|
--- a/kernel/sched/topology.c
|
|
+++ b/kernel/sched/topology.c
|
|
@@ -1117,7 +1117,7 @@ sd_init(struct sched_domain_topology_level *tl,
|
|
sd_flags = (*tl->sd_flags)();
|
|
if (WARN_ONCE(sd_flags & ~TOPOLOGY_SD_FLAGS,
|
|
"wrong sd_flags in topology description\n"))
|
|
- sd_flags &= ~TOPOLOGY_SD_FLAGS;
|
|
+ sd_flags &= TOPOLOGY_SD_FLAGS;
|
|
|
|
*sd = (struct sched_domain){
|
|
.min_interval = sd_weight,
|
|
diff --git a/kernel/trace/ftrace.c b/kernel/trace/ftrace.c
|
|
index 8a8d92a8045b1..7cbfccd2fb031 100644
|
|
--- a/kernel/trace/ftrace.c
|
|
+++ b/kernel/trace/ftrace.c
|
|
@@ -5721,8 +5721,11 @@ static int referenced_filters(struct dyn_ftrace *rec)
|
|
int cnt = 0;
|
|
|
|
for (ops = ftrace_ops_list; ops != &ftrace_list_end; ops = ops->next) {
|
|
- if (ops_references_rec(ops, rec))
|
|
- cnt++;
|
|
+ if (ops_references_rec(ops, rec)) {
|
|
+ cnt++;
|
|
+ if (ops->flags & FTRACE_OPS_FL_SAVE_REGS)
|
|
+ rec->flags |= FTRACE_FL_REGS;
|
|
+ }
|
|
}
|
|
|
|
return cnt;
|
|
@@ -5871,8 +5874,8 @@ void ftrace_module_enable(struct module *mod)
|
|
if (ftrace_start_up)
|
|
cnt += referenced_filters(rec);
|
|
|
|
- /* This clears FTRACE_FL_DISABLED */
|
|
- rec->flags = cnt;
|
|
+ rec->flags &= ~FTRACE_FL_DISABLED;
|
|
+ rec->flags += cnt;
|
|
|
|
if (ftrace_start_up && cnt) {
|
|
int failed = __ftrace_replace_code(rec, 1);
|
|
@@ -6239,12 +6242,12 @@ void ftrace_pid_follow_fork(struct trace_array *tr, bool enable)
|
|
if (enable) {
|
|
register_trace_sched_process_fork(ftrace_pid_follow_sched_process_fork,
|
|
tr);
|
|
- register_trace_sched_process_exit(ftrace_pid_follow_sched_process_exit,
|
|
+ register_trace_sched_process_free(ftrace_pid_follow_sched_process_exit,
|
|
tr);
|
|
} else {
|
|
unregister_trace_sched_process_fork(ftrace_pid_follow_sched_process_fork,
|
|
tr);
|
|
- unregister_trace_sched_process_exit(ftrace_pid_follow_sched_process_exit,
|
|
+ unregister_trace_sched_process_free(ftrace_pid_follow_sched_process_exit,
|
|
tr);
|
|
}
|
|
}
|
|
diff --git a/kernel/trace/trace_events.c b/kernel/trace/trace_events.c
|
|
index 421166a39253a..e72a44ecb81da 100644
|
|
--- a/kernel/trace/trace_events.c
|
|
+++ b/kernel/trace/trace_events.c
|
|
@@ -533,12 +533,12 @@ void trace_event_follow_fork(struct trace_array *tr, bool enable)
|
|
if (enable) {
|
|
register_trace_prio_sched_process_fork(event_filter_pid_sched_process_fork,
|
|
tr, INT_MIN);
|
|
- register_trace_prio_sched_process_exit(event_filter_pid_sched_process_exit,
|
|
+ register_trace_prio_sched_process_free(event_filter_pid_sched_process_exit,
|
|
tr, INT_MAX);
|
|
} else {
|
|
unregister_trace_sched_process_fork(event_filter_pid_sched_process_fork,
|
|
tr);
|
|
- unregister_trace_sched_process_exit(event_filter_pid_sched_process_exit,
|
|
+ unregister_trace_sched_process_free(event_filter_pid_sched_process_exit,
|
|
tr);
|
|
}
|
|
}
|
|
diff --git a/kernel/trace/trace_hwlat.c b/kernel/trace/trace_hwlat.c
|
|
index bff6c033d70e2..64a98a5bb6410 100644
|
|
--- a/kernel/trace/trace_hwlat.c
|
|
+++ b/kernel/trace/trace_hwlat.c
|
|
@@ -272,6 +272,7 @@ static bool disable_migrate;
|
|
static void move_to_next_cpu(void)
|
|
{
|
|
struct cpumask *current_mask = &save_cpumask;
|
|
+ struct trace_array *tr = hwlat_trace;
|
|
int next_cpu;
|
|
|
|
if (disable_migrate)
|
|
@@ -285,7 +286,7 @@ static void move_to_next_cpu(void)
|
|
goto disable;
|
|
|
|
get_online_cpus();
|
|
- cpumask_and(current_mask, cpu_online_mask, tracing_buffer_mask);
|
|
+ cpumask_and(current_mask, cpu_online_mask, tr->tracing_cpumask);
|
|
next_cpu = cpumask_next(smp_processor_id(), current_mask);
|
|
put_online_cpus();
|
|
|
|
@@ -359,7 +360,7 @@ static int start_kthread(struct trace_array *tr)
|
|
/* Just pick the first CPU on first iteration */
|
|
current_mask = &save_cpumask;
|
|
get_online_cpus();
|
|
- cpumask_and(current_mask, cpu_online_mask, tracing_buffer_mask);
|
|
+ cpumask_and(current_mask, cpu_online_mask, tr->tracing_cpumask);
|
|
put_online_cpus();
|
|
next_cpu = cpumask_first(current_mask);
|
|
|
|
diff --git a/lib/dynamic_debug.c b/lib/dynamic_debug.c
|
|
index c7c96bc7654af..91c451e0f4741 100644
|
|
--- a/lib/dynamic_debug.c
|
|
+++ b/lib/dynamic_debug.c
|
|
@@ -85,22 +85,22 @@ static struct { unsigned flag:8; char opt_char; } opt_array[] = {
|
|
{ _DPRINTK_FLAGS_NONE, '_' },
|
|
};
|
|
|
|
+struct flagsbuf { char buf[ARRAY_SIZE(opt_array)+1]; };
|
|
+
|
|
/* format a string into buf[] which describes the _ddebug's flags */
|
|
-static char *ddebug_describe_flags(struct _ddebug *dp, char *buf,
|
|
- size_t maxlen)
|
|
+static char *ddebug_describe_flags(unsigned int flags, struct flagsbuf *fb)
|
|
{
|
|
- char *p = buf;
|
|
+ char *p = fb->buf;
|
|
int i;
|
|
|
|
- BUG_ON(maxlen < 6);
|
|
for (i = 0; i < ARRAY_SIZE(opt_array); ++i)
|
|
- if (dp->flags & opt_array[i].flag)
|
|
+ if (flags & opt_array[i].flag)
|
|
*p++ = opt_array[i].opt_char;
|
|
- if (p == buf)
|
|
+ if (p == fb->buf)
|
|
*p++ = '_';
|
|
*p = '\0';
|
|
|
|
- return buf;
|
|
+ return fb->buf;
|
|
}
|
|
|
|
#define vpr_info(fmt, ...) \
|
|
@@ -142,7 +142,7 @@ static int ddebug_change(const struct ddebug_query *query,
|
|
struct ddebug_table *dt;
|
|
unsigned int newflags;
|
|
unsigned int nfound = 0;
|
|
- char flagbuf[10];
|
|
+ struct flagsbuf fbuf;
|
|
|
|
/* search for matching ddebugs */
|
|
mutex_lock(&ddebug_lock);
|
|
@@ -199,8 +199,7 @@ static int ddebug_change(const struct ddebug_query *query,
|
|
vpr_info("changed %s:%d [%s]%s =%s\n",
|
|
trim_prefix(dp->filename), dp->lineno,
|
|
dt->mod_name, dp->function,
|
|
- ddebug_describe_flags(dp, flagbuf,
|
|
- sizeof(flagbuf)));
|
|
+ ddebug_describe_flags(dp->flags, &fbuf));
|
|
}
|
|
}
|
|
mutex_unlock(&ddebug_lock);
|
|
@@ -779,7 +778,7 @@ static int ddebug_proc_show(struct seq_file *m, void *p)
|
|
{
|
|
struct ddebug_iter *iter = m->private;
|
|
struct _ddebug *dp = p;
|
|
- char flagsbuf[10];
|
|
+ struct flagsbuf flags;
|
|
|
|
vpr_info("called m=%p p=%p\n", m, p);
|
|
|
|
@@ -792,7 +791,7 @@ static int ddebug_proc_show(struct seq_file *m, void *p)
|
|
seq_printf(m, "%s:%u [%s]%s =%s \"",
|
|
trim_prefix(dp->filename), dp->lineno,
|
|
iter->table->mod_name, dp->function,
|
|
- ddebug_describe_flags(dp, flagsbuf, sizeof(flagsbuf)));
|
|
+ ddebug_describe_flags(dp->flags, &flags));
|
|
seq_escape(m, dp->format, "\t\r\n\"");
|
|
seq_puts(m, "\"\n");
|
|
|
|
diff --git a/lib/test_kmod.c b/lib/test_kmod.c
|
|
index cf619795a1822..c0ce0156d54bb 100644
|
|
--- a/lib/test_kmod.c
|
|
+++ b/lib/test_kmod.c
|
|
@@ -747,7 +747,7 @@ static int trigger_config_run_type(struct kmod_test_device *test_dev,
|
|
break;
|
|
case TEST_KMOD_FS_TYPE:
|
|
kfree_const(config->test_fs);
|
|
- config->test_driver = NULL;
|
|
+ config->test_fs = NULL;
|
|
copied = config_copy_test_fs(config, test_str,
|
|
strlen(test_str));
|
|
break;
|
|
diff --git a/mm/khugepaged.c b/mm/khugepaged.c
|
|
index acf66c5dc9bd9..04b4c38d0c184 100644
|
|
--- a/mm/khugepaged.c
|
|
+++ b/mm/khugepaged.c
|
|
@@ -1252,6 +1252,7 @@ static void collect_mm_slot(struct mm_slot *mm_slot)
|
|
static void retract_page_tables(struct address_space *mapping, pgoff_t pgoff)
|
|
{
|
|
struct vm_area_struct *vma;
|
|
+ struct mm_struct *mm;
|
|
unsigned long addr;
|
|
pmd_t *pmd, _pmd;
|
|
|
|
@@ -1265,7 +1266,8 @@ static void retract_page_tables(struct address_space *mapping, pgoff_t pgoff)
|
|
continue;
|
|
if (vma->vm_end < addr + HPAGE_PMD_SIZE)
|
|
continue;
|
|
- pmd = mm_find_pmd(vma->vm_mm, addr);
|
|
+ mm = vma->vm_mm;
|
|
+ pmd = mm_find_pmd(mm, addr);
|
|
if (!pmd)
|
|
continue;
|
|
/*
|
|
@@ -1274,14 +1276,16 @@ static void retract_page_tables(struct address_space *mapping, pgoff_t pgoff)
|
|
* re-fault. Not ideal, but it's more important to not disturb
|
|
* the system too much.
|
|
*/
|
|
- if (down_write_trylock(&vma->vm_mm->mmap_sem)) {
|
|
- spinlock_t *ptl = pmd_lock(vma->vm_mm, pmd);
|
|
- /* assume page table is clear */
|
|
- _pmd = pmdp_collapse_flush(vma, addr, pmd);
|
|
- spin_unlock(ptl);
|
|
- up_write(&vma->vm_mm->mmap_sem);
|
|
- atomic_long_dec(&vma->vm_mm->nr_ptes);
|
|
- pte_free(vma->vm_mm, pmd_pgtable(_pmd));
|
|
+ if (down_write_trylock(&mm->mmap_sem)) {
|
|
+ if (!khugepaged_test_exit(mm)) {
|
|
+ spinlock_t *ptl = pmd_lock(mm, pmd);
|
|
+ /* assume page table is clear */
|
|
+ _pmd = pmdp_collapse_flush(vma, addr, pmd);
|
|
+ spin_unlock(ptl);
|
|
+ atomic_long_dec(&mm->nr_ptes);
|
|
+ pte_free(mm, pmd_pgtable(_pmd));
|
|
+ }
|
|
+ up_write(&mm->mmap_sem);
|
|
}
|
|
}
|
|
i_mmap_unlock_write(mapping);
|
|
diff --git a/mm/mmap.c b/mm/mmap.c
|
|
index 8c6ed06983f9e..724b7c4f1a5b5 100644
|
|
--- a/mm/mmap.c
|
|
+++ b/mm/mmap.c
|
|
@@ -3065,6 +3065,7 @@ void exit_mmap(struct mm_struct *mm)
|
|
if (vma->vm_flags & VM_ACCOUNT)
|
|
nr_accounted += vma_pages(vma);
|
|
vma = remove_vma(vma);
|
|
+ cond_resched();
|
|
}
|
|
vm_unacct_memory(nr_accounted);
|
|
}
|
|
diff --git a/net/9p/trans_fd.c b/net/9p/trans_fd.c
|
|
index 32de8afbfbf8e..9f020559c1928 100644
|
|
--- a/net/9p/trans_fd.c
|
|
+++ b/net/9p/trans_fd.c
|
|
@@ -829,20 +829,28 @@ static int p9_fd_open(struct p9_client *client, int rfd, int wfd)
|
|
return -ENOMEM;
|
|
|
|
ts->rd = fget(rfd);
|
|
+ if (!ts->rd)
|
|
+ goto out_free_ts;
|
|
+ if (!(ts->rd->f_mode & FMODE_READ))
|
|
+ goto out_put_rd;
|
|
ts->wr = fget(wfd);
|
|
- if (!ts->rd || !ts->wr) {
|
|
- if (ts->rd)
|
|
- fput(ts->rd);
|
|
- if (ts->wr)
|
|
- fput(ts->wr);
|
|
- kfree(ts);
|
|
- return -EIO;
|
|
- }
|
|
+ if (!ts->wr)
|
|
+ goto out_put_rd;
|
|
+ if (!(ts->wr->f_mode & FMODE_WRITE))
|
|
+ goto out_put_wr;
|
|
|
|
client->trans = ts;
|
|
client->status = Connected;
|
|
|
|
return 0;
|
|
+
|
|
+out_put_wr:
|
|
+ fput(ts->wr);
|
|
+out_put_rd:
|
|
+ fput(ts->rd);
|
|
+out_free_ts:
|
|
+ kfree(ts);
|
|
+ return -EIO;
|
|
}
|
|
|
|
static int p9_socket_open(struct p9_client *client, struct socket *csocket)
|
|
diff --git a/net/bluetooth/6lowpan.c b/net/bluetooth/6lowpan.c
|
|
index 357475cceec61..9a75f9b00b512 100644
|
|
--- a/net/bluetooth/6lowpan.c
|
|
+++ b/net/bluetooth/6lowpan.c
|
|
@@ -57,6 +57,7 @@ static bool enable_6lowpan;
|
|
/* We are listening incoming connections via this channel
|
|
*/
|
|
static struct l2cap_chan *listen_chan;
|
|
+static DEFINE_MUTEX(set_lock);
|
|
|
|
struct lowpan_peer {
|
|
struct list_head list;
|
|
@@ -1082,12 +1083,14 @@ static void do_enable_set(struct work_struct *work)
|
|
|
|
enable_6lowpan = set_enable->flag;
|
|
|
|
+ mutex_lock(&set_lock);
|
|
if (listen_chan) {
|
|
l2cap_chan_close(listen_chan, 0);
|
|
l2cap_chan_put(listen_chan);
|
|
}
|
|
|
|
listen_chan = bt_6lowpan_listen();
|
|
+ mutex_unlock(&set_lock);
|
|
|
|
kfree(set_enable);
|
|
}
|
|
@@ -1139,11 +1142,13 @@ static ssize_t lowpan_control_write(struct file *fp,
|
|
if (ret == -EINVAL)
|
|
return ret;
|
|
|
|
+ mutex_lock(&set_lock);
|
|
if (listen_chan) {
|
|
l2cap_chan_close(listen_chan, 0);
|
|
l2cap_chan_put(listen_chan);
|
|
listen_chan = NULL;
|
|
}
|
|
+ mutex_unlock(&set_lock);
|
|
|
|
if (conn) {
|
|
struct lowpan_peer *peer;
|
|
diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c
|
|
index 56e4ae7d7f638..70b8e2de40cf4 100644
|
|
--- a/net/bluetooth/hci_event.c
|
|
+++ b/net/bluetooth/hci_event.c
|
|
@@ -2094,7 +2094,7 @@ static void hci_inquiry_result_evt(struct hci_dev *hdev, struct sk_buff *skb)
|
|
|
|
BT_DBG("%s num_rsp %d", hdev->name, num_rsp);
|
|
|
|
- if (!num_rsp)
|
|
+ if (!num_rsp || skb->len < num_rsp * sizeof(*info) + 1)
|
|
return;
|
|
|
|
if (hci_dev_test_flag(hdev, HCI_PERIODIC_INQ))
|
|
@@ -3623,6 +3623,9 @@ static void hci_inquiry_result_with_rssi_evt(struct hci_dev *hdev,
|
|
struct inquiry_info_with_rssi_and_pscan_mode *info;
|
|
info = (void *) (skb->data + 1);
|
|
|
|
+ if (skb->len < num_rsp * sizeof(*info) + 1)
|
|
+ goto unlock;
|
|
+
|
|
for (; num_rsp; num_rsp--, info++) {
|
|
u32 flags;
|
|
|
|
@@ -3644,6 +3647,9 @@ static void hci_inquiry_result_with_rssi_evt(struct hci_dev *hdev,
|
|
} else {
|
|
struct inquiry_info_with_rssi *info = (void *) (skb->data + 1);
|
|
|
|
+ if (skb->len < num_rsp * sizeof(*info) + 1)
|
|
+ goto unlock;
|
|
+
|
|
for (; num_rsp; num_rsp--, info++) {
|
|
u32 flags;
|
|
|
|
@@ -3664,6 +3670,7 @@ static void hci_inquiry_result_with_rssi_evt(struct hci_dev *hdev,
|
|
}
|
|
}
|
|
|
|
+unlock:
|
|
hci_dev_unlock(hdev);
|
|
}
|
|
|
|
@@ -3826,7 +3833,7 @@ static void hci_extended_inquiry_result_evt(struct hci_dev *hdev,
|
|
|
|
BT_DBG("%s num_rsp %d", hdev->name, num_rsp);
|
|
|
|
- if (!num_rsp)
|
|
+ if (!num_rsp || skb->len < num_rsp * sizeof(*info) + 1)
|
|
return;
|
|
|
|
if (hci_dev_test_flag(hdev, HCI_PERIODIC_INQ))
|
|
diff --git a/net/compat.c b/net/compat.c
|
|
index 790851e70dabb..45349658ed010 100644
|
|
--- a/net/compat.c
|
|
+++ b/net/compat.c
|
|
@@ -289,6 +289,7 @@ void scm_detach_fds_compat(struct msghdr *kmsg, struct scm_cookie *scm)
|
|
break;
|
|
}
|
|
/* Bump the usage count and install the file. */
|
|
+ __receive_sock(fp[i]);
|
|
fd_install(new_fd, get_file(fp[i]));
|
|
}
|
|
|
|
diff --git a/net/core/sock.c b/net/core/sock.c
|
|
index af1201676abc3..3b65fedf77ca7 100644
|
|
--- a/net/core/sock.c
|
|
+++ b/net/core/sock.c
|
|
@@ -2563,6 +2563,27 @@ int sock_no_mmap(struct file *file, struct socket *sock, struct vm_area_struct *
|
|
}
|
|
EXPORT_SYMBOL(sock_no_mmap);
|
|
|
|
+/*
|
|
+ * When a file is received (via SCM_RIGHTS, etc), we must bump the
|
|
+ * various sock-based usage counts.
|
|
+ */
|
|
+void __receive_sock(struct file *file)
|
|
+{
|
|
+ struct socket *sock;
|
|
+ int error;
|
|
+
|
|
+ /*
|
|
+ * The resulting value of "error" is ignored here since we only
|
|
+ * need to take action when the file is a socket and testing
|
|
+ * "sock" for NULL is sufficient.
|
|
+ */
|
|
+ sock = sock_from_file(file, &error);
|
|
+ if (sock) {
|
|
+ sock_update_netprioidx(&sock->sk->sk_cgrp_data);
|
|
+ sock_update_classid(&sock->sk->sk_cgrp_data);
|
|
+ }
|
|
+}
|
|
+
|
|
ssize_t sock_no_sendpage(struct socket *sock, struct page *page, int offset, size_t size, int flags)
|
|
{
|
|
ssize_t res;
|
|
diff --git a/net/ipv4/fib_trie.c b/net/ipv4/fib_trie.c
|
|
index 3f9509679f0e1..0c8fcc050ad23 100644
|
|
--- a/net/ipv4/fib_trie.c
|
|
+++ b/net/ipv4/fib_trie.c
|
|
@@ -1729,7 +1729,7 @@ struct fib_table *fib_trie_unmerge(struct fib_table *oldtb)
|
|
while ((l = leaf_walk_rcu(&tp, key)) != NULL) {
|
|
struct key_vector *local_l = NULL, *local_tp;
|
|
|
|
- hlist_for_each_entry_rcu(fa, &l->leaf, fa_list) {
|
|
+ hlist_for_each_entry(fa, &l->leaf, fa_list) {
|
|
struct fib_alias *new_fa;
|
|
|
|
if (local_tb->tb_id != fa->tb_id)
|
|
diff --git a/net/ipv4/gre_offload.c b/net/ipv4/gre_offload.c
|
|
index 6a7d980105f60..095c30863745a 100644
|
|
--- a/net/ipv4/gre_offload.c
|
|
+++ b/net/ipv4/gre_offload.c
|
|
@@ -19,12 +19,12 @@ static struct sk_buff *gre_gso_segment(struct sk_buff *skb,
|
|
netdev_features_t features)
|
|
{
|
|
int tnl_hlen = skb_inner_mac_header(skb) - skb_transport_header(skb);
|
|
+ bool need_csum, need_recompute_csum, gso_partial;
|
|
struct sk_buff *segs = ERR_PTR(-EINVAL);
|
|
u16 mac_offset = skb->mac_header;
|
|
__be16 protocol = skb->protocol;
|
|
u16 mac_len = skb->mac_len;
|
|
int gre_offset, outer_hlen;
|
|
- bool need_csum, gso_partial;
|
|
|
|
if (!skb->encapsulation)
|
|
goto out;
|
|
@@ -45,6 +45,7 @@ static struct sk_buff *gre_gso_segment(struct sk_buff *skb,
|
|
skb->protocol = skb->inner_protocol;
|
|
|
|
need_csum = !!(skb_shinfo(skb)->gso_type & SKB_GSO_GRE_CSUM);
|
|
+ need_recompute_csum = skb->csum_not_inet;
|
|
skb->encap_hdr_csum = need_csum;
|
|
|
|
features &= skb->dev->hw_enc_features;
|
|
@@ -102,7 +103,15 @@ static struct sk_buff *gre_gso_segment(struct sk_buff *skb,
|
|
}
|
|
|
|
*(pcsum + 1) = 0;
|
|
- *pcsum = gso_make_checksum(skb, 0);
|
|
+ if (need_recompute_csum && !skb_is_gso(skb)) {
|
|
+ __wsum csum;
|
|
+
|
|
+ csum = skb_checksum(skb, gre_offset,
|
|
+ skb->len - gre_offset, 0);
|
|
+ *pcsum = csum_fold(csum);
|
|
+ } else {
|
|
+ *pcsum = gso_make_checksum(skb, 0);
|
|
+ }
|
|
} while ((skb = skb->next));
|
|
out:
|
|
return segs;
|
|
diff --git a/net/ipv4/inet_connection_sock.c b/net/ipv4/inet_connection_sock.c
|
|
index 7826fba34b14b..08ba0f91f2aba 100644
|
|
--- a/net/ipv4/inet_connection_sock.c
|
|
+++ b/net/ipv4/inet_connection_sock.c
|
|
@@ -276,51 +276,12 @@ static inline int sk_reuseport_match(struct inet_bind_bucket *tb,
|
|
ipv6_only_sock(sk), true);
|
|
}
|
|
|
|
-/* Obtain a reference to a local port for the given sock,
|
|
- * if snum is zero it means select any available local port.
|
|
- * We try to allocate an odd port (and leave even ports for connect())
|
|
- */
|
|
-int inet_csk_get_port(struct sock *sk, unsigned short snum)
|
|
+void inet_csk_update_fastreuse(struct inet_bind_bucket *tb,
|
|
+ struct sock *sk)
|
|
{
|
|
- bool reuse = sk->sk_reuse && sk->sk_state != TCP_LISTEN;
|
|
- struct inet_hashinfo *hinfo = sk->sk_prot->h.hashinfo;
|
|
- int ret = 1, port = snum;
|
|
- struct inet_bind_hashbucket *head;
|
|
- struct net *net = sock_net(sk);
|
|
- struct inet_bind_bucket *tb = NULL;
|
|
kuid_t uid = sock_i_uid(sk);
|
|
+ bool reuse = sk->sk_reuse && sk->sk_state != TCP_LISTEN;
|
|
|
|
- if (!port) {
|
|
- head = inet_csk_find_open_port(sk, &tb, &port);
|
|
- if (!head)
|
|
- return ret;
|
|
- if (!tb)
|
|
- goto tb_not_found;
|
|
- goto success;
|
|
- }
|
|
- head = &hinfo->bhash[inet_bhashfn(net, port,
|
|
- hinfo->bhash_size)];
|
|
- spin_lock_bh(&head->lock);
|
|
- inet_bind_bucket_for_each(tb, &head->chain)
|
|
- if (net_eq(ib_net(tb), net) && tb->port == port)
|
|
- goto tb_found;
|
|
-tb_not_found:
|
|
- tb = inet_bind_bucket_create(hinfo->bind_bucket_cachep,
|
|
- net, head, port);
|
|
- if (!tb)
|
|
- goto fail_unlock;
|
|
-tb_found:
|
|
- if (!hlist_empty(&tb->owners)) {
|
|
- if (sk->sk_reuse == SK_FORCE_REUSE)
|
|
- goto success;
|
|
-
|
|
- if ((tb->fastreuse > 0 && reuse) ||
|
|
- sk_reuseport_match(tb, sk))
|
|
- goto success;
|
|
- if (inet_csk_bind_conflict(sk, tb, true, true))
|
|
- goto fail_unlock;
|
|
- }
|
|
-success:
|
|
if (hlist_empty(&tb->owners)) {
|
|
tb->fastreuse = reuse;
|
|
if (sk->sk_reuseport) {
|
|
@@ -364,6 +325,54 @@ success:
|
|
tb->fastreuseport = 0;
|
|
}
|
|
}
|
|
+}
|
|
+
|
|
+/* Obtain a reference to a local port for the given sock,
|
|
+ * if snum is zero it means select any available local port.
|
|
+ * We try to allocate an odd port (and leave even ports for connect())
|
|
+ */
|
|
+int inet_csk_get_port(struct sock *sk, unsigned short snum)
|
|
+{
|
|
+ bool reuse = sk->sk_reuse && sk->sk_state != TCP_LISTEN;
|
|
+ struct inet_hashinfo *hinfo = sk->sk_prot->h.hashinfo;
|
|
+ int ret = 1, port = snum;
|
|
+ struct inet_bind_hashbucket *head;
|
|
+ struct net *net = sock_net(sk);
|
|
+ struct inet_bind_bucket *tb = NULL;
|
|
+
|
|
+ if (!port) {
|
|
+ head = inet_csk_find_open_port(sk, &tb, &port);
|
|
+ if (!head)
|
|
+ return ret;
|
|
+ if (!tb)
|
|
+ goto tb_not_found;
|
|
+ goto success;
|
|
+ }
|
|
+ head = &hinfo->bhash[inet_bhashfn(net, port,
|
|
+ hinfo->bhash_size)];
|
|
+ spin_lock_bh(&head->lock);
|
|
+ inet_bind_bucket_for_each(tb, &head->chain)
|
|
+ if (net_eq(ib_net(tb), net) && tb->port == port)
|
|
+ goto tb_found;
|
|
+tb_not_found:
|
|
+ tb = inet_bind_bucket_create(hinfo->bind_bucket_cachep,
|
|
+ net, head, port);
|
|
+ if (!tb)
|
|
+ goto fail_unlock;
|
|
+tb_found:
|
|
+ if (!hlist_empty(&tb->owners)) {
|
|
+ if (sk->sk_reuse == SK_FORCE_REUSE)
|
|
+ goto success;
|
|
+
|
|
+ if ((tb->fastreuse > 0 && reuse) ||
|
|
+ sk_reuseport_match(tb, sk))
|
|
+ goto success;
|
|
+ if (inet_csk_bind_conflict(sk, tb, true, true))
|
|
+ goto fail_unlock;
|
|
+ }
|
|
+success:
|
|
+ inet_csk_update_fastreuse(tb, sk);
|
|
+
|
|
if (!inet_csk(sk)->icsk_bind_hash)
|
|
inet_bind_hash(sk, tb, port);
|
|
WARN_ON(inet_csk(sk)->icsk_bind_hash != tb);
|
|
diff --git a/net/ipv4/inet_hashtables.c b/net/ipv4/inet_hashtables.c
|
|
index 0af13f5bdc9a3..8a54babf5c903 100644
|
|
--- a/net/ipv4/inet_hashtables.c
|
|
+++ b/net/ipv4/inet_hashtables.c
|
|
@@ -160,6 +160,7 @@ int __inet_inherit_port(const struct sock *sk, struct sock *child)
|
|
return -ENOMEM;
|
|
}
|
|
}
|
|
+ inet_csk_update_fastreuse(tb, child);
|
|
}
|
|
inet_bind_hash(child, tb, port);
|
|
spin_unlock(&head->lock);
|
|
diff --git a/net/ipv6/anycast.c b/net/ipv6/anycast.c
|
|
index 0bbab8a4b5d84..4d8b3d1d530bd 100644
|
|
--- a/net/ipv6/anycast.c
|
|
+++ b/net/ipv6/anycast.c
|
|
@@ -170,7 +170,7 @@ int ipv6_sock_ac_drop(struct sock *sk, int ifindex, const struct in6_addr *addr)
|
|
return 0;
|
|
}
|
|
|
|
-void ipv6_sock_ac_close(struct sock *sk)
|
|
+void __ipv6_sock_ac_close(struct sock *sk)
|
|
{
|
|
struct ipv6_pinfo *np = inet6_sk(sk);
|
|
struct net_device *dev = NULL;
|
|
@@ -178,10 +178,7 @@ void ipv6_sock_ac_close(struct sock *sk)
|
|
struct net *net = sock_net(sk);
|
|
int prev_index;
|
|
|
|
- if (!np->ipv6_ac_list)
|
|
- return;
|
|
-
|
|
- rtnl_lock();
|
|
+ ASSERT_RTNL();
|
|
pac = np->ipv6_ac_list;
|
|
np->ipv6_ac_list = NULL;
|
|
|
|
@@ -198,6 +195,16 @@ void ipv6_sock_ac_close(struct sock *sk)
|
|
sock_kfree_s(sk, pac, sizeof(*pac));
|
|
pac = next;
|
|
}
|
|
+}
|
|
+
|
|
+void ipv6_sock_ac_close(struct sock *sk)
|
|
+{
|
|
+ struct ipv6_pinfo *np = inet6_sk(sk);
|
|
+
|
|
+ if (!np->ipv6_ac_list)
|
|
+ return;
|
|
+ rtnl_lock();
|
|
+ __ipv6_sock_ac_close(sk);
|
|
rtnl_unlock();
|
|
}
|
|
|
|
diff --git a/net/ipv6/ipv6_sockglue.c b/net/ipv6/ipv6_sockglue.c
|
|
index c183222967d09..3f44316db51b0 100644
|
|
--- a/net/ipv6/ipv6_sockglue.c
|
|
+++ b/net/ipv6/ipv6_sockglue.c
|
|
@@ -207,6 +207,7 @@ static int do_ipv6_setsockopt(struct sock *sk, int level, int optname,
|
|
|
|
fl6_free_socklist(sk);
|
|
__ipv6_sock_mc_close(sk);
|
|
+ __ipv6_sock_ac_close(sk);
|
|
|
|
/*
|
|
* Sock is moving from IPv6 to IPv4 (sk_prot), so
|
|
diff --git a/net/mac80211/sta_info.c b/net/mac80211/sta_info.c
|
|
index 77ab9cc1a230a..6af5fda6461ce 100644
|
|
--- a/net/mac80211/sta_info.c
|
|
+++ b/net/mac80211/sta_info.c
|
|
@@ -952,7 +952,7 @@ static void __sta_info_destroy_part2(struct sta_info *sta)
|
|
might_sleep();
|
|
lockdep_assert_held(&local->sta_mtx);
|
|
|
|
- while (sta->sta_state == IEEE80211_STA_AUTHORIZED) {
|
|
+ if (sta->sta_state == IEEE80211_STA_AUTHORIZED) {
|
|
ret = sta_info_move_state(sta, IEEE80211_STA_ASSOC);
|
|
WARN_ON_ONCE(ret);
|
|
}
|
|
diff --git a/net/netfilter/ipvs/ip_vs_core.c b/net/netfilter/ipvs/ip_vs_core.c
|
|
index 2156571455dbf..a95fe5fe9f046 100644
|
|
--- a/net/netfilter/ipvs/ip_vs_core.c
|
|
+++ b/net/netfilter/ipvs/ip_vs_core.c
|
|
@@ -1916,14 +1916,14 @@ ip_vs_in(struct netns_ipvs *ipvs, unsigned int hooknum, struct sk_buff *skb, int
|
|
|
|
conn_reuse_mode = sysctl_conn_reuse_mode(ipvs);
|
|
if (conn_reuse_mode && !iph.fragoffs && is_new_conn(skb, &iph) && cp) {
|
|
- bool uses_ct = false, resched = false;
|
|
+ bool old_ct = false, resched = false;
|
|
|
|
if (unlikely(sysctl_expire_nodest_conn(ipvs)) && cp->dest &&
|
|
unlikely(!atomic_read(&cp->dest->weight))) {
|
|
resched = true;
|
|
- uses_ct = ip_vs_conn_uses_conntrack(cp, skb);
|
|
+ old_ct = ip_vs_conn_uses_old_conntrack(cp, skb);
|
|
} else if (is_new_conn_expected(cp, conn_reuse_mode)) {
|
|
- uses_ct = ip_vs_conn_uses_conntrack(cp, skb);
|
|
+ old_ct = ip_vs_conn_uses_old_conntrack(cp, skb);
|
|
if (!atomic_read(&cp->n_control)) {
|
|
resched = true;
|
|
} else {
|
|
@@ -1931,15 +1931,17 @@ ip_vs_in(struct netns_ipvs *ipvs, unsigned int hooknum, struct sk_buff *skb, int
|
|
* that uses conntrack while it is still
|
|
* referenced by controlled connection(s).
|
|
*/
|
|
- resched = !uses_ct;
|
|
+ resched = !old_ct;
|
|
}
|
|
}
|
|
|
|
if (resched) {
|
|
+ if (!old_ct)
|
|
+ cp->flags &= ~IP_VS_CONN_F_NFCT;
|
|
if (!atomic_read(&cp->n_control))
|
|
ip_vs_conn_expire_now(cp);
|
|
__ip_vs_conn_put(cp);
|
|
- if (uses_ct)
|
|
+ if (old_ct)
|
|
return NF_DROP;
|
|
cp = NULL;
|
|
}
|
|
diff --git a/net/nfc/rawsock.c b/net/nfc/rawsock.c
|
|
index e2188deb08dc3..b927730d9ab06 100644
|
|
--- a/net/nfc/rawsock.c
|
|
+++ b/net/nfc/rawsock.c
|
|
@@ -344,10 +344,13 @@ static int rawsock_create(struct net *net, struct socket *sock,
|
|
if ((sock->type != SOCK_SEQPACKET) && (sock->type != SOCK_RAW))
|
|
return -ESOCKTNOSUPPORT;
|
|
|
|
- if (sock->type == SOCK_RAW)
|
|
+ if (sock->type == SOCK_RAW) {
|
|
+ if (!capable(CAP_NET_RAW))
|
|
+ return -EPERM;
|
|
sock->ops = &rawsock_raw_ops;
|
|
- else
|
|
+ } else {
|
|
sock->ops = &rawsock_ops;
|
|
+ }
|
|
|
|
sk = sk_alloc(net, PF_NFC, GFP_ATOMIC, nfc_proto->proto, kern);
|
|
if (!sk)
|
|
diff --git a/net/openvswitch/conntrack.c b/net/openvswitch/conntrack.c
|
|
index 737e37b28d93b..a39ef1a048fde 100644
|
|
--- a/net/openvswitch/conntrack.c
|
|
+++ b/net/openvswitch/conntrack.c
|
|
@@ -255,10 +255,6 @@ void ovs_ct_fill_key(const struct sk_buff *skb, struct sw_flow_key *key)
|
|
ovs_ct_update_key(skb, NULL, key, false, false);
|
|
}
|
|
|
|
-#define IN6_ADDR_INITIALIZER(ADDR) \
|
|
- { (ADDR).s6_addr32[0], (ADDR).s6_addr32[1], \
|
|
- (ADDR).s6_addr32[2], (ADDR).s6_addr32[3] }
|
|
-
|
|
int ovs_ct_put_key(const struct sw_flow_key *swkey,
|
|
const struct sw_flow_key *output, struct sk_buff *skb)
|
|
{
|
|
@@ -280,24 +276,30 @@ int ovs_ct_put_key(const struct sw_flow_key *swkey,
|
|
|
|
if (swkey->ct_orig_proto) {
|
|
if (swkey->eth.type == htons(ETH_P_IP)) {
|
|
- struct ovs_key_ct_tuple_ipv4 orig = {
|
|
- output->ipv4.ct_orig.src,
|
|
- output->ipv4.ct_orig.dst,
|
|
- output->ct.orig_tp.src,
|
|
- output->ct.orig_tp.dst,
|
|
- output->ct_orig_proto,
|
|
- };
|
|
+ struct ovs_key_ct_tuple_ipv4 orig;
|
|
+
|
|
+ memset(&orig, 0, sizeof(orig));
|
|
+ orig.ipv4_src = output->ipv4.ct_orig.src;
|
|
+ orig.ipv4_dst = output->ipv4.ct_orig.dst;
|
|
+ orig.src_port = output->ct.orig_tp.src;
|
|
+ orig.dst_port = output->ct.orig_tp.dst;
|
|
+ orig.ipv4_proto = output->ct_orig_proto;
|
|
+
|
|
if (nla_put(skb, OVS_KEY_ATTR_CT_ORIG_TUPLE_IPV4,
|
|
sizeof(orig), &orig))
|
|
return -EMSGSIZE;
|
|
} else if (swkey->eth.type == htons(ETH_P_IPV6)) {
|
|
- struct ovs_key_ct_tuple_ipv6 orig = {
|
|
- IN6_ADDR_INITIALIZER(output->ipv6.ct_orig.src),
|
|
- IN6_ADDR_INITIALIZER(output->ipv6.ct_orig.dst),
|
|
- output->ct.orig_tp.src,
|
|
- output->ct.orig_tp.dst,
|
|
- output->ct_orig_proto,
|
|
- };
|
|
+ struct ovs_key_ct_tuple_ipv6 orig;
|
|
+
|
|
+ memset(&orig, 0, sizeof(orig));
|
|
+ memcpy(orig.ipv6_src, output->ipv6.ct_orig.src.s6_addr32,
|
|
+ sizeof(orig.ipv6_src));
|
|
+ memcpy(orig.ipv6_dst, output->ipv6.ct_orig.dst.s6_addr32,
|
|
+ sizeof(orig.ipv6_dst));
|
|
+ orig.src_port = output->ct.orig_tp.src;
|
|
+ orig.dst_port = output->ct.orig_tp.dst;
|
|
+ orig.ipv6_proto = output->ct_orig_proto;
|
|
+
|
|
if (nla_put(skb, OVS_KEY_ATTR_CT_ORIG_TUPLE_IPV6,
|
|
sizeof(orig), &orig))
|
|
return -EMSGSIZE;
|
|
diff --git a/net/packet/af_packet.c b/net/packet/af_packet.c
|
|
index 102750bd751cc..c2356611b3cba 100644
|
|
--- a/net/packet/af_packet.c
|
|
+++ b/net/packet/af_packet.c
|
|
@@ -989,6 +989,7 @@ static int prb_queue_frozen(struct tpacket_kbdq_core *pkc)
|
|
}
|
|
|
|
static void prb_clear_blk_fill_status(struct packet_ring_buffer *rb)
|
|
+ __releases(&pkc->blk_fill_in_prog_lock)
|
|
{
|
|
struct tpacket_kbdq_core *pkc = GET_PBDQC_FROM_RB(rb);
|
|
atomic_dec(&pkc->blk_fill_in_prog);
|
|
@@ -1036,6 +1037,7 @@ static void prb_fill_curr_block(char *curr,
|
|
struct tpacket_kbdq_core *pkc,
|
|
struct tpacket_block_desc *pbd,
|
|
unsigned int len)
|
|
+ __acquires(&pkc->blk_fill_in_prog_lock)
|
|
{
|
|
struct tpacket3_hdr *ppd;
|
|
|
|
@@ -2311,8 +2313,11 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev,
|
|
if (do_vnet &&
|
|
virtio_net_hdr_from_skb(skb, h.raw + macoff -
|
|
sizeof(struct virtio_net_hdr),
|
|
- vio_le(), true, 0))
|
|
+ vio_le(), true, 0)) {
|
|
+ if (po->tp_version == TPACKET_V3)
|
|
+ prb_clear_blk_fill_status(&po->rx_ring);
|
|
goto drop_n_account;
|
|
+ }
|
|
|
|
if (po->tp_version <= TPACKET_V2) {
|
|
packet_increment_rx_head(po, &po->rx_ring);
|
|
@@ -2418,7 +2423,7 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev,
|
|
__clear_bit(slot_id, po->rx_ring.rx_owner_map);
|
|
spin_unlock(&sk->sk_receive_queue.lock);
|
|
sk->sk_data_ready(sk);
|
|
- } else {
|
|
+ } else if (po->tp_version == TPACKET_V3) {
|
|
prb_clear_blk_fill_status(&po->rx_ring);
|
|
}
|
|
|
|
diff --git a/net/rxrpc/call_object.c b/net/rxrpc/call_object.c
|
|
index 7021725fa38a7..1c98a026b41ac 100644
|
|
--- a/net/rxrpc/call_object.c
|
|
+++ b/net/rxrpc/call_object.c
|
|
@@ -275,7 +275,7 @@ struct rxrpc_call *rxrpc_new_client_call(struct rxrpc_sock *rx,
|
|
*/
|
|
ret = rxrpc_connect_call(call, cp, srx, gfp);
|
|
if (ret < 0)
|
|
- goto error;
|
|
+ goto error_attached_to_socket;
|
|
|
|
trace_rxrpc_call(call, rxrpc_call_connected, atomic_read(&call->usage),
|
|
here, NULL);
|
|
@@ -295,18 +295,29 @@ struct rxrpc_call *rxrpc_new_client_call(struct rxrpc_sock *rx,
|
|
error_dup_user_ID:
|
|
write_unlock(&rx->call_lock);
|
|
release_sock(&rx->sk);
|
|
- ret = -EEXIST;
|
|
-
|
|
-error:
|
|
__rxrpc_set_call_completion(call, RXRPC_CALL_LOCAL_ERROR,
|
|
- RX_CALL_DEAD, ret);
|
|
+ RX_CALL_DEAD, -EEXIST);
|
|
trace_rxrpc_call(call, rxrpc_call_error, atomic_read(&call->usage),
|
|
- here, ERR_PTR(ret));
|
|
+ here, ERR_PTR(-EEXIST));
|
|
rxrpc_release_call(rx, call);
|
|
mutex_unlock(&call->user_mutex);
|
|
rxrpc_put_call(call, rxrpc_call_put);
|
|
- _leave(" = %d", ret);
|
|
- return ERR_PTR(ret);
|
|
+ _leave(" = -EEXIST");
|
|
+ return ERR_PTR(-EEXIST);
|
|
+
|
|
+ /* We got an error, but the call is attached to the socket and is in
|
|
+ * need of release. However, we might now race with recvmsg() when
|
|
+ * completing the call queues it. Return 0 from sys_sendmsg() and
|
|
+ * leave the error to recvmsg() to deal with.
|
|
+ */
|
|
+error_attached_to_socket:
|
|
+ trace_rxrpc_call(call, rxrpc_call_error, atomic_read(&call->usage),
|
|
+ here, ERR_PTR(ret));
|
|
+ set_bit(RXRPC_CALL_DISCONNECTED, &call->flags);
|
|
+ __rxrpc_set_call_completion(call, RXRPC_CALL_LOCAL_ERROR,
|
|
+ RX_CALL_DEAD, ret);
|
|
+ _leave(" = c=%08x [err]", call->debug_id);
|
|
+ return call;
|
|
}
|
|
|
|
/*
|
|
diff --git a/net/rxrpc/conn_object.c b/net/rxrpc/conn_object.c
|
|
index af02328205979..0e5087b9e07c9 100644
|
|
--- a/net/rxrpc/conn_object.c
|
|
+++ b/net/rxrpc/conn_object.c
|
|
@@ -196,9 +196,11 @@ void rxrpc_disconnect_call(struct rxrpc_call *call)
|
|
|
|
call->peer->cong_cwnd = call->cong_cwnd;
|
|
|
|
- spin_lock_bh(&conn->params.peer->lock);
|
|
- hlist_del_init(&call->error_link);
|
|
- spin_unlock_bh(&conn->params.peer->lock);
|
|
+ if (!hlist_unhashed(&call->error_link)) {
|
|
+ spin_lock_bh(&conn->params.peer->lock);
|
|
+ hlist_del_init(&call->error_link);
|
|
+ spin_unlock_bh(&conn->params.peer->lock);
|
|
+ }
|
|
|
|
if (rxrpc_is_client_call(call))
|
|
return rxrpc_disconnect_client_call(call);
|
|
diff --git a/net/rxrpc/recvmsg.c b/net/rxrpc/recvmsg.c
|
|
index e82e91fe61789..1cdd8b380d47b 100644
|
|
--- a/net/rxrpc/recvmsg.c
|
|
+++ b/net/rxrpc/recvmsg.c
|
|
@@ -522,7 +522,7 @@ try_again:
|
|
goto error_unlock_call;
|
|
}
|
|
|
|
- if (msg->msg_name) {
|
|
+ if (msg->msg_name && call->peer) {
|
|
struct sockaddr_rxrpc *srx = msg->msg_name;
|
|
size_t len = sizeof(call->peer->srx);
|
|
|
|
diff --git a/net/rxrpc/sendmsg.c b/net/rxrpc/sendmsg.c
|
|
index f4386ad975cf0..8f9a2a7eeb7ce 100644
|
|
--- a/net/rxrpc/sendmsg.c
|
|
+++ b/net/rxrpc/sendmsg.c
|
|
@@ -579,6 +579,9 @@ int rxrpc_do_sendmsg(struct rxrpc_sock *rx, struct msghdr *msg, size_t len)
|
|
if (IS_ERR(call))
|
|
return PTR_ERR(call);
|
|
/* ... and we have the call lock. */
|
|
+ ret = 0;
|
|
+ if (READ_ONCE(call->state) == RXRPC_CALL_COMPLETE)
|
|
+ goto out_put_unlock;
|
|
} else {
|
|
switch (READ_ONCE(call->state)) {
|
|
case RXRPC_CALL_UNINITIALISED:
|
|
diff --git a/net/socket.c b/net/socket.c
|
|
index 6a5ec658fcd83..c74cfe1ee1699 100644
|
|
--- a/net/socket.c
|
|
+++ b/net/socket.c
|
|
@@ -496,7 +496,7 @@ static struct socket *sockfd_lookup_light(int fd, int *err, int *fput_needed)
|
|
if (f.file) {
|
|
sock = sock_from_file(f.file, err);
|
|
if (likely(sock)) {
|
|
- *fput_needed = f.flags;
|
|
+ *fput_needed = f.flags & FDPUT_FPUT;
|
|
return sock;
|
|
}
|
|
fdput(f);
|
|
diff --git a/net/wireless/nl80211.c b/net/wireless/nl80211.c
|
|
index d0b75781e6f7a..9be7ee322093b 100644
|
|
--- a/net/wireless/nl80211.c
|
|
+++ b/net/wireless/nl80211.c
|
|
@@ -11859,13 +11859,13 @@ static int nl80211_vendor_cmd(struct sk_buff *skb, struct genl_info *info)
|
|
if (!wdev_running(wdev))
|
|
return -ENETDOWN;
|
|
}
|
|
-
|
|
- if (!vcmd->doit)
|
|
- return -EOPNOTSUPP;
|
|
} else {
|
|
wdev = NULL;
|
|
}
|
|
|
|
+ if (!vcmd->doit)
|
|
+ return -EOPNOTSUPP;
|
|
+
|
|
if (info->attrs[NL80211_ATTR_VENDOR_DATA]) {
|
|
data = nla_data(info->attrs[NL80211_ATTR_VENDOR_DATA]);
|
|
len = nla_len(info->attrs[NL80211_ATTR_VENDOR_DATA]);
|
|
diff --git a/security/smack/smackfs.c b/security/smack/smackfs.c
|
|
index 371ae368da355..accd3846f1e3e 100644
|
|
--- a/security/smack/smackfs.c
|
|
+++ b/security/smack/smackfs.c
|
|
@@ -912,7 +912,7 @@ static ssize_t smk_set_cipso(struct file *file, const char __user *buf,
|
|
}
|
|
|
|
ret = sscanf(rule, "%d", &maplevel);
|
|
- if (ret != 1 || maplevel > SMACK_CIPSO_MAXLEVEL)
|
|
+ if (ret != 1 || maplevel < 0 || maplevel > SMACK_CIPSO_MAXLEVEL)
|
|
goto out;
|
|
|
|
rule += SMK_DIGITLEN;
|
|
@@ -933,6 +933,10 @@ static ssize_t smk_set_cipso(struct file *file, const char __user *buf,
|
|
|
|
for (i = 0; i < catlen; i++) {
|
|
rule += SMK_DIGITLEN;
|
|
+ if (rule > data + count) {
|
|
+ rc = -EOVERFLOW;
|
|
+ goto out;
|
|
+ }
|
|
ret = sscanf(rule, "%u", &cat);
|
|
if (ret != 1 || cat > SMACK_CIPSO_MAXCATNUM)
|
|
goto out;
|
|
@@ -2746,7 +2750,6 @@ static int smk_open_relabel_self(struct inode *inode, struct file *file)
|
|
static ssize_t smk_write_relabel_self(struct file *file, const char __user *buf,
|
|
size_t count, loff_t *ppos)
|
|
{
|
|
- struct task_smack *tsp = current_security();
|
|
char *data;
|
|
int rc;
|
|
LIST_HEAD(list_tmp);
|
|
@@ -2771,11 +2774,21 @@ static ssize_t smk_write_relabel_self(struct file *file, const char __user *buf,
|
|
kfree(data);
|
|
|
|
if (!rc || (rc == -EINVAL && list_empty(&list_tmp))) {
|
|
+ struct cred *new;
|
|
+ struct task_smack *tsp;
|
|
+
|
|
+ new = prepare_creds();
|
|
+ if (!new) {
|
|
+ rc = -ENOMEM;
|
|
+ goto out;
|
|
+ }
|
|
+ tsp = new->security;
|
|
smk_destroy_label_list(&tsp->smk_relabel);
|
|
list_splice(&list_tmp, &tsp->smk_relabel);
|
|
+ commit_creds(new);
|
|
return count;
|
|
}
|
|
-
|
|
+out:
|
|
smk_destroy_label_list(&list_tmp);
|
|
return rc;
|
|
}
|
|
diff --git a/sound/core/seq/oss/seq_oss.c b/sound/core/seq/oss/seq_oss.c
|
|
index 8cdf489df80e0..4b78979599131 100644
|
|
--- a/sound/core/seq/oss/seq_oss.c
|
|
+++ b/sound/core/seq/oss/seq_oss.c
|
|
@@ -181,10 +181,16 @@ static long
|
|
odev_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
|
|
{
|
|
struct seq_oss_devinfo *dp;
|
|
+ long rc;
|
|
+
|
|
dp = file->private_data;
|
|
if (snd_BUG_ON(!dp))
|
|
return -ENXIO;
|
|
- return snd_seq_oss_ioctl(dp, cmd, arg);
|
|
+
|
|
+ mutex_lock(®ister_mutex);
|
|
+ rc = snd_seq_oss_ioctl(dp, cmd, arg);
|
|
+ mutex_unlock(®ister_mutex);
|
|
+ return rc;
|
|
}
|
|
|
|
#ifdef CONFIG_COMPAT
|
|
diff --git a/sound/pci/echoaudio/echoaudio.c b/sound/pci/echoaudio/echoaudio.c
|
|
index e1f0bcd45c378..b58a098a7270d 100644
|
|
--- a/sound/pci/echoaudio/echoaudio.c
|
|
+++ b/sound/pci/echoaudio/echoaudio.c
|
|
@@ -2215,7 +2215,6 @@ static int snd_echo_resume(struct device *dev)
|
|
if (err < 0) {
|
|
kfree(commpage_bak);
|
|
dev_err(dev, "resume init_hw err=%d\n", err);
|
|
- snd_echo_free(chip);
|
|
return err;
|
|
}
|
|
|
|
@@ -2242,7 +2241,6 @@ static int snd_echo_resume(struct device *dev)
|
|
if (request_irq(pci->irq, snd_echo_interrupt, IRQF_SHARED,
|
|
KBUILD_MODNAME, chip)) {
|
|
dev_err(chip->card->dev, "cannot grab irq\n");
|
|
- snd_echo_free(chip);
|
|
return -EBUSY;
|
|
}
|
|
chip->irq = pci->irq;
|
|
diff --git a/sound/soc/intel/boards/bxt_rt298.c b/sound/soc/intel/boards/bxt_rt298.c
|
|
index 7843104fadcbf..1b01bc318fd25 100644
|
|
--- a/sound/soc/intel/boards/bxt_rt298.c
|
|
+++ b/sound/soc/intel/boards/bxt_rt298.c
|
|
@@ -529,6 +529,7 @@ static int bxt_card_late_probe(struct snd_soc_card *card)
|
|
/* broxton audio machine driver for SPT + RT298S */
|
|
static struct snd_soc_card broxton_rt298 = {
|
|
.name = "broxton-rt298",
|
|
+ .owner = THIS_MODULE,
|
|
.dai_link = broxton_rt298_dais,
|
|
.num_links = ARRAY_SIZE(broxton_rt298_dais),
|
|
.controls = broxton_controls,
|
|
@@ -544,6 +545,7 @@ static struct snd_soc_card broxton_rt298 = {
|
|
|
|
static struct snd_soc_card geminilake_rt298 = {
|
|
.name = "geminilake-rt298",
|
|
+ .owner = THIS_MODULE,
|
|
.dai_link = broxton_rt298_dais,
|
|
.num_links = ARRAY_SIZE(broxton_rt298_dais),
|
|
.controls = broxton_controls,
|
|
diff --git a/sound/usb/card.h b/sound/usb/card.h
|
|
index ed87cc83eb47d..0cde519bfa420 100644
|
|
--- a/sound/usb/card.h
|
|
+++ b/sound/usb/card.h
|
|
@@ -126,6 +126,7 @@ struct snd_usb_substream {
|
|
unsigned int tx_length_quirk:1; /* add length specifier to transfers */
|
|
unsigned int fmt_type; /* USB audio format type (1-3) */
|
|
unsigned int pkt_offset_adj; /* Bytes to drop from beginning of packets (for non-compliant devices) */
|
|
+ unsigned int stream_offset_adj; /* Bytes to drop from beginning of stream (for non-compliant devices) */
|
|
|
|
unsigned int running: 1; /* running status */
|
|
|
|
diff --git a/sound/usb/mixer_quirks.c b/sound/usb/mixer_quirks.c
|
|
index 5604cce30a582..d7878ed5ecc07 100644
|
|
--- a/sound/usb/mixer_quirks.c
|
|
+++ b/sound/usb/mixer_quirks.c
|
|
@@ -196,6 +196,7 @@ static const struct rc_config {
|
|
{ USB_ID(0x041e, 0x3042), 0, 1, 1, 1, 1, 0x000d }, /* Usb X-Fi S51 */
|
|
{ USB_ID(0x041e, 0x30df), 0, 1, 1, 1, 1, 0x000d }, /* Usb X-Fi S51 Pro */
|
|
{ USB_ID(0x041e, 0x3237), 0, 1, 1, 1, 1, 0x000d }, /* Usb X-Fi S51 Pro */
|
|
+ { USB_ID(0x041e, 0x3263), 0, 1, 1, 1, 1, 0x000d }, /* Usb X-Fi S51 Pro */
|
|
{ USB_ID(0x041e, 0x3048), 2, 2, 6, 6, 2, 0x6e91 }, /* Toshiba SB0500 */
|
|
};
|
|
|
|
diff --git a/sound/usb/pcm.c b/sound/usb/pcm.c
|
|
index ff38fca1781b6..f27213b846e6b 100644
|
|
--- a/sound/usb/pcm.c
|
|
+++ b/sound/usb/pcm.c
|
|
@@ -1313,6 +1313,12 @@ static void retire_capture_urb(struct snd_usb_substream *subs,
|
|
// continue;
|
|
}
|
|
bytes = urb->iso_frame_desc[i].actual_length;
|
|
+ if (subs->stream_offset_adj > 0) {
|
|
+ unsigned int adj = min(subs->stream_offset_adj, bytes);
|
|
+ cp += adj;
|
|
+ bytes -= adj;
|
|
+ subs->stream_offset_adj -= adj;
|
|
+ }
|
|
frames = bytes / stride;
|
|
if (!subs->txfr_quirk)
|
|
bytes = frames * stride;
|
|
diff --git a/sound/usb/quirks-table.h b/sound/usb/quirks-table.h
|
|
index ec56ce3820619..689fd3103e5b6 100644
|
|
--- a/sound/usb/quirks-table.h
|
|
+++ b/sound/usb/quirks-table.h
|
|
@@ -3335,7 +3335,13 @@ AU0828_DEVICE(0x2040, 0x7270, "Hauppauge", "HVR-950Q"),
|
|
* with.
|
|
*/
|
|
{
|
|
- USB_DEVICE(0x534d, 0x2109),
|
|
+ .match_flags = USB_DEVICE_ID_MATCH_DEVICE |
|
|
+ USB_DEVICE_ID_MATCH_INT_CLASS |
|
|
+ USB_DEVICE_ID_MATCH_INT_SUBCLASS,
|
|
+ .idVendor = 0x534d,
|
|
+ .idProduct = 0x2109,
|
|
+ .bInterfaceClass = USB_CLASS_AUDIO,
|
|
+ .bInterfaceSubClass = USB_SUBCLASS_AUDIOCONTROL,
|
|
.driver_info = (unsigned long) &(const struct snd_usb_audio_quirk) {
|
|
.vendor_name = "MacroSilicon",
|
|
.product_name = "MS2109",
|
|
@@ -3374,5 +3380,61 @@ AU0828_DEVICE(0x2040, 0x7270, "Hauppauge", "HVR-950Q"),
|
|
}
|
|
}
|
|
},
|
|
+{
|
|
+ /*
|
|
+ * PIONEER DJ DDJ-RB
|
|
+ * PCM is 4 channels out, 2 dummy channels in @ 44.1 fixed
|
|
+ * The feedback for the output is the dummy input.
|
|
+ */
|
|
+ USB_DEVICE_VENDOR_SPEC(0x2b73, 0x000e),
|
|
+ .driver_info = (unsigned long) &(const struct snd_usb_audio_quirk) {
|
|
+ .ifnum = QUIRK_ANY_INTERFACE,
|
|
+ .type = QUIRK_COMPOSITE,
|
|
+ .data = (const struct snd_usb_audio_quirk[]) {
|
|
+ {
|
|
+ .ifnum = 0,
|
|
+ .type = QUIRK_AUDIO_FIXED_ENDPOINT,
|
|
+ .data = &(const struct audioformat) {
|
|
+ .formats = SNDRV_PCM_FMTBIT_S24_3LE,
|
|
+ .channels = 4,
|
|
+ .iface = 0,
|
|
+ .altsetting = 1,
|
|
+ .altset_idx = 1,
|
|
+ .endpoint = 0x01,
|
|
+ .ep_attr = USB_ENDPOINT_XFER_ISOC|
|
|
+ USB_ENDPOINT_SYNC_ASYNC,
|
|
+ .rates = SNDRV_PCM_RATE_44100,
|
|
+ .rate_min = 44100,
|
|
+ .rate_max = 44100,
|
|
+ .nr_rates = 1,
|
|
+ .rate_table = (unsigned int[]) { 44100 }
|
|
+ }
|
|
+ },
|
|
+ {
|
|
+ .ifnum = 0,
|
|
+ .type = QUIRK_AUDIO_FIXED_ENDPOINT,
|
|
+ .data = &(const struct audioformat) {
|
|
+ .formats = SNDRV_PCM_FMTBIT_S24_3LE,
|
|
+ .channels = 2,
|
|
+ .iface = 0,
|
|
+ .altsetting = 1,
|
|
+ .altset_idx = 1,
|
|
+ .endpoint = 0x82,
|
|
+ .ep_attr = USB_ENDPOINT_XFER_ISOC|
|
|
+ USB_ENDPOINT_SYNC_ASYNC|
|
|
+ USB_ENDPOINT_USAGE_IMPLICIT_FB,
|
|
+ .rates = SNDRV_PCM_RATE_44100,
|
|
+ .rate_min = 44100,
|
|
+ .rate_max = 44100,
|
|
+ .nr_rates = 1,
|
|
+ .rate_table = (unsigned int[]) { 44100 }
|
|
+ }
|
|
+ },
|
|
+ {
|
|
+ .ifnum = -1
|
|
+ }
|
|
+ }
|
|
+ }
|
|
+},
|
|
|
|
#undef USB_DEVICE_VENDOR_SPEC
|
|
diff --git a/sound/usb/quirks.c b/sound/usb/quirks.c
|
|
index cd36394e27ae6..4f4dc43e56a7b 100644
|
|
--- a/sound/usb/quirks.c
|
|
+++ b/sound/usb/quirks.c
|
|
@@ -1120,6 +1120,9 @@ void snd_usb_set_format_quirk(struct snd_usb_substream *subs,
|
|
case USB_ID(0x041e, 0x3f19): /* E-Mu 0204 USB */
|
|
set_format_emu_quirk(subs, fmt);
|
|
break;
|
|
+ case USB_ID(0x534d, 0x2109): /* MacroSilicon MS2109 */
|
|
+ subs->stream_offset_adj = 2;
|
|
+ break;
|
|
}
|
|
}
|
|
|
|
diff --git a/sound/usb/stream.c b/sound/usb/stream.c
|
|
index d1776e5517ffe..452646959586e 100644
|
|
--- a/sound/usb/stream.c
|
|
+++ b/sound/usb/stream.c
|
|
@@ -95,6 +95,7 @@ static void snd_usb_init_substream(struct snd_usb_stream *as,
|
|
subs->tx_length_quirk = as->chip->tx_length_quirk;
|
|
subs->speed = snd_usb_get_speed(subs->dev);
|
|
subs->pkt_offset_adj = 0;
|
|
+ subs->stream_offset_adj = 0;
|
|
|
|
snd_usb_set_pcm_ops(as->pcm, stream);
|
|
|
|
diff --git a/tools/build/Build.include b/tools/build/Build.include
|
|
index d9048f145f97a..63bb9752612a8 100644
|
|
--- a/tools/build/Build.include
|
|
+++ b/tools/build/Build.include
|
|
@@ -74,7 +74,8 @@ dep-cmd = $(if $(wildcard $(fixdep)),
|
|
# dependencies in the cmd file
|
|
if_changed_dep = $(if $(strip $(any-prereq) $(arg-check)), \
|
|
@set -e; \
|
|
- $(echo-cmd) $(cmd_$(1)) && $(dep-cmd))
|
|
+ $(echo-cmd) $(cmd_$(1)); \
|
|
+ $(dep-cmd))
|
|
|
|
# if_changed - execute command if any prerequisite is newer than
|
|
# target, or command line has changed
|
|
diff --git a/tools/build/Makefile.feature b/tools/build/Makefile.feature
|
|
index c71a05b9c984f..79427b09590c5 100644
|
|
--- a/tools/build/Makefile.feature
|
|
+++ b/tools/build/Makefile.feature
|
|
@@ -7,7 +7,7 @@ endif
|
|
|
|
feature_check = $(eval $(feature_check_code))
|
|
define feature_check_code
|
|
- feature-$(1) := $(shell $(MAKE) OUTPUT=$(OUTPUT_FEATURES) CFLAGS="$(EXTRA_CFLAGS) $(FEATURE_CHECK_CFLAGS-$(1))" CXXFLAGS="$(EXTRA_CXXFLAGS) $(FEATURE_CHECK_CXXFLAGS-$(1))" LDFLAGS="$(LDFLAGS) $(FEATURE_CHECK_LDFLAGS-$(1))" -C $(feature_dir) $(OUTPUT_FEATURES)test-$1.bin >/dev/null 2>/dev/null && echo 1 || echo 0)
|
|
+ feature-$(1) := $(shell $(MAKE) OUTPUT=$(OUTPUT_FEATURES) CC="$(CC)" CXX="$(CXX)" CFLAGS="$(EXTRA_CFLAGS) $(FEATURE_CHECK_CFLAGS-$(1))" CXXFLAGS="$(EXTRA_CXXFLAGS) $(FEATURE_CHECK_CXXFLAGS-$(1))" LDFLAGS="$(LDFLAGS) $(FEATURE_CHECK_LDFLAGS-$(1))" -C $(feature_dir) $(OUTPUT_FEATURES)test-$1.bin >/dev/null 2>/dev/null && echo 1 || echo 0)
|
|
endef
|
|
|
|
feature_set = $(eval $(feature_set_code))
|
|
diff --git a/tools/build/feature/Makefile b/tools/build/feature/Makefile
|
|
index 96982640fbf88..26316749e594a 100644
|
|
--- a/tools/build/feature/Makefile
|
|
+++ b/tools/build/feature/Makefile
|
|
@@ -55,8 +55,6 @@ FILES= \
|
|
|
|
FILES := $(addprefix $(OUTPUT),$(FILES))
|
|
|
|
-CC ?= $(CROSS_COMPILE)gcc
|
|
-CXX ?= $(CROSS_COMPILE)g++
|
|
PKG_CONFIG ?= $(CROSS_COMPILE)pkg-config
|
|
LLVM_CONFIG ?= llvm-config
|
|
|
|
diff --git a/tools/lib/traceevent/event-parse.c b/tools/lib/traceevent/event-parse.c
|
|
index 8211e8010e09b..d260ca680f074 100644
|
|
--- a/tools/lib/traceevent/event-parse.c
|
|
+++ b/tools/lib/traceevent/event-parse.c
|
|
@@ -2780,6 +2780,7 @@ process_dynamic_array_len(struct event_format *event, struct print_arg *arg,
|
|
if (read_expected(EVENT_DELIM, ")") < 0)
|
|
goto out_err;
|
|
|
|
+ free_token(token);
|
|
type = read_token(&token);
|
|
*tok = token;
|
|
|
|
diff --git a/tools/perf/bench/mem-functions.c b/tools/perf/bench/mem-functions.c
|
|
index 0251dd348124a..4864fc67d01b5 100644
|
|
--- a/tools/perf/bench/mem-functions.c
|
|
+++ b/tools/perf/bench/mem-functions.c
|
|
@@ -222,12 +222,8 @@ static int bench_mem_common(int argc, const char **argv, struct bench_mem_info *
|
|
return 0;
|
|
}
|
|
|
|
-static u64 do_memcpy_cycles(const struct function *r, size_t size, void *src, void *dst)
|
|
+static void memcpy_prefault(memcpy_t fn, size_t size, void *src, void *dst)
|
|
{
|
|
- u64 cycle_start = 0ULL, cycle_end = 0ULL;
|
|
- memcpy_t fn = r->fn.memcpy;
|
|
- int i;
|
|
-
|
|
/* Make sure to always prefault zero pages even if MMAP_THRESH is crossed: */
|
|
memset(src, 0, size);
|
|
|
|
@@ -236,6 +232,15 @@ static u64 do_memcpy_cycles(const struct function *r, size_t size, void *src, vo
|
|
* to not measure page fault overhead:
|
|
*/
|
|
fn(dst, src, size);
|
|
+}
|
|
+
|
|
+static u64 do_memcpy_cycles(const struct function *r, size_t size, void *src, void *dst)
|
|
+{
|
|
+ u64 cycle_start = 0ULL, cycle_end = 0ULL;
|
|
+ memcpy_t fn = r->fn.memcpy;
|
|
+ int i;
|
|
+
|
|
+ memcpy_prefault(fn, size, src, dst);
|
|
|
|
cycle_start = get_cycles();
|
|
for (i = 0; i < nr_loops; ++i)
|
|
@@ -251,11 +256,7 @@ static double do_memcpy_gettimeofday(const struct function *r, size_t size, void
|
|
memcpy_t fn = r->fn.memcpy;
|
|
int i;
|
|
|
|
- /*
|
|
- * We prefault the freshly allocated memory range here,
|
|
- * to not measure page fault overhead:
|
|
- */
|
|
- fn(dst, src, size);
|
|
+ memcpy_prefault(fn, size, src, dst);
|
|
|
|
BUG_ON(gettimeofday(&tv_start, NULL));
|
|
for (i = 0; i < nr_loops; ++i)
|
|
diff --git a/tools/perf/util/intel-pt-decoder/intel-pt-decoder.c b/tools/perf/util/intel-pt-decoder/intel-pt-decoder.c
|
|
index 4357141c7c924..6522b6513895c 100644
|
|
--- a/tools/perf/util/intel-pt-decoder/intel-pt-decoder.c
|
|
+++ b/tools/perf/util/intel-pt-decoder/intel-pt-decoder.c
|
|
@@ -1129,6 +1129,7 @@ static int intel_pt_walk_fup(struct intel_pt_decoder *decoder)
|
|
return 0;
|
|
if (err == -EAGAIN ||
|
|
intel_pt_fup_with_nlip(decoder, &intel_pt_insn, ip, err)) {
|
|
+ decoder->pkt_state = INTEL_PT_STATE_IN_SYNC;
|
|
if (intel_pt_fup_event(decoder))
|
|
return 0;
|
|
return -EAGAIN;
|
|
@@ -1780,17 +1781,13 @@ next:
|
|
}
|
|
if (decoder->set_fup_mwait)
|
|
no_tip = true;
|
|
+ if (no_tip)
|
|
+ decoder->pkt_state = INTEL_PT_STATE_FUP_NO_TIP;
|
|
+ else
|
|
+ decoder->pkt_state = INTEL_PT_STATE_FUP;
|
|
err = intel_pt_walk_fup(decoder);
|
|
- if (err != -EAGAIN) {
|
|
- if (err)
|
|
- return err;
|
|
- if (no_tip)
|
|
- decoder->pkt_state =
|
|
- INTEL_PT_STATE_FUP_NO_TIP;
|
|
- else
|
|
- decoder->pkt_state = INTEL_PT_STATE_FUP;
|
|
- return 0;
|
|
- }
|
|
+ if (err != -EAGAIN)
|
|
+ return err;
|
|
if (no_tip) {
|
|
no_tip = false;
|
|
break;
|
|
@@ -2375,15 +2372,11 @@ const struct intel_pt_state *intel_pt_decode(struct intel_pt_decoder *decoder)
|
|
err = intel_pt_walk_tip(decoder);
|
|
break;
|
|
case INTEL_PT_STATE_FUP:
|
|
- decoder->pkt_state = INTEL_PT_STATE_IN_SYNC;
|
|
err = intel_pt_walk_fup(decoder);
|
|
if (err == -EAGAIN)
|
|
err = intel_pt_walk_fup_tip(decoder);
|
|
- else if (!err)
|
|
- decoder->pkt_state = INTEL_PT_STATE_FUP;
|
|
break;
|
|
case INTEL_PT_STATE_FUP_NO_TIP:
|
|
- decoder->pkt_state = INTEL_PT_STATE_IN_SYNC;
|
|
err = intel_pt_walk_fup(decoder);
|
|
if (err == -EAGAIN)
|
|
err = intel_pt_walk_trace(decoder);
|
|
diff --git a/tools/testing/selftests/net/msg_zerocopy.c b/tools/testing/selftests/net/msg_zerocopy.c
|
|
index e11fe84de0fd9..6184d2a4c4a62 100644
|
|
--- a/tools/testing/selftests/net/msg_zerocopy.c
|
|
+++ b/tools/testing/selftests/net/msg_zerocopy.c
|
|
@@ -121,9 +121,8 @@ static int do_setcpu(int cpu)
|
|
CPU_ZERO(&mask);
|
|
CPU_SET(cpu, &mask);
|
|
if (sched_setaffinity(0, sizeof(mask), &mask))
|
|
- error(1, 0, "setaffinity %d", cpu);
|
|
-
|
|
- if (cfg_verbose)
|
|
+ fprintf(stderr, "cpu: unable to pin, may increase variance.\n");
|
|
+ else if (cfg_verbose)
|
|
fprintf(stderr, "cpu: %u\n", cpu);
|
|
|
|
return 0;
|
|
diff --git a/tools/testing/selftests/powerpc/benchmarks/context_switch.c b/tools/testing/selftests/powerpc/benchmarks/context_switch.c
|
|
index f4241339edd2a..7136eae2170b7 100644
|
|
--- a/tools/testing/selftests/powerpc/benchmarks/context_switch.c
|
|
+++ b/tools/testing/selftests/powerpc/benchmarks/context_switch.c
|
|
@@ -22,6 +22,7 @@
|
|
#include <limits.h>
|
|
#include <sys/time.h>
|
|
#include <sys/syscall.h>
|
|
+#include <sys/sysinfo.h>
|
|
#include <sys/types.h>
|
|
#include <sys/shm.h>
|
|
#include <linux/futex.h>
|
|
@@ -97,8 +98,9 @@ static void start_thread_on(void *(*fn)(void *), void *arg, unsigned long cpu)
|
|
|
|
static void start_process_on(void *(*fn)(void *), void *arg, unsigned long cpu)
|
|
{
|
|
- int pid;
|
|
- cpu_set_t cpuset;
|
|
+ int pid, ncpus;
|
|
+ cpu_set_t *cpuset;
|
|
+ size_t size;
|
|
|
|
pid = fork();
|
|
if (pid == -1) {
|
|
@@ -109,14 +111,23 @@ static void start_process_on(void *(*fn)(void *), void *arg, unsigned long cpu)
|
|
if (pid)
|
|
return;
|
|
|
|
- CPU_ZERO(&cpuset);
|
|
- CPU_SET(cpu, &cpuset);
|
|
+ ncpus = get_nprocs();
|
|
+ size = CPU_ALLOC_SIZE(ncpus);
|
|
+ cpuset = CPU_ALLOC(ncpus);
|
|
+ if (!cpuset) {
|
|
+ perror("malloc");
|
|
+ exit(1);
|
|
+ }
|
|
+ CPU_ZERO_S(size, cpuset);
|
|
+ CPU_SET_S(cpu, size, cpuset);
|
|
|
|
- if (sched_setaffinity(0, sizeof(cpuset), &cpuset)) {
|
|
+ if (sched_setaffinity(0, size, cpuset)) {
|
|
perror("sched_setaffinity");
|
|
+ CPU_FREE(cpuset);
|
|
exit(1);
|
|
}
|
|
|
|
+ CPU_FREE(cpuset);
|
|
fn(arg);
|
|
|
|
exit(0);
|
|
diff --git a/tools/testing/selftests/powerpc/utils.c b/tools/testing/selftests/powerpc/utils.c
|
|
index d46916867a6fb..77db4f6ecf2f0 100644
|
|
--- a/tools/testing/selftests/powerpc/utils.c
|
|
+++ b/tools/testing/selftests/powerpc/utils.c
|
|
@@ -12,6 +12,7 @@
|
|
#include <sched.h>
|
|
#include <stdio.h>
|
|
#include <sys/stat.h>
|
|
+#include <sys/sysinfo.h>
|
|
#include <sys/types.h>
|
|
#include <unistd.h>
|
|
|
|
@@ -81,26 +82,38 @@ void *get_auxv_entry(int type)
|
|
|
|
int pick_online_cpu(void)
|
|
{
|
|
- cpu_set_t mask;
|
|
- int cpu;
|
|
+ int ncpus, cpu = -1;
|
|
+ cpu_set_t *mask;
|
|
+ size_t size;
|
|
+
|
|
+ ncpus = get_nprocs_conf();
|
|
+ size = CPU_ALLOC_SIZE(ncpus);
|
|
+ mask = CPU_ALLOC(ncpus);
|
|
+ if (!mask) {
|
|
+ perror("malloc");
|
|
+ return -1;
|
|
+ }
|
|
|
|
- CPU_ZERO(&mask);
|
|
+ CPU_ZERO_S(size, mask);
|
|
|
|
- if (sched_getaffinity(0, sizeof(mask), &mask)) {
|
|
+ if (sched_getaffinity(0, size, mask)) {
|
|
perror("sched_getaffinity");
|
|
- return -1;
|
|
+ goto done;
|
|
}
|
|
|
|
/* We prefer a primary thread, but skip 0 */
|
|
- for (cpu = 8; cpu < CPU_SETSIZE; cpu += 8)
|
|
- if (CPU_ISSET(cpu, &mask))
|
|
- return cpu;
|
|
+ for (cpu = 8; cpu < ncpus; cpu += 8)
|
|
+ if (CPU_ISSET_S(cpu, size, mask))
|
|
+ goto done;
|
|
|
|
/* Search for anything, but in reverse */
|
|
- for (cpu = CPU_SETSIZE - 1; cpu >= 0; cpu--)
|
|
- if (CPU_ISSET(cpu, &mask))
|
|
- return cpu;
|
|
+ for (cpu = ncpus - 1; cpu >= 0; cpu--)
|
|
+ if (CPU_ISSET_S(cpu, size, mask))
|
|
+ goto done;
|
|
|
|
printf("No cpus in affinity mask?!\n");
|
|
- return -1;
|
|
+
|
|
+done:
|
|
+ CPU_FREE(mask);
|
|
+ return cpu;
|
|
}
|